Completed documentation for plugins

This commit is contained in:
Fabio Manganiello 2018-06-25 19:57:43 +02:00
parent 1cbef67f2c
commit b876f17f81
23 changed files with 661 additions and 16 deletions

View file

@ -0,0 +1,6 @@
``platypush.plugins.pushbullet``
================================
.. automodule:: platypush.plugins.pushbullet
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.redis``
===========================
.. automodule:: platypush.plugins.redis
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.serial``
============================
.. automodule:: platypush.plugins.serial
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.shell``
===========================
.. automodule:: platypush.plugins.shell
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.switch``
============================
.. automodule:: platypush.plugins.switch
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.switch.switchbot``
======================================
.. automodule:: platypush.plugins.switch.switchbot
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.switch.wemo``
=================================
.. automodule:: platypush.plugins.switch.wemo
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.tts``
=========================
.. automodule:: platypush.plugins.tts
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.variable``
==============================
.. automodule:: platypush.plugins.variable
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.video.omxplayer``
=====================================
.. automodule:: platypush.plugins.video.omxplayer
:members:

View file

@ -0,0 +1,6 @@
``platypush.plugins.weather.forecast``
======================================
.. automodule:: platypush.plugins.weather.forecast
:members:

View file

@ -26,4 +26,15 @@ Plugins
platypush/plugins/midi.rst platypush/plugins/midi.rst
platypush/plugins/mqtt.rst platypush/plugins/mqtt.rst
platypush/plugins/music.mpd.rst platypush/plugins/music.mpd.rst
platypush/plugins/pushbullet.rst
platypush/plugins/redis.rst
platypush/plugins/serial.rst
platypush/plugins/shell.rst
platypush/plugins/switch.rst
platypush/plugins/switch.switchbot.rst
platypush/plugins/switch.wemo.rst
platypush/plugins/tts.rst
platypush/plugins/variable.rst
platypush/plugins/video.omxplayer.rst
platypush/plugins/weather.forecast.rst

View file

@ -8,7 +8,24 @@ from platypush.plugins import Plugin
class PushbulletPlugin(Plugin): class PushbulletPlugin(Plugin):
"""
This plugin allows you to send pushes and files to your PushBullet account.
Note: This plugin will only work if the :mod:`platypush.backend.pushbullet`
backend is configured.
Requires:
* **requests** (``pip install requests``)
"""
def send_push(self, **kwargs): def send_push(self, **kwargs):
"""
Send a push.
:param kwargs: Push arguments, see https://docs.pushbullet.com/#create-push
:type kwargs: dict
"""
pushbullet = get_backend('pushbullet') pushbullet = get_backend('pushbullet')
resp = requests.post('https://api.pushbullet.com/v2/ephemerals', resp = requests.post('https://api.pushbullet.com/v2/ephemerals',
data=json.dumps({ data=json.dumps({
@ -27,6 +44,13 @@ class PushbulletPlugin(Plugin):
def send_file(self, filename): def send_file(self, filename):
"""
Send a file.
:param filename: Path to the local file
:type filename: str
"""
pushbullet = get_backend('pushbullet') pushbullet = get_backend('pushbullet')
resp = requests.post('https://api.pushbullet.com/v2/upload-request', resp = requests.post('https://api.pushbullet.com/v2/upload-request',
data=json.dumps({'file_name': os.path.basename(filename)}), data=json.dumps({'file_name': os.path.basename(filename)}),

View file

@ -5,7 +5,31 @@ from platypush.plugins import Plugin
class RedisPlugin(Plugin): class RedisPlugin(Plugin):
"""
Plugin to send messages on Redis queues.
Requires:
* **redis** (``pip install redis``)
"""
def send_message(self, queue, msg, *args, **kwargs): def send_message(self, queue, msg, *args, **kwargs):
"""
Send a message to a Redis queu.
:param queue: Queue name
:type queue: str
:param msg: Message to be sent
:type msg: str, bytes, list, dict, Message object
:param args: Args passed to the Redis constructor (see https://redis-py.readthedocs.io/en/latest/#redis.Redis)
:type args: list
:param kwargs: Kwargs passed to the Redis constructor (see https://redis-py.readthedocs.io/en/latest/#redis.Redis)
:type kwargs: dict
"""
redis = Redis(*args, **kwargs) redis = Redis(*args, **kwargs)
redis.rpush(queue, msg) redis.rpush(queue, msg)
return Response(output={'state': 'ok'}) return Response(output={'state': 'ok'})

View file

@ -17,6 +17,14 @@ class SerialPlugin(Plugin):
""" """
def __init__(self, device, baud_rate=9600, *args, **kwargs): def __init__(self, device, baud_rate=9600, *args, **kwargs):
"""
:param device: Device path (e.g. ``/dev/ttyUSB0`` or ``/dev/ttyACM0``)
:type device: str
:param baud_rate: Serial baud rate (default: 9600)
:type baud_rate: int
"""
super().__init__(*args, **kwargs) super().__init__(*args, **kwargs)
self.device = device self.device = device
@ -53,6 +61,10 @@ class SerialPlugin(Plugin):
return output.decode().strip() return output.decode().strip()
def get_data(self): def get_data(self):
"""
Reads JSON data from the serial device and returns it as a message
"""
ser = serial.Serial(self.device, self.baud_rate) ser = serial.Serial(self.device, self.baud_rate)
try: try:

View file

@ -5,7 +5,20 @@ from platypush.message.response import Response
from .. import Plugin from .. import Plugin
class ShellPlugin(Plugin): class ShellPlugin(Plugin):
"""
Plugin to run custom shell commands.
"""
def exec(self, cmd): def exec(self, cmd):
"""
Execute a command.
:param cmd: Command to execute
:type cmd: str
:returns: A response object where the ``output`` field will contain the command output as a string, and the ``errors`` field will contain whatever was sent to stderr.
"""
output = None output = None
errors = [] errors = []

View file

@ -1,16 +1,24 @@
from .. import Plugin from .. import Plugin
class SwitchPlugin(Plugin): class SwitchPlugin(Plugin):
"""
Abstract class for interacting with switch devices
"""
def on(self, args): def on(self, args):
""" Turn the device on """
raise NotImplementedError() raise NotImplementedError()
def off(self, args): def off(self, args):
""" Turn the device off """
raise NotImplementedError() raise NotImplementedError()
def toggle(self, args): def toggle(self, args):
""" Toggle the device status (on/off) """
raise NotImplementedError() raise NotImplementedError()
def status(self): def status(self):
""" Get the device state """
raise NotImplementedError() raise NotImplementedError()

View file

@ -80,15 +80,38 @@ class Driver(object):
class SwitchSwitchbotPlugin(SwitchPlugin): class SwitchSwitchbotPlugin(SwitchPlugin):
""" """
Plugin to interact with a Switchbot (https://www.switch-bot.com/) device and
programmatically control buttons.
NOTE: since the interaction with the Switchbot requires root privileges NOTE: since the interaction with the Switchbot requires root privileges
(in order to scan on the bluetooth interface or setting gattlib in random), (in order to scan on the bluetooth interface or setting gattlib in random),
this plugin just wraps the module into a `sudo` flavor, since running this plugin just wraps the module into a `sudo` flavor, since running
Platypush with root privileges should be considered as a very bad idea. Platypush with root privileges should be considered as a very bad idea.
Make sure that your user has sudo privileges for running this bit of code. Make sure that your user has sudo privileges for running this plugin.
Requires:
* **pybluez** (``pip install pybluez``)
* **gattlib** (``pip install gattlib``)
* **libboost** (on Debian ```apt-get install libboost-python-dev libboost-thread-dev``)
""" """
def __init__(self, bt_interface=None, connect_timeout=None, def __init__(self, bt_interface=None, connect_timeout=None,
scan_timeout=None, devices={}, *args, **kwargs): scan_timeout=None, devices={}, *args, **kwargs):
"""
:param bt_interface: Bluetooth interface to use (e.g. hci0) default: first available one
:type bt_interface: str
:param connecct_timeout: Timeout for the conncection to the Switchbot device - default: None
:type connect_timeout: float
:param scan_timeout: Timeout for the scan operations - default: None
:type scan_timeout: float
:param devices: Devices to control, as a BMAC address -> name map
:type devices: dict
"""
self.bt_interface = bt_interface self.bt_interface = bt_interface
self.connect_timeout = connect_timeout if connect_timeout else 5 self.connect_timeout = connect_timeout if connect_timeout else 5
self.scan_timeout = scan_timeout if scan_timeout else 2 self.scan_timeout = scan_timeout if scan_timeout else 2
@ -118,15 +141,34 @@ class SwitchSwitchbotPlugin(SwitchPlugin):
def press(self, device): def press(self, device):
"""
Send a press button command to a device
:param device: Device name or address
:type device: str
"""
return self._run(device) return self._run(device)
def on(self, device): def on(self, device):
"""
Send a press-on button command to a device
:param device: Device name or address
:type device: str
"""
return self._run(device, 'on') return self._run(device, 'on')
def off(self, device): def off(self, device):
"""
Send a press-off button command to a device
:param device: Device name or address
:type device: str
"""
return self._run(device, 'off') return self._run(device, 'off')
def scan(self): def scan(self):
""" Scan for available Switchbot devices nearby """
output = None output = None
errors = [] errors = []
@ -145,5 +187,6 @@ class SwitchSwitchbotPlugin(SwitchPlugin):
return Response(output=output, errors=errors) return Response(output=output, errors=errors)
# vim:sw=4:ts=4:et: # vim:sw=4:ts=4:et:

View file

@ -6,7 +6,20 @@ from platypush.message.response import Response
from .. import SwitchPlugin from .. import SwitchPlugin
class SwitchWemoPlugin(SwitchPlugin): class SwitchWemoPlugin(SwitchPlugin):
"""
Plugin to control a Belkin WeMo smart switch
(https://www.belkin.com/us/Products/home-automation/c/wemo-home-automation/)
Requires:
* **ouimeaux** (``pip install ouimeaux``)
"""
def __init__(self, discovery_seconds=3, *args, **kwargs): def __init__(self, discovery_seconds=3, *args, **kwargs):
"""
:param discovery_seconds: Discovery time when scanning for devices (default: 3)
:type discovery_seconds: int
"""
super().__init__(*args, **kwargs) super().__init__(*args, **kwargs)
self.discovery_seconds=discovery_seconds self.discovery_seconds=discovery_seconds
@ -15,11 +28,34 @@ class SwitchWemoPlugin(SwitchPlugin):
self.refresh_devices() self.refresh_devices()
def refresh_devices(self): def refresh_devices(self):
""" Update the list of available devices """
self.logger.info('Starting WeMo discovery') self.logger.info('Starting WeMo discovery')
self.env.discover(seconds=self.discovery_seconds) self.env.discover(seconds=self.discovery_seconds)
self.devices = self.env.devices self.devices = self.env.devices
def get_devices(self): def get_devices(self):
"""
Get the list of available devices
:returns: The list of devices.
Example output::
output = {
"devices": [
{
"host": "192.168.1.123",
"name": "Switch 1",
"state": 1,
"model": "Belkin Plugin Socket 1.0",
"serialnumber": "123456ABCDEF"
},
{
# ...
}
]
}
"""
self.refresh_devices() self.refresh_devices()
return Response( return Response(
output = { 'devices': [ output = { 'devices': [
@ -49,12 +85,30 @@ class SwitchWemoPlugin(SwitchPlugin):
return Response(output=json.dumps(resp)) return Response(output=json.dumps(resp))
def on(self, device): def on(self, device):
"""
Turn a switch on
:param device: Device name
:type device: str
"""
return self._exec('on', device) return self._exec('on', device)
def off(self, device): def off(self, device):
"""
Turn a switch off
:param device: Device name
:type device: str
"""
return self._exec('off', device) return self._exec('off', device)
def toggle(self, device): def toggle(self, device):
"""
Toggle the state of a switch (on/off)
:param device: Device name
:type device: str
"""
return self._exec('toggle', device) return self._exec('toggle', device)

View file

@ -6,14 +6,28 @@ from platypush.message.response import Response
from .. import Plugin from .. import Plugin
class TtsPlugin(Plugin): class TtsPlugin(Plugin):
""" Default Text-to-Speech plugin. It leverages Google Translate and """
requires mplayer """ Default Text-to-Speech plugin. It leverages Google Translate.
Requires:
* **mplayer** - see your distribution docs on how to install the mplayer package
"""
def __init__(self, lang='en-gb'): def __init__(self, lang='en-gb'):
super().__init__() super().__init__()
self.lang=lang self.lang=lang
def say(self, phrase, lang=None): def say(self, phrase, lang=None):
"""
Say a phrase
:param phrase: Phrase to say
:type phrase: str
:param lang: Language code
:type lang: str
"""
if lang is None: lang=self.lang if lang is None: lang=self.lang
output = None output = None
errors = [] errors = []
@ -34,5 +48,6 @@ class TtsPlugin(Plugin):
return Response(output=output, errors=errors) return Response(output=output, errors=errors)
# vim:sw=4:ts=4:et: # vim:sw=4:ts=4:et:

View file

@ -13,14 +13,37 @@ class VariablePlugin(Plugin):
self._variables = {} self._variables = {}
def get(self, name, default_value=None): def get(self, name, default_value=None):
"""
Get the value of a variable by name.
:param name: Variable name
:type name: str
:param default_value: What will be returned if the variable is not defined (default: None)
:returns: A map in the format ``{"<name>":"<value>"}``
"""
return Response(output={name: self._variables.get(name, default_value)}) return Response(output={name: self._variables.get(name, default_value)})
def set(self, **kwargs): def set(self, **kwargs):
"""
Set a variable or a set of variables.
:param kwargs: Key-value list of variables to set (e.g. ``foo='bar', answer=42``)
"""
for (name, value) in kwargs.items(): for (name, value) in kwargs.items():
self._variables[name] = value self._variables[name] = value
return Response(output=kwargs) return Response(output=kwargs)
def unset(self, name): def unset(self, name):
"""
Unset a variable by name if it's set
:param name: Name of the variable to remove
:type name: str
"""
if name in self._variables: if name in self._variables:
del self._variables[name] del self._variables[name]
return Response(output={'status':'ok'}) return Response(output={'status':'ok'})

View file

@ -19,6 +19,22 @@ from platypush.message.event.video import VideoPlayEvent, VideoPauseEvent, \
from .. import Plugin from .. import Plugin
class VideoOmxplayerPlugin(Plugin): class VideoOmxplayerPlugin(Plugin):
"""
Plugin to control video and media playback on your Raspberry Pi or
ARM-compatible device using OMXPlayer.
It can play local files, remote URLs, YouTube URLs and it supports torrents
search, download and play.
Requires:
* **omxplayer** installed on your system (see your distro instructions)
* **omxplayer-wrapper** (``pip install omxplayer-wrapper``)
* **python-libtorrent** (``pip install python-libtorrent``), optional for Torrent support
* **youtube-dl** installed on your system (see your distro instructions), optional for YouTube support
"""
""" Supported video extensions """
video_extensions = { video_extensions = {
'.avi', '.flv', '.wmv', '.mov', '.mp4', '.m4v', '.mpg', '.mpeg', '.avi', '.flv', '.wmv', '.mov', '.mp4', '.m4v', '.mpg', '.mpeg',
'.rm', '.swf', '.vob', '.mkv' '.rm', '.swf', '.vob', '.mkv'
@ -28,6 +44,20 @@ class VideoOmxplayerPlugin(Plugin):
torrent_state = {} torrent_state = {}
def __init__(self, args=[], media_dirs=[], download_dir=None, torrent_ports=[], *argv, **kwargs): def __init__(self, args=[], media_dirs=[], download_dir=None, torrent_ports=[], *argv, **kwargs):
"""
:param args: Arguments that will be passed to the OMXPlayer constructor (e.g. subtitles, volume, start position, window size etc.) see https://github.com/popcornmix/omxplayer#synopsis and http://python-omxplayer-wrapper.readthedocs.io/en/latest/omxplayer/#omxplayer.player.OMXPlayer
:type args: list
:param media_dirs: Directories that will be scanned for media files when a search is performed (default: none)
:type media_dirs: list
:param download_dir: Directory where the videos/torrents will be downloaded (default: none)
:type download_dir: str
:param torrent_ports: Torrent ports to listen on (default: 6881 and 6891)
:type torrent_ports: list[int]
"""
super().__init__(*argv, **kwargs) super().__init__(*argv, **kwargs)
self.args = args self.args = args
@ -54,6 +84,17 @@ class VideoOmxplayerPlugin(Plugin):
self.torrent_ports = torrent_ports if torrent_ports else self.default_torrent_ports self.torrent_ports = torrent_ports if torrent_ports else self.default_torrent_ports
def play(self, resource): def play(self, resource):
"""
Play a resource.
:param resource: Resource to play. Supported types:
* Local files (format: ``file://<path>/<file>``)
* Remote videos (format: ``https://<url>/<resource>``)
* YouTube videos (format: ``https://www.youtube.com/watch?v=<id>``)
* Torrents (format: ``magnet:?<magnet_uri>``)
"""
if resource.startswith('youtube:') \ if resource.startswith('youtube:') \
or resource.startswith('https://www.youtube.com/watch?v='): or resource.startswith('https://www.youtube.com/watch?v='):
resource = self._get_youtube_content(resource) resource = self._get_youtube_content(resource)
@ -90,9 +131,11 @@ class VideoOmxplayerPlugin(Plugin):
return self.status() return self.status()
def pause(self): def pause(self):
""" Pause the playback """
if self.player: self.player.play_pause() if self.player: self.player.play_pause()
def stop(self): def stop(self):
""" Stop the playback """
if self.player: if self.player:
self.player.stop() self.player.stop()
self.player.quit() self.player.quit()
@ -101,26 +144,31 @@ class VideoOmxplayerPlugin(Plugin):
return self.status() return self.status()
def voldown(self): def voldown(self):
""" Volume down by 10% """
if self.player: if self.player:
self.player.set_volume(max(-6000, self.player.volume()-1000)) self.player.set_volume(max(-6000, self.player.volume()-1000))
return self.status() return self.status()
def volup(self): def volup(self):
""" Volume up by 10% """
if self.player: if self.player:
self.player.set_volume(min(0, self.player.volume()+1000)) self.player.set_volume(min(0, self.player.volume()+1000))
return self.status() return self.status()
def back(self): def back(self):
""" Back by 30 seconds """
if self.player: if self.player:
self.player.seek(-30) self.player.seek(-30)
return self.status() return self.status()
def forward(self): def forward(self):
""" Forward by 30 seconds """
if self.player: if self.player:
self.player.seek(+30) self.player.seek(+30)
return self.status() return self.status()
def next(self): def next(self):
""" Play the next track/video """
if self.player: if self.player:
self.player.stop() self.player.stop()
@ -132,48 +180,103 @@ class VideoOmxplayerPlugin(Plugin):
def hide_subtitles(self): def hide_subtitles(self):
""" Hide the subtitles """
if self.player: self.player.hide_subtitles() if self.player: self.player.hide_subtitles()
return self.status() return self.status()
def hide_video(self): def hide_video(self):
""" Hide the video """
if self.player: self.player.hide_video() if self.player: self.player.hide_video()
return self.status() return self.status()
def is_playing(self): def is_playing(self):
"""
:returns: True if it's playing, False otherwise
"""
if self.player: return self.player.is_playing() if self.player: return self.player.is_playing()
else: return False else: return False
def load(self, source, pause=False): def load(self, resource, pause=False):
if self.player: self.player.load(source, pause) """
Load a resource/video in the player.
:param pause: If set, load the video in paused mode (default: False)
:type pause: bool
"""
if self.player: self.player.load(resource, pause)
return self.status() return self.status()
def metadata(self): def metadata(self):
""" Get the metadata of the current video """
if self.player: return Response(output=self.player.metadata()) if self.player: return Response(output=self.player.metadata())
return self.status() return self.status()
def mute(self): def mute(self):
""" Mute the player """
if self.player: self.player.mute() if self.player: self.player.mute()
return self.status() return self.status()
def unmute(self): def unmute(self):
""" Unmute the player """
if self.player: self.player.unmute() if self.player: self.player.unmute()
return self.status() return self.status()
def seek(self, relative_position): def seek(self, relative_position):
"""
Seek backward/forward by the specified number of seconds
:param relative_position: Number of seconds relative to the current cursor
:type relative_position: int
"""
if self.player: self.player.seek(relative_position) if self.player: self.player.seek(relative_position)
return self.status() return self.status()
def set_position(self, position): def set_position(self, position):
"""
Seek backward/forward to the specified absolute position
:param position: Number of seconds from the start
:type position: int
"""
if self.player: self.player.set_seek(position) if self.player: self.player.set_seek(position)
return self.status() return self.status()
def set_volume(self, volume): def set_volume(self, volume):
"""
Set the volume
:param volume: Volume value between 0 and 100
:type volume: int
"""
# Transform a [0,100] value to an OMXPlayer volume in [-6000,0] # Transform a [0,100] value to an OMXPlayer volume in [-6000,0]
volume = 60.0*volume - 6000 volume = 60.0*volume - 6000
if self.player: self.player.set_volume(volume) if self.player: self.player.set_volume(volume)
return self.status() return self.status()
def status(self): def status(self):
"""
Get the current player state.
:returns: A dictionary containing the current state.
Example::
output = {
"source": "https://www.youtube.com/watch?v=7L9KkZoNZkA",
"state": "play",
"volume": 80,
"elapsed": 123,
"duration": 300,
"width": 800,
"height": 600
}
"""
state = PlayerState.STOP.value state = PlayerState.STOP.value
if self.player: if self.player:
@ -233,6 +336,22 @@ class VideoOmxplayerPlugin(Plugin):
self.player.stopEvent += self.on_stop() self.player.stopEvent += self.on_stop()
def search(self, query, types=None, queue_results=False, autoplay=False): def search(self, query, types=None, queue_results=False, autoplay=False):
"""
Perform a video search.
:param query: Query string, video name or partial name
:type query: str
:param types: Video types to search (default: ``["youtube", "file", "torrent"]``)
:type types: list
:param queue_results: Append the results to the current playing queue (default: False)
:type queue_results: bool
:param autoplay: Play the first result of the search (default: False)
:type autoplay: bool
"""
results = [] results = []
if types is None: if types is None:
types = { 'youtube', 'file', 'torrent' } types = { 'youtube', 'file', 'torrent' }
@ -360,6 +479,13 @@ class VideoOmxplayerPlugin(Plugin):
return Response(output=results) return Response(output=results)
def download_torrent(self, magnet): def download_torrent(self, magnet):
"""
Download a torrent to ``download_dir`` by Magnet URI
:param magnet: Magnet URI
:type magnet: str
"""
import libtorrent as lt import libtorrent as lt
if not self.download_dir: if not self.download_dir:

View file

@ -3,27 +3,253 @@ from platypush.plugins.http.request import HttpRequestPlugin
class WeatherForecastPlugin(HttpRequestPlugin): class WeatherForecastPlugin(HttpRequestPlugin):
""" Plugin for getting weather updates through Darksky API """ """
Plugin for getting weather updates through Darksky API
Requires:
* **requests** (``pip install requests``)
"""
def __init__(self, darksky_token, lat, long, units='si', **kwargs): def __init__(self, darksky_token, lat, long, units='si', **kwargs):
""" Supported unit types: ca, uk2, us, si """ """
:param darksky_token: Your token for using the darksky API, see https://darksky.net/dev
:type darksky_token: str
:param lat: Default forecast latitude
:type lat: float
:param long: Default forecast longitude
:type long: float
:param units: Weather units (default: "si").
Supported units:
* **si** (international system)
* **us** (US imperial units)
* **uk** (UK imperial units)
* **ca** (Canada imperial units)
:type units: str
"""
super().__init__(method='get', output='json') super().__init__(method='get', output='json')
self.darksky_token = darksky_token
self.units = units
self.lat = lat
self.long = long
self.latest_bulletin = {} self.latest_bulletin = {}
self.url = 'https://api.darksky.net/forecast/{}/{},{}?units={}'. \
format(darksky_token, lat, long, units)
def get_current_weather(self, **kwargs): def _get_url(self, lat=None, long=None):
response = self.get(self.url) return 'https://api.darksky.net/forecast/{}/{},{}?units={}'. \
print(response) format(self.darksky_token, (lat or self.lat), (long or self.long),
self.units)
def get_current_weather(self, lat=None, long=None, **kwargs):
"""
Get the current weather.
:param lat: Weather latitude (default: configured latitude)
:type lat: float
:param long: Weather longitude (default: configured longitude)
:type long: float
:returns: A dictionary containing the current weather object.
Example output::
output = {
"time": 1529947892,
"summary": "Mostly Cloudy",
"icon": "partly-cloudy-day",
"precipIntensity": 0.0483,
"precipProbability": 0.04,
"precipType": "rain",
"temperature": 27.94,
"apparentTemperature": 29.6,
"dewPoint": 20.01,
"humidity": 0.62,
"pressure": 1009.34,
"windSpeed": 1.83,
"windGust": 5.49,
"windBearing": 192,
"cloudCover": 0.66,
"uvIndex": 0,
"visibility": 16.09,
"ozone": 273.74
}
"""
response = self.get(self._get_url(lat, long))
return Response(output=response.output['currently']) return Response(output=response.output['currently'])
def get_hourly_forecast(self, **kwargs): def get_hourly_forecast(self, lat=None, long=None, **kwargs):
response = self.get(self.url) """
Get the hourly forecast.
:param lat: Weather latitude (default: configured latitude)
:type lat: float
:param long: Weather longitude (default: configured longitude)
:type long: float
:returns: A forecast object.
Example output::
output = {
"summary": "Partly cloudy starting tomorrow morning, continuing until tomorrow evening.",
"icon": "partly-cloudy-day",
"data": [
{
"time": 1529946000,
"summary": "Clear",
"icon": "clear-day",
"precipIntensity": 0,
"precipProbability": 0,
"temperature": 18.94,
"apparentTemperature": 18.94,
"dewPoint": 11.99,
"humidity": 0.64,
"pressure": 1025.53,
"windSpeed": 5.1,
"windGust": 6.22,
"windBearing": 329,
"cloudCover": 0.14,
"uvIndex": 1,
"visibility": 14.19,
"ozone": 334.3
},
{
"time": 1529949600,
"summary": "Clear",
"icon": "clear-day",
"precipIntensity": 0,
"precipProbability": 0,
"temperature": 18.41,
"apparentTemperature": 18.41,
"dewPoint": 11.12,
"humidity": 0.63,
"pressure": 1025.54,
"windSpeed": 4.6,
"windGust": 6.18,
"windBearing": 340,
"cloudCover": 0.07,
"uvIndex": 1,
"visibility": 16.09,
"ozone": 333.53
},
# ...
}
"""
response = self.get(self._get_url(lat, long))
return Response(output=response.output['hourly']) return Response(output=response.output['hourly'])
def get_daily_forecast(self, **kwargs): def get_daily_forecast(self, lat=None, long=None, **kwargs):
response = self.get(self.url) """
Get the daily forecast.
:param lat: Weather latitude (default: configured latitude)
:type lat: float
:param long: Weather longitude (default: configured longitude)
:type long: float
:returns: A forecast object.
Example output::
"output": {
"summary": "Light rain on Sunday, with high temperatures rising to 28°C on Sunday.",
"icon": "rain",
"data": [
{
"time": 1529877600,
"summary": "Mostly cloudy until afternoon.",
"icon": "partly-cloudy-day",
"sunriseTime": 1529896835,
"sunsetTime": 1529957280,
"moonPhase": 0.42,
"precipIntensity": 0,
"precipIntensityMax": 0.0051,
"precipIntensityMaxTime": 1529888400,
"precipProbability": 0,
"temperatureHigh": 20.04,
"temperatureHighTime": 1529931600,
"temperatureLow": 10.68,
"temperatureLowTime": 1529982000,
"apparentTemperatureHigh": 20.04,
"apparentTemperatureHighTime": 1529931600,
"apparentTemperatureLow": 10.68,
"apparentTemperatureLowTime": 1529982000,
"dewPoint": 12.18,
"humidity": 0.77,
"pressure": 1025.16,
"windSpeed": 3.84,
"windGust": 6.51,
"windGustTime": 1529881200,
"windBearing": 336,
"cloudCover": 0.5,
"uvIndex": 6,
"uvIndexTime": 1529928000,
"visibility": 14.08,
"ozone": 331.24,
"temperatureMin": 13.89,
"temperatureMinTime": 1529960400,
"temperatureMax": 20.04,
"temperatureMaxTime": 1529931600,
"apparentTemperatureMin": 13.89,
"apparentTemperatureMinTime": 1529960400,
"apparentTemperatureMax": 20.04,
"apparentTemperatureMaxTime": 1529931600
},
{
"time": 1529964000,
"summary": "Partly cloudy throughout the day.",
"icon": "partly-cloudy-day",
"sunriseTime": 1529983261,
"sunsetTime": 1530043677,
"moonPhase": 0.45,
"precipIntensity": 0,
"precipIntensityMax": 0,
"precipProbability": 0,
"temperatureHigh": 20.95,
"temperatureHighTime": 1530018000,
"temperatureLow": 11.47,
"temperatureLowTime": 1530064800,
"apparentTemperatureHigh": 20.95,
"apparentTemperatureHighTime": 1530018000,
"apparentTemperatureLow": 11.47,
"apparentTemperatureLowTime": 1530064800,
"dewPoint": 10.19,
"humidity": 0.69,
"pressure": 1026.14,
"windSpeed": 3.67,
"windGust": 7.13,
"windGustTime": 1530036000,
"windBearing": 4,
"cloudCover": 0.3,
"uvIndex": 5,
"uvIndexTime": 1530010800,
"visibility": 16.09,
"ozone": 328.59,
"temperatureMin": 10.68,
"temperatureMinTime": 1529982000,
"temperatureMax": 20.95,
"temperatureMaxTime": 1530018000,
"apparentTemperatureMin": 10.68,
"apparentTemperatureMinTime": 1529982000,
"apparentTemperatureMax": 20.95,
"apparentTemperatureMaxTime": 1530018000
},
# ...
}
"""
response = self.get(self._get_url(lat, long))
return Response(output=response.output['daily']) return Response(output=response.output['daily'])