Problem/Motivation
As it's implemented the negotiator Drupal\consumers\Negotiator is looking on either a custom header X-Consumer-ID or custom query argument _consumer_id
For any 3rd party module that will require this functionality, the discovery process can not be extended.
I am currently using simple_oauth that is working with consumers internally and logging a user, giving roles from the consumer and everything works. My issue at the moment is that the negotiator is not discovering the consumer that was activated / used by the authentication mechanism.
Sending the client ID in a request seems redundant, as the data needed is already part of the request tokens and it was already processed, so the simple_oauth can expose that information somehow.
Proposed resolution
Option 1: Introduce a plugin-based system for negotiators. Once a module get's activated, it's plug-in will provide client ID. First to pass a client ID wins. Plugins should have a priority value set, so some ordering can be enforced.
Option 2: Have a new interface added, so we can implement negotiator decorators. Any module that wants to change the behavior can implement a decorator over the interface. This will allow granular control over the behavior and execution order of the negotiators. Though it might give bigger permissions on implementing modules.
I prefer option 1, as more easy to scale-out, following many core examples in the matter.
Any other ideas will be appreciated.
Remaining tasks
Discussion (is this needed or not)
Decide on an approach.
Patch, etc...
User interface changes
None.
API changes
API addition, internal refactoring.
What is now a hard-coded negotiation logic will become a new extensible sub-system.
Data model changes
None.
| Comment | File | Size | Author |
|---|---|---|---|
| #25 | joor.png | 470.69 KB | lawxen |
| #25 | joo.png | 267.61 KB | lawxen |
| #21 | simple_oauth-2961782-extend-auth-with-consumer-negotiators-v2-D8-21.patch | 3.05 KB | ndobromirov |
| #11 | simple_oauth-2961782-extend-auth-with-consumer-negotiators-D8-11.patch | 2.66 KB | ndobromirov |
| #5 | interdiff-3-5.txt | 612 bytes | ndobromirov |
Comments
Comment #2
vtcore commented+1
Comment #3
ndobromirov commentedHere is a POC with a plug-in system for the negotiators.
Comment #4
vtcore commentedShouldn't priorities of the two Negotiators be different?
Comment #5
ndobromirov commentedNever do copy-paste :D. Yes they should be different, as the original order should be enforced.
First the header and then the query negotiator.
Comment #6
e0ipsoI'm hesitant to introduce flexibility that needs to be maintained further down the line. Can you highlight how this would work with simple_oauth? I may be willing to introduce simple_oauth's needs as the 3rd hard-coded scenario.
Comment #7
ndobromirov commentedWell simple_oauth is having the meta-data available to get the consumer UUID from the token being passed in.
I do not want to send consumer UUID on every request, as the data is already present and used during authentication.
Here is the decorator that solved it for me, changing simple_oauth behavior...
The main part is I am setting the header dynamically just after the successful authentication, so existing negotiators will kick in.
Comment #8
e0ipsoI think this is a very valid approach. This would be a great addition to the Simple OAuth module. The authentication code could set the header there.
Moving to the other issue queue.
Comment #9
ndobromirov commentedThis is related: #2962050: Strange interface.
Comment #10
ndobromirov commentedSo your suggestion at the moment is to put the decorator directly in the authentication service.
Comment #11
ndobromirov commentedHere is a patch to resolve that directly on the auth service.
Changes:
- Marked the interface as internal (same as the only class implementing it).
- New accessor method added on the interface and TokenAuthUser class.
- Set the header on successful authentication.
Comment #13
e0ipsoThanks! I am pretty sure test fails are unrelated.
Comment #14
e0ipsoAlso, it goes without saying. Thanks for the fantastic job.
Comment #15
fy1128 commentedGet error like this:
The website encountered an unexpected error. Please try again later.
ng>Error: Call to a member function uuid() on null in Drupal\simple_oauth\Authentication\Provider\SimpleOauthAuthenticationProvider->authenticate() (line 81 of modules/contrib/simple_oauth/src/Authentication/Provider/SimpleOauthAuthenticationProvider.php).
seems like getConsumer() return null.
Comment #16
ndobromirov commentedIt should be impossible to get a null, as the customer is set only when there is a valid consumer found in this method.
The rest is just property access.
If you are getting an error as stated in the comment i think we need more info to resolve it...
Comment #17
fy1128 commentedI just did some tests. found
got a 'Drupal\user\Entity\User' object,
so
would be always false.
Here was the example request post by postman:
Comment #18
ndobromirov commentedYea, there was the underlying issue that there was not a client instance in all cases. Here is a patch that should resolve the issue.
On top of that it shows that we have missing test coverage in case where user is set on consumer level, resulting in somewhat different authentication process (unified to a big extent now).
Comment #19
司南 commentedyes, get the error too, hope to fix it soon.
Comment #20
ndobromirov commentedAre you using the patch, as I am seeing differences...
If there is no $client, you should be getting
OAuthServerExceptionin that case.Comment #21
ndobromirov commentedComment #22
e0ipsoI am also confused by this. I don't see how that could be the case.
Comment #23
lawxen commentedI got the same error of #15
Comment #24
e0ipso@caseylau When does it happen? What are you doing to trigger it?
Comment #25
lawxen commented@e0ipso Happened on requesting jsonapi when using simple_oauth.

All works well until we updated our site to drupal8.5.3 and simple_oauth to last dev version(version: 20 Apr 2018 version) yesterday.
Comment #26
ndobromirov commentedOk you are getting a token and an exception...
- How are the consumers configured?
- Any other modules that interact with simple_oauth?
- Anything specific to allow us to reproduce the issue?
Comment #27
br0kenThe patch that fixes the issue introduced by #11 available at #2962958: Fatal error when authenticating with a token, obtained by the "password" grant type.
Comment #28
lawxen commented#25 has been fixed too at #2962958: Fatal error when authenticating with a token, obtained by the "password" grant type.
Comment #29
berdirYeah, setting back to fixed, if someone still has a problem that is not fixed by updating to the latest version then I would suggest opening a new issue. The new call here just exposed the problem, it didn't really cause it.