Skip to content

fix: honor external_browser_timeout in the externalbrowser flow - #3046

Open
inchang-ing wants to merge 1 commit into
snowflakedb:mainfrom
inchang-ing:fix-3045-externalbrowser-timeout
Open

inchang-ing wants to merge 1 commit into
snowflakedb:mainfrom
inchang-ing:fix-3045-externalbrowser-timeout

Conversation

@inchang-ing

Copy link
Copy Markdown

Summary

Fixes #3045.

AuthByWebBrowser._receive_saml_token waited for the browser callback with select.select([socket_connection], [], []) and no timeout, so when the login was never completed the connection blocked forever — login_timeout and external_browser_timeout had no effect on that wait.

This change passes external_browser_timeout from SnowflakeConnection into AuthByWebBrowser and uses it as an overall deadline for the callback wait. When the budget is spent, the authentication fails with ER_OAUTH_SERVER_TIMEOUT and the message the OAuth authorization-code flow (_receive_authorization_callback) already uses for its callback timeout. The two tests in test/auth/test_external_browser.py that are currently skipped pending SNOW-2007651 ("Adding custom browser timeout") assert exactly that message, so this follows the behaviour already planned there rather than introducing a new errno.

When external_browser_timeout is not configured, the wait stays unbounded (we pass None through), preserving the behaviour of direct AuthByWebBrowser users.

Reproduction

Offline (no account, no browser) — external_browser_timeout=3 and a stubbed SSO URL:

OK: connect() returned after 3.1s: DatabaseError: 251016 (08001): Failed to connect to DB: ...,
Unable to receive the OAuth message within a given timeout. Please check the redirect URI and try again.

Before the fix the same script hangs well past the timeout (verified on 4.8.0 / main).

Verification

  • New unit tests in test/unit/test_auth_webbrowser.py:
    • test_auth_webbrowser_fails_when_browser_login_is_never_completed — external_browser_timeout set, select.select never reports the socket readable → _handle_failure is called once with ER_OAUTH_SERVER_TIMEOUT.
    • test_auth_webbrowser_without_timeout_keeps_the_wait_unbounded — without the timeout, select.select still gets None for its timeout argument.
    • Both tests fail (IndexError) if the select.select timeout is reverted, so they guard the regression.
  • The existing SAML-token happy-path tests (test_auth_webbrowser_get / test_auth_webbrowser_post) mock select.select to return the socket, so they are unaffected by the new argument.

Scope note

The same unbounded select.select() exists in aio/auth/_webbrowser.py. I left it untouched to keep this change focused and easily reviewable; it can be fixed the same way in a follow-up if you'd like.

(Generated with the help of an AI coding assistant; the root-cause analysis and the version matrix above are from runs I did myself.)

AuthByWebBrowser._receive_saml_token waited for the browser callback with
select.select() and no timeout, so a login that was never completed blocked the
connection forever; neither login_timeout nor external_browser_timeout bounded
that wait (snowflakedb#3045).

Pass external_browser_timeout down from SnowflakeConnection and use it as an
overall deadline for the callback wait. When the budget is spent the
authentication fails with ER_OAUTH_SERVER_TIMEOUT and the message the OAuth
authorization-code flow already uses for its callback timeout - the two tests
in test/auth/test_external_browser.py that are skipped pending SNOW-2007651
assert exactly that message, so this follows the behaviour already planned
there rather than inventing a new errno.

When external_browser_timeout is not configured the wait stays unbounded,
preserving the behaviour of direct AuthByWebBrowser users.

The same unbounded select.select() exists in aio/auth/_webbrowser.py; it is
left untouched here to keep this change focused, and can be fixed the same way
in a follow-up.

Fixes snowflakedb#3045

Signed-off-by: inchang-ing <197932532+inchang-ing@users.noreply.github.com>

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

SNOW-4218366: externalbrowser authentication waits forever if the browser login is never completed

1 participant