diff --git a/crates/lang_handler/Cargo.toml b/crates/lang_handler/Cargo.toml index ce15b3b..0e45f7c 100644 --- a/crates/lang_handler/Cargo.toml +++ b/crates/lang_handler/Cargo.toml @@ -8,15 +8,7 @@ name = "lang_handler" crate-type = ["cdylib", "rlib"] path = "src/lib.rs" -[features] -default = [] -napi = ["dep:napi", "dep:napi-build"] - -[build-dependencies] -napi-build = { version = "2.0.1", optional = true } - [dependencies] bytes = "1.10.1" -napi = { version = "2.16.17", optional = true } regex = "1.11.1" url = "2.5.4" diff --git a/crates/lang_handler/build.rs b/crates/lang_handler/build.rs deleted file mode 100644 index 4ecbc6c..0000000 --- a/crates/lang_handler/build.rs +++ /dev/null @@ -1,7 +0,0 @@ -#[cfg(feature = "napi")] -extern crate napi_build; - -fn main() { - #[cfg(feature = "napi")] - napi_build::setup(); -} diff --git a/crates/lang_handler/src/headers.rs b/crates/lang_handler/src/headers.rs index 3687193..c16ed78 100644 --- a/crates/lang_handler/src/headers.rs +++ b/crates/lang_handler/src/headers.rs @@ -38,47 +38,6 @@ impl From> for Header { } } -#[cfg(feature = "napi")] -mod napi_header { - use super::*; - - use napi::bindgen_prelude::*; - use napi::sys; - - impl FromNapiValue for Header { - unsafe fn from_napi_value(env: sys::napi_env, value: sys::napi_value) -> Result { - let mut header_type = sys::ValueType::napi_undefined; - unsafe { check_status!(sys::napi_typeof(env, value, &mut header_type)) }?; - - let header_type: ValueType = header_type.into(); - - match header_type { - ValueType::String => { - let s = String::from_napi_value(env, value)?; - Ok(Header::Single(s)) - } - ValueType::Object => { - let obj = Vec::::from_napi_value(env, value)?; - Ok(Header::Multiple(obj)) - } - _ => Err(napi::Error::new( - Status::InvalidArg, - "Expected a string or an object for Header", - )), - } - } - } - - impl ToNapiValue for Header { - unsafe fn to_napi_value(env: sys::napi_env, value: Self) -> Result { - match value { - Header::Single(value) => String::to_napi_value(env, value), - Header::Multiple(values) => Vec::::to_napi_value(env, values), - } - } - } -} - /// A multi-map of HTTP headers. /// /// # Examples @@ -371,87 +330,3 @@ impl Default for Headers { Self::new() } } - -#[cfg(feature = "napi")] -mod napi_headers { - use super::*; - - use std::ptr; - - use napi::bindgen_prelude::*; - use napi::sys; - - impl FromNapiValue for Headers { - unsafe fn from_napi_value(env: sys::napi_env, value: sys::napi_value) -> Result { - let mut header_type = sys::ValueType::napi_undefined; - unsafe { check_status!(sys::napi_typeof(env, value, &mut header_type)) }?; - - let header_type: ValueType = header_type.into(); - - if header_type != ValueType::Object { - return Err(napi::Error::new( - napi::Status::InvalidArg, - "Expected an object for Headers", - )); - } - - let mut headers = Headers::new(); - unsafe { - let mut keys: sys::napi_value = ptr::null_mut(); - check_status!( - sys::napi_get_property_names(env, value, &mut keys), - "Failed to get Headers property names" - )?; - - let mut key_count = 0; - check_status!(sys::napi_get_array_length(env, keys, &mut key_count))?; - - for i in 0..key_count { - let mut key: sys::napi_value = ptr::null_mut(); - check_status!( - sys::napi_get_element(env, keys, i, &mut key), - "Failed to get header name" - )?; - let key_str = String::from_napi_value(env, key)?; - let key_cstr = std::ffi::CString::new(key_str.clone())?; - - let mut header_value: sys::napi_value = ptr::null_mut(); - check_status!( - sys::napi_get_named_property(env, value, key_cstr.as_ptr(), &mut header_value), - "Failed to get header value" - )?; - - if let Ok(header) = Header::from_napi_value(env, header_value) { - headers.set(key_str, header); - } - } - } - - Ok(headers) - } - } - - impl ToNapiValue for Headers { - unsafe fn to_napi_value(env: sys::napi_env, value: Self) -> Result { - let mut result: sys::napi_value = ptr::null_mut(); - unsafe { - check_status!( - sys::napi_create_object(env, &mut result), - "Failed to create Headers object" - )?; - - for (key, header) in value.iter() { - let key_cstr = std::ffi::CString::new(key.to_string())?; - let value_napi_value = Header::to_napi_value(env, header.to_owned())?; - - check_status!( - sys::napi_set_named_property(env, result, key_cstr.as_ptr(), value_napi_value), - "Failed to set header property" - )?; - } - } - - Ok(result) - } - } -} diff --git a/crates/php/Cargo.toml b/crates/php/Cargo.toml index 79f3fed..93320e8 100644 --- a/crates/php/Cargo.toml +++ b/crates/php/Cargo.toml @@ -16,7 +16,7 @@ bytes = "1.10.1" hostname = "0.4.1" ext-php-rs = { git = "https://github.com/platformatic/ext-php-rs.git" } # ext-php-rs = { path = "../../../ext-php-rs" } -lang_handler = { path = "../lang_handler", features = ["napi"] } +lang_handler = { path = "../lang_handler" } libc = "0.2.171" once_cell = "1.21.0" diff --git a/crates/php_node/src/headers.rs b/crates/php_node/src/headers.rs index 85f1598..1641005 100644 --- a/crates/php_node/src/headers.rs +++ b/crates/php_node/src/headers.rs @@ -1,4 +1,4 @@ -use std::ptr; +use std::{collections::HashMap, ptr}; use napi::bindgen_prelude::*; use napi::Result; @@ -73,22 +73,35 @@ impl Into for PhpHeaders { } } -impl From for PhpHeaders { - fn from(headers: Headers) -> Self { +pub type PhpHeadersMap = HashMap>>; +pub type PhpHeadersInput = Either, PhpHeadersMap>; + +impl From for PhpHeaders { + fn from(map: PhpHeadersMap) -> Self { + let mut headers = Headers::new(); + + // Convert the map to a Headers instance. + for (k, v) in map.into_iter() { + match v { + Either::A(value) => headers.set(k, value), + Either::B(values) => { + for value in values { + headers.add(k.clone(), value); + } + } + } + } + PhpHeaders { headers } } } -// This replaces the FromNapiValue impl inherited from ClassInstance to allow -// unwrapping a PhpHeaders instance directly to Headers. This allows both -// object and instance form of Headers to be used interchangeably. -impl FromNapiValue for PhpHeaders { - unsafe fn from_napi_value(env: sys::napi_env, napi_val: sys::napi_value) -> Result { - let headers = ClassInstance::::from_napi_value(env, napi_val) - .map(|php_headers| php_headers.headers.clone()) - .or_else(|_| Headers::from_napi_value(env, napi_val))?; - - Ok(PhpHeaders { headers }) +impl From for PhpHeaders { + fn from(input: PhpHeadersInput) -> Self { + match input { + Either::A(instance) => instance.clone(), + Either::B(map) => map.into(), + } } } @@ -102,9 +115,13 @@ impl PhpHeaders { /// const headers = new Headers(); /// ``` #[napi(constructor)] - pub fn constructor(headers: Option) -> Self { - PhpHeaders { - headers: headers.unwrap_or_default(), + pub fn constructor(input: Option) -> Self { + match input { + None => PhpHeaders { + headers: Headers::new(), + }, + Some(Either::A(input)) => input.clone(), + Some(Either::B(input)) => input.into(), } } diff --git a/crates/php_node/src/lib.rs b/crates/php_node/src/lib.rs index 4d583a5..7ec3d89 100644 --- a/crates/php_node/src/lib.rs +++ b/crates/php_node/src/lib.rs @@ -7,7 +7,7 @@ mod response; mod rewriter; mod runtime; -pub use headers::PhpHeaders; +pub use headers::{PhpHeaders, PhpHeadersInput}; pub use request::PhpRequest; pub use response::PhpResponse; pub use rewriter::PhpRewriter; diff --git a/crates/php_node/src/request.rs b/crates/php_node/src/request.rs index 62bc25d..86d423a 100644 --- a/crates/php_node/src/request.rs +++ b/crates/php_node/src/request.rs @@ -3,7 +3,7 @@ use napi::Result; use php::{Request, RequestBuilder}; -use crate::PhpHeaders; +use crate::{PhpHeaders, PhpHeadersInput}; #[napi(object)] #[derive(Default)] @@ -31,7 +31,7 @@ pub struct PhpRequestOptions { /// The URL for the request. pub url: String, /// The headers for the request. - pub headers: Option, + pub headers: Option, /// The body for the request. pub body: Option, /// The socket information for the request. @@ -110,7 +110,7 @@ impl PhpRequest { } if let Some(headers) = options.headers { - builder = builder.headers(headers); + builder = builder.headers(Into::::into(headers)); } if let Some(body) = options.body { diff --git a/crates/php_node/src/response.rs b/crates/php_node/src/response.rs index fecbb72..7911a19 100644 --- a/crates/php_node/src/response.rs +++ b/crates/php_node/src/response.rs @@ -3,7 +3,7 @@ use napi::Result; use php::Response; -use crate::PhpHeaders; +use crate::{PhpHeaders, PhpHeadersInput}; /// Options for creating a new PHP response. #[napi(object)] @@ -12,7 +12,7 @@ pub struct PhpResponseOptions { /// The HTTP status code for the response. pub status: Option, /// The headers for the response. - pub headers: Option, + pub headers: Option, /// The body for the response. pub body: Option, /// The log for the response. @@ -59,7 +59,7 @@ impl PhpResponse { } if let Some(headers) = options.headers { - builder = builder.headers(headers); + builder = builder.headers(Into::::into(headers)); } if let Some(body) = options.body {