diff --git a/wp_api/src/lib.rs b/wp_api/src/lib.rs index d0f7041a7..cd6dc5196 100644 --- a/wp_api/src/lib.rs +++ b/wp_api/src/lib.rs @@ -1,6 +1,9 @@ #![allow(dead_code, unused_variables)] -use request::{endpoint::ApiEndpoint, RequestMethod, WPNetworkRequest, WPNetworkResponse}; +use request::{ + endpoint::{ApiEndpoint, ApiEndpointUrl}, + RequestMethod, WPNetworkRequest, WPNetworkResponse, +}; use std::collections::HashMap; use url::Url; @@ -23,7 +26,6 @@ const CONTENT_TYPE_JSON: &str = "application/json"; #[derive(Debug, uniffi::Object)] pub struct WPApiHelper { api_endpoint: ApiEndpoint, - site_url: Url, authentication: WPAuthentication, } @@ -45,15 +47,15 @@ impl WPApiHelper { Self { api_endpoint, - site_url: url, authentication, } } + // TODO: Remove this because we want to build all requests within the crate pub fn raw_request(&self, url: String) -> WPNetworkRequest { WPNetworkRequest { method: RequestMethod::GET, - url: Url::parse(url.as_str()).unwrap().into(), + url: ApiEndpointUrl::new(Url::parse(url.as_str()).unwrap()).into(), header_map: self.header_map(), body: None, } diff --git a/wp_api/src/request.rs b/wp_api/src/request.rs index e0a34d450..9132e940d 100644 --- a/wp_api/src/request.rs +++ b/wp_api/src/request.rs @@ -5,13 +5,15 @@ use url::Url; use crate::WPApiError; +use self::endpoint::WpEndpointUrl; + pub mod endpoint; // Has custom `Debug` trait implementation #[derive(uniffi::Record)] pub struct WPNetworkRequest { pub method: RequestMethod, - pub url: String, + pub url: WpEndpointUrl, // TODO: We probably want to implement a specific type for these headers instead of using a // regular HashMap. // @@ -33,7 +35,7 @@ impl Debug for WPNetworkRequest { indoc::indoc! {" WPNetworkRequest {{ method: '{:?}', - url: '{}', + url: '{:?}', header_map: '{:?}', body: '{:?}' }} @@ -137,7 +139,7 @@ impl Debug for WPNetworkResponse { } } -#[derive(Debug, uniffi::Enum)] +#[derive(Debug, Clone, uniffi::Enum)] pub enum RequestMethod { GET, POST, diff --git a/wp_api/src/request/endpoint.rs b/wp_api/src/request/endpoint.rs index b9b71b16d..c670b0f06 100644 --- a/wp_api/src/request/endpoint.rs +++ b/wp_api/src/request/endpoint.rs @@ -10,8 +10,43 @@ mod users_endpoint; const WP_JSON_PATH_SEGMENTS: [&str; 3] = ["wp-json", "wp", "v2"]; +uniffi::custom_newtype!(WpEndpointUrl, String); +#[derive(Debug)] +pub struct WpEndpointUrl(pub String); + +#[derive(Debug)] +pub(crate) struct ApiEndpointUrl { + url: Url, +} + +impl ApiEndpointUrl { + pub fn new(url: Url) -> Self { + Self { url } + } + + fn url(&self) -> &Url { + &self.url + } + + pub fn as_str(&self) -> &str { + self.url.as_str() + } +} + +impl From for ApiEndpointUrl { + fn from(url: Url) -> Self { + Self::new(url) + } +} + +impl From for WpEndpointUrl { + fn from(url: ApiEndpointUrl) -> Self { + Self(url.as_str().to_string()) + } +} + #[derive(Debug, Clone)] -pub struct ApiBaseUrl { +pub(crate) struct ApiBaseUrl { url: Url, } @@ -49,7 +84,7 @@ impl ApiBaseUrl { } #[derive(Debug)] -pub struct ApiEndpoint { +pub(crate) struct ApiEndpoint { pub base_url: ApiBaseUrl, pub users: UsersEndpoint, pub plugins: PluginsEndpoint, @@ -167,7 +202,7 @@ mod tests { ApiBaseUrl::new("https://example.com").unwrap() } - pub fn validate_endpoint(endpoint_url: Url, path: &str) { + pub fn validate_endpoint(endpoint_url: ApiEndpointUrl, path: &str) { assert_eq!( endpoint_url.as_str(), format!("{}{}", fixture_api_base_url().as_str(), path) diff --git a/wp_api/src/request/endpoint/plugins_endpoint.rs b/wp_api/src/request/endpoint/plugins_endpoint.rs index a49947178..20e6f51ab 100644 --- a/wp_api/src/request/endpoint/plugins_endpoint.rs +++ b/wp_api/src/request/endpoint/plugins_endpoint.rs @@ -2,10 +2,10 @@ use url::Url; use crate::{plugins::PluginListParams, PluginSlug, SparsePluginField, WPContext}; -use super::{ApiBaseUrl, UrlExtension}; +use super::{ApiBaseUrl, ApiEndpointUrl, UrlExtension}; #[derive(Debug)] -pub struct PluginsEndpoint { +pub(crate) struct PluginsEndpoint { api_base_url: ApiBaseUrl, } @@ -14,22 +14,22 @@ impl PluginsEndpoint { Self { api_base_url } } - pub fn create(&self) -> Url { - self.plugins_base_url() + pub fn create(&self) -> ApiEndpointUrl { + self.plugins_base_url().into() } - pub fn delete(&self, plugin: &PluginSlug) -> Url { - self.plugins_url_with_slug(plugin) + pub fn delete(&self, plugin: &PluginSlug) -> ApiEndpointUrl { + self.plugins_url_with_slug(plugin).into() } - pub fn list(&self, context: WPContext, params: Option<&PluginListParams>) -> Url { + pub fn list(&self, context: WPContext, params: Option<&PluginListParams>) -> ApiEndpointUrl { let mut url = self.plugins_base_url(); url.query_pairs_mut() .append_pair("context", context.as_str()); if let Some(params) = params { url.query_pairs_mut().extend_pairs(params.query_pairs()); } - url + url.into() } pub fn filter_list( @@ -37,15 +37,18 @@ impl PluginsEndpoint { context: WPContext, params: Option<&PluginListParams>, fields: &[SparsePluginField], - ) -> Url { - self.list(context, params).append_filter_fields(fields) + ) -> ApiEndpointUrl { + self.list(context, params) + .url + .append_filter_fields(fields) + .into() } - pub fn retrieve(&self, context: WPContext, plugin: &PluginSlug) -> Url { + pub fn retrieve(&self, context: WPContext, plugin: &PluginSlug) -> ApiEndpointUrl { let mut url = self.plugins_url_with_slug(plugin); url.query_pairs_mut() .append_pair("context", context.as_str()); - url + url.into() } pub fn filter_retrieve( @@ -53,12 +56,15 @@ impl PluginsEndpoint { context: WPContext, plugin: &PluginSlug, fields: &[SparsePluginField], - ) -> Url { - self.retrieve(context, plugin).append_filter_fields(fields) + ) -> ApiEndpointUrl { + self.retrieve(context, plugin) + .url + .append_filter_fields(fields) + .into() } - pub fn update(&self, plugin: &PluginSlug) -> Url { - self.plugins_url_with_slug(plugin) + pub fn update(&self, plugin: &PluginSlug) -> ApiEndpointUrl { + self.plugins_url_with_slug(plugin).into() } fn plugins_base_url(&self) -> Url { diff --git a/wp_api/src/request/endpoint/users_endpoint.rs b/wp_api/src/request/endpoint/users_endpoint.rs index 01b527dc0..e6ed0a7d3 100644 --- a/wp_api/src/request/endpoint/users_endpoint.rs +++ b/wp_api/src/request/endpoint/users_endpoint.rs @@ -1,11 +1,9 @@ -use url::Url; - use crate::{SparseUserField, UserDeleteParams, UserId, UserListParams, WPContext}; -use super::{ApiBaseUrl, UrlExtension}; +use super::{ApiBaseUrl, ApiEndpointUrl, UrlExtension}; #[derive(Debug)] -pub struct UsersEndpoint { +pub(crate) struct UsersEndpoint { api_base_url: ApiBaseUrl, } @@ -14,32 +12,32 @@ impl UsersEndpoint { Self { api_base_url } } - pub fn create(&self) -> Url { - self.api_base_url.by_appending("users") + pub fn create(&self) -> ApiEndpointUrl { + self.api_base_url.by_appending("users").into() } - pub fn delete(&self, user_id: UserId, params: &UserDeleteParams) -> Url { + pub fn delete(&self, user_id: UserId, params: &UserDeleteParams) -> ApiEndpointUrl { let mut url = self .api_base_url .by_extending(["users", &user_id.to_string()]); url.query_pairs_mut().extend_pairs(params.query_pairs()); - url + url.into() } - pub fn delete_me(&self, params: &UserDeleteParams) -> Url { + pub fn delete_me(&self, params: &UserDeleteParams) -> ApiEndpointUrl { let mut url = self.api_base_url.by_extending(["users", "me"]); url.query_pairs_mut().extend_pairs(params.query_pairs()); - url + url.into() } - pub fn list(&self, context: WPContext, params: Option<&UserListParams>) -> Url { + pub fn list(&self, context: WPContext, params: Option<&UserListParams>) -> ApiEndpointUrl { let mut url = self.api_base_url.by_appending("users"); url.query_pairs_mut() .append_pair("context", context.as_str()); if let Some(params) = params { url.query_pairs_mut().extend_pairs(params.query_pairs()); } - url + url.into() } pub fn filter_list( @@ -47,17 +45,20 @@ impl UsersEndpoint { context: WPContext, params: Option<&UserListParams>, fields: &[SparseUserField], - ) -> Url { - self.list(context, params).append_filter_fields(fields) + ) -> ApiEndpointUrl { + self.list(context, params) + .url + .append_filter_fields(fields) + .into() } - pub fn retrieve(&self, user_id: UserId, context: WPContext) -> Url { + pub fn retrieve(&self, user_id: UserId, context: WPContext) -> ApiEndpointUrl { let mut url = self .api_base_url .by_extending(["users", &user_id.to_string()]); url.query_pairs_mut() .append_pair("context", context.as_str()); - url + url.into() } pub fn filter_retrieve( @@ -65,28 +66,39 @@ impl UsersEndpoint { user_id: UserId, context: WPContext, fields: &[SparseUserField], - ) -> Url { - self.retrieve(user_id, context).append_filter_fields(fields) + ) -> ApiEndpointUrl { + self.retrieve(user_id, context) + .url + .append_filter_fields(fields) + .into() } - pub fn retrieve_me(&self, context: WPContext) -> Url { + pub fn retrieve_me(&self, context: WPContext) -> ApiEndpointUrl { let mut url = self.api_base_url.by_extending(["users", "me"]); url.query_pairs_mut() .append_pair("context", context.as_str()); - url + url.into() } - pub fn filter_retrieve_me(&self, context: WPContext, fields: &[SparseUserField]) -> Url { - self.retrieve_me(context).append_filter_fields(fields) + pub fn filter_retrieve_me( + &self, + context: WPContext, + fields: &[SparseUserField], + ) -> ApiEndpointUrl { + self.retrieve_me(context) + .url + .append_filter_fields(fields) + .into() } - pub fn update(&self, user_id: UserId) -> Url { + pub fn update(&self, user_id: UserId) -> ApiEndpointUrl { self.api_base_url .by_extending(["users", &user_id.to_string()]) + .into() } - pub fn update_me(&self) -> Url { - self.api_base_url.by_extending(["users", "me"]) + pub fn update_me(&self) -> ApiEndpointUrl { + self.api_base_url.by_extending(["users", "me"]).into() } } diff --git a/wp_api/tests/integration_test_common.rs b/wp_api/tests/integration_test_common.rs index 68738a98d..f25a34fbb 100644 --- a/wp_api/tests/integration_test_common.rs +++ b/wp_api/tests/integration_test_common.rs @@ -185,7 +185,7 @@ impl AsyncWPNetworking { let mut request = self .client - .request(Self::request_method(wp_request.method), wp_request.url) + .request(Self::request_method(wp_request.method), wp_request.url.0) .headers(request_headers); if let Some(body) = wp_request.body { request = request.body(body); diff --git a/wp_api/tests/test_users_err.rs b/wp_api/tests/test_users_err.rs index b063ea381..dbec0a757 100644 --- a/wp_api/tests/test_users_err.rs +++ b/wp_api/tests/test_users_err.rs @@ -1,5 +1,6 @@ use integration_test_common::SECOND_USER_EMAIL; use wp_api::{ + request::endpoint::WpEndpointUrl, users::{ UserCreateParams, UserDeleteParams, UserId, UserListParams, UserUpdateParams, WPApiParamUsersOrderBy, WPApiParamUsersWho, @@ -317,7 +318,7 @@ async fn update_user_err_user_invalid_slug() { #[tokio::test] async fn create_user_err_user_exists() { let mut request = api().create_user_request(&valid_user_create_params()); - request.url.push_str("?id=1"); + request.url.0.push_str("?id=1"); request .execute() .await @@ -334,7 +335,7 @@ async fn delete_user_err_trash_not_supported() { reassign: SECOND_USER_ID, }, ); - request.url = request.url.replace("&force=true", ""); + request.url = WpEndpointUrl(request.url.0.replace("&force=true", "")); request .execute() .await