Skip to content

Commit

Permalink
v0.706 - further weather data sourcing
Browse files Browse the repository at this point in the history
  • Loading branch information
FlyingFathead committed May 25, 2024
1 parent 9ef052f commit 06146e7
Show file tree
Hide file tree
Showing 5 changed files with 114 additions and 8 deletions.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ yt-dlp>=2024.3.10
- Use the `configmerger.py` to update old configuration files into a newer version's `config.ini`. You can do this by creating a copy of your existing config to i.e. a file named `myconfig.txt` and including in it the lines you want to keep for the newer version. Then, just run `python configmerger.py config.ini myconfig.txt` and all your existing config lines will be migrated to the new one. Works in most cases, but remember to be careful and double-check any migration issues with i.e. `diff`!

# Changelog
- v0.706 - further weather fetching options; additional country-based data fetching
- v0.705 - improved weather data combining; small tweaks
- v0.703 - Language translations and tweaks to WeatherAPI data fetching
- v0.70 - WeatherAPI support added, to enable, get an API key from weatherapi.com
Expand Down
80 changes: 80 additions & 0 deletions api_get_additional_weather_data.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
# api_get_additional_weather_data.py

import logging
import asyncio
import re

## NOTE: this is ONLY for example purposes!
async def get_additional_data_dump():
try:
# Execute the lynx command and capture the output
command = 'lynx --dump -nolist https://www.foreca.fi/'
process = await asyncio.create_subprocess_shell(
command,
stdout=asyncio.subprocess.PIPE,
stderr=asyncio.subprocess.PIPE
)

stdout, stderr = await process.communicate()

if stderr:
logging.error(f"Error in get_additional_data_dump: {stderr.decode()}")
return "Error fetching data."

output = stdout.decode()

# Regular expressions to trim the output
start_marker = r'Suomen sää juuri nyt'
end_marker = r'Foreca YouTubessa'
trimmed_output = re.search(rf'{start_marker}(.*?){end_marker}', output, re.DOTALL)

# Return the trimmed output if markers are found
if trimmed_output:
debug_output = trimmed_output.group(1)

# Parsing the specific weather forecast section
parsed_forecast = parse_foreca_data(debug_output)

# Format the parsed data for output
formatted_forecast = f"{parsed_forecast}"

# Print the output for debugging
logging.info(formatted_forecast)

return formatted_forecast
else:
return "Start or stop marker not found in the output."

except Exception as e:
# Handle errors (e.g., lynx not installed, network issues)
logging.error(f"Exception in get_additional_data_dump: {e}")
return str(e)

def parse_foreca_data(data):
# Regular expressions to identify the start and end of the desired section
start_marker = r'Sääennuste koko maahan'
end_marker = r'Lähipäivien sää'

# Extract the section
forecast_section = re.search(rf'{start_marker}(.*?){end_marker}', data, re.DOTALL)
if forecast_section:
forecast_data = forecast_section.group(1).strip()
# Further parsing can be done here to extract regional forecasts
# Format the data for output
return forecast_data
else:
return "Relevant weather forecast section not found."

# Example usage
# Assuming 'output' contains the lynx dump

# Example usage
if __name__ == "__main__":
# Create an asyncio event loop
loop = asyncio.get_event_loop()

# Run the async function inside asyncio.run()
result = loop.run_until_complete(get_additional_data_dump())

# Print the result
print(result)
36 changes: 29 additions & 7 deletions api_get_openweathermap.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@
# github.com/FlyingFathead/TelegramBot-OpenAI-API/
# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#
# >>> this weather fetcher module version: v0.705 (25-May-2024)
# >>> weather fetcher module version: v0.706
# >>> (Updated May 25 2024)
#
# This API functionality requires both OpenWeatherMap and MapTiler API keys.
# You can get both from the corresponding service providers.
Expand All @@ -25,6 +26,9 @@
# Stuff we want to get via WeatherAPI:
from api_get_weatherapi import get_moon_phase, get_timezone, get_daily_forecast, get_current_weather_via_weatherapi

# Import the additional data fetching function for Finland
from api_get_additional_weather_data import get_additional_data_dump

# get the combined weather
async def get_weather(city_name, country, exclude='', units='metric', lang='fi'):
api_key = os.getenv('OPENWEATHERMAP_API_KEY')
Expand All @@ -39,8 +43,8 @@ async def get_weather(city_name, country, exclude='', units='metric', lang='fi')

