- make realtime replacement and analysis result writes transactional\n- consolidate SCADA repositories and remove process-global project state\n- validate SCADA batches and use indexed GIS-backed business queries\n\nBREAKING CHANGE: remove the public analysis result writer and the pipeline-health network_name query parameter.
286 lines
7.0 KiB
Python
286 lines
7.0 KiB
Python
"""Application-facing water-network service boundary.
|
|
|
|
The native WNDB package is organized by responsibility. This module only
|
|
combines operations that need more than one native module and re-exports the
|
|
small set of operations used by HTTP and algorithm services.
|
|
"""
|
|
|
|
from typing import Any
|
|
|
|
import app.infra.epanet as epanet
|
|
from app.algorithms.water_demand import (
|
|
calculate_demand_to_network,
|
|
calculate_demand_to_nodes,
|
|
calculate_demand_to_region,
|
|
)
|
|
from app.infra.db.postgresql.scada import (
|
|
get_all_scada_info,
|
|
get_scada_info,
|
|
get_scada_info_schema,
|
|
)
|
|
from app.native.wndb.commands.api import (
|
|
delete_curve_cascade as delete_curve,
|
|
delete_junction_cascade as delete_junction,
|
|
delete_pattern_cascade as delete_pattern,
|
|
delete_pipe_cascade as delete_pipe,
|
|
delete_pump_cascade as delete_pump,
|
|
delete_reservoir_cascade as delete_reservoir,
|
|
delete_tank_cascade as delete_tank,
|
|
delete_valve_cascade as delete_valve,
|
|
set_option_ex as set_option,
|
|
set_option_v3_ex as set_option_v3,
|
|
)
|
|
from app.native.wndb.core.database import ChangeSet, read_all
|
|
from app.native.wndb.core.projects import (
|
|
copy_project,
|
|
create_project,
|
|
delete_project,
|
|
have_project,
|
|
list_project,
|
|
)
|
|
from app.native.wndb.gis.backdrop import (
|
|
get_backdrop,
|
|
get_backdrop_schema,
|
|
set_backdrop,
|
|
)
|
|
from app.native.wndb.gis.coordinates import get_node_coord
|
|
from app.native.wndb.gis.labels import (
|
|
add_label,
|
|
delete_label,
|
|
get_label,
|
|
get_label_schema,
|
|
set_label,
|
|
)
|
|
from app.native.wndb.gis.network_views import (
|
|
get_major_node_coords,
|
|
get_major_pipe_nodes,
|
|
get_network_link_nodes,
|
|
get_network_node_coords,
|
|
)
|
|
from app.native.wndb.gis.region_geometry import get_nodes_in_region
|
|
from app.native.wndb.gis.regions import (
|
|
add_region,
|
|
delete_region,
|
|
get_region,
|
|
get_region_schema,
|
|
set_region,
|
|
)
|
|
from app.native.wndb.gis.vertices import (
|
|
add_vertex,
|
|
delete_vertex,
|
|
get_all_vertex_links,
|
|
get_all_vertices,
|
|
get_vertex,
|
|
get_vertex_schema,
|
|
set_vertex,
|
|
)
|
|
from app.native.wndb.inp.exporter import dump_inp, export_inp
|
|
from app.native.wndb.inp.importer import convert_inp_v3_to_v2, read_inp
|
|
from app.native.wndb.model.controls import (
|
|
get_control,
|
|
get_control_schema,
|
|
set_control,
|
|
)
|
|
from app.native.wndb.model.curves import (
|
|
add_curve,
|
|
get_curve,
|
|
get_curve_schema,
|
|
set_curve,
|
|
)
|
|
from app.native.wndb.model.demands import get_demand, get_demand_schema, set_demand
|
|
from app.native.wndb.model.elements import (
|
|
get_curves,
|
|
get_element_type,
|
|
get_element_type_value,
|
|
get_link_type,
|
|
get_links,
|
|
get_node_links,
|
|
get_node_type,
|
|
get_nodes,
|
|
get_patterns,
|
|
get_regions,
|
|
is_curve,
|
|
is_junction,
|
|
is_link,
|
|
is_node,
|
|
is_pattern,
|
|
is_pipe,
|
|
is_pump,
|
|
is_reservoir,
|
|
is_tank,
|
|
is_valve,
|
|
)
|
|
from app.native.wndb.model.emitters import (
|
|
get_emitter,
|
|
get_emitter_schema,
|
|
set_emitter,
|
|
)
|
|
from app.native.wndb.model.energy import (
|
|
get_energy,
|
|
get_energy_schema,
|
|
get_pump_energy,
|
|
get_pump_energy_schema,
|
|
set_energy,
|
|
set_pump_energy,
|
|
)
|
|
from app.native.wndb.model.junctions import (
|
|
add_junction,
|
|
get_all_junctions,
|
|
get_junction,
|
|
get_junction_schema,
|
|
set_junction,
|
|
)
|
|
from app.native.wndb.model.mixing import (
|
|
add_mixing,
|
|
delete_mixing,
|
|
get_mixing,
|
|
get_mixing_schema,
|
|
set_mixing,
|
|
)
|
|
from app.native.wndb.model.options import (
|
|
OPTION_DEMAND_MODEL_PDA,
|
|
OPTION_QUALITY_CHEMICAL,
|
|
get_option,
|
|
get_option_v3,
|
|
get_option_v3_schema,
|
|
)
|
|
from app.native.wndb.model.patterns import (
|
|
add_pattern,
|
|
get_pattern,
|
|
get_pattern_schema,
|
|
set_pattern,
|
|
)
|
|
from app.native.wndb.model.pipes import (
|
|
PIPE_STATUS_OPEN,
|
|
add_pipe,
|
|
get_all_pipes,
|
|
get_pipe,
|
|
get_pipe_schema,
|
|
set_pipe,
|
|
)
|
|
from app.native.wndb.model.pumps import (
|
|
add_pump,
|
|
get_all_pumps,
|
|
get_pump,
|
|
get_pump_schema,
|
|
set_pump,
|
|
)
|
|
from app.native.wndb.model.quality import (
|
|
get_quality,
|
|
get_quality_schema,
|
|
set_quality,
|
|
)
|
|
from app.native.wndb.model.reactions import (
|
|
get_pipe_reaction,
|
|
get_pipe_reaction_schema,
|
|
get_reaction,
|
|
get_reaction_schema,
|
|
get_tank_reaction,
|
|
get_tank_reaction_schema,
|
|
set_pipe_reaction,
|
|
set_reaction,
|
|
set_tank_reaction,
|
|
)
|
|
from app.native.wndb.model.reservoirs import (
|
|
add_reservoir,
|
|
get_all_reservoirs,
|
|
get_reservoir,
|
|
get_reservoir_schema,
|
|
set_reservoir,
|
|
)
|
|
from app.native.wndb.model.rules import get_rule, get_rule_schema, set_rule
|
|
from app.native.wndb.model.sources import (
|
|
SOURCE_TYPE_SETPOINT,
|
|
add_source,
|
|
delete_source,
|
|
get_source,
|
|
get_source_schema,
|
|
set_source,
|
|
)
|
|
from app.native.wndb.model.status import (
|
|
get_status,
|
|
get_status_schema,
|
|
set_status,
|
|
)
|
|
from app.native.wndb.model.tags import get_tag, get_tag_schema, get_tags, set_tag
|
|
from app.native.wndb.model.tanks import (
|
|
add_tank,
|
|
get_all_tanks,
|
|
get_tank,
|
|
get_tank_schema,
|
|
set_tank,
|
|
)
|
|
from app.native.wndb.model.times import get_time, get_time_schema, set_time
|
|
from app.native.wndb.model.title import get_title, get_title_schema, set_title
|
|
from app.native.wndb.model.valves import (
|
|
VALVES_TYPE_PRV,
|
|
add_valve,
|
|
get_all_valves,
|
|
get_valve,
|
|
get_valve_schema,
|
|
set_valve,
|
|
)
|
|
|
|
|
|
def run_project_return_dict(name: str) -> dict[str, Any]:
|
|
return epanet.run_project_return_dict(name, True)
|
|
|
|
|
|
def run_project(name: str) -> str:
|
|
return epanet.run_project(name)
|
|
|
|
|
|
def run_inp(name: str) -> str:
|
|
return epanet.run_inp(name)
|
|
|
|
|
|
def dump_output(path: str) -> str:
|
|
return epanet.dump_output(path)
|
|
|
|
|
|
def get_node_properties(name: str, node_id: str) -> dict[str, Any]:
|
|
if is_junction(name, node_id):
|
|
return get_junction(name, node_id)
|
|
if is_reservoir(name, node_id):
|
|
return get_reservoir(name, node_id)
|
|
if is_tank(name, node_id):
|
|
return get_tank(name, node_id)
|
|
return {}
|
|
|
|
|
|
def get_link_properties(name: str, link_id: str) -> dict[str, Any]:
|
|
if is_pipe(name, link_id):
|
|
return get_pipe(name, link_id)
|
|
if is_pump(name, link_id):
|
|
return get_pump(name, link_id)
|
|
if is_valve(name, link_id):
|
|
return get_valve(name, link_id)
|
|
return {}
|
|
|
|
|
|
def get_element_properties_with_type(
|
|
name: str, element_type: str, element_id: str
|
|
) -> dict[str, Any]:
|
|
if element_type == "node":
|
|
return get_node_properties(name, element_id)
|
|
if element_type == "link":
|
|
return get_link_properties(name, element_id)
|
|
if element_type == "scada":
|
|
return get_scada_info(name, element_id)
|
|
return {}
|
|
|
|
|
|
def get_element_properties(name: str, element_id: str) -> dict[str, Any]:
|
|
if is_node(name, element_id):
|
|
return get_node_properties(name, element_id)
|
|
if is_link(name, element_id):
|
|
return get_link_properties(name, element_id)
|
|
return get_scada_info(name, element_id)
|
|
|
|
|
|
def get_network_in_extent(
|
|
name: str, x1: float, y1: float, x2: float, y2: float
|
|
) -> dict[str, Any]:
|
|
# Kept as the existing API placeholder; spatial filtering belongs in GIS.
|
|
return {}
|