Use Playwright to login and extract cookies to bypass Cloudflare 403
(self)
| 234 | return stdout.decode().strip() |
| 235 | |
| 236 | async def _setup_leetcode_cookie(self): |
| 237 | """Use Playwright to login and extract cookies to bypass Cloudflare 403""" |
| 238 | logger.info("| 🔍 Logging in to LeetCode via browser to fetch session cookies...") |
| 239 | |
| 240 | try: |
| 241 | if self.leetcode_cookie: |
| 242 | logger.info("| 🔍 LeetCode cookie already exists, skipping login") |
| 243 | return |
| 244 | |
| 245 | # 1. Navigate to login page |
| 246 | await self.page.goto("https://leetcode.com/accounts/login/", wait_until="networkidle") |
| 247 | await asyncio.sleep(2) |
| 248 | |
| 249 | # 2. Check if already logged in (due to persistent context) |
| 250 | if "login" not in self.page.url: |
| 251 | logger.info("| 🔍 Already logged in to LeetCode.") |
| 252 | else: |
| 253 | logger.info("| 🔍 Entering LeetCode credentials...") |
| 254 | # LeetCode uses specific IDs for login inputs |
| 255 | await self.page.fill('input[name="login"]', os.getenv("LEETCODE_USERNAME")) |
| 256 | await self.page.fill('input[name="password"]', os.getenv("LEETCODE_PASSWORD")) |
| 257 | |
| 258 | # Click sign in and wait for navigation |
| 259 | await self.page.click('button[type="submit"], #signin_btn') |
| 260 | |
| 261 | # Wait for navigation back to home or dashboard |
| 262 | try: |
| 263 | await self.page.wait_for_url("https://leetcode.com/", timeout=20000) |
| 264 | logger.info("| ✅ LeetCode web login successful.") |
| 265 | except: |
| 266 | logger.warning("| ⚠️ Login navigation timed out, checking cookies anyway...") |
| 267 | |
| 268 | # 3. Extract cookies from context |
| 269 | cookies = await self.context.cookies() |
| 270 | cookie_str = "; ".join([f"{c['name']}={c['value']}" for c in cookies if c['domain'].endswith("leetcode.com")]) |
| 271 | |
| 272 | if "LEETCODE_SESSION" in cookie_str: |
| 273 | self.leetcode_cookie = cookie_str |
| 274 | logger.info(f"| ✅ Successfully extracted LeetCode cookies (length: {len(cookie_str)})") |
| 275 | else: |
| 276 | logger.error("| ❌ Failed to find LEETCODE_SESSION in cookies.") |
| 277 | |
| 278 | except Exception as e: |
| 279 | logger.error(f"| ❌ Error during LeetCode cookie setup: {str(e)}") |
| 280 | raise e |
| 281 | |
| 282 | async def _login_and_navigate(self): |
| 283 | """Login GitHub and enter specified Codespace""" |