0

我们用于HttpWebRequest对远程服务器进行 Web 服务调用。该调用需要从本地计算机加载证书。

我们遇到的问题是,如果应用程序池标识设置为NetworkService然后调用失败,并在调用中出现通用 TLS/SSL 错误HttpWebResponse.GetResponse()。如果我们将应用程序池用户的身份更改为,LocalSystem则它可以正常运行。

我想弄清楚的是为什么。什么LocalSystem可以访问NetworkService不影响 post call 的内容?

代码非常简单:

    string URL = "https://mywebserver.net";
    X509Store store = new X509Store(StoreName.Root, StoreLocation.CurrentUser);
    store.Open(OpenFlags.ReadOnly);

    var certResults = store.Certificates.Find(X509FindType.FindBySubjectName, "nameofthecertificate", false);

    /* I have confirmed that the certificate is found regardless of 
     * how the application pool is configured.
    */
    X509Certificate cert = certResults[0];

    HttpWebRequest req = (HttpWebRequest)WebRequest.Create(URL);

    req.AllowAutoRedirect = true;

    req.ClientCertificates.Add(cert);

    req.Method = "POST";

    req.ContentType = "application/soap+xml;charset=UTF-8";

    StringBuilder postData = new StringBuilder();
    postData.Append("some soap info");

    byte[] postBytes = Encoding.UTF8.GetBytes(postData.ToString());

    using (Stream postStream = req.GetRequestStream())
    {
        postStream.Write(postBytes, 0, postBytes.Length);
        postStream.Flush();
        postStream.Close();
    }

    // dies here when running under NetworkService
    HttpWebResponse resp = (HttpWebResponse)req.GetResponse();
    String data = String.Empty;

    using (StreamReader reader = new StreamReader(resp.GetResponseStream()))
    {
        data = reader.ReadToEnd();
        reader.Close();
    }
4

1 回答 1

1

一般来说,应用程序池需要一个身份才能运行。您可以配置身份使其像您一样运行,但请记住,不同的身份具有不同级别的权限。

您的问题可能很简单,因为应用程序池身份没有使用它尝试执行的代码的权限。您可以通过查看已部署的项目文件夹权限来查看。

既然您提到了 SSL/TLS 错误,我会认为该身份对已安装的证书没有权限。打开并检查商店mmc中是否有证书。Local Computer/Personal/Certificates如果这样做,请右键单击证书并转到All Tasks -> Manage Private Keys.... 通过从您的计算机位置添加应用程序池标识来添加它:

IIS AppPool\YourNameOfAppPool.

你不应该得到另一个对话框说它没有找到你正确地添加了它。

在此处阅读有关应用程序池标识的更多信息。

于 2019-09-26T17:40:15.197 回答