Skip to content

Commit

Permalink
added troute to the nexus metadata
Browse files Browse the repository at this point in the history
  • Loading branch information
romer8 committed Jun 9, 2024
1 parent 5653630 commit de95254
Show file tree
Hide file tree
Showing 8 changed files with 276 additions and 4 deletions.
46 changes: 45 additions & 1 deletion reactapp/features/hydroFabric/components/hydroFabricLinePlot.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,9 @@ import '../css/chart.css';
const chartOptions = {
axisX: {
type: FixedScaleAxis,
divisor: 5,
divisor: 10,
labelInterpolationFnc: function(value) {
console.log(value)
return new Date(value).toLocaleDateString();
}
},
Expand All @@ -29,6 +30,8 @@ const chartOptions = {
};




const HydroFabricLinePlot = (props) => {
// Reference to the chart container
const chartRef = useRef(null);
Expand All @@ -39,6 +42,7 @@ const HydroFabricLinePlot = (props) => {
useEffect(() => {
if (!state.nexus.series) return;
const nexusSeries = state.nexus.series.map(point => ({x: new Date(point.x), y: point.y}));

const chartData = {
series: [
{ name: 'Nexus', data: nexusSeries },
Expand All @@ -53,6 +57,7 @@ const HydroFabricLinePlot = (props) => {


return () => {
console.log("retuirnin")
if(chartInstance && props.singleRowOn){
actions.reset_nexus();
chartInstance.current.detach();
Expand Down Expand Up @@ -100,6 +105,45 @@ const HydroFabricLinePlot = (props) => {
};
}, [state.catchment.series]); // Re-run effect if series data changes



useEffect(() => {
if (!state.troute.series) return;
if (chartRef.current) {
const trouteSeries = state.troute.series.map(point => ({x: new Date(point.x), y: point.y}));
const chartData = {
series: [
{ name: 'Troute', data: trouteSeries },
]
};

chartInstance.current = new LineChart(chartRef.current, chartData, chartOptions);

addAnimationToLineChart(chartInstance.current, easings)
makeAxis(
chartRef.current,
'Time (Date)',
`${state.troute.variable ? state.troute.variable.toLowerCase() : state.troute.variable_list ? state.troute.variable_list[0].label : null}`
)

makeTitle(
chartRef.current,
`${state.troute.variable ? state.troute.variable.toLowerCase() : state.troute.variable_list ? state.troute.variable_list[0].label : null}: ${state.troute.id} `)
}

return () => {
if(props.singleRowOn){
console.log(props.singleRowOn)
actions.reset_troute();
chartRef.current.detach();
document.getElementById('x-axis-title')?.remove();
document.getElementById('y-axis-title')?.remove();
}

};
}, [state.troute.series]); // Re-run effect if series data changes


return (
<div ref={chartRef} style={{ width: "100%", height: "90%", position: "relative"}}></div>
);
Expand Down
5 changes: 5 additions & 0 deletions reactapp/features/hydroFabric/hooks/useHydroFabric.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,11 @@ const useHydroFabric = () => {
set_nexus_list: (list) => dispatch({ type: hydroFabricActionsTypes.set_nexus_list, payload: list}),
set_catchment_list: (list) => dispatch({ type: hydroFabricActionsTypes.set_catchment_list, payload: list}),
set_catchment_variable_list: (list) => dispatch({ type: hydroFabricActionsTypes.set_catchment_variable_list, payload: list}),
set_troute_series: (series) => dispatch({ type: hydroFabricActionsTypes.set_troute_series, payload: series }),
set_troute_id: (id) => dispatch({ type: hydroFabricActionsTypes.set_troute_id, payload: id }),
set_troute_variable: (variable) => dispatch({ type: hydroFabricActionsTypes.set_troute_variable, payload: variable }),
set_troute_variable_list: (list) => dispatch({ type: hydroFabricActionsTypes.set_troute_variable_list, payload: list }),
reset_troute: () => dispatch({ type: hydroFabricActionsTypes.reset_troute }),
reset_nexus: () => dispatch({ type: hydroFabricActionsTypes.reset_nexus }),
reset_catchment: () => dispatch({ type: hydroFabricActionsTypes.reset_catchment }),
reset: () => dispatch({ type: hydroFabricActionsTypes.reset }),
Expand Down
5 changes: 5 additions & 0 deletions reactapp/features/hydroFabric/store/actions/actionsTypes.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,13 @@ const hydroFabricActionsTypes = {
set_catchment_id: 'SET_CATCHMENT_ID',
set_catchment_variable: 'SET_CATCHMENT_VARIABLE',
set_catchment_variable_list: 'SET_CATCHMENT_VARIABLE_LIST',
set_troute_series: 'SET_TROUTE_SERIES',
set_troute_id: 'SET_TROUTE_ID',
set_troute_variable: 'SET_TROUTE_VARIABLE',
set_troute_variable_list: 'SET_TROUTE_VARIABLE_LIST',
reset_nexus: 'RESET_NEXUS',
reset_catchment: 'RESET_CATCHMENT',
reset_troute: 'RESET_TROUTE',
reset: 'RESET',
};

Expand Down
65 changes: 65 additions & 0 deletions reactapp/features/hydroFabric/store/reducers/hydroFabricReducer.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,13 @@ const hydroFabricInitialStore = {
list:null,
variable_list:null
},
troute:{
series:null,
variable:null,
id:null,
list:null,
variable_list:null
}

},
actions:{}
Expand Down Expand Up @@ -124,6 +131,64 @@ const hydroFabricReducer = (state, action) => {
}
}
};
case hydroFabricActionsTypes.set_troute_series:
return {
...state,
state: {
...state.state,
troute: {
...state.state.troute,
series: action.payload
}
}
};
case hydroFabricActionsTypes.set_troute_id:
return {
...state,
state: {
...state.state,
troute: {
...state.state.troute,
id: action.payload
}
}
};
case hydroFabricActionsTypes.set_troute_variable:
return {
...state,
state: {
...state.state,
troute: {
...state.state.troute,
variable: action.payload
}
}
};
case hydroFabricActionsTypes.set_troute_variable_list:
return {
...state,
state: {
...state.state,
troute: {
...state.state.troute,
variable_list: action.payload
}
}
};
case hydroFabricActionsTypes.reset_troute:
return {
...state,
state: {
...state.state,
troute: {
series:null,
variable:null,
id:null,
list:null,
variable_list:null
}
}
};
case hydroFabricActionsTypes.reset_nexus:
return {
...state,
Expand Down
8 changes: 7 additions & 1 deletion reactapp/services/api/app.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,12 @@ const appAPI = {
getCatchmentTimeSeries: (params) => {
return apiClient.get(`${APP_ROOT_URL}getCatchmentTimeSeries/`, { params });
},
};
getTrouteVariables: (params) => {
return apiClient.get(`${APP_ROOT_URL}getTrouteVariables/`, { params });
},
getTrouteTimeSeries: (params) => {
return apiClient.get(`${APP_ROOT_URL}getTrouteTimeSeries/`, { params });
}
}

export default appAPI;
60 changes: 60 additions & 0 deletions reactapp/views/ngiab/hydroFabricView.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ const HydroFabricView = (props) => {
appAPI.getNexusTimeSeries(params).then((response) => {
actions.set_nexus_series(response.data);
actions.set_nexus_list(response.nexus_ids);
actions.set_troute_id(state.nexus.id);
props.toggleSingleRow(false);
}).catch((error) => {
console.log("Error fetching nexus time series", error);
Expand All @@ -33,6 +34,51 @@ const HydroFabricView = (props) => {

}, [state.nexus.id]);

useEffect(() => {
if (!state.troute.id) return;
props.setIsLoading(true);

var params = {
troute_id: state.troute.id
}
appAPI.getTrouteVariables(params).then((response) => {
actions.set_troute_variable_list(response.troute_variables);
props.toggleSingleRow(false);
props.setIsLoading(false);
}).catch((error) => {
props.setIsLoading(false);
console.log("Error fetching troute variables", error);
})
return () => {
if (state.troute.id) return;
actions.reset_troute();
}
},[state.troute.id]);


useEffect(() => {
if (!state.troute.variable || !state.troute.id) return;
// actions.reset_nexus();
props.setIsLoading(true);
var params = {
troute_id: state.troute.id,
troute_variable: state.troute.variable
}
appAPI.getTrouteTimeSeries(params).then((response) => {
actions.set_troute_series(response.data);
props.toggleSingleRow(false);
props.setIsLoading(false);
}).catch((error) => {
props.setIsLoading(false);
console.log("Error fetching troute time series", error);
})
return () => {
if (state.troute.id) return;
actions.reset_troute();
}
},[state.troute.variable]);



useEffect(() => {
if (!state.catchment.id) return;
Expand Down Expand Up @@ -132,8 +178,22 @@ const HydroFabricView = (props) => {
}
/>
</Fragment>

}

{
state.troute.id &&
<Fragment>
<h5>Troute</h5>
<label>Current Variable</label>
<SelectComponent
optionsList={state.troute.variable_list}
onChangeHandler={actions.set_troute_variable}
/>
</Fragment>
}


</SelectContainer>
<Suspense fallback={<LoadingAnimation />}>
<HydroFabricPlotContainer>
Expand Down
60 changes: 58 additions & 2 deletions tethysapp/ngiab/controllers.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,15 @@
import json
import geopandas as gpd
from tethys_sdk.routing import controller
from .utils import get_base_output, getCatchmentsIds, getNexusIDs
from .utils import (
get_base_output,
getCatchmentsIds,
getNexusIDs,
check_troute_id,
get_troute_vars,
get_troute_df,
)

from .app import App


Expand Down Expand Up @@ -95,4 +103,52 @@ def getNexusTimeSeries(request, app_workspace):
for time, streamflow in zip(time_col.tolist(), streamflow_cms_col.tolist())
]

return JsonResponse({"data": data, "nexus_ids": getNexusIDs(app_workspace)})
return JsonResponse(
{
"data": data,
"nexus_ids": getNexusIDs(app_workspace),
}
)


@controller(app_workspace=True)
def getTrouteVariables(request, app_workspace):
troute_id = request.GET.get("troute_id")
clean_troute_id = troute_id.split("-")[1]
df = get_troute_df(app_workspace)
try:
if check_troute_id(df, clean_troute_id):
vars = get_troute_vars(df)
else:
vars = []
except Exception as e:
vars = []

return JsonResponse({"troute_variables": vars})


@controller(app_workspace=True)
def getTrouteTimeSeries(request, app_workspace):
troute_id = request.GET.get("troute_id")
clean_troute_id = troute_id.split("-")[1]
variable_column = request.GET.get("troute_variable")
df = get_troute_df(app_workspace)
df_sliced_by_id = df[df["feature_id"] == int(clean_troute_id)]

df_sliced_by_id["t0"] = pd.to_datetime(df_sliced_by_id["t0"].iloc[0])

# Convert the time_offset column to timedelta
df_sliced_by_id["time"] = pd.to_timedelta(df_sliced_by_id["time"])

df_sliced_by_id["t1"] = df_sliced_by_id["t0"] + df_sliced_by_id["time"]
try:
time_col = df_sliced_by_id["t1"]
var_col = df_sliced_by_id[variable_column]
data = [
{"x": time, "y": val}
for time, val in zip(time_col.tolist(), var_col.tolist())
]
except Exception as e:
data = []

return JsonResponse({"data": data})
31 changes: 31 additions & 0 deletions tethysapp/ngiab/utils.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,36 @@
import os
import json
import pandas as pd
import glob


def _get_base_troute_output(app_workspace):
base_output_path = os.path.join(
app_workspace.path, "ngen-data", "outputs", "troute"
)
return base_output_path


def get_troute_df(app_workspace):
base_output_path = _get_base_troute_output(app_workspace)
troute_output_files = glob.glob(base_output_path + "/*.csv")
df = pd.read_csv(troute_output_files[0])
return df


def check_troute_id(df, id):
if int(id) in df["feature_id"].values:
return True
return False


def get_troute_vars(df):
list_variables = df.columns.tolist()[3:] # remove feature, time and t0

variables = [
{"value": variable, "label": variable.lower()} for variable in list_variables
]
return variables


def get_base_output(app_workspace):
Expand Down

0 comments on commit de95254

Please sign in to comment.