importjsonimportpaho.mqtt.publish as publishclass Thread(threading.Thread): #开启一个线程
def __init__(self, dat):
threading.Thread.__init__(self)
self.Dat=datdefrun(self):
c=self.Dat
c.client=mqtt.Client(c.client_id)
c.client.on_connect= c.on_connect #设置连接上服务器回调函数
c.client.on_message = c.on_message #设置接收到服务器消息回调函数
c.client.on_subscribe =c.on_subscribec.client.on_publish=c.on_publish
c.client.on_unsubscribe=c.on_unsubscribe
c.client.on_disconnect=c.on_disconnectnRet=Falsetry:
c.client.connect(c.host, c.port, c.keepalive)#连接服务器,端口为1883,维持心跳为60秒
nRet =TrueexceptException as e:print('MQTT errorA', e) #打错误
c.client.loop_forever(retry_first_connection=True)classClientProtcal(object):def __init__(self):pass
defByte(self, op):
data= json.dumps(op).encode('utf-8')returndatadefParse(self, buf):
op=Nonetry:
op= json.loads(buf.decode('utf-8'))exceptException as e:print('error', e)returnopclassMqttClient(object):
protcal=ClientProtcal()
logName= ''
def __init__(self, obj, host, port=1883, keepalive=60, bind_address="", log=None):iflog:
self.l=log
self.name= 'Mqtt' #类名
self.obj = obj #对象
self.q =obj.q
self.topical= obj.topical #主题self.client_id=obj.client_id
self.host=host
self.port=port
self.keepalive=keepalive
self.bind_address=bind_address
self.client=None
self.thread=Thread(self)
self.thread.start()deflog(self, msg):ifself.l:
self.l.logInfo(msg)defsetName(self, name):
self.name=namedef on_connect(self, client, userdata, flags, rc): #连接成功
ifself.client:for t inself.topical:#topical = '%s%s' % ('', t)
self.client.subscribe(t) #订阅主题
self.log('订阅主题:[%s]' %t)defsubscribes(self, topicals):for topical intopicals:
self.subscribe(topical)defsubscribe(self, topical):ifself.client:
self.client.subscribe(topical)
self.log('订阅主题:[%s]' %topical)defunSubscribe(self, topical):ifself.client:
self.client.unsubscribe(topical)
self.log('取消订阅:[%s]' %topical)def on_message(self, client, userdata, msg): #接收到消息
op =self.protcal.Parse(msg.payload)
s= '收到[%s]推送:[%s]' %(msg.topic, str(op))
print(s)self.q.put(op)
defon_socket_close(self, client, userdata, socket):
self.obj.strNetStaut= 'OffLine'self.obj.netState=0pass
defclose(self):ifself.client:
self.client.disconnect()def Send(self, topical, op): #发送消息
ifself.client:
payload=MqttClient.protcal.Byte(op)
res=self.client.publish(topical, payload)@classmethoddefsingle(cls, stopic, payload, host, port):
d=MqttClient.protcal.Byte(payload)try:
publish.single(stopic,
payload=d,
hostname=host,
client_id="lora1",
port=port,
protocol=mqtt.MQTTv311)
MqttClient.log(MqttClient.logName,'推送主题:[%s][%s]' %(stopic, str(payload)))exceptException as e:print("publish.single err:", e)