Skip to content

Commit d92915f

Browse files
authored
Create /templates endpoint (#723)
* Create `/templates` endpoint * Remove `status` & `template_type` parameters from `TemplateCreateParams`
1 parent 4b8b69a commit d92915f

File tree

5 files changed

+159
-11
lines changed

5 files changed

+159
-11
lines changed

wp_api/src/api_error.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -278,6 +278,8 @@ pub enum WpErrorCode {
278278
TaxonomyInvalid,
279279
#[serde(rename = "rest_template_already_trashed")]
280280
TemplateAlreadyTrashed,
281+
#[serde(rename = "rest_template_insert_error")]
282+
TemplateInsertError,
281283
#[serde(rename = "rest_template_not_found")]
282284
TemplateNotFound,
283285
#[serde(rename = "rest_term_invalid")]

wp_api/src/request/endpoint/templates_endpoint.rs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@ enum TemplatesRequest {
1212
List,
1313
#[contextual_get(url = "/templates/<template_id>", output = crate::templates::SparseTemplate, filter_by = crate::templates::SparseTemplateField)]
1414
Retrieve,
15+
#[post(url = "/templates", params = &crate::templates::TemplateCreateParams, output = crate::templates::TemplateWithEditContext)]
16+
Create,
1517
#[delete(url = "/templates/<template_id>", output = crate::templates::TemplateDeleteResponse)]
1618
Delete,
1719
#[delete(url = "/templates/<template_id>", output = crate::templates::TemplateWithEditContext)]
@@ -80,6 +82,11 @@ mod tests {
8082
use rstest::*;
8183
use std::sync::Arc;
8284

85+
#[rstest]
86+
fn create_template(endpoint: TemplatesRequestEndpoint) {
87+
validate_wp_v2_endpoint(endpoint.create(), "/templates");
88+
}
89+
8390
#[rstest]
8491
#[case(TemplateListParams::default(), "")]
8592
#[case(generate!(TemplateListParams, (post_id, Some(PostId(2)))), "wp_id=2")]

wp_api/src/templates.rs

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -232,3 +232,46 @@ pub struct TemplateUpdateParams {
232232
// don't seem to take place when they are included in the request. So, we decided not to
233233
// include them until we figure out under which conditions they'll be allowed to update.
234234
}
235+
236+
#[derive(Debug, Serialize, uniffi::Record)]
237+
pub struct TemplateCreateParams {
238+
// Unique slug identifying the template.
239+
pub slug: String,
240+
// Theme identifier for the template.
241+
#[uniffi(default = None)]
242+
#[serde(skip_serializing_if = "Option::is_none")]
243+
pub theme: Option<String>,
244+
// Content of template.
245+
#[uniffi(default = None)]
246+
#[serde(skip_serializing_if = "Option::is_none")]
247+
pub content: Option<String>,
248+
// Title of template.
249+
#[uniffi(default = None)]
250+
#[serde(skip_serializing_if = "Option::is_none")]
251+
pub title: Option<String>,
252+
// Description of template.
253+
#[uniffi(default = None)]
254+
#[serde(skip_serializing_if = "Option::is_none")]
255+
pub description: Option<String>,
256+
// The ID for the author of the template.
257+
#[uniffi(default = None)]
258+
#[serde(skip_serializing_if = "Option::is_none")]
259+
pub author: Option<UserId>,
260+
// https://developer.wordpress.org/rest-api/reference/wp_templates/#create-a-template
261+
// The documentation includes `status` & `type` parameters, but the created templates don't
262+
// seem to take these into account. So, we decided not to include them until we figure out
263+
// under which conditions they'll be taken into account.
264+
}
265+
266+
impl TemplateCreateParams {
267+
pub fn new(slug: String) -> Self {
268+
Self {
269+
slug,
270+
theme: None,
271+
content: None,
272+
title: None,
273+
description: None,
274+
author: None,
275+
}
276+
}
277+
}

wp_api_integration_tests/tests/test_templates_err.rs

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,17 @@
1-
use wp_api::templates::{TemplateId, TemplateUpdateParams};
1+
use wp_api::templates::{TemplateCreateParams, TemplateId, TemplateUpdateParams};
22
use wp_api_integration_tests::prelude::*;
33

4+
#[tokio::test]
5+
#[parallel]
6+
async fn create_template_err_empty_content() {
7+
// Creating a template requires `title` or `content`
8+
api_client()
9+
.templates()
10+
.create(&TemplateCreateParams::new("foo".to_string()))
11+
.await
12+
.assert_wp_error(WpErrorCode::EmptyContent)
13+
}
14+
415
#[tokio::test]
516
#[parallel]
617
async fn delete_template_err_invalid_template() {

wp_api_integration_tests/tests/test_templates_mut.rs

Lines changed: 95 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,75 @@
11
use macro_helper::generate_update_test;
22
use wp_api::templates::{
33
SparseTemplateContent, SparseTemplateContentWrapper, SparseTemplateTitle,
4-
SparseTemplateTitleWrapper, TemplateId, TemplateStatus, TemplateUpdateParams,
5-
TemplateWithEditContext,
4+
SparseTemplateTitleWrapper, TemplateCreateParams, TemplateId, TemplateStatus,
5+
TemplateUpdateParams, TemplateWithEditContext,
66
};
77
use wp_api_integration_tests::prelude::*;
88

9+
const TEST_SLUG: &str = "foo_template_slug";
10+
const TEST_TITLE: &str = "foo template title";
11+
12+
#[tokio::test]
13+
#[serial]
14+
async fn create_template_with_slug_and_content() {
15+
let content = "foo template content";
16+
let mut params = TemplateCreateParams::new(TEST_SLUG.to_string());
17+
params.content = Some(content.to_string());
18+
test_create_template(&params, |created_template| {
19+
assert_slug(&created_template);
20+
assert_eq!(
21+
created_template.content,
22+
SparseTemplateContentWrapper::Object(SparseTemplateContent {
23+
raw: Some(content.to_string()),
24+
rendered: None,
25+
protected: None,
26+
block_version: None
27+
})
28+
);
29+
})
30+
.await;
31+
}
32+
33+
#[tokio::test]
34+
#[serial]
35+
async fn create_template_with_slug_and_title() {
36+
let mut params = TemplateCreateParams::new(TEST_SLUG.to_string());
37+
params.title = Some(TEST_TITLE.to_string());
38+
test_create_template(&params, |created_template| {
39+
assert_slug(&created_template);
40+
assert_title(&created_template);
41+
})
42+
.await;
43+
}
44+
45+
#[tokio::test]
46+
#[serial]
47+
async fn create_template_with_slug_title_and_theme() {
48+
let theme = "foo template theme";
49+
let mut params = TemplateCreateParams::new(TEST_SLUG.to_string());
50+
params.title = Some(TEST_TITLE.to_string());
51+
params.theme = Some(theme.to_string());
52+
test_create_template(&params, |created_template| {
53+
assert_slug(&created_template);
54+
assert_title(&created_template);
55+
assert_eq!(created_template.theme, theme);
56+
})
57+
.await;
58+
}
59+
60+
#[tokio::test]
61+
#[serial]
62+
async fn create_template_with_slug_title_and_author() {
63+
let mut params = TemplateCreateParams::new(TEST_SLUG.to_string());
64+
params.title = Some(TEST_TITLE.to_string());
65+
params.author = Some(SECOND_USER_ID);
66+
test_create_template(&params, |created_template| {
67+
assert_title(&created_template);
68+
assert_eq!(created_template.author, SECOND_USER_ID);
69+
})
70+
.await;
71+
}
72+
973
#[tokio::test]
1074
#[serial]
1175
async fn delete_template() {
@@ -70,15 +134,9 @@ generate_update_test!(
70134
generate_update_test!(
71135
update_title,
72136
title,
73-
"new_title".to_string(),
137+
TEST_TITLE.to_string(),
74138
|updated_template| {
75-
assert_eq!(
76-
updated_template.title,
77-
SparseTemplateTitleWrapper::Object(SparseTemplateTitle {
78-
raw: Some("new_title".to_string()),
79-
rendered: Some("new_title".to_string())
80-
})
81-
);
139+
assert_title(&updated_template);
82140
}
83141
);
84142
generate_update_test!(
@@ -113,6 +171,33 @@ where
113171
RestoreServer::db().await;
114172
}
115173

174+
async fn test_create_template<F>(params: &TemplateCreateParams, assert: F)
175+
where
176+
F: Fn(TemplateWithEditContext),
177+
{
178+
let response = api_client()
179+
.templates()
180+
.create(params)
181+
.await
182+
.assert_response();
183+
assert(response.data);
184+
RestoreServer::db().await;
185+
}
186+
187+
fn assert_slug(template: &TemplateWithEditContext) {
188+
assert_eq!(template.slug, TEST_SLUG);
189+
}
190+
191+
fn assert_title(template: &TemplateWithEditContext) {
192+
assert_eq!(
193+
template.title,
194+
SparseTemplateTitleWrapper::Object(SparseTemplateTitle {
195+
raw: Some(TEST_TITLE.to_string()),
196+
rendered: Some(TEST_TITLE.to_string())
197+
})
198+
);
199+
}
200+
116201
mod macro_helper {
117202
macro_rules! generate_update_test {
118203
($ident:ident, $field:ident, $new_value:expr, $assertion:expr) => {

0 commit comments

Comments
 (0)