base_url = 'http:https://api.openweathermap.org/data/2.5/'

lat, lon, country = await get_coordinates(city_name, country=country)
if lat is None or lon is None or country is None:
lat, lon, resolved_country = await get_coordinates(city_name, country=country)
if lat is None or lon is None or resolved_country is None:
logging.info("Failed to retrieve coordinates or country.")
return "[Unable to retrieve coordinates or country for the specified location. Ask the user for clarification.]"

Expand All @@ -60,10 +64,19 @@ async def get_weather(city_name, country, exclude='', units='metric', lang='fi')
moon_phase_data = await get_moon_phase(lat, lon)
daily_forecast_data = await get_daily_forecast(f"{lat},{lon}")
current_weather_data_from_weatherapi = await get_current_weather_via_weatherapi(f"{lat},{lon}")
return await combine_weather_data(city_name, country, lat, lon, current_weather_data, forecast_data, moon_phase_data, daily_forecast_data, current_weather_data_from_weatherapi)

# Fetch additional data for Finland
additional_data = ""
if resolved_country.lower() == "fi": # Case-insensitive check
logging.info("Fetching additional weather data for Finland.")
additional_data = await get_additional_data_dump()
logging.info(f"Additional data fetched: {additional_data}")

combined_data = await combine_weather_data(city_name, resolved_country, lat, lon, current_weather_data, forecast_data, moon_phase_data, daily_forecast_data, current_weather_data_from_weatherapi, additional_data)
return combined_data
else:
logging.error(f"Failed to fetch weather data: {current_weather_response.text} / {forecast_response.text}")
return "[Inform the user that data fetching from OpenWeatherMap API failed, current information could not be fetched. Reply in the user's language.]"
return "[Inform the user that data fetching the weather data failed, current information could not be fetched. Reply in the user's language.]"

# get coordinates
async def get_coordinates(city_name, country=None):
Expand Down Expand Up @@ -144,7 +157,7 @@ def degrees_to_cardinal(d):
return dirs[ix % 16]

# combined weather data
async def combine_weather_data(city_name, country, lat, lon, current_weather_data, forecast_data, moon_phase_data, daily_forecast_data, current_weather_data_from_weatherapi):
async def combine_weather_data(city_name, country, lat, lon, current_weather_data, forecast_data, moon_phase_data, daily_forecast_data, current_weather_data_from_weatherapi, additional_data):
tf = TimezoneFinder()
timezone_str = tf.timezone_at(lat=lat, lng=lon) # get timezone using the coordinates
local_timezone = pytz.timezone(timezone_str)
Expand Down Expand Up @@ -260,8 +273,17 @@ async def combine_weather_data(city_name, country, lat, lon, current_weather_dat
"For example, use 🌞 for sunny, 🌧️ for rain, ⛅ for partly cloudy, etc and include a relevant and concise overview of what was asked."
)

combined_info = f"{detailed_weather_info}\n\n{final_forecast}\n\n{additional_info_to_add}"
combined_info = f"{detailed_weather_info}\n\n{final_forecast}"

# Append additional data for Finland if available
if additional_data:
combined_info += f"\n\n[ Lisätiedot Suomeen (lähde: foreca.fi -- MAINITSE LÄHDE) ]\n{additional_data}"

# Append the additional info at the end
combined_info += f"\n\n{additional_info_to_add}"

logging.info(f"Formatted combined weather data being sent: {combined_info}")

return combined_info

# Format the weather information and translate it if necessary.
Expand Down
3 changes: 3 additions & 0 deletions api_get_weatherapi.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,9 @@
# github.com/FlyingFathead/TelegramBot-OpenAI-API/
# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#
# >>> weather fetcher module version: v0.706
# >>> (Updated May 25 2024)
#
# This API functionality requires WeatherAPI key.
# You can get the API key from the corresponding service provider.
# Once you have the API key, add it to your environment variables:
Expand Down
2 changes: 1 addition & 1 deletion main.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
# https://github.com/FlyingFathead/TelegramBot-OpenAI-API
#
# version of this program
version_number = "0.705"
version_number = "0.706"

# experimental modules
import requests
Expand Down

0 comments on commit 06146e7

Please sign in to comment.