忽然在后台看到Typecho更新了,正好趁着服务器到期换了一个服务器,顺手把升级一下。
新版最低需要php7.3,就这样
忽然在后台看到Typecho更新了,正好趁着服务器到期换了一个服务器,顺手把升级一下。
新版最低需要php7.3,就这样
上一篇写服务端的文章已经是去年年底,现在MQTTnet的版本是4.2.1.781,总的来说改动不大。下面以新版为例实现一个客户端。
var mqttClientOptions = new MqttClientOptionsBuilder()
.WithTcpServer("地址", 端口)
.WithClientId("我是客户端名称")//连接id
.WithCredentials("demo","123456")//如果有用户名密码
.WithTls()//如果启用了ssl/tls
.WithProtocolVersion(MqttProtocolVersion.V500)//如果用mqtt5
.Build();//配置
IMqttClient client = new MqttFactory().CreateMqttClient();//创建连接
client.ApplicationMessageReceivedAsync += MqttClient_ApplicationMessageReceivedAsync;//收到消息的方法
client.ConnectedAsync += Client_ConnectedAsync;//连接成功的方法
client.ConnectingAsync += Client_ConnectingAsync;//连接中的方法
配置里面一个大坑害我调了一个小时,如果mqtt服务端需要用户名和密码,那么使用.WithCredentials()来填写。我一直以为是.WithUserProperty(),极有迷惑性。
连接并订阅主题
// User proper cancellation and no while(true).
while (true)
{
try
{
// This code will also do the very first connect! So no call to _ConnectAsync_ is required in the first place.
if (!await client.TryPingAsync())
{
var response= await client.ConnectAsync(mqttClientOptions, CancellationToken.None);
DelegateSetRtbText(response.ReasonString);
// Subscribe to topics when session is clean etc.
var mqttSubscribeOptions = new MqttFactory().CreateSubscribeOptionsBuilder()
.WithTopicFilter(
f =>
{
f.WithTopic("shi");//订阅主题
})
.Build();
await client.SubscribeAsync(mqttSubscribeOptions);
}
}
catch
{
// Handle the exception properly (logging etc.).
}
finally
{
// Check the connection state every 5 seconds and perform a reconnect if required.
await Task.Delay(TimeSpan.FromSeconds(5));
}
}
好了,就这么简单
最近在精益论坛上看到有个叫FBro浏览器库,是对CEF3的一个封装。除了易语言模块,还提供了C#版,正好有个网页填表在selenium和cef下都被反爬策略识别了,所以试了下这个模块,碰到并解决了一些问题,供大家借鉴。
这个模块只支持64位编译,所以32位的操作系统是没法使用的。这也是我最终放弃的原因,公司的公用电脑是32位的win7,重装系统不现实。
这个提供了nuget包,直接在nuget管理器里搜索就有了。
需要把FBroSharp.x64和FBroSharp.Common.x64两个包都装上。我在生成的时候碰到了下图的错误:
这是由于本身不支持32位,VS默认目标平台是Any CPU,所以只要在点击项目——属性——生成,将平台由Any CPU改成x64即可。
粗略看了下文档,封装的还是挺不错的,比直接用cefsharp简单点。可惜不符合我的要求,继续鼓捣webview2去了。
MQTT主要用于物联网,最近因为一些特殊需求,需要做个类似SCADA的东西,经过评估MQTT比较符合预期。
对于MQTT,.Net下有个使用最广泛的库MQTTnet,nuget里最新的版本是4.1.4.563。网上搜了一下,现有教程基本都是2或者3这些版本,而到了4.0版里面的使用发放确实不太一样,所以本篇以上述版本为例,实现一个简单的服务端和客户端。
创建服务端:
MqttServer server;
var optionbuilder = new MqttServerOptionsBuilder()
.WithDefaultEndpoint()//设置默认地址127.0.0.1
.WithDefaultEndpointPort(1883);//设置端口
server = new MqttFactory().CreateMqttServer(optionbuilder.Build());//创建服务端实例
server.ClientConnectedAsync += Server_ClientConnectedAsync;//实现客户端连接方法
server.StartAsync();//启动服务端
对于其中的客户端连接后的方法:
private Task Server_ClientConnectedAsync(ClientConnectedEventArgs arg)
{
MessageBox.Show($"{arg.ClientId}上线了!");
return Task.CompletedTask;
}
一般情况下,服务端(broker)只是一个中转站,所有的消息都是由客户端发送至服务端,然后服务端转发至其他客户端。但服务端也提供了一个方法,可以实现服务端向客户端进行广播:
server.InjectApplicationMessage(
new InjectedMqttApplicationMessage(
new MqttApplicationMessageBuilder()
.WithTopic("主题")
.WithPayload("消息内容")
.Build()
)
);
最近在请求内网MIS系统的某一接口时,发现请求超时了。一开始以为网络卡,延长请求超时时间到1分钟,依然超时。
加断点调试,发现请求Requeset请求一直卡在ReadToEnd()
using (Stream streamReceive = response.GetResponseStream())
{
using (StreamReader streamReader = new StreamReader(streamReceive, encoding))
{
string strResult = streamReader.ReadToEnd();
try
{
return strResult;
}
catch (Exception ex)
{
return ex.Message;
}
}
}
查询了一下,发现原因出在了HTTP协议的版本上。
内网MIS服务器的HTTP版本是1.1,发送request后,response不会断开,所以ReadToEnd()就会读不完数据,造成一直卡在这里。
所以解决办法有两个:
1.设置request的http版本为1.0
request.ProtocolVersion=HttpVersion.Version10;
2.不使用ReadToEnd(),而是根据response里和content_length长度来决定需要读多少字节。读到够数就立刻关闭。