fix: set session cookie in cookie jar instead of manual header

Using self._session.cookies.set() ensures the cookie is sent correctly
by the requests session on all calls, including /api/auth/session.
Also add sec-fetch-* headers required by chatgpt.com.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
JesseMarkowitz
2026-02-27 23:39:38 -05:00
parent 6a33de682a
commit d236fdb21a

View File

@@ -38,30 +38,42 @@ class ChatGPTProvider(BaseProvider):
), ),
) )
self._session_token = token self._session_token = token
# Set the session cookie in the cookie jar (proper cookie handling, not a raw header)
self._session.cookies.set(
"__Secure-next-auth.session-token",
token,
domain="chatgpt.com",
path="/",
)
# Additional browser-like headers required by chatgpt.com
self._session.headers.update( self._session.headers.update(
{ {
"Referer": "https://chatgpt.com/", "Referer": "https://chatgpt.com/",
"Origin": "https://chatgpt.com", "Origin": "https://chatgpt.com",
"sec-fetch-dest": "empty",
"sec-fetch-mode": "cors",
"sec-fetch-site": "same-origin",
} }
) )
# Exchange the session cookie for an access token immediately
self._access_token: str = self._fetch_access_token(token) # Exchange the session cookie for an access token
self._access_token: str = self._fetch_access_token()
self._session.headers["Authorization"] = f"Bearer {self._access_token}" self._session.headers["Authorization"] = f"Bearer {self._access_token}"
logger.debug("[chatgpt] Session initialised — access token obtained (token: [REDACTED])") logger.debug("[chatgpt] Session initialised — access token obtained (token: [REDACTED])")
def _fetch_access_token(self, session_token: str) -> str: def _fetch_access_token(self) -> str:
"""Exchange the session cookie for a Bearer access token. """Exchange the session cookie for a Bearer access token.
Calls GET /api/auth/session with the session cookie, which returns Calls GET /api/auth/session the cookie jar already contains the
{"accessToken": "...", "user": {...}}. session token, so no manual Cookie header is needed.
Returns {"accessToken": "...", "user": {...}}.
""" """
logger.debug("[chatgpt] Fetching access token from %s", AUTH_SESSION_URL) logger.debug("[chatgpt] Fetching access token from %s", AUTH_SESSION_URL)
try: try:
resp = self._session.get( resp = self._session.get(AUTH_SESSION_URL, timeout=REQUEST_TIMEOUT)
AUTH_SESSION_URL,
headers={"Cookie": f"__Secure-next-auth.session-token={session_token}"},
timeout=REQUEST_TIMEOUT,
)
resp.raise_for_status() resp.raise_for_status()
data = resp.json() data = resp.json()
except Exception as e: except Exception as e:
@@ -70,7 +82,7 @@ class ChatGPTProvider(BaseProvider):
"fetch_access_token", "fetch_access_token",
RuntimeError( RuntimeError(
f"Could not exchange session token for access token: {e}. " f"Could not exchange session token for access token: {e}. "
"Check that your CHATGPT_SESSION_TOKEN is current." "Check that your CHATGPT_SESSION_TOKEN is current and not expired."
), ),
) from e ) from e