[wp-trac] [WordPress Trac] #44096: REST API: Taxonomy and term endpoints should use correct permission checks

WordPress Trac noreply at wordpress.org
Tue May 15 18:19:28 UTC 2018


#44096: REST API: Taxonomy and term endpoints should use correct permission checks
-----------------------------+--------------------------------------
 Reporter:  danielbachhuber  |      Owner:  (none)
     Type:  defect (bug)     |     Status:  new
 Priority:  normal           |  Milestone:  4.9.7
Component:  Taxonomy         |    Version:
 Severity:  normal           |   Keywords:  has-patch has-unit-tests
  Focuses:  rest-api         |
-----------------------------+--------------------------------------
 There are a couple of key changes we need to make:

 1. Switch `GET /wp/v2/taxonomies?context=edit` to reference
 `$taxonomy->cap->assign_terms` instead of `$taxonomy->cap->manage_terms`.
 Users who can assign terms need to be able to see all corresponding
 labeling.
 2. Permit users with `$taxonomy->cap->assign_terms` to create terms for
 non-hierarchical taxonomies (e.g. tags).

 These suggestions are based on research for
 [https://github.com/WordPress/gutenberg/issues/5879
 WordPress/gutenberg#5879], which I'll copy below for posterity.

 ----

 Here's my
 [https://gist.github.com/danielbachhuber/da5d66da0b6672fd893b83b44994086d
 table of UI-focused permission review].

 The key difference between categories and tags: contributors and authors
 can create tags, but they can't create categories. This distinction
 applies more broadly to non-hierarchical vs. hierarchical taxonomies.

 ''Fortunately'', the only low-level permissions check is in
 `wp_insert_post()`. More specifically:

 {{{
 foreach ( $postarr['tax_input'] as $taxonomy => $tags ) {
         $taxonomy_obj = get_taxonomy( $taxonomy );
         // array = hierarchical, string = non-hierarchical.
         if ( is_array( $tags ) ) {
                 $tags = array_filter( $tags );
         }
         if ( current_user_can( $taxonomy_obj->cap->assign_terms ) ) {
                 wp_set_post_terms( $post_ID, $tags, $taxonomy );
         }
 }
 }}}

 After this logic, `wp_set_post_terms()` calls `wp_set_object_terms()` and
 neither has permissions checks. Because of how `wp_set_object_terms()`
 behaves, strings passed for a non-hierarchical taxonomy will be magically
 transformed into terms. `wp_set_object_terms()` always expects an array of
 integers (representing valid terms) for hierarchical taxonomies.

 I say "fortunately" because core's existing implementation also means we
 don't have to enter the rabbit hole of developer-defined custom taxonomy
 UI. `edit_post()` blindly accepts and processes data included in
 `tax_input`, regardless of whether a developer implemented some bespoke UI
 for the taxonomy.

 Given this information, we can assume:

 1. A user can set terms on a post if they have `assign_terms` for the
 taxonomy and can edit the post. This also means they can access ''all''
 terms (including empty, non-public ones).
 2. A user can create new terms if they have `assign_terms` for a non-
 hierarchical taxonomy, or `edit_terms` for a hierarchical taxonomy.

 However, now we run into
 [https://github.com/WordPress/gutenberg/issues/6361
 WordPress/gutenberg#6361] because capabilities are evaluated at runtime.

-- 
Ticket URL: <https://core.trac.wordpress.org/ticket/44096>
WordPress Trac <https://core.trac.wordpress.org/>
WordPress publishing platform


More information about the wp-trac mailing list