单独的html文件 直接访问mqtt

问题遇到的现象和发生背景

我在101.200.239.3:1883有个mqtt服务
我想做一个简单的html里面有javascript的,可以给这个服务器publish一些信息
网页是基于flask搭的

这个功能是做原型展示,所以就用微信直接把链接发过去,他就可以在网页上操作了。
后续会做进小程序里,现在先不考虑

问题相关代码,请勿粘贴截图

flask

@app.route('/iot_oper', methods=['GET'])
def iot_oper():
    data = request.args
    dev_id = data['dev_id']
    return render_template('iot_oper.html', dev_id=dev_id)

template/iot_oper.html




<!DOCTYPE html>
<html lang="en">
<head>
    {#    <meta >#}
{#    <meta charset="UTF-8"/>#}
        <meta charset="UTF-8" name="viewport"
              content="width=device-width,initial-scale=1.0,user-scalable=no,minimum-scale=1.0,maximum-scale=1.0"/>
    <title>名瑞运苗车控制系统</title>
    <style>
        .page {
            display: block;
        {#justify-content: center;#}{#text-align: center;#}
        }

        .form-row {
            display: flex;
            margin: 30px auto;
            text-align: center;
            width: min-content;
        }

        .dev_id {
            display: inherit;
            text-align: center;
            width: min-content;
        }

        .middle-btn {
            border: black 1px solid;
            text-align: center;
            margin: 30px auto;
            display: inherit;
            width: 150px;
            height: 40px;
        }

        label {
            text-align: center;
        }
    </style>
    {#    <script type="text/javascript" src="">#}
    <script src="https://unpkg.com/mqtt@4.0.1/dist/mqtt.js"></script>
    <script type="text/javascript">

  就是下面这个函数不好用
        function oper_machine(cmd) {
            var dev_id = document.getElementById('dev_id').value;
            {#var mqtt = require('mqtt');#}
            var client = mqtt.connect('ws://101.200.239.3');  
            {#var client = mqtt.connect('mqtt://test.mosquitto.org');#}
            client.on('connect', function () {
                console.log('>>> connected')
                // client.subscribe('/tips')
                setInterval(
                    () => {
                        client.publish("MingRui/" + dev_id + "/set", cmd);
                    },
                    3000
                );
            })
        }
    </script>
</head>

<body>
<div class="page">
    <div class="form-row">
        <div class="label">设备ID:</div>
        <input id="dev_id" class="dev_id" value="{{ dev_id }}"></div>
    <button style="background:yellow" onclick="oper_machine('{&quot;cmd&quot:&quot;AA&quot}')">蜂鸣
    </button>
    <button style="background:greenyellow"
            onclick="oper_machine('{&quot;data&quot:[&quot;A2&quot]}')">前进
    </button>
    <button class="middle-btn" style="background:red" onclick="oper_machine('{&quot;data&quot:[&quot;A3&quot]}')">停止
    </button>
    <button class="middle-btn" style="background:deepskyblue"
            onclick="oper_machine('{&quot;data&quot:[&quot;A4&quot]}')">后退
    </button>
</div>
</body>
</html>


运行结果及报错内容
WebSocket connection to 'ws://101.200.239.3/' failed: Could not connect to the server.

WebSocket connection to 'ws://101.200.239.3/' failed: There was a bad response from the server
我的解答思路和尝试过的方法

最开始的方案是html去访问后台接口,接口去publish。但是没搞明白为什么,每次都是flask重启前几分钟好用,之后就不行了。
接口可以访问,也可以正常运行里面的代码,也会触发publish的函数,但mqtt接收端就是没反应
代码如下

@app.route('/iot_test', methods=['GET'])
def iot_test():
    data = request.args
    dev_id = data['dev_id']
    payload = data['cmd']
    print(payload)
    # 下面这行  就不publish了
    client.publish('MingRui/%s/set' % dev_id, payload)
    # print 还能正常显示,我就很奇怪了
    print('MingRui/%s/set' % dev_id, payload)
    return payload

这个方案不准备用了,感觉还是网页直接去publish比较方便

我想要达到的结果

我看了一圈各种教程,还是不会
有可能需要登录服务器后台操作
系统环境:阿里云centos8 。yum已经改完源,可以使用

所以现在的需求其实就是 利用js来连接mqtt服务器从而接受数据是吧?

根据你的报错信息来看:

WebSocket connection to 'ws://101.200.239.3/' failed: Could not connect to the server.
WebSocket connection to 'ws://101.200.239.3/' failed: There was a bad response from the server

目前是mqtt无法连接的状态。

  • 要么是配置有问题,
  • 要么是 端口没开放
  • 要么第三方库的语法使用错误

解决方法

1、首先需要确认下mqtt服务器这个地址是否正确可以使用,端口是否开放
这行代码修改为:

var client = mqtt.connect('ws://101.200.239.30:1883');

或者这种

const options = {
  // Clean session
  clean: true,
  connectTimeout: 4000,
  // Auth
  clientId: 'emqx_test',
  username: 'emqx_test',
  password: 'emqx_test',
}
const client = mqtt.connect('mqtt://broker.emqx.io:1883', options)

2、需要确认下js中调用mqtt语法是否正常

剩下的需要更多的信息来进行判断

或许你可以先通过这个官方的Demo来看下使用:

const mqtt = require('mqtt')
const options = {
  // Clean session
  clean: true,
  connectTimeout: 4000,
  // Auth
  clientId: 'emqx_test',
  username: 'emqx_test',
  password: 'emqx_test',
}
const client = mqtt.connect('mqtt://broker.emqx.io:1883', options)
client.on('connect', function () {
  console.log('Connected')
  client.subscribe('test', function (err) {
    if (!err) {
      client.publish('test', 'Hello mqtt')
    }
  })
})

client.on('message', function (topic, message) {
  // message is Buffer
  console.log(message.toString())
  client.end()
})

如果确认无误后,修改成自己的mqtt服务器ip地址和端口号

参考链接:


如有问题及时沟通

你这个地址连不上,是不是没有加端口

var client = mqtt.connect('ws://101.200.239.3:1883');

看你的错误是无法连接服务器,你看看云服务器安全配置哪里mqtt的端口是不是没有设置开放端口,提醒:别轻易把服务器ip放出来,容易被黑。
下面的链接可供参考

好了