Improved Lora classes & addded threaded sending

This commit is contained in:
Filip Znachor 2022-12-07 15:45:29 +01:00
parent 51b5714135
commit abda8def8f
3 changed files with 70 additions and 57 deletions

View file

@ -5,7 +5,7 @@ import json
import requests import requests
from dateutil import parser from dateutil import parser
from datetime import datetime from datetime import datetime
from lora import DeviceController from lora import lora_controller
from math import floor from math import floor
@ -83,11 +83,11 @@ class Departure:
self.departure = departure self.departure = departure
self.type = type self.type = type
self.update(delay) self.update(delay)
DeviceController.data(self) lora_controller.data(self)
def update(self, delay): def update(self, delay):
self.delay = delay self.delay = delay
DeviceController.data(self) lora_controller.data(self)
def get_departure(self): def get_departure(self):
departure = -round(((datetime.now().timestamp() - (self.departure + self.delay*60))/60)*10) departure = -round(((datetime.now().timestamp() - (self.departure + self.delay*60))/60)*10)

View file

@ -2,6 +2,7 @@ import requests
from requests.structures import CaseInsensitiveDict from requests.structures import CaseInsensitiveDict
import config import config
import json import json
import threading
from time import sleep from time import sleep
from base64 import b64encode from base64 import b64encode
from datetime import datetime from datetime import datetime
@ -9,10 +10,15 @@ from datetime import datetime
import urllib3 import urllib3
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning) urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
class LoraDevice: class LoraController:
@staticmethod def __init__(self):
def generate_token(): self.storage = dict()
self.devices = []
self.message_pool = []
self.thread = None
def generate_token(self):
url = f"https://lora.plzen.eu/api/v2/login" url = f"https://lora.plzen.eu/api/v2/login"
@ -26,58 +32,65 @@ class LoraDevice:
data = requests.post(url, verify=False, headers=headers, data=json.dumps(data)).json() data = requests.post(url, verify=False, headers=headers, data=json.dumps(data)).json()
config.lora_api_token = data["token"] config.lora_api_token = data["token"]
def new(self, id):
self.devices.append(LoraDevice(self, id))
def time(self):
for d in self.devices:
d.send(f"TIME|{(datetime.now() - datetime(1970, 1, 1)).total_seconds():.0f}")
def data(self, data):
sent = True
if data.id in self.storage:
d = self.storage[data.id]
if data.line != d["line"] or data.last_stop != d["last_stop"] or data.delay != d["delay"]:
sent = False
else:
sent = False
self.storage[data.id] = { 'line': data.line, 'last_stop': data.last_stop, 'delay': data.delay }
if sent:
return
string = f"{data.id}|{data.type}|{data.line}|{data.last_stop}|{data.get_departure()}"
for d in self.devices:
d.send(f"{string}")
def send(self, id, port, msg):
self.message_pool.append((id, port, msg))
if not self.thread or not self.thread.is_alive():
self.thread = threading.Thread(target=self.thread_sending)
self.thread.start()
def thread_sending(self):
while True:
if not len(self.message_pool):
break
data = self.message_pool.pop()
url = f"https://lora.plzen.eu/api/v2/nodes/{data[0]:0>16x}/queue"
print(f"Sending {data[2]}")
headers = CaseInsensitiveDict()
headers["Content-Type"] = "application/json"
headers["Authorization"] = f"Bearer {config.lora_api_token}"
payload = {
"confirmed": True,
"data": b64encode(data[2].encode("utf-8")).decode("ascii"),
"fPort": data[1],
"reference": "string"
}
requests.post(url, verify=False, headers=headers, data=json.dumps(payload))
class LoraDevice:
def __init__(self, deveui: int): def __init__(self, controller: LoraController, deveui: int):
self.controller = controller
self.id = deveui self.id = deveui
self.port = 1 self.port = 0
def send(self, msg: str): def send(self, msg: str):
self.controller.send(self.id, self.port+1, msg)
self.port = (self.port + 1) % 15
url = f"https://lora.plzen.eu/api/v2/nodes/{self.id:0>16x}/queue"
print(f"Sending {msg}") lora_controller = LoraController()
headers = CaseInsensitiveDict() lora_controller.new(0xbdea85badeedf1)
headers["Content-Type"] = "application/json"
headers["Authorization"] = f"Bearer {config.lora_api_token}"
data = {
"confirmed": True,
"data": b64encode(msg.encode("utf-8")).decode("ascii"),
"fPort": self.port,
"reference": "string"
}
self.port = (self.port + 1) % 15 + 1;
data = requests.post(url, verify=False, headers=headers, data=json.dumps(data))
dev = LoraDevice(0xbdea85badeedf1)
class DeviceController:
storage = dict()
@staticmethod
def time():
dev.send(f"TIME|{(datetime.now() - datetime(1970, 1, 1)).total_seconds():.0f}")
@staticmethod
def data(data):
send = False
if data.id in DeviceController.storage:
d = DeviceController.storage[data.id]
if data.line != d["line"] or data.last_stop != d["last_stop"] or data.delay != d["delay"]:
send = True
else:
send = True
DeviceController.storage[data.id] = {
'line': data.line,
'last_stop': data.last_stop,
'delay': data.delay
}
if not send:
return
string = f"{data.id}|{data.type}|{data.line}|{data.last_stop}|{data.get_departure()}"
dev.send(f"{string}")

View file

@ -1,15 +1,15 @@
from departures import Departure from departures import Departure
from time import sleep from time import sleep
from lora import LoraDevice, DeviceController from lora import lora_controller
refetch = 0 refetch = 0
LoraDevice.generate_token() lora_controller.generate_token()
while True: while True:
if refetch == 0: if refetch == 0:
DeviceController.time() lora_controller.time()
Departure.fetch("40", 10) Departure.fetch("40", 10)
refetch = (refetch + 1) % 10 refetch = (refetch + 1) % 10