2017-03-26 4 views
1

C# HttpWebRequest를 사용하여 클라이언트 인증서를 통해 인증하는 웹 서비스에 XML 요청을 보내고 있습니다 (인증서는 공용 기관에서 제공했으며 서버 인증서 저장소에 유효하고 올바르게 설치되어 있습니다).HttpWebRequest 클라이언트 인증서가 항상 "요청이 중단되었습니다. SSL/TLS 보안 채널을 만들지 못했습니다."라는 오류 메시지가 나타납니다.

public void CallWebService() 
    { 
     var _url = webServiceUrl; 
     var _action = "soapActionToCall"; 
     X509Certificate2 Cert = null; 

     try 
     { 
      //Search for the certificate in the store 
      X509Store Store = new X509Store(StoreName.Root); 
      Store.Open(OpenFlags.ReadOnly); 
      X509Certificate2Collection Coll = Store.Certificates.Find(X509FindType.FindBySubjectName, "certifcateCommonName", false); 
      if (Coll != null && Coll.Count > 0) 
      { 
       Cert = Coll[0]; 
      } 
      else 
       throw new Exception("Certificate non found!"); 

      //Method to create the soap XML envelope 
      XmlDocument soapEnvelopeXml = CreateSoapEnvelope(typeOfService); 
      HttpWebRequest webRequest = CreateWebRequest(_url, _action, soapEnvelopeXml.InnerText.Length); 

      webRequest.ClientCertificates.Add(Cert); 
      InsertSoapEnvelopeIntoWebRequest(soapEnvelopeXml, webRequest); 

      // begin async call to web request. 
      IAsyncResult asyncResult = webRequest.BeginGetResponse(null, null); 

      // suspend this thread until call is complete. You might want to 
      // do something usefull here like update your UI. 
      asyncResult.AsyncWaitHandle.WaitOne(); 

      // get the response from the completed web request. 
      string soapResult; 
      using (WebResponse webResponse = webRequest.EndGetResponse(asyncResult)) 
      { 
       using (StreamReader rd = new StreamReader(webResponse.GetResponseStream())) 
       { 
        soapResult = rd.ReadToEnd(); 
       } 

       //Display the XML result 
       txtResponse.Text = soapResult; 
      } 
     } 
     catch (WebException webEx) 
     { 
      WebResponse errResp = webEx.Response; 
      string text = ""; 
      XmlDocument xmlRsp = null; 
      string error = ""; 

      if (errResp != null) 
      { 
       using (Stream respStream = errResp.GetResponseStream()) 
       { 
        StreamReader reader = new StreamReader(respStream); 
        text = reader.ReadToEnd(); 
       } 

       xmlRsp = new XmlDocument(); 
       xmlRsp.LoadXml(text); 
       if (xmlRsp.GetElementsByTagName("soapenv:Fault").Count > 0) 
        error = xmlRsp.SelectSingleNode("//error").InnerText; 

       if (error.Length > 0) 
        throw new Exception(error); 
       else 
        throw webEx; 
      } 
      else 
       throw webEx; 

     } 
    } 

    private HttpWebRequest CreateWebRequest(string url, string action, int contentLength) 
    { 
     HttpWebRequest webRequest = (HttpWebRequest)WebRequest.Create(url); 
     webRequest.Headers.Add("SOAPAction", action); 
     webRequest.Host = "host"; 
     webRequest.ContentType = "text/xml;charset=\"utf-8\""; 
     webRequest.ContentLength = contentLength; 
     webRequest.Accept = "text/xml"; 
     webRequest.Method = "POST"; 
     ServicePointManager.Expect100Continue = true; 
     // { Ssl3 = 48, Tls = 192, Tls11 = 768, Tls12 = 3072, } }. 
     ServicePointManager.SecurityProtocol = (SecurityProtocolType)3072; 

     // allows for validation of SSL conversations 
     ServicePointManager.ServerCertificateValidationCallback = delegate(
     Object obj, X509Certificate certificate, X509Chain chain, 
     SslPolicyErrors errors) 
     { 
      return (true); 
     }; 


     return webRequest; 
    } 

    private XmlDocument CreateSoapEnvelope() 
    { 
     XmlDocument soapEnvelop = new XmlDocument(); 
     soapEnvelop.Load("XmlFileToSend.xml"); 
     return soapEnvelop; 
    } 

    private void InsertSoapEnvelopeIntoWebRequest(XmlDocument soapEnvelopeXml, HttpWebRequest webRequest) 
    { 
     using (Stream stream = webRequest.GetRequestStream()) 
     { 
      soapEnvelopeXml.Save(stream); 
     } 
    } 

난 항상 오류 검색 오전 : 여기

내 코드는 "요청이 중단되었다 :. SSL/TLS 보안 채널을 생성 할 수 없습니다" 코드에서 webRequest.GetRequestStream() 줄에 InsertSoapEnvelopeIntoWebRequest 메서드를 입력하면됩니다. 누군가 나를 도울 생각이 있습니까?

답변

1

방금 ​​비슷한 문제를 해결했습니다. 제 경우에는 WebRequestHandler에 클라이언트 인증서를 첨부하자마자 "요청이 중단되었습니다 : SSL/TLS 보안 채널을 만들 수 없습니다."라는 메시지가 나타납니다. 오류.

해결 방법은 IIS_IUSRS 사용자 그룹에게 클라이언트 인증서의 개인 키를 읽을 수있는 권한을 부여하는 것입니다. 그 일이 끝나자 마자 오류가 사라졌습니다.

mmc의 인증서 스냅인에서이 작업을 수행 할 수 있습니다. 해당 저장소에서 클라이언트 인증서를 찾아 마우스 오른쪽 단추로 클릭하고 모든 작업 -> 개인 키 관리 -> 프로세스를 실행하는 사용자 또는 사용자 그룹 추가 (IIS에서 실행중인 경우 IIS_IUSRS가 작동 함) 읽기 "권한.

관련 문제