Conversation
kadamwhite
left a comment
There was a problem hiding this comment.
This plugin's a WIP prototype, so I have no formal objection to merging as-is if it'll keep us moving; there's lots to be done and this does provide a decent foundation.
However, there's a couple wishlist things I'd like to see here before pushing the green button:
- A little more rigor around documentation, commenting, and style; on the theory that if we start strong, it'll be easier to end strong
- A comment thoroughly walking through the flow of requests necessary to generate a token
- Some skeleton documentation around the overall structure; as evidenced by the conversation in Slack today several of us are not confidant we can suss out the flows from the code alone, so a talk-through would be very valuable.
| { | ||
| "env": { | ||
| "browser": true | ||
| }, |
There was a problem hiding this comment.
We'll probably want to clean this up in a similar way to WordPress/grunt-patch-wordpress#72 -- consume the core eslint plugin, etc -- but that's a follow-up, not necessary to resolve for this PR.
There was a problem hiding this comment.
Pulled this out into #3 so we can table it for now and revisit once the important stuff is done 👌
.travis.yml
Outdated
|
|
||
| # Newer versions like trusty don't have PHP 5.2 or 5.3 | ||
| # https://blog.travis-ci.com/2017-07-11-trusty-as-default-linux-is-coming | ||
| dist: precise |
There was a problem hiding this comment.
With the work we're doing to bump minimum version, let's code towards a 7.x future and only test down to 5.6 at minimum.
There was a problem hiding this comment.
We can test down to 5.6, which is fine, but we still would support 5.3 through static analysis.
There was a problem hiding this comment.
I slightly disagree, 5.3 is long past EOL and the timeline we have for this would put us into a zone where we shouldn't have to worry about it with regard to core development. I don't think it should hold this up but I don't think we need to go all the way back to precise.
jwt-auth.php
Outdated
|
|
||
| if ( version_compare( PHP_VERSION, '5.3', '<' ) ) { | ||
| deactivate_plugins( plugin_basename( __FILE__ ) ); | ||
| wp_die( esc_html__( 'The JWT Auth plugin requires PHP Version 5.3 or above.', 'jwt-auth' ) ); |
There was a problem hiding this comment.
See above note about 5.6
There was a problem hiding this comment.
@kadamwhite Changing this to 5.6 is not needed. The minimum PHP version required for the code to work is 5.3 and Core is adopting 5.3, so what would the benefit of making this 5.6 be?
There was a problem hiding this comment.
Per this post: https://wordpress.org/news/2019/04/minimum-php-version-update/ the PHP minimum version for core is, "5.6 now and soon 7+"
tests/autoload.php
Outdated
| $config = getenv( 'WP_TESTS_CONFIG' ); | ||
|
|
||
| /** | ||
| * Supports loading the wp-tests-config.php from a non VVV custom directory. |
There was a problem hiding this comment.
Nitpick: let's remove the VVV-specific language.
There was a problem hiding this comment.
At this point the only environment the unit tests work in is VVV, or have been tested in would be more accurate.
There was a problem hiding this comment.
@valendesigns Do you mean it can only run inside VVV? Because I was able to run it via Laravel Valet.
| * | ||
| * This class only allows REST authentication to the `{api_prefix}/wp/v2/token` | ||
| * endpoint with an API key:secret. This allows a user to be identified via the | ||
| * REST API without using their login credentials to generate a JSON Web Token. |
There was a problem hiding this comment.
I see what's intended here, but as discussed in Slack I think this flow is confusing and that we'll need a request flow example (Either in js, php, whichever, saying, POST to /wp-json/tokens/generate, then take X from that response, etc…) before we make any progress on that.
| */ | ||
| public function register_routes() { | ||
| $args = array( | ||
| array( |
There was a problem hiding this comment.
I'm not clear why this is an array of arrays. Shouldn't these all just be one level? None of the core endpoints use nested arrays in this way, they pass $args = array( 'args' => array(), 'methods' => ... ) etc.
| 'callback' => array( | ||
| $this, | ||
| 'delete_key_pair', | ||
| ), |
There was a problem hiding this comment.
Absolute style nit but we try to keep these callback arrays to one line in the core controller code, to make it more obvious it's a class method lookup.
| if ( isset( $_POST['pass1'] ) && ! empty( $_POST['pass1'] ) ) { // phpcs:ignore | ||
| $keypairs = $this->get_user_key_pairs( $user_id ); | ||
| if ( ! empty( $keypairs ) ) { | ||
| $this->set_user_key_pairs( $user_id, array() ); |
There was a problem hiding this comment.
Could use a clarifying comment, here or in the function docbloc, clearly explaining what's being cleared.
| @@ -0,0 +1,379 @@ | |||
| <?php | |||
|
|
|||
| namespace Firebase\JWT; | |||
There was a problem hiding this comment.
Anybody know the policy on external dependencies like this, in terms of where they should go in the codebase? Most of them go into /wp-includes/[ project ], looking at SimplePie, Requests, etc. I'd expect this should be followed here
There was a problem hiding this comment.
I've moved it 👍
|
I see in the checklist: I think right now, as long as there are appropriate filters/hooks/public methods for any API to hook into, then at the moment it should be WPGraphQL's responsibility to provide some "adapter" to work with this. There's no official plan (that I know of) to move WPGraphQL into core, so a plugin like this that is targeting core should probably not be concerned with explicit WPGraphQL support, but rather general access for any API layer to make use of. REST and GraphQL aren't the only API's that will exist for WordPress. Whatever cool new API tech 5 years from now should also be able to make use of whatever foundation is there. I'll try and review the code shortly and provide thoughts on how I would want to hook in and if any changes are necessary to be able to accomplish what I would need to do |
|
@kadamwhite I'll work on updates from the review on Monday. Thanks for reviewing! @jasonbahl Yes the intent is to ensure the current hooks/filters and workflow support WPGraphQL not to write specific code only used for it. |
renatonascalves
left a comment
There was a problem hiding this comment.
Thoughts on my initial review!
tests/autoload.php
Outdated
| $config = getenv( 'WP_TESTS_CONFIG' ); | ||
|
|
||
| /** | ||
| * Supports loading the wp-tests-config.php from a non VVV custom directory. |
There was a problem hiding this comment.
@valendesigns Do you mean it can only run inside VVV? Because I was able to run it via Laravel Valet.
tests/autoload.php
Outdated
| $config = getenv( 'WP_TESTS_CONFIG' ); | ||
|
|
||
| /** | ||
| * Supports loading the wp-tests-config.php from a non VVV custom directory. |
| */ | ||
| public function register_routes() { | ||
| $args = array( | ||
| array( |
| $args = array( | ||
| array( | ||
| 'methods' => WP_REST_Server::CREATABLE, | ||
| 'callback' => array( |
There was a problem hiding this comment.
Suggestion: leave in one line: 'callback' => array( $this, 'generate_key_pair' ) This and others below.
| 'callback' => array( | ||
| $this, | ||
| 'delete_key_pair', | ||
| ), |
| public function get_item_schema() { | ||
| $schema = array( | ||
| '$schema' => 'http://json-schema.org/draft-04/schema#', | ||
| 'title' => esc_html__( 'Key-pair', 'jwt-auth' ), |
There was a problem hiding this comment.
Shouldn't this be lower case and with the underscore? key_pair?
| * @param mixed $user The user that's being authenticated. | ||
| * @param WP_REST_Request $request The REST request object. | ||
| * | ||
| * @return bool|object|mixed |
There was a problem hiding this comment.
Suggestion: Add the objects returned: WP_User and WP_Error so that I don't have to read the code/method to know which objects are returned.
There was a problem hiding this comment.
Technically if someone has filtered rest_authentication_user it could be any kind of object. If $user is not equal to false the method returns the value so yes the intention is that it will return a WP_User but that's not a guarantee and will work perfectly with any type of object with the correct properties. If someone wanted to build their own decoupled user system that's possible by filtering rest_authentication_user. I'll update the docblock to call this out.
| * | ||
| * @param object $jwt The JSON Web Token. | ||
| * | ||
| * @return object|WP_Error |
There was a problem hiding this comment.
Same here! Which object is that?
Uses the built-in `get_rest_url` API to handle all situations. Return only the path from `get_rest_uri`
|
The key thing we're waiting on here, if you have bandwidth @valendesigns , is this:
If we can get a human-language walkthrough of the full auth process, that will help move everything else along. |
|
I'm wondering what the reason was for invalidating a token when an email changes in 7ccfc84? |
|
I’d extend the same question to user_login. I don’t see why a username change would invalidate a token. I even have doubts about whether a password change should, not sure if there has been a discussion about that, or just going with what cookie authentication does. |
|
A password change doesn't invalidate the token currently, which I think is fine. Since one of the principles of JWT is stateless I'm suggesting to just drop If we follow this we could remove all the user data/type handling to keep it simple. Maybe even use the |
|
I need to get caught up on the codebase and conversations, but I would submit that Username and password changes should for sure invalidate tokens. If we go the "stateless" approach, we need to issue very short lived tokens (few minute expiration max) and an additional revokeable longer-lived refresh token. A token that's valid when it's issued should only be trusted for a very short time. If a users account is compromised - let's say a malicious co-worker or relative used their username and password - the compromised user should be able to take action, like resetting their password, and the compromised tokens should no longer be valid. Even think of Netflix, etc which give you a "Sign out of all accounts" option. That's invalidating all previously issued tokens. The way we've approached this on WPGraphQL JWT Authentication is issuing 2 tokens. A short-lived access/auth token (5 min expiration) and a long-lived (1-year) refresh token. The authToken can be used to do things like read private data, execute mutations (writes), etc. The refreshToken is only good for getting a new Anyway, our flow looks like this:
If we're using a single token (haven't really dug into the code yet) then it absolutely needs to be stateful. |
Review fixes
Refresh Tokens
Create readme.md
Allow for both plain and pretty permalink structures
|
After discussion with @TimothyBJacobs , the size of this PR is prohibitive for a thorough review. We've all had a lot of eyes on it over the past few months; let's land this and iterate rather than letting this linger further. Thank you @valendesigns ! |
|
@kadamwhite agree! Cool! :) |

Uh oh!
There was an error while loading. Please reload this page.