oxigdal_services/csw/
mod.rs1pub mod capabilities;
13pub mod records;
14
15use crate::error::{ServiceError, ServiceResult};
16use axum::{
17 extract::{Query, State},
18 response::Response,
19};
20use serde::Deserialize;
21use std::sync::Arc;
22
23#[derive(Clone)]
25pub struct CswState {
26 pub service_info: Arc<ServiceInfo>,
28 pub records: Arc<dashmap::DashMap<String, MetadataRecord>>,
30}
31
32#[derive(Debug, Clone)]
34pub struct ServiceInfo {
35 pub title: String,
37 pub abstract_text: Option<String>,
39 pub provider: String,
41 pub service_url: String,
43 pub versions: Vec<String>,
45}
46
47#[derive(Debug, Clone)]
49pub struct MetadataRecord {
50 pub identifier: String,
52 pub title: String,
54 pub abstract_text: Option<String>,
56 pub keywords: Vec<String>,
58 pub bbox: Option<(f64, f64, f64, f64)>,
60}
61
62#[derive(Debug, Deserialize)]
64#[serde(rename_all = "UPPERCASE")]
65pub struct CswRequest {
66 pub service: Option<String>,
68 pub version: Option<String>,
70 pub request: String,
72 #[serde(flatten)]
74 pub params: serde_json::Value,
75}
76
77impl CswState {
78 pub fn new(service_info: ServiceInfo) -> Self {
80 Self {
81 service_info: Arc::new(service_info),
82 records: Arc::new(dashmap::DashMap::new()),
83 }
84 }
85
86 pub fn add_record(&self, record: MetadataRecord) -> ServiceResult<()> {
88 self.records.insert(record.identifier.clone(), record);
89 Ok(())
90 }
91}
92
93pub async fn handle_csw_request(
95 State(state): State<CswState>,
96 Query(params): Query<CswRequest>,
97) -> Result<Response, ServiceError> {
98 if let Some(ref service) = params.service {
99 if service.to_uppercase() != "CSW" {
100 return Err(ServiceError::InvalidParameter(
101 "SERVICE".to_string(),
102 format!("Expected 'CSW', got '{}'", service),
103 ));
104 }
105 }
106
107 match params.request.to_uppercase().as_str() {
108 "GETCAPABILITIES" => {
109 let version = params.version.as_deref().unwrap_or("2.0.2");
110 capabilities::handle_get_capabilities(&state, version).await
111 }
112 "GETRECORDS" => {
113 let version = params.version.as_deref().unwrap_or("2.0.2");
114 records::handle_get_records(&state, version, ¶ms.params).await
115 }
116 "GETRECORDBYID" => {
117 let version = params.version.as_deref().unwrap_or("2.0.2");
118 records::handle_get_record_by_id(&state, version, ¶ms.params).await
119 }
120 _ => Err(ServiceError::UnsupportedOperation(params.request.clone())),
121 }
122}