Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Themes REST API endpoint: Add stylesheet_uri and template_uri fields to the response #6399

Conversation

andrewserong
Copy link
Contributor

@andrewserong andrewserong commented Apr 17, 2024

Based on an idea from @ramonjd and @noisysocks in WordPress/gutenberg#60578, this PR explores adding stylesheet_uri and template_uri fields to the API response for the themes endpoint. The goal being to expose the URI of the directory for a theme (or its parent theme when dealing with child themes) so that theme relative URIs can be constructed by consumers of this endpoint. An example use case is in WordPress/gutenberg#60578

A quick way to test this is to apply the PR and then open up the post editor and run the following from the console:

wp.apiFetch( { path: '/wp/v2/themes/twentytwentyfour' } );

In the API response, you should see stylesheet and template uris in the response:

image

Trac ticket: https://core.trac.wordpress.org/ticket/61021


This Pull Request is for code review only. Please keep all other discussion in the Trac ticket. Do not merge this Pull Request. See GitHub Pull Requests for Code Review in the Core Handbook for more details.

Copy link

github-actions bot commented Apr 17, 2024

The following accounts have interacted with this PR and/or linked issues. I will continue to update these lists as activity occurs. You can also manually ask me to refresh this list by adding the props-bot label.

Core Committers: Use this line as a base for the props when committing in SVN:

Props andrewserong, timothyblynjacobs, noisysocks, ramonopoly, peterwilsoncc.

To understand the WordPress project's expectations around crediting contributors, please review the Contributor Attribution page in the Core Handbook.

Copy link

Test using WordPress Playground

The changes in this pull request can previewed and tested using a WordPress Playground instance.

WordPress Playground is an experimental project that creates a full WordPress instance entirely within the browser.

Some things to be aware of

  • The Plugin and Theme Directories cannot be accessed within Playground.
  • All changes will be lost when closing a tab with a Playground instance.
  • All changes will be lost when refreshing the page.
  • A fresh instance is created each time the link below is clicked.
  • Every time this pull request is updated, a new ZIP file containing all changes is created. If changes are not reflected in the Playground instance,
    it's possible that the most recent build failed, or has not completed. Check the list of workflow runs to be sure.

For more details about these limitations and more, check out the Limitations page in the WordPress Playground documentation.

Test this pull request with WordPress Playground.

@andrewserong
Copy link
Contributor Author

I've updated and added tests. A few questions for anyone reviewing:

  • These two fields refer to the directory, should that be in the name as well, or is stylesheet_uri and template_uri straightforward enough?
  • Other fields have raw and rendered versions of the URI (i.e. author_uri and theme_uri are objects with raw and rendered keys). Should we do that for these, too? My assumption is that since these new fields are meant to be used to construct URIs rather than to be displayed, the answer would be no. But for consistency it might be confusing if these are just strings.
  • Are these values safe to expose in this way? I.e. if you have permission to get all the other data from this endpoint, is this extra data consistent with the current permissions / capabilities?

@TimothyBJacobs
Copy link
Member

It seems unexpected that this is not applying the stylesheet_directory_uri because it isn't using the global get_stylesheet_directory_uri function. We probably need to alter how the response is prepared if it's the current theme or not. See the is_same_theme helper.

@andrewserong
Copy link
Contributor Author

Thanks for the review @TimothyBJacobs!

It seems unexpected that this is not applying the stylesheet_directory_uri because it isn't using the global get_stylesheet_directory_uri function

Good catch! I've updated the logic in b1dd7ff so that it calls the global functions for both the template directory uri and the stylesheet directory uri if the current theme matches the requested theme, so I believe this should hook into those filters now. I'm not very familiar with this part of the code base, though, so do let me know if there's anything off with this approach.

Thanks!

@noisysocks
Copy link
Member

noisysocks commented Apr 18, 2024

Gave this for a spin locally by checking the branch out and creating a child theme of TT4 called tt4-child:

% http -a "admin:password" GET http://localhost:8889/wp-json/wp/v2/themes | jq '.[] | { stylesheet, status, template_uri, stylesheet_uri }'
{
  "stylesheet": "tt4-child",
  "status": "active",
  "template_uri": "http://localhost:8889/wp-content/themes/twentytwentyfour",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/tt4-child"
}
{
  "stylesheet": "twentyeleven",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentyeleven",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentyeleven"
}
{
  "stylesheet": "twentyfifteen",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentyfifteen",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentyfifteen"
}
{
  "stylesheet": "twentyfourteen",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentyfourteen",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentyfourteen"
}
{
  "stylesheet": "twentynineteen",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentynineteen",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentynineteen"
}
{
  "stylesheet": "twentyseventeen",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentyseventeen",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentyseventeen"
}
{
  "stylesheet": "twentysixteen",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentysixteen",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentysixteen"
}
{
  "stylesheet": "twentyten",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentyten",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentyten"
}
{
  "stylesheet": "twentythirteen",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentythirteen",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentythirteen"
}
{
  "stylesheet": "twentytwelve",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentytwelve",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentytwelve"
}
{
  "stylesheet": "twentytwenty",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentytwenty",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentytwenty"
}
{
  "stylesheet": "twentytwentyfour",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentytwentyfour",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentytwentyfour"
}
{
  "stylesheet": "twentytwentyone",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentytwentyone",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentytwentyone"
}
{
  "stylesheet": "twentytwentythree",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentytwentythree",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentytwentythree"
}
{
  "stylesheet": "twentytwentytwo",
  "status": "inactive",
  "template_uri": "http://localhost:8889/wp-content/themes/twentytwentytwo",
  "stylesheet_uri": "http://localhost:8889/wp-content/themes/twentytwentytwo"
}

Copy link
Member

@noisysocks noisysocks left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code LGTM to me too. Nice work 👍

* @ticket 61021
*/
public function test_theme_template_uri() {
$response = self::perform_active_theme_request();
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would it worth testing inactive themes as well after b1dd7ff?

Copy link
Contributor Author

@andrewserong andrewserong Apr 18, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh, thanks for spotting that! I've updated the tests in b444489 to include both active and inactive themes in the response, and loop over the results to check against the global function or the method on the theme object, depending on the status.

Let me know if you think it's better to split into separate tests, though.

foreach ( $result as $theme_result ) {
$this->assertArrayHasKey( 'template_uri', $theme_result );
if ( 'active' === $theme_result['status'] ) {
$this->assertSame( get_template_directory_uri(), $theme_result['template_uri'] );
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for updating! LGTM

The only thing I'd do is add a message as the third argument to the assertSames so that failing tests return something meaningful.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point 👍

Added in: 23cae05. Happy to tweak the wording if need be.

@ramonjd
Copy link
Member

ramonjd commented Apr 18, 2024

Thanks for working on this 🙇🏻 LGTM!

@andrewserong
Copy link
Contributor Author

Thanks for all the reviews, everyone! I'll be AFK over the next week, so in case there's any further feedback, I won't be able to get to it until the week after. In the meantime, feel free to commit to this branch if anyone would like to make changes, (or commit the changeset if this feels like it's in a good enough place). Cheers!

@TimothyBJacobs
Copy link
Member

Merged in r58282.

@ramonjd
Copy link
Member

ramonjd commented Jun 3, 2024

Should we also sync these changes to Gutenberg?

There's currently no feature that relies on these properties, but maybe it should be synced to compat/6.6 in case that changes between now and 6.9 (when support for 6.6 is dropped in the plugin).

It's likely these properties will be needed to resolve relative asset paths in template/pattern files.

I'd already synced the REST change for a previous experiment so I threw up a PR just in case:

@andrewserong
Copy link
Contributor Author

Good idea @ramonjd — yes, even though there are no features depending on it, I think it'd be good to have parity for the feature in Gutenberg to make it easier to use if need be.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants