无法使用 Flutter 连接到 wss
Posted
技术标签:
【中文标题】无法使用 Flutter 连接到 wss【英文标题】:Cannot connect to wss with Flutter 【发布时间】:2020-01-03 15:12:38 【问题描述】:我在 Nodejs 中编写了一个 wss 服务器,现在我正在尝试使用 Flutter 连接到这样的服务器。
这是 NodeJS 中的代码:
//Dependencies
const WebSocket = require('ws');
const fs = require('fs');
const https = require('https');
//Dependencies
//Server declarations
const server = https.createServer(
key: fs.readFileSync('pathTo/key.pem'),
cert: fs.readFileSync('pathTo/cert.pem')
);
server.listen(xxxx);
const wss = new WebSocket.Server( server );
//Server declarations
wss.on('connection', function connection(ws)
ws.on('message', function incoming(message)
console.log('Received: ' + message);
ws.send('echo: ' + message);
);
ws.send('Connected!');
);
这是 Flutter 中的代码:
import 'package:flutter/material.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/services.dart';
import 'package:web_socket_channel/io.dart';
import 'package:connectivity/connectivity.dart';
import 'package:web_socket_channel/web_socket_channel.dart';
class MyApp extends StatelessWidget
@override
Widget build(BuildContext context)
final title = 'LumenApp Prototype';
IOWebSocketChannel channel;
try
channel = new IOWebSocketChannel.connect('wss://xxxxxxxx.xxx.xxx:xxxx/');
MyHomePageState.noResponse = false;
catch(e)
MyHomePageState.noResponse = true;
return MaterialApp(
title: title,
theme: ThemeData(
primarySwatch: Colors.blue,
primaryTextTheme: TextTheme(
title: TextStyle(
color: Colors.yellow[600],
),
),
),
home: MyHomePage(
title: title,
channel: channel,
),
);
Flutter 上的错误是:WebSocketChannelException: WebSocketChannelException: HandshakeException: Handshake error in client (OS Error: CERTIFICATE_VERIFY_FAILED: self signed certificate(handshake.cc:354))
这发生在这个函数内部:
void initPlatformState()
widget.channel.stream.listen((message)
setState(() noResponse = false; );
//Handle message...
,
onError: (error)
print(error);
if(mounted)
setState(() noResponse = true;);
,
onDone: ()
if(mounted)
setState(() noResponse = true; );
);
我使用了一个由 openssl 制作的自签名证书服务器端。 知道如何解决这个问题吗?
【问题讨论】:
第一个假设是您的 websocket 服务器没有 SSL 证书,因此无法运行 WSS。 @JoãoSoares 我使用 OpenSSL 获得了一个 ssl 密钥和一个 ssl 证书。 您是否测试过您的 WSS 在不是您的 Flutter 应用的其他客户端上正常工作? @JoãoSoares 我尝试使用 Postman,但无论是使用 ws 还是使用 wss,它都不起作用,即使使用 ws 和 Flutter 也可以。 那里肯定发生了一些奇怪的事情,但您需要确保您的服务器正常工作,然后再继续查看您的 Flutter 应用程序是否存在问题。 【参考方案1】:如果你碰巧碰到this GitHub post,你可以按照this comment的临时修复:
class MyHttpOverrides extends HttpOverrides @override HttpClient createHttpClient(SecurityContext context) return super.createHttpClient(context) ..badCertificateCallback = (X509Certificate cert, String host, int port)=> true; void main() HttpOverrides.global = new MyHttpOverrides(); runApp(new MyApp());
它适用于具有自签名证书的本地 IP。
详细说明,here is the same solution:
只是为了清楚起见,特别是为了新手 Flutter/Dart,这是启用此功能所需要做的 项目中的全局选项:
在您的 main.dart 文件中,添加或导入以下类:
HttpClient createHttpClient(SecurityContext? context) return super.createHttpClient(context) ..badCertificateCallback = (X509Certificate cert, String host, int port)=> true; ```
在您的主函数中,在函数定义后添加以下行:
HttpOverrides.global = MyHttpOverrides();
This 评论对解决这个问题很有帮助,请 请注意...
这应该在开发模式下使用,不要这样做 你想发布到生产中,这个答案的目的是让 开发对您来说更容易一些,对于生产,您需要修复 您的证书问题并正确使用它,请查看其他答案 因为它可能对您的情况有所帮助。
另外值得一提的是,签名证书现在免费提供 (https://letsencrypt.org/)。
另外,我认为 Flutter 团队正在努力向enhance the documentation 寻求有关此问题的更好参考。正在跟踪here。
【讨论】:
以上是关于无法使用 Flutter 连接到 wss的主要内容,如果未能解决你的问题,请参考以下文章
无法连接到 wss://(连接建立错误:net::ERR_CONNECTION_CLOSED)
无法从 https 客户端通过 wss 连接到 emqx mqtt 代理