diff --git a/README.md b/README.md index c6bbb6d30..adefb6eed 100644 --- a/README.md +++ b/README.md @@ -166,6 +166,7 @@ Currently the following service providers are supported: - [Peterborough City Council - peterborough.gov.uk](./doc/source/peterborough_gov_uk.md) - [South Cambridgeshire District Council - scambs.gov.uk](./doc/source/scambs_gov_uk.md) - [City of York Council - york.gov.uk](./doc/source/york_gov_uk.md) +- [West Berkshire Council - westberks.gov.uk](./doc/source/westberks_gov_uk.md) - [Wiltshire Council - wiltshire.gov.uk](./doc/source/wiltshire_gov_uk.md) ## Installation diff --git a/custom_components/waste_collection_schedule/waste_collection_schedule/source/westberks_gov_uk.py b/custom_components/waste_collection_schedule/waste_collection_schedule/source/westberks_gov_uk.py new file mode 100644 index 000000000..9a24b47de --- /dev/null +++ b/custom_components/waste_collection_schedule/waste_collection_schedule/source/westberks_gov_uk.py @@ -0,0 +1,113 @@ +from datetime import date, datetime + +import time +import json +import requests + +from waste_collection_schedule import Collection + +TITLE = "West Berkshire Council, UK" +DESCRIPTION = "Source for westberks.gov.uk services for West Berkshire Council" +URL = "westberks.gov.uk" + +TEST_CASES = { + "known_uprn": {"uprn": "100080241094"}, + "unknown_uprn_by_name": {"postcode": "RG7 6NZ", "housenumberorname": "PARROG HOUSE"}, + "unknown_uprn_by_number": {"postcode": "RG18 4QU", "housenumberorname": "6"}, + "unknown_uprn_business": {"postcode": "RG18 4GE", "housenumberorname": "3"} +} + +ICONS = { + "RUBBISH": "mdi:trash-can", + "RECYCLING": "mdi:recycle", +} + +SEARCH_URLS = { + "uprn_search": "https://www.westberks.gov.uk/apiserver/ajaxlibrary", + "collection_search": "https://www.westberks.gov.uk/apiserver/ajaxlibrary", +} + +COLLECTIONS = {"Rubbish", "Recycling"} + +class Source: + def __init__( + self, uprn=None, postcode=None, housenumberorname=None + ): # argX correspond to the args dict in the source configuration + self._uprn = uprn + self._postcode = postcode + self._housenumberorname = housenumberorname + + def fetch(self): + entries = [] + session = requests.Session() + + # Find the UPRN based on the postcode and the property name/number + if self._uprn is None: + self._postcode = self._postcode.strip() + jsonrpc = {"id": str(int(time.time())),"method": "location.westberks.echoPostcodeFinder","params": {"provider": "", "postcode": self._postcode}} + args = { "callback": "HomeAssistant", "jsonrpc": json.dumps(jsonrpc), "_": 0 } + r = requests.get(SEARCH_URLS["uprn_search"], params = args) + + # I don't really know python so there *must* be a better way to do these four lines! + response_str = r.content.decode("utf-8") + data_length = len(response_str) -1 + response_sub = response_str[14:data_length] + address_data = json.loads(response_sub) + + propertyUprns = address_data['result'] + for match in propertyUprns: + if match['line1'].startswith(self._housenumberorname): + self._uprn = match["udprn"] + if match['buildingnumber'].startswith(self._housenumberorname): # no evidence (yet) that their database uses this + self._uprn = match["udprn"] + + entries = [] + + # Get the collection days based on the UPRN (either supplied through arguments or searched for above) + if self._uprn is not None: + + # POST request - one for each type as it is a separate method in the api + rubbish_args = {"jsonrpc":"2.0","id":str(int(time.time())) ,"method":"goss.echo.westberks.forms.getNextRubbishCollectionDate","params":{"uprn":self._uprn}} + recycling_args = {"jsonrpc":"2.0","id":str(int(time.time())),"method":"goss.echo.westberks.forms.getNextRecyclingCollectionDate","params":{"uprn":self._uprn}} + r = session.post(SEARCH_URLS["collection_search"], json = rubbish_args) + rubbish_data = json.loads(r.content) + r = session.post(SEARCH_URLS["collection_search"], json = recycling_args) + recycling_data = json.loads(r.content) + + # if subtext is empty, use datetext + # if both have values, use subtext + + # Extract dates from json + waste_type = "Rubbish" + if not rubbish_data['result']['nextRubbishDateSubText']: + dt_str = rubbish_data['result']['nextRubbishDateText'] + " " + str(date.today().year) + else: + if len(rubbish_data['result']['nextRubbishDateText'])<12: + dt_str = rubbish_data['result']['nextRubbishDateSubText'] + " " + str(date.today().year) + dt_zulu = datetime.strptime(dt_str, '%A %d %B %Y') + dt_local = dt_zulu.astimezone(None) + entries.append( + Collection( + date=dt_local.date(), + t=waste_type, + icon=ICONS.get(waste_type.upper()), + ) + ) + + waste_type = "Recycling" + if not recycling_data['result']['nextRecyclingDateSubText']: + dt_str = recycling_data['result']['nextRecyclingDateText'] + " " + str(date.today().year) + else: + if len(recycling_data['result']['nextRecyclingDateText'])<12: + dt_str = recycling_data['result']['nextRecyclingDateSubText'] + " " + str(date.today().year) + dt_zulu = datetime.strptime(dt_str, '%A %d %B %Y') + dt_local = dt_zulu.astimezone(None) + entries.append( + Collection( + date=dt_local.date(), + t=waste_type, + icon=ICONS.get(waste_type.upper()), + ) + ) + + return entries diff --git a/doc/source/westberks_gov_uk.md b/doc/source/westberks_gov_uk.md new file mode 100644 index 000000000..3e39be4c5 --- /dev/null +++ b/doc/source/westberks_gov_uk.md @@ -0,0 +1,52 @@ +# West Berkshire Council + +Support for schedules provided by [West Berkshire Council](https://www.westberks.gov.uk/). + +If collection data is available for the address provided, it will return rubbish and recycling waste collection dates. + +## Configuration via configuration.yaml + +```yaml +waste_collection_schedule: + sources: + - name: westberks_gov_uk + args: + postcode: POSTCODE + uprn: UPRN +``` + +### Configuration Variables + +**postcode**
+_(string) (optional)_ + +**hournameornumber**
+_(string) (optional)_ + +**uprn**
+_(string) (optional)_ + +Either the postcode _and_ housenameornumber or the UPRN should be supplied in the arguments + +## Examples + +```yaml +waste_collection_schedule: + sources: + - name: westberks_gov_uk + args: + uprn: "100080241094" +``` + +```yaml +waste_collection_schedule: + sources: + - name: westberks_gov_uk + args: + postcode: "RG18 4QU" + housenameornumber: "6" +``` + +## How to find your UPRN + +An easy way to discover your Unique Property Reference Number (UPRN) is by going to [Find My Address](https://www.findmyaddress.co.uk/) and providing your address details. diff --git a/info.md b/info.md index 1527d80a5..6ad02b588 100644 --- a/info.md +++ b/info.md @@ -152,4 +152,5 @@ Currently the following service providers are supported: - [Peterborough City Council - peterborough.gov.uk](https://github.com/mampfes/hacs_waste_collection_schedule/blob/master/doc/source/peterborough_gov_uk.md) - [South Cambridgeshire District Council - scambs.gov.uk](https://github.com/mampfes/hacs_waste_collection_schedule/blob/master/doc/source/scambs_gov_uk.md) - [City of York Council - york.gov.uk](https://github.com/mampfes/hacs_waste_collection_schedule/blob/master/doc/source/york_gov_uk.md) -- [Wiltshire Council - wiltshire.gov.uk](https://github.com/mampfes/hacs_waste_collection_schedule/blob/master/doc/source/wiltshire_gov_uk.md) \ No newline at end of file +- [West Berkshire Council - westberks.gov.uk](./doc/source/westberks_gov_uk.md) +- [Wiltshire Council - wiltshire.gov.uk](https://github.com/mampfes/hacs_waste_collection_schedule/blob/master/doc/source/wiltshire_gov_uk.md)