You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

.NET Core API使用PKCE从OneLogin获取AccessToken时遇400错误求助

使用OneLogin PKCE授权码流程获取AccessToken时遇到400错误请求问题排查

我正尝试通过带PKCE的授权码流程从OneLogin获取AccessToken,已经完成PKCE第一步并成功拿到授权码,但用这个授权码请求令牌时一直收到400错误请求。我已经按照OneLogin官网要求配置了第二步请求的所有必填参数,以下是我的代码,希望有人帮忙排查问题:

public async Task GetAccessToken(string redirecturl, string authCode)
{
    HttpClientHandler clientHandler = new HttpClientHandler();
    clientHandler.ServerCertificateCustomValidationCallback = (sender, cert, chain, sslPolicyErrors) => { return true; };

    var client = new HttpClient(clientHandler);
    
    var body = JsonConvert.SerializeObject(new
    {
        grant_type = "authorization_code",
        code = authCode, // 第一步从OneLogin获取的授权码
        client_id=XXXXXXXXXXXXXXXXXX386d707215718", // 语法错误:开头缺失引号,结尾多了引号
        redirect_uri=redirecturl, // 在OneLogin账户中注册的重定向URL
        code_verifier=GetCacheEntry(CodeKey) // 第一步使用的code verifier
    });
    var req = new HttpRequestMessage
    {
        Method = HttpMethod.Post,
        RequestUri = new Uri("https://MySubdomain.onelogin.com/oidc/2/token"),
        Content = new StringContent(body)

    };
    req.Content.Headers.ContentType= new MediaTypeHeaderValue(@"application/x-www-form-urlencoded");

    var response = await client.SendAsync(req);
    if (response.StatusCode == HttpStatusCode.OK)
    {
        var responseBody =await response.Content.ReadAsStringAsync();

        var json = JsonConvert.DeserializeObject<OAuthTokenResponse>(responseBody);
        memoryCache.Remove(CodeKey);
        return Ok(json);
    }
    
    return BadRequest(response);
}

核心问题及修正方案

  • 请求体格式不匹配:你把请求内容序列化为JSON字符串,但设置的Content-Type是application/x-www-form-urlencoded,OneLogin令牌接口要求表单格式的请求体,而非JSON。需改用FormUrlEncodedContent构建请求体。
  • client_id语法错误:代码中client_id的引号配对错误,正确写法应为client_id = "XXXXXXXXXXXXXXXXXX386d707215718"。
  • 注释格式错误:C#单行注释需用//,而非---或--。

修正后的代码示例

public async Task<IActionResult> GetAccessToken(string redirecturl, string authCode)
{
    HttpClientHandler clientHandler = new HttpClientHandler();
    clientHandler.ServerCertificateCustomValidationCallback = (sender, cert, chain, sslPolicyErrors) => true;

    using var client = new HttpClient(clientHandler);
    
    // 构建表单格式的请求体
    var formContent = new FormUrlEncodedContent(new Dictionary<string, string>
    {
        {"grant_type", "authorization_code"},
        {"code", authCode},
        {"client_id", "XXXXXXXXXXXXXXXXXX386d707215718"},
        {"redirect_uri", redirecturl},
        {"code_verifier", GetCacheEntry(CodeKey)}
    });

    var req = new HttpRequestMessage
    {
        Method = HttpMethod.Post,
        RequestUri = new Uri("https://MySubdomain.onelogin.com/oidc/2/token"),
        Content = formContent
    };

    var response = await client.SendAsync(req);
    if (response.IsSuccessStatusCode)
    {
        var responseBody = await response.Content.ReadAsStringAsync();
        var json = JsonConvert.DeserializeObject<OAuthTokenResponse>(responseBody);
        memoryCache.Remove(CodeKey);
        return Ok(json);
    }
    
    // 读取错误响应内容,便于精准排查
    var errorContent = await response.Content.ReadAsStringAsync();
    return BadRequest(errorContent);
}

额外提示:返回错误时读取并返回响应的具体内容,能获取OneLogin给出的详细错误描述,更快定位问题。

内容的提问来源于stack exchange,提问作者Nasiem

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.15 03:15:57