OAuth Bearer Token提前过期:本地正常远程服务器1小时内失效
Hey there, let's break down why your OAuth Bearer tokens are expiring way earlier than the 365-day window you set once deployed to a remote server. This is a common gotcha with ASP.NET OAuth deployments, so here are the most likely culprits and fixes:
1. Server Clock Drift
If your remote server's system clock is significantly out of sync with actual time (either ahead or behind), the token's expiry calculation will be thrown off. For example, if the server thinks it's already hours ahead of real time, a token set to expire in 365 days will appear to die within minutes or hours.
- Fix: Sync your remote server's clock to a reliable NTP server. Most hosting platforms have this option in server settings, or you can run commands like
w32tm /resyncon Windows Server to force a sync.
2. IIS Application Pool Recycling
The biggest culprit here is almost always IIS recycling your app pool. By default, IIS recycles app pools every 29 hours (or when memory limits are hit). If you're using the default in-memory ticket protection (which your code is doing right now), the encryption keys used to sign tokens are stored in memory. When the app pool recycles, those keys are lost—so any existing tokens can't be validated, and your API acts like they're expired.
- Fix: Use a persistent key store like
MachineKeyto protect your tokens. Update yourConfigureOAuthmethod to explicitly set the token format with a machine-key-based protector:
This way, even if the app pool recycles, thepublic void ConfigureOAuth(IAppBuilder app) { // Create a shared data protector for consistent token signing/validation var dataProtector = new MachineKeyDataProtector( typeof(OAuthAuthorizationServerMiddleware).Namespace, "Access_Token", "v1" ); var ticketFormat = new TicketDataFormat(dataProtector); OAuthAuthorizationServerOptions OAuthServerOptions = new OAuthAuthorizationServerOptions() { TokenEndpointPath = new PathString("/Auth/Login"), AccessTokenExpireTimeSpan = TimeSpan.FromDays(365), AllowInsecureHttp = true, Provider = new AuthorizationServerProvider(), AccessTokenFormat = ticketFormat // Use persistent key storage }; app.UseOAuthAuthorizationServer(OAuthServerOptions); app.UseOAuthBearerAuthentication(new OAuthBearerAuthenticationOptions() { Provider = new OAuthBearerProvider(), AccessTokenFormat = ticketFormat // Match the server's token format }); }MachineKey(stored in your server's config or web.config) stays consistent, so tokens remain valid.
3. Multi-Server/Load Balanced Environment
If you're deploying to multiple servers behind a load balancer, each server generates its own default encryption keys. A token created on Server A will fail validation on Server B because the keys don't match—this often presents as an "expired token" error.
- Fix: Configure a shared
MachineKeyacross all servers in your web.config. Add this section to your root web.config:
You can generate secure keys using built-in .NET tools, just make sure to use the same keys on every server in your cluster.<system.web> <machineKey validationKey="YOUR_SECURE_VALIDATION_KEY" decryptionKey="YOUR_SECURE_DECRYPTION_KEY" validation="SHA1" decryption="AES" /> </system.web>
4. Accidental Client-Side Expiry Checks
Double-check your client application code. If the client is manually setting an expiry time on stored tokens (e.g., in local storage) that's shorter than 365 days, it might be discarding valid tokens early.
- Fix: Verify that your client uses the
expclaim from the token itself to determine expiry, not a hardcoded value.
Start with checking IIS app pool recycling and server clock sync first—those are the most common causes for this exact issue.
内容的提问来源于stack exchange,提问作者Furkan Bozkurt

