diff --git a/docs/meshtastic/index.html b/docs/meshtastic/index.html index 485594d..d2c4151 100644 --- a/docs/meshtastic/index.html +++ b/docs/meshtastic/index.html @@ -218,7 +218,7 @@ class MeshInterface: self.noProto = noProto self.myInfo = None # We don't have device info yet self.responseHandlers = {} # A map from request ID to the handler - self.failure = None # If we've encountered a fatal exception it will be kept here + self.failure = None # If we've encountered a fatal exception it will be kept here random.seed() # FIXME, we should not clobber the random seedval here, instead tell user they must call it self.currentPacketId = random.randint(0, 0xffffffff) self._startConfig() @@ -377,10 +377,21 @@ class MeshInterface: p.set_radio.CopyFrom(self.radioConfig) self.sendData(p, self.myInfo.my_node_num, - portNum=portnums_pb2.PortNum.ADMIN_APP, - wantAck=True) + portNum=portnums_pb2.PortNum.ADMIN_APP, + wantAck=True) logging.debug("Wrote config") + def writeChannel(self, channelIndex): + """Write the current (edited) channel to the device""" + + p = admin_pb2.AdminMessage() + p.set_channel.CopyFrom(self.channels[channelIndex]) + + self.sendData(p, self.myInfo.my_node_num, + portNum=portnums_pb2.PortNum.ADMIN_APP, + wantAck=True) + logging.debug("Wrote channel {channelIndex}") + def getMyNodeInfo(self): if self.myInfo is None: return None @@ -460,8 +471,16 @@ class MeshInterface: decodedURL = base64.urlsafe_b64decode(splitURL[-1]) channelSet = apponly_pb2.ChannelSet() channelSet.ParseFromString(decodedURL) - fixme("set self.channels, see https://developers.google.com/protocol-buffers/docs/reference/python-generated?csw=1#repeated-fields") - self._writeChannels() + + i = 0 + for chs in channelSet.settings: + ch = channel_pb2.Channel() + ch.role = channel_pb2.Channel.Role.PRIMARY if i == 0 else channel_pb2.Channel.Role.SECONDARY + ch.index = i + ch.settings.CopyFrom(chs) + self.channels[ch.index] = ch + self.writeChannel(ch.index) + i = i + 1 def _waitConnected(self): """Block until the initial node db download is complete, or timeout @@ -596,7 +615,7 @@ class MeshInterface: if failmsg: self.failure = Exception(failmsg) - self.isConnected.set() # let waitConnected return this exception + self.isConnected.set() # let waitConnected return this exception self.close() elif fromRadio.HasField("node_info"): @@ -1221,6 +1240,7 @@ noProto – If True, don't try to run our protocol on the link - just be a d
  • setOwner
  • setURL
  • waitForConfig
  • +
  • writeChannel
  • writeConfig
  • @@ -1304,7 +1324,7 @@ noProto – If True, don't try to run our protocol on the link - just be a d self.noProto = noProto self.myInfo = None # We don't have device info yet self.responseHandlers = {} # A map from request ID to the handler - self.failure = None # If we've encountered a fatal exception it will be kept here + self.failure = None # If we've encountered a fatal exception it will be kept here random.seed() # FIXME, we should not clobber the random seedval here, instead tell user they must call it self.currentPacketId = random.randint(0, 0xffffffff) self._startConfig() @@ -1463,10 +1483,21 @@ noProto – If True, don't try to run our protocol on the link - just be a d p.set_radio.CopyFrom(self.radioConfig) self.sendData(p, self.myInfo.my_node_num, - portNum=portnums_pb2.PortNum.ADMIN_APP, - wantAck=True) + portNum=portnums_pb2.PortNum.ADMIN_APP, + wantAck=True) logging.debug("Wrote config") + def writeChannel(self, channelIndex): + """Write the current (edited) channel to the device""" + + p = admin_pb2.AdminMessage() + p.set_channel.CopyFrom(self.channels[channelIndex]) + + self.sendData(p, self.myInfo.my_node_num, + portNum=portnums_pb2.PortNum.ADMIN_APP, + wantAck=True) + logging.debug("Wrote channel {channelIndex}") + def getMyNodeInfo(self): if self.myInfo is None: return None @@ -1546,8 +1577,16 @@ noProto – If True, don't try to run our protocol on the link - just be a d decodedURL = base64.urlsafe_b64decode(splitURL[-1]) channelSet = apponly_pb2.ChannelSet() channelSet.ParseFromString(decodedURL) - fixme("set self.channels, see https://developers.google.com/protocol-buffers/docs/reference/python-generated?csw=1#repeated-fields") - self._writeChannels() + + i = 0 + for chs in channelSet.settings: + ch = channel_pb2.Channel() + ch.role = channel_pb2.Channel.Role.PRIMARY if i == 0 else channel_pb2.Channel.Role.SECONDARY + ch.index = i + ch.settings.CopyFrom(chs) + self.channels[ch.index] = ch + self.writeChannel(ch.index) + i = i + 1 def _waitConnected(self): """Block until the initial node db download is complete, or timeout @@ -1682,7 +1721,7 @@ noProto – If True, don't try to run our protocol on the link - just be a d if failmsg: self.failure = Exception(failmsg) - self.isConnected.set() # let waitConnected return this exception + self.isConnected.set() # let waitConnected return this exception self.close() elif fromRadio.HasField("node_info"): @@ -2121,8 +2160,16 @@ wantResponse – True if you want the service on the other side to send an a decodedURL = base64.urlsafe_b64decode(splitURL[-1]) channelSet = apponly_pb2.ChannelSet() channelSet.ParseFromString(decodedURL) - fixme("set self.channels, see https://developers.google.com/protocol-buffers/docs/reference/python-generated?csw=1#repeated-fields") - self._writeChannels() + + i = 0 + for chs in channelSet.settings: + ch = channel_pb2.Channel() + ch.role = channel_pb2.Channel.Role.PRIMARY if i == 0 else channel_pb2.Channel.Role.SECONDARY + ch.index = i + ch.settings.CopyFrom(chs) + self.channels[ch.index] = ch + self.writeChannel(ch.index) + i = i + 1
    @@ -2143,6 +2190,27 @@ wantResponse – True if you want the service on the other side to send an a return False +
    +def writeChannel(self, channelIndex) +
    +
    +

    Write the current (edited) channel to the device

    +
    + +Expand source code + +
    def writeChannel(self, channelIndex):
    +    """Write the current (edited) channel to the device"""
    +
    +    p = admin_pb2.AdminMessage()
    +    p.set_channel.CopyFrom(self.channels[channelIndex])
    +
    +    self.sendData(p, self.myInfo.my_node_num,
    +                  portNum=portnums_pb2.PortNum.ADMIN_APP,
    +                  wantAck=True)
    +    logging.debug("Wrote channel {channelIndex}")
    +
    +
    def writeConfig(self)
    @@ -2161,8 +2229,8 @@ wantResponse – True if you want the service on the other side to send an a p.set_radio.CopyFrom(self.radioConfig) self.sendData(p, self.myInfo.my_node_num, - portNum=portnums_pb2.PortNum.ADMIN_APP, - wantAck=True) + portNum=portnums_pb2.PortNum.ADMIN_APP, + wantAck=True) logging.debug("Wrote config") @@ -2270,6 +2338,7 @@ debugOut {stream} – If a stream is provided, any debug serial output from
  • setOwner
  • setURL
  • waitForConfig
  • +
  • writeChannel
  • writeConfig
  • @@ -2506,6 +2575,7 @@ start the reading thread later.

  • setOwner
  • setURL
  • waitForConfig
  • +
  • writeChannel
  • writeConfig
  • @@ -2584,6 +2654,7 @@ hostname {string} – Hostname/IP address of the device to connect to

    setOwner
  • setURL
  • waitForConfig
  • +
  • writeChannel
  • writeConfig
  • @@ -2655,6 +2726,7 @@ hostname {string} – Hostname/IP address of the device to connect to

    setOwner
  • setURL
  • waitForConfig
  • +
  • writeChannel
  • writeConfig
  • diff --git a/meshtastic/__main__.py b/meshtastic/__main__.py index 4a29f13..bc27ca5 100644 --- a/meshtastic/__main__.py +++ b/meshtastic/__main__.py @@ -34,14 +34,16 @@ def onReceive(packet, interface): logging.debug(f"Received: {packet}") try: + d = packet.get('decoded') + # Exit once we receive a reply - if args.sendtext and packet["to"] == interface.myInfo.my_node_num: + if args.sendtext and packet["to"] == interface.myInfo.my_node_num and d["portnum"] == portnums_pb2.PortNum.TEXT_MESSAGE_APP: interface.close() # after running command then exit # Reply to every received message with some stats if args.reply: - if packet['decoded']['data'] is not None: - msg = packet['decoded']['data']['text'] + msg = d.get('text') + if msg: #shortName = packet['decoded']['data']['shortName'] rxSnr = packet['rxSnr'] hopLimit = packet['hopLimit'] diff --git a/setup.py b/setup.py index 3524f46..44e9f98 100644 --- a/setup.py +++ b/setup.py @@ -12,7 +12,7 @@ with open("README.md", "r") as fh: # This call to setup() does all the work setup( name="meshtastic", - version="1.2.2", + version="1.2.3", description="Python API & client shell for talking to Meshtastic devices", long_description=long_description, long_description_content_type="text/markdown",