2

这可能是一个重复的问题,但我仍然找不到任何可以解决我的问题的答案,因此再次发布它。在Azure Worker角色中托管的ApiController中访问客户端证书

我有一个天蓝色的工作者角色,并且我使用Owin selfhost为它添加了一个ApiController(请参阅this以供参考)。

在我的自定义控制器中,我有一个POST API,它尝试通过从Request对象中提取证书来执行客户端证书身份验证,但是当部署到Azure cemulator时,证书始终为空。

这里是我的样本客户端代码:

enter code here 

公共静态异步任务GetResponseAsync(WebApiRequestInfo webApiRequestInfo)

{ 
    if (webApiRequestInfo == null) 
    { 
     throw new ArgumentNullException("webApiRequestInfo"); 
    } 

    WebRequestHandler requestHandler = null; 

    if (webApiRequestInfo.Certificate != null) 
    { 
     requestHandler = new WebRequestHandler { ClientCertificateOptions = ClientCertificateOption.Manual }; 
     requestHandler.ClientCertificates.Add(webApiRequestInfo.Certificate); 
    } 

    using (var client = requestHandler != null 
     ? new HttpClient(requestHandler) {BaseAddress = webApiRequestInfo.BaseUrl} 
     : new HttpClient {BaseAddress = webApiRequestInfo.BaseUrl}) 
    { 

     client.DefaultRequestHeaders.Accept.Clear(); 
     client.DefaultRequestHeaders.Accept.Add(
      new MediaTypeWithQualityHeaderValue(webApiRequestInfo.MediaType)); 

     var method = new HttpMethod(webApiRequestInfo.HttpMethod); 

     var request = new HttpRequestMessage(method, webApiRequestInfo.RelativeUrl) 
     { 
      Content = 
       webApiRequestInfo.Content != null 
        ? new StringContent(JsonConvert.SerializeObject(webApiRequestInfo.Content), Encoding.UTF8, 
         "application/json") 
        : null 
     }; 

     var response = await client.SendAsync(request); 

     return response; 

控制器代码如下所示:

[HttpPost] 
     public async Task<HttpResponseMessage> GetPackage([FromBody]PackageInfo packageInfo) 
     { 
      string correlationId = null; 
      var logger = TraceLogger<LogData>.Logger; 

      try 
      { 
       if (string.IsNullOrEmpty(packageInfo.Partner)) 
       { 
        throw new ArgumentException("Partner undefined"); 
       } 

       if (string.IsNullOrEmpty(packageInfo.ServiceEnvironment)) 
       { 
        throw new ArgumentException("ServiceEnvironment undefined"); 
       } 

       if (string.IsNullOrEmpty(packageInfo.StorageEnvironment)) 
       { 
        throw new ArgumentException("StorageEnvironment undefined"); 
       } 

       var cert1 = Request.GetClientCertificate();// this is always null 
} 

有我缺少的东西,或者如果这是天蓝色模拟器设计的东西。在我部署到云服务之前,我想澄清这一点,以确保这里没有任何缺失。任何建议来解决这将是非常有益的。

+0

请检查''webApiRequestInfo.BaseUrl'',是不是** ** HTTP或HTTPS ** **? –

回答

0

基于我的测试,我可以访问ASP.NET Web API(托管在Azure工作者角色中)控制器操作中的客户端证书。以下示例代码供您参考。

TestController.cs

public class TestController : ApiController 
{ 
    public HttpResponseMessage Get() 
    { 
     return new HttpResponseMessage() 
     { 
      Content = new StringContent("Hello from OWIN!") 
     }; 
    } 
    public HttpResponseMessage Get(int id) 
    { 
     var Thumbprint = Request.GetClientCertificate().Thumbprint.ToString(); 
     string msg = String.Format("Hello from OWIN (id = {0})", id); 
     return new HttpResponseMessage() 
     { 
      Content = new StringContent(msg) 
     }; 
    } 
} 

在一个控制台应用程序

X509Certificate2 certificate = new X509Certificate2(certName, password); 

var Thumbprint = certificate.Thumbprint.ToString(); 

Console.WriteLine($"client certificate Thumbprint: {Thumbprint}"); 

WebRequestHandler requestHandler = new WebRequestHandler(); 

requestHandler = new WebRequestHandler { ClientCertificateOptions = ClientCertificateOption.Manual }; 
requestHandler.ServerCertificateValidationCallback = new RemoteCertificateValidationCallback(ValidateServerCertificate); 

requestHandler.ClientCertificates.Add(certificate); 


using (var client = new HttpClient(requestHandler)) 
{ 
    HttpResponseMessage response = await client.GetAsync("https://127.0.0.1:9527/test/5"); 

    if (response.IsSuccessStatusCode) 
    { 
     string content = await response.Content.ReadAsStringAsync(); 
     Console.WriteLine($"Received response: {content}"); 
    } 
    else 
    { 
     Console.WriteLine($"Error, received status code {response.StatusCode}: {response.ReasonPhrase}"); 
    } 
} 

可以在网页API控制器动作访问客户端证书发送请求

enter image description here

控制台应用程序输出

enter image description here

+0

您的证书是自签名证书还是由受信任的CA(服务器的可信列表)签名? – ashish1238

+0

在我的测试中,我使用的是自签名证书。 –