platypush/platypush/backend/pushbullet/__init__.py

90 lines
2.1 KiB
Python

import logging
import json
import websocket
from pushbullet import Pushbullet
from .. import Backend
class PushbulletBackend(Backend):
_requires = [
'pushbullet'
]
def _init(self, token, device):
self.token = token
self.device = device
@staticmethod
def _on_init(ws):
logging.info('Connection opened')
@staticmethod
def _on_close(ws):
logging.info('Connection closed')
@staticmethod
def _on_msg(ws, msg):
ws.backend._on_push(msg)
@staticmethod
def _on_error(ws, e):
logging.exception(e)
self.ws.close()
self._init_socket()
def _on_push(self, data):
try:
data = json.loads(data) if isinstance(data, str) else push
except Exception as e:
logging.exception(e)
return
if data['type'] != 'push':
return # Not a push notification
push = data['push']
logging.debug('Received push: {}'.format(push))
if 'body' not in push:
return
body = push['body']
try:
body = json.loads(body)
except ValueError as e:
return
self.on_msg(body)
def _init_socket(self):
self.ws = websocket.WebSocketApp(
'wss://stream.pushbullet.com/websocket/' + self.token,
on_open = self._on_init,
on_message = self._on_msg,
on_error = self._on_error,
on_close = self._on_close)
self.ws.backend = self
def send_msg(self, msg):
if isinstance(msg, dict):
msg = json.dumps(msg)
if not isinstance(msg, str):
raise RuntimeError('Invalid non-JSON message')
pb = Pushbullet(self.token)
devices = [dev for dev in pb.devices if dev.nickname == self.device]
if not devices:
raise RuntimeError('No such device: {}'.format(self.device))
device = devices[0]
pb.push_note('', msg, device)
def run(self):
self._init_socket()
self.ws.run_forever()
# vim:sw=4:ts=4:et: