import solara
import zarr
import pandas as pd
import altair as alt
import requests
from io import BytesIO
@solara.component
def Page():
river_number = 110123714 # Replace with the desired river number
date = '2024040100' # Replace with the desired date
forecast_data = get_forecast_data(river_number, date)
if not forecast_data.empty:
solara.Markdown(f"## Forecast data for RiverNumber {river_number} on {date}:")
solara.DataFrame(forecast_data)
chart = create_altair_chart(forecast_data)
solara.Markdown("## Forecast Visualization")
solara.Viz(chart)
else:
solara.Markdown(f"No forecast data found for RiverNumber {river_number} on {date}.")
def get_forecast_data(river_number, date):
s3_bucket_url = f'https://geoglows-v2-forecasts.s3.amazonaws.com/{date}.zarr/'
try:
rivid_url = s3_bucket_url + 'rivid'
qout_url = s3_bucket_url + 'Qout'
time_url = s3_bucket_url + 'time'
ensemble_url = s3_bucket_url + 'ensemble'
rivid_array = fetch_zarr_array(rivid_url)
if river_number in rivid_array:
river_index = list(rivid_array).index(river_number)
qout_array = fetch_zarr_array(qout_url)[:, :, river_index]
time_array = fetch_zarr_array(time_url)
ensemble_array = fetch_zarr_array(ensemble_url)
forecast_df = pd.DataFrame(qout_array, columns=time_array)
forecast_df.index = [f"ensemble_{i}" for i in ensemble_array]
forecast_df.columns = time_array
forecast_df = forecast_df.transpose()
return forecast_df
else:
return pd.DataFrame()
except Exception as e:
print(f"Error accessing data for RiverNumber {river_number} on {date}: {e}")
return pd.DataFrame()
def fetch_zarr_array(url):
response = requests.get(url)
response.raise_for_status()
store = zarr.storage.ZipStore(BytesIO(response.content))
zarr_array = zarr.open(store, mode='r')
return zarr_array[:]
def create_altair_chart(forecast_df):
forecast_df_reset = forecast_df.reset_index().melt(id_vars=['index'], var_name='Time', value_name='Flow')
chart = alt.Chart(forecast_df_reset).mark_line().encode(
x='Time:T',
y='Flow:Q',
color='index:N'
).properties(
title='Forecast Flow Data',
width=800,
height=400
)
return chart