Merge pull request #3 from bmartin5692/Ozmo930

Ozmo930 working
This commit is contained in:
Brian Martin
2019-02-27 23:03:36 -05:00
committed by GitHub
3 changed files with 38 additions and 14 deletions
+19 -9
View File
@@ -6,9 +6,11 @@ from collections import OrderedDict
from threading import Event from threading import Event
import threading import threading
import sched import sched
import random
import ssl
import requests import requests
import stringcase import stringcase
from sleekxmpp import ClientXMPP, Callback, MatchXPath from sleekxmpp import ClientXMPP, Callback, MatchXPath
from sleekxmpp.xmlstream import ET from sleekxmpp.xmlstream import ET
from sleekxmpp.exceptions import XMPPError from sleekxmpp.exceptions import XMPPError
@@ -17,8 +19,6 @@ from paho.mqtt.client import Client as ClientMQTT
from paho.mqtt import publish as MQTTPublish from paho.mqtt import publish as MQTTPublish
from paho.mqtt import subscribe as MQTTSubscribe from paho.mqtt import subscribe as MQTTSubscribe
import ssl
_LOGGER = logging.getLogger(__name__) _LOGGER = logging.getLogger(__name__)
# These consts define all of the vocabulary used by this library when presenting various states and components. # These consts define all of the vocabulary used by this library when presenting various states and components.
@@ -856,7 +856,7 @@ class EcoVacsIOTMQ(ClientMQTT):
class EcoVacsXMPP(ClientXMPP): class EcoVacsXMPP(ClientXMPP):
def __init__(self, user, domain, resource, secret, continent, vacuum, server_address=None ): def __init__(self, user, domain, resource, secret, continent, vacuum, server_address=None ):
ClientXMPP.__init__(self, user + '@' + domain, '0/' + resource + '/' + secret) ClientXMPP.__init__(self, "{}@{}/{}".format(user, domain,resource), '0/' + resource + '/' + secret) #Init with resource to bind it
self.user = user self.user = user
self.domain = domain self.domain = domain
self.resource = resource self.resource = resource
@@ -922,12 +922,24 @@ class EcoVacsXMPP(ClientXMPP):
def _wrap_command(self, ctl, recipient): def _wrap_command(self, ctl, recipient):
q = self.make_iq_query(xmlns=u'com:ctl', ito=recipient, ifrom=self._my_address()) q = self.make_iq_query(xmlns=u'com:ctl', ito=recipient, ifrom=self._my_address())
q['type'] = 'set' q['type'] = 'set'
if not "id" in ctl.attrib:
ctl.attrib["id"] = self.getReqID() #If no ctl id provided, add an id to the ctl. This was required for the ozmo930 and shouldn't hurt others
for child in q.xml: for child in q.xml:
if child.tag.endswith('query'): if child.tag.endswith('query'):
child.append(ctl) child.append(ctl)
return q return q
def getReqID(self, customid="0"): #Generate a somewhat random string for request id, with minium 8 chars. Works similar to ecovacs app.
if customid != "0":
return "{}".format(customid) #return provided id as string
else:
rtnval = str(random.randint(1,50))
while len(str(rtnval)) <= 8:
rtnval = "{}{}".format(rtnval,random.randint(0,50))
return "{}".format(rtnval) #return as string
def _my_address(self): def _my_address(self):
if not self.vacuum['iotmq']: if not self.vacuum['iotmq']:
return self.user + '@' + self.domain + '/' + self.boundjid.resource return self.user + '@' + self.domain + '/' + self.boundjid.resource
@@ -995,10 +1007,8 @@ class VacBotCommand:
class Clean(VacBotCommand): class Clean(VacBotCommand):
def __init__(self, mode='auto', speed='normal', iotmq=False, action='start',terminal=False, **kwargs): def __init__(self, mode='auto', speed='normal', iotmq=False, action='start',terminal=False, **kwargs):
if kwargs == {}: if kwargs == {}:
if not iotmq: #Looks like action is needed for some bots, shouldn't affect older models
super().__init__('Clean', {'clean': {'type': CLEAN_MODE_TO_ECOVACS[mode], 'speed': FAN_SPEED_TO_ECOVACS[speed]}}) super().__init__('Clean', {'clean': {'type': CLEAN_MODE_TO_ECOVACS[mode], 'speed': FAN_SPEED_TO_ECOVACS[speed],'act': CLEAN_ACTION_TO_ECOVACS[action]}})
else:
super().__init__('Clean', {'clean': {'type': CLEAN_MODE_TO_ECOVACS[mode], 'speed': FAN_SPEED_TO_ECOVACS[speed],'act': CLEAN_ACTION_TO_ECOVACS[action]}})
else: else:
initcmd = {'type': CLEAN_MODE_TO_ECOVACS[mode], 'speed': FAN_SPEED_TO_ECOVACS[speed]} initcmd = {'type': CLEAN_MODE_TO_ECOVACS[mode], 'speed': FAN_SPEED_TO_ECOVACS[speed]}
for kkey, kvalue in kwargs.items(): for kkey, kvalue in kwargs.items():
+5 -5
View File
@@ -43,11 +43,11 @@ def test_custom_command_noargs():
def test_clean_command(): def test_clean_command():
c = Clean() c = Clean()
assert_equals(ElementTree.tostring(c.to_xml()), assert_equals(ElementTree.tostring(c.to_xml()),
b'<ctl td="Clean"><clean speed="standard" type="auto" /></ctl>') # protocol has attribs in other order b'<ctl td="Clean"><clean act="s" speed="standard" type="auto" /></ctl>') # protocol has attribs in other order
c = Clean('edge', 'high') c = Clean('edge', 'high')
assert_equals(ElementTree.tostring(c.to_xml()), assert_equals(ElementTree.tostring(c.to_xml()),
b'<ctl td="Clean"><clean speed="strong" type="border" /></ctl>') # protocol has attribs in other order b'<ctl td="Clean"><clean act="s" speed="strong" type="border" /></ctl>') # protocol has attribs in other order
c = Clean(iotmq=True) c = Clean(iotmq=True)
assert_equals(ElementTree.tostring(c.to_xml()), assert_equals(ElementTree.tostring(c.to_xml()),
@@ -93,13 +93,13 @@ def test_spotarea_command():
def test_edge_command(): def test_edge_command():
c = Edge() c = Edge()
assert_equals(ElementTree.tostring(c.to_xml()), assert_equals(ElementTree.tostring(c.to_xml()),
b'<ctl td="Clean"><clean speed="strong" type="border" /></ctl>') # protocol has attribs in other order b'<ctl td="Clean"><clean act="s" speed="strong" type="border" /></ctl>') # protocol has attribs in other order
def test_spot_command(): def test_spot_command():
c = Spot() c = Spot()
assert_equals(ElementTree.tostring(c.to_xml()), assert_equals(ElementTree.tostring(c.to_xml()),
b'<ctl td="Clean"><clean speed="strong" type="spot" /></ctl>') # protocol has attribs in other order b'<ctl td="Clean"><clean act="s" speed="strong" type="spot" /></ctl>') # protocol has attribs in other order
def test_charge_command(): def test_charge_command():
@@ -111,7 +111,7 @@ def test_charge_command():
def test_stop_command(): def test_stop_command():
c = Stop() c = Stop()
assert_equals(ElementTree.tostring(c.to_xml()), assert_equals(ElementTree.tostring(c.to_xml()),
b'<ctl td="Clean"><clean speed="standard" type="stop" /></ctl>') b'<ctl td="Clean"><clean act="s" speed="standard" type="stop" /></ctl>')
def test_play_sound_command(): def test_play_sound_command():
+14
View File
@@ -13,6 +13,20 @@ def test_wrap_command():
c = str(x._wrap_command(Clean().to_xml(), 'E0000000001234567890@126.ecorobot.net/atom')) c = str(x._wrap_command(Clean().to_xml(), 'E0000000001234567890@126.ecorobot.net/atom'))
assert_true(search(r'from="20170101abcdefabcdefa@ecouser.net/abcdef12"', c)) assert_true(search(r'from="20170101abcdefabcdefa@ecouser.net/abcdef12"', c))
assert_true(search(r'to="E0000000001234567890@126.ecorobot.net/atom"', c)) assert_true(search(r'to="E0000000001234567890@126.ecorobot.net/atom"', c))
assert_true(search(r'td="Clean" id="',c)) #Check that an id was added to ctl
cwithid = Clean().to_xml()
cwithid.attrib["id"] = "12345678"
c = str(x._wrap_command(cwithid, 'E0000000001234567890@126.ecorobot.net/atom'))
assert_true(search(r'td="Clean" id="12345678',c)) #Check that customid was added to ctl
def test_getReqID():
x = make_ecovacs_xmpp()
rid = x.getReqID("12345678")
assert_equals(rid, "12345678") #Check returned ID is the same as provided
rid2 = x.getReqID()
assert_true(len(rid2) >= 8) #Check returned random ID is at least 8 chars
def test_subscribe_to_ctls(): def test_subscribe_to_ctls():
response = None response = None