summaryrefslogtreecommitdiff
path: root/searx
diff options
context:
space:
mode:
authorAlexandre Flament <alex@al-f.net>2022-09-23 18:14:09 +0200
committerGitHub <noreply@github.com>2022-09-23 18:14:09 +0200
commitbef3984d0320b2010c50097e186b07b6673a9647 (patch)
tree70f6681bde74f5fde8dbeeebcbf1a3de25b8d348 /searx
parentd3fec1388cd07567690903922022f7081a4ba5f1 (diff)
parent12f7d4a46b4469e27effce7c57cf42ce67c419f2 (diff)
downloadsearxng-bef3984d0320b2010c50097e186b07b6673a9647.tar.gz
searxng-bef3984d0320b2010c50097e186b07b6673a9647.zip
Merge pull request #1728 from liimee/eng-ddw
add duckduckgo weather engine
Diffstat (limited to 'searx')
-rw-r--r--searx/engines/duckduckgo_weather.py136
-rw-r--r--searx/settings.yml5
2 files changed, 141 insertions, 0 deletions
diff --git a/searx/engines/duckduckgo_weather.py b/searx/engines/duckduckgo_weather.py
new file mode 100644
index 000000000..d0f34d60f
--- /dev/null
+++ b/searx/engines/duckduckgo_weather.py
@@ -0,0 +1,136 @@
+# SPDX-License-Identifier: AGPL-3.0-or-later
+# lint: pylint
+"""DuckDuckGo Weather"""
+
+from json import loads
+from urllib.parse import quote
+
+from datetime import datetime
+from flask_babel import gettext
+
+about = {
+ "website": 'https://duckduckgo.com/',
+ "wikidata_id": 'Q12805',
+ "official_api_documentation": None,
+ "use_official_api": True,
+ "require_api_key": False,
+ "results": "JSON",
+}
+
+categories = ["others"]
+
+url = "https://duckduckgo.com/js/spice/forecast/{query}/{lang}"
+
+
+def generate_condition_table(condition):
+ res = ""
+
+ res += f"<tr><td><b>{gettext('Condition')}</b></td>" f"<td><b>{condition['summary']}</b></td></tr>"
+
+ res += (
+ f"<tr><td><b>{gettext('Temperature')}</b></td>"
+ f"<td><b>{f_to_c(condition['temperature'])}°C / {condition['temperature']}°F</b></td></tr>"
+ )
+
+ res += (
+ f"<tr><td>{gettext('Feels like')}</td><td>{f_to_c(condition['apparentTemperature'])}°C / "
+ f"{condition['apparentTemperature']}°F</td></tr>"
+ )
+
+ res += (
+ f"<tr><td>{gettext('Wind')}</td><td>{condition['windBearing']}° — "
+ f"{'%.2f' % (condition['windSpeed'] * 1.6093440006147)} km/h / {condition['windSpeed']} mph</td></tr>"
+ )
+
+ res += f"<tr><td>{gettext('Visibility')}</td><td>{condition['visibility']} km</td>"
+
+ res += f"<tr><td>{gettext('Humidity')}</td><td>{condition['humidity'] * 100}%</td></tr>"
+
+ return res
+
+
+def generate_day_table(day):
+ res = ""
+
+ res += (
+ f"<tr><td>{gettext('Min temp.')}</td><td>{f_to_c(day['temperatureLow'])}°C / "
+ f"{day['temperatureLow']}°F</td></tr>"
+ )
+ res += (
+ f"<tr><td>{gettext('Max temp.')}</td><td>{f_to_c(day['temperatureHigh'])}°C / "
+ f"{day['temperatureHigh']}°F</td></tr>"
+ )
+ res += f"<tr><td>{gettext('UV index')}</td><td>{day['uvIndex']}</td></tr>"
+ res += (
+ f"<tr><td>{gettext('Sunrise')}</td><td>{datetime.fromtimestamp(day['sunriseTime']).strftime('%H:%M')}</td></tr>"
+ )
+ res += (
+ f"<tr><td>{gettext('Sunset')}</td><td>{datetime.fromtimestamp(day['sunsetTime']).strftime('%H:%M')}</td></tr>"
+ )
+
+ return res
+
+
+def request(query, params):
+ params["url"] = url.format(query=quote(query), lang=params['language'].split('-')[0])
+
+ return params
+
+
+def f_to_c(temperature):
+ return "%.2f" % ((temperature - 32) / 1.8)
+
+
+def response(resp):
+ results = []
+
+ if resp.text.strip() == "ddg_spice_forecast();":
+ return []
+
+ result = loads(resp.text[resp.text.find('\n') + 1 : resp.text.rfind('\n') - 2])
+
+ current = result["currently"]
+
+ title = result['flags']['ddg-location']
+
+ infobox = f"<h3>{gettext('Current condition')}</h3><table><tbody>"
+
+ infobox += generate_condition_table(current)
+
+ infobox += "</tbody></table>"
+
+ last_date = None
+
+ for time in result['hourly']['data']:
+ current_time = datetime.fromtimestamp(time['time'])
+
+ if last_date != current_time.date():
+ if last_date is not None:
+ infobox += "</tbody></table>"
+
+ infobox += f"<h3>{current_time.strftime('%Y-%m-%d')}</h3>"
+
+ infobox += "<table><tbody>"
+
+ for day in result['daily']['data']:
+ if datetime.fromtimestamp(day['time']).date() == current_time.date():
+ infobox += generate_day_table(day)
+
+ infobox += "</tbody></table><table><tbody>"
+
+ last_date = current_time.date()
+
+ infobox += f"<tr><td rowspan=\"7\"><b>{current_time.strftime('%H:%M')}</b></td></tr>"
+
+ infobox += generate_condition_table(time)
+
+ infobox += "</tbody></table>"
+
+ results.append(
+ {
+ "infobox": title,
+ "content": infobox,
+ }
+ )
+
+ return results
diff --git a/searx/settings.yml b/searx/settings.yml
index a3e19768d..3f07bb2dd 100644
--- a/searx/settings.yml
+++ b/searx/settings.yml
@@ -553,6 +553,11 @@ engines:
timeout: 3.0
disabled: true
+ - name: duckduckgo weather
+ engine: duckduckgo_weather
+ shortcut: ddw
+ disabled: true
+
- name: apple maps
engine: apple_maps
shortcut: apm