feat(kernel): finish phase3 bridge cutover and phase4 tree projection
- add generic mnote-web query transport and bridge routes for workspace/request/trace - route sidebar compat traffic through mnote-web and tighten fixture fallback to dev/test - unify sidebar/page tree/file tree/picker consumers on page_tree projection - sync phase3/phase4 checklist, breakdown docs, and harness progress state
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
use crate::context::RequestContext;
|
||||
use axum::http::StatusCode;
|
||||
use axum::http::{HeaderName, HeaderValue};
|
||||
use axum::response::{IntoResponse, Response};
|
||||
use axum::Json;
|
||||
use serde::Serialize;
|
||||
@@ -20,6 +21,7 @@ pub struct WebError {
|
||||
code: &'static str,
|
||||
message: String,
|
||||
request_context: Option<RequestContext>,
|
||||
headers: Vec<(&'static str, String)>,
|
||||
}
|
||||
|
||||
impl WebError {
|
||||
@@ -29,6 +31,7 @@ impl WebError {
|
||||
code,
|
||||
message: message.into(),
|
||||
request_context: None,
|
||||
headers: Vec::new(),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -36,14 +39,35 @@ impl WebError {
|
||||
Self::new(StatusCode::BAD_REQUEST, "bad_request", message)
|
||||
}
|
||||
|
||||
pub fn bad_request_code(code: &'static str, message: impl Into<String>) -> Self {
|
||||
Self::new(StatusCode::BAD_REQUEST, code, message)
|
||||
}
|
||||
|
||||
pub fn internal(message: impl Into<String>) -> Self {
|
||||
Self::new(StatusCode::INTERNAL_SERVER_ERROR, "internal_error", message)
|
||||
}
|
||||
|
||||
pub fn bad_gateway_code(code: &'static str, message: impl Into<String>) -> Self {
|
||||
Self::new(StatusCode::BAD_GATEWAY, code, message)
|
||||
}
|
||||
|
||||
pub fn service_unavailable_code(code: &'static str, message: impl Into<String>) -> Self {
|
||||
Self::new(StatusCode::SERVICE_UNAVAILABLE, code, message)
|
||||
}
|
||||
|
||||
pub fn gateway_timeout_code(code: &'static str, message: impl Into<String>) -> Self {
|
||||
Self::new(StatusCode::GATEWAY_TIMEOUT, code, message)
|
||||
}
|
||||
|
||||
pub fn with_context(mut self, request_context: &RequestContext) -> Self {
|
||||
self.request_context = Some(request_context.clone());
|
||||
self
|
||||
}
|
||||
|
||||
pub fn with_header(mut self, name: &'static str, value: impl Into<String>) -> Self {
|
||||
self.headers.push((name, value.into()));
|
||||
self
|
||||
}
|
||||
}
|
||||
|
||||
impl IntoResponse for WebError {
|
||||
@@ -61,6 +85,21 @@ impl IntoResponse for WebError {
|
||||
.as_ref()
|
||||
.map(|context| context.trace.trace_id.clone()),
|
||||
};
|
||||
(self.status, Json(body)).into_response()
|
||||
let mut response = (self.status, Json(body)).into_response();
|
||||
if let Ok(name) = HeaderName::from_lowercase(b"x-error-code") {
|
||||
if let Ok(value) = HeaderValue::from_str(self.code) {
|
||||
response.headers_mut().insert(name, value);
|
||||
}
|
||||
}
|
||||
for (name, value) in self.headers {
|
||||
let Ok(header_name) = HeaderName::from_lowercase(name.as_bytes()) else {
|
||||
continue;
|
||||
};
|
||||
let Ok(header_value) = HeaderValue::from_str(&value) else {
|
||||
continue;
|
||||
};
|
||||
response.headers_mut().insert(header_name, header_value);
|
||||
}
|
||||
response
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user