Thank you for sharing the implementation details.
We understand that your custom Durable Functions Monitor endpoint is being executed multiple times due to the auth flow, and you're encountering a “token already redeemed” error on repeated invocations. Based on our analysis, this can occur when the same authorization code is used more than once or when the token is not cached correctly.
To address this, please try the following update to your function logic:
Suggested Fix in Code
Update your function to ensure the code
is only processed once, and cache the token to avoid redeeming the code multiple times:
// Token cache (could be improved with distributed or persistent cache for production use)
private static AuthenticationResult _cachedAuthResult;
[Function(nameof(MyCustomDfMonEndpoint))]
public async Task<HttpResponseData> ServeDfMonStatics(
[HttpTrigger(AuthorizationLevel.Anonymous, "get", Route = Globals.DfMonRoutePrefix + "/{p1?}/{p2?}/{p3?}")] HttpRequestData req,
string p1, string p2, string p3)
{
string code = req.Query["code"];
if (_cachedAuthResult == null)
{
if (string.IsNullOrEmpty(code))
{
// Redirect to login if no code is present
var authUrl = $"https://login.microsoftonline.com/{tenant}/oauth2/v2.0/authorize?...";
var response = req.CreateResponse(HttpStatusCode.Redirect);
response.Headers.Add("Location", authUrl);
return response;
}
// Acquire token only once
var app = ConfidentialClientApplicationBuilder.Create(clientId)
.WithClientSecret(clientSecret)
.WithRedirectUri(redirectUri)
.WithAuthority(new Uri($"https://login.microsoftonline.com/{tenant}"))
.Build();
_cachedAuthResult = await app.AcquireTokenByAuthorizationCode(
new[] { "openid", "profile", "email" }, code).ExecuteAsync();
}
// Serve monitor UI if token is cached
if (_cachedAuthResult != null && !string.IsNullOrEmpty(_cachedAuthResult.AccessToken))
{
return await this.DfmServeStaticsFunction(req, p1, p2, p3);
}
return req.CreateResponse(HttpStatusCode.BadRequest);
}
Note: This sample uses a simple static cache. In a production setting, you may want to store the token securely per user/session or integrate with a more robust caching mechanism.
We recommend testing this approach in your environment. If it resolves the repeated invocation issue, we can further help harden the solution for your needs.
Please let us know how it goes, and feel free to reach out with any follow-up questions.
Hope this helps. Do let us know if you have any further queries.
If this answers your query, do click Accept Answer and Yes for "Was this answer helpful." And if you have any further questions, let us know.