SSL 上的 C# HttpListener 完全失败

Posted

技术标签:

【中文标题】SSL 上的 C# HttpListener 完全失败【英文标题】:C# HttpListener total failure on SSL 【发布时间】:2018-02-27 13:33:09 【问题描述】:

好的,如果我运行这个简化的代码 sn-p 程序会剧烈崩溃,甚至不会抛出异常。

所以这是我事先所做的:

已创建 ssl 证书 绑定到8443端口 通过“httpcfg -list”验证 确保“8443.cer”和“8443.pkv”在“user/.config/.mono/httplistener”中

所以一切都应该正常吗?错误的!这让我发疯了好几个小时..

using System;
using System.Net;
using System.Text;

public class HttpListenerTest 

	public static void Main(string[] args) 

		Console.WriteLine("Initialize..");
		HttpListener listener = new HttpListener();
		listener.Prefixes.Add("http://*:8089/");
		listener.Prefixes.Add("https://*:8443/");
		listener.Start();

		while (true) 
			Console.WriteLine("Listening..");
			HttpListenerContext context = listener.GetContext();

			Console.WriteLine("Respond..");
			byte[] bytes = Encoding.UTF8.GetBytes("works!");
			context.Response.OutputStream.Write(bytes, 0, bytes.Length);
			context.Response.OutputStream.Flush();
			context.Response.OutputStream.Close();
			context.Response.Close();
		
	

如果我运行此代码并在端口 8089 上发出 http 请求,一切都很好。 8443 上的 https 请求终止了进程,唯一发生的事情是“异常事件”( Screenshot here ) 在调试模式下。

..google 了丢失的文件名,得到了 4 个不相关的结果。

我的知识已经走到了尽头,真的需要 ssl 才能与侦听器一起工作。

所以如果您对此有任何经验或建议,请告诉我。

【问题讨论】:

什么版本的单声道?你是否启用了boringssl? 1. Mono 5.2.0.224 (d15-3/14f2c81) (64-bit) 2. 得赶紧调查 我想我无法通过控制台项目启用它。 (适用于 Mac 的 xamarin 和 Visual Studio) 在 IDE 中,设置环境。通过运行配置 (MONO_TLS_PROVIDER=btls) 进行变量,如果您从 shell 运行,只需导出 env。 var 或将它与您的单声道 cmd 传递到同一行 好吧,我希望我这样做是正确的screenshot,但不幸的是它没有改变任何东西 【参考方案1】:

2解决这个问题:

如果您需要快速修复 localhost(仅适用于 localhost)

感谢 SushiHangovers 的评论,将缺少的环境变量 'MONO_TLS_PROVIDER' 设置为 'btls' (BoringSSL) 解决了问题。

$ MONO_TLS_PROVIDER=btls mono servertest.exe

如果您需要它在服务器上工作

感谢 Gusman,这里有一个简短易懂的指南,介绍如何使用 nginx 管理 SSL 和向 Mono 服务器发送 Http 请求。

1.首先安装/设置Nginx

www.digitalocean.com/community/tutorials/how-to-install-nginx-on-ubuntu-16-04

2.然后安装Certbot

certbot.eff.org

3. 并使用 Certbot 保护 Nginx

www.digitalocean.com/community/tutorials/how-to-secure-nginx-with-let-s-encrypt-on-ubuntu-16-04

4. 反向代理到您的 HttpListener 端口 (taken from here)

4.1 打开 Nginx 配置文件

 $ sudo nano /etc/nginx/sites-available/default

4.2注释掉默认的try_files行并指定反向代理设置

 . . .
        location / 
                # First attempt to serve request as file, then
                # as directory, then fall back to displaying a 404.
                # try_files $uri $uri/ =404;

                # Reverse proxy settings
                include proxy_params;
                proxy_pass http://localhost:8010;
             
. . . 

然后改变

server_name _;

server_name example.com www.example.com;

现在你应该可以走了。

【讨论】:

以上是关于SSL 上的 C# HttpListener 完全失败的主要内容,如果未能解决你的问题,请参考以下文章

支持 HTTPS 的 Httplistener

如何在 C# 中的随机端口上创建 HttpListener 类?

HttpListener supports SSL only for localhost? install certificate

使用 C# HttpListener 处理多个请求

使用 C# HttpListener 提供大文件

使用 C# HttpListener 时无法设置 MIME 类型