Skip to content

Framework does not handle refreshed tokens correctly #1250

Open

Description

@pematth

Initial Checks

Description

I use python sdk with Keycloak as external authz provider. I allowed my mcp client (in my test scenario it is latest VSC) to get AT and RT (using offline_access scope). I have implemented a TokenVerifier that is doing validation of the MCP keycloak JWT. And then in some MCP tool, i use get_access_token() from the framework to use the JWT. I log both values and i can clearly see that it works fine initially, but after the token was refreshed on client-side, i still get the old accesst token from get_access_token() function. Not sure if you intended to support token refresh in a clean way. But IMHO that is a bug that should be fixed soon.

Example Code

Python & MCP Python SDK

1.12.4

Activity

  1. added
    bugSomething isn't working
    needs reproneeds additional information to be able to reproduce bug
    authIssues and PRs related to Authentication / OAuth
    on Oct 3, 2025
  2. felixweinberger commented on Oct 3, 2025

    @felixweinberger
    Contributor

    Hi @pematth could you provide a code snippet that demonstrates the specific issue you're getting that we can run to debug?

  3. bgaidioz commented on Oct 3, 2025

    @bgaidioz

    I ran into a similar situation when I tried to implement token refresh on our MCP server (after adding load_refresh_token and exchange_refresh_token to our OAuthAuthorizationServerProvider). I could see the new token being passed to auth_context_var.reset(token) in auth_context.py, but get_access_token was still returning the old token when the client issued a new call.

    I’m mentioning this because it seems to confirm that the framework isn’t propagating the refreshed token consistently, which may be the root of what’s being reported here.

    I don’t have a minimal code snippet handy, but I’d be happy to try and put one together when I’m back working on this part of the code.

  4. felixweinberger commented on Oct 3, 2025

    @felixweinberger
    Contributor

    I ran into a similar situation when I tried to implement token refresh on our MCP server (after adding load_refresh_token and exchange_refresh_token to our OAuthAuthorizationServerProvider). I could see the new token being passed to auth_context_var.reset(token) in auth_context.py, but get_access_token was still returning the old token when the client issued a new call.

    I’m mentioning this because it seems to confirm that the framework isn’t propagating the refreshed token consistently, which may be the root of what’s being reported here.

    I don’t have a minimal code snippet handy, but I’d be happy to try and put one together when I’m back working on this part of the code.

    That'd be great thank you!

  5. bgaidioz commented on Oct 6, 2025

    @bgaidioz

    I ran into a similar situation when I tried to implement token refresh on our MCP server (after adding load_refresh_token and exchange_refresh_token to our OAuthAuthorizationServerProvider). I could see the new token being passed to auth_context_var.reset(token) in auth_context.py, but get_access_token was still returning the old token when the client issued a new call.
    I’m mentioning this because it seems to confirm that the framework isn’t propagating the refreshed token consistently, which may be the root of what’s being reported here.
    I don’t have a minimal code snippet handy, but I’d be happy to try and put one together when I’m back working on this part of the code.

    That'd be great thank you!

    I pushed code to https://github.com/raw-labs/python-sdk-issue-1250: a minimal OAuth implementation that issues 30-second tokens.

    When used with Claude Code:

    1. At connection time, there are multiple calls to refresh the access token. (I don't remember seeing that earlier but I wasn't paying attention maybe),
    2. When invoking the tool, even after refresh, the tool's code still receives an old (possibly expired) token from get_access_token.
  6. added
    P1Significant bug affecting many users, highly requested feature
    ready for workEnough information for someone to start working on
    and removed
    needs reproneeds additional information to be able to reproduce bug
    on Oct 6, 2025
  7. felixweinberger commented on Oct 6, 2025

    @felixweinberger
    Contributor

    I ran into a similar situation when I tried to implement token refresh on our MCP server (after adding load_refresh_token and exchange_refresh_token to our OAuthAuthorizationServerProvider). I could see the new token being passed to auth_context_var.reset(token) in auth_context.py, but get_access_token was still returning the old token when the client issued a new call.
    I’m mentioning this because it seems to confirm that the framework isn’t propagating the refreshed token consistently, which may be the root of what’s being reported here.
    I don’t have a minimal code snippet handy, but I’d be happy to try and put one together when I’m back working on this part of the code.

    That'd be great thank you!

    I pushed code to https://github.com/raw-labs/python-sdk-issue-1250: a minimal OAuth implementation that issues 30-second tokens.

    When used with Claude Code:

    1. At connection time, there are multiple calls to refresh the access token. (I don't remember seeing that earlier but I wasn't paying attention maybe),
    2. When invoking the tool, even after refresh, the tool's code still receives an old (possibly expired) token from get_access_token.

    Thanks for providing the repro!

  8. added
    P0Broken core functionality, security issues, critical missing feature
    and removed
    P1Significant bug affecting many users, highly requested feature
    on Oct 6, 2025
  9. pematth commented on Oct 7, 2025

    @pematth
    Author

    Hi, sorry for not responding, i was on holiday. I guess you are fine with the code provided by Benjamin. Otherwise please let me know.

  10. lucheng-hugh commented on Oct 28, 2025

    @lucheng-hugh

    Hi, do we have any updates on this bug? We also face the same bug where get_access_token() returns the old token. Weirdly, the TokenVerifier will receive the new token, but it won't be accessible during processing the MCP request unless the session is refreshed.

    I can confirm the bug still exists in 1.16.0

  11. lucheng-hugh commented on Oct 28, 2025

    @lucheng-hugh

    I confirmed the bug still exists in the latest 1.19.0

  12. bgaidioz commented on Dec 3, 2025

    @bgaidioz

    This GitHub issue was referenced in FastMCP because it describes the same problem (PrefectHQ/fastmcp#1863). It’s also related to the implementation that uses a context variable. The fix is here: PrefectHQ/fastmcp#2505

  13. bgaidioz commented on Feb 5, 2026

    @bgaidioz

    Hello.

    Here's a patch that I believe fixes the issue.

    I added a regression test that fails as one would expect without the patch (the old token is seen on the server side). CI failed on coverage for the new branch in _handle_request. I did some efforts for that, added a small, low‑level unit test to cover it, but it’s fairly close to internals and I’m not sure this is the preferred approach.

    This isn't a direct port of the patch to fastmcp. Setting the context var felt reasonable to me.

    That fixes the demo repro and our own MCP server when running against keycloak.

    I hope this helps.

  14. grahonan commented on Feb 12, 2026

    @grahonan

    I also ran into this and would love to see it fixed soon.

  15. added
    P1Significant bug affecting many users, highly requested feature
    and removed
    P0Broken core functionality, security issues, critical missing feature
    on Feb 19, 2026
  16. maxisbey commented on Feb 19, 2026

    @maxisbey
    Contributor

    This may be addressed as part of the broader auth rework in #1743. Keeping as a standalone issue for now in case it can be fixed independently before the rework lands.

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

Metadata

Metadata

Assignees

No one assigned

    Labels

    P1Significant bug affecting many users, highly requested featureauthIssues and PRs related to Authentication / OAuthbugSomething isn't workingready for workEnough information for someone to start working on

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions