I'm having a very strange issue. As an authorised user I can login and get a node entity no problems, but I can't for the life of me create with a post, I keep getting a 401 access denied. However, I can of course create the node on the site no problem. As admin user it works no problem. If I set the permission Bypass content access control for the auth user it also works fine. Any ideas??
Comments
Comment #1
7wonders commentedAnd yes it works fine with regular services too but I want the clean controller!?!
Comment #2
randallknutson commentedI'll take a look at this when I get a chance.
Comment #3
that0n3guy commentedI can verify this as well. I can create with user1 just fine. Normal users can create in web interface, but not with services.
My un-educated guess as to the why:
I've noticed that when creating nodes with clean controller and user1, the author is not set (ie, the node says the author is anon). I have to specify the author, this seems like a bug. If I create nodes with normal services, the user is set to the logged in user (this is the correct way I think).
My guess is this has something to do w/ it. :)
Comment #4
that0n3guy commentedOh, I should note, this is with "session authentication". I don't know if this is the case w/ oauth or basic http....
Comment #5
that0n3guy commentedAhh, I think I figured this out. This is because entity_access does not provide a generic bundle create op access check.
I swiped some code from http://drupal.org/node/1856978#comment-6956976 and made a patch. Works for clean controller, it should work w/ the "dirty" controller as well (if one is clean... isn't the other dirty :P ) but I didn't test it.
Comment #6
joachim commentedI don't think that making a special case of node is a good thing here.
However, we could do what I already do in Entity Operations: overload entity_access() to take a bundle name in the 'create' op, same as node_access().
> entity_access($op, $entity_type, $entity = NULL, $account = NULL)
That way, if your custom entity's access callback knows what to do with that, it can handle it. If it doesn't, it should have no business looking at the $entity parameter in a 'create' op anyway :) Provided we document the trick we're pulling, of course...
Comment #7
that0n3guy commentedI'm not sure I get how that works, maybe its too late :).
Comment #8
joachim commentedHeh, I know the feeling :)
entity_access() just hands over to your entity type's 'access callback'.
I don't know what ECK does for that, but if it's a custom entity, you can do what you want. Currently, on a 'create' op, you get a NULL for $entity. So access callbacks will currently ignore that parameter on $op 'create'.
What I'm suggesting is that we extend this by overloading the $entity parameter, the same way that node_access() overloads the $node param.
Then your own access callback can take this into account.
Comment #9
that0n3guy commentedI see your point. Maybe multiple and single need to be separated. Use case:
load all a webforms submissions
loop through the submissions to get the webform_data type
send an email to someone using token data from the submissions.
Comment #10
that0n3guy commentedAlright, this is the way I got it to work. See my attached patch.
Comment #11
joachim commentedYup, that's along the lines of that I meant.
Though --
That's a bit harsh! Not all entity types will be using this in their access callback. Least of all the ones with no bundles!
Comment #12
joachim commentedComment #13
Raphael Dürst commentedI had a similar problem, I was using Services Entity API with the Entity Registration module.
When trying to create a registration, I got an error that the access callback of the registration entity needs a full entity object.
This problem is actually solved with the simple path I attached.
With this patch the bundle gets also passed to the access callback.
Comment #14
Raphael Dürst commentedI just realized that my patch doesn't work properly, sorry.
Made a small change, now it works.
Comment #15
joachim commented> I got an error that the access callback of the registration entity needs a full entity object.
That's non-standard. It's useful, but not how other Entity API modules do it. Look at profile2, for instance.
Comment #16
wodenx commentedLooking at https://drupal.org/node/1780646 it seems like the approach in #14 is being taken by entity_api, so perhaps it is becoming the new standard? The patch candidate is in #136 of that thread, or: https://drupal.org/files/entity-entity_access-1780646-136.patch
Comment #17
joachim commented> Looking at https://drupal.org/node/1780646 it seems like the approach in #14 is being taken by entity_api, so perhaps it is becoming the new standard?
That would definitely be a good thing -- would solve a lot of problems!
I suppose adding the parameter to entity_access() won't have any effect on entity types whose access callback doesn't support it, so it's fine to do it.
I think it would be a good idea to add a comment to the call to entity_access() though, to explain what we're doing and why.
Also, here's another small tweak that should be made:
Instead of $args[1], $entity should be picked out with the list() operator.
Comment #18
wodenx commentedMade those changes to #14.
Comment #19
wodenx commentedRealized that this requires slightly different handling for the clean controller.
Comment #20
joachim commentedThis issue is quite similar to another one, isn't it? I've been getting them confused :/
Isn't there a thing on Entity module to now pass a full entity to entity_access() even on create? How would that change affect this?
Comment #21
wodenx commentedYes the Entity API issue is #1780646: entity_access() fails to check node type specific create access. The latest patch candidate there (#191) passes a full entity on create, and that's the approach taken here as well. I suppose we could wait for that to settle, though it hasn't received much maintainer input lately. But without this fix, it's not possible to create nodes without 'bypass node access' permissions. This fix works even without the Entity API patch, but it generates notices.
Comment #22
joachim commentedThese comments lines need wrapping.
Is it because of the property names the clean controller uses that we need this? As in, instead of 'field_foo', our incoming data is just 'foo'?
I do think the clean controller is more trouble than it's worth... and the removal of 'field' I think is just asking for a clash.
More critically, I think we have to postpone on #1780646: entity_access() fails to check node type specific create access (and a release of Entity API with that change).
Otherwise, the node access callback that Entity API adds will crash with our change, AFAICT. We'll be passing in a $node to entity_access(), and the following code will try to load the $node we've passed in and fail:
Comment #23
wodenx commentedI disagree about the clean controller. I think it takes better advantage of the entity metadata, both for access and validation checks, and as a general description of the properties of an entity. Though I do agree that stripping the "field_" is a nicety that isn't worth it. I'd be more than happy to remove that, but it might affect others using the controller.
Specifically, transform_values() also takes care of decoding "resource references" (the way the clean controller handles referenced entities).
Regarding postponement, the patch actually works with the current version of entity api -- it just throws a few notices. Eventually by the time our skeleton node gets passed to node_node_access(), we have:
If you still want to postpone, that's fine - but as it is it's not possible to create a node with the clean controller unless you have "bypass node access" permission, which is not a happy state of affairs.
Comment #24
joachim commented> Though I do agree that stripping the "field_" is a nicety that isn't worth it. I'd be more than happy to remove that, but it might affect others using the controller.
Well we're still in alpha, so we'd be fine to make that sort of change. I'll open a new issue for that.
> If you still want to postpone, that's fine - but as it is it's not possible to create a node with the clean controller unless you have "bypass node access" permission, which is not a happy state of affairs.
Ah, I didn't realize that. Sorry, I keep flitting in and out of this issue whenever I have spare time :(
Would it be possible to commit this patch in two halves:
1. Fix the clean controller so it works
2. When the Entity API patch lands and is released, commit the change to the regular controller
Comment #25
wodenx commentedActually, I think it will fail in the regular controller as well. See the attached test.
Comment #26
wodenx commentedOK how about this workaround - a special case for nodes until the Entity API bug is fixed.
Comment #28
wodenx commented#26: 1865102-26-services_entity-access-bundle.patch queued for re-testing.
Comment #30
wodenx commentedAutomated tests are broken -- see #2109167: Testbot not downloading all dependencies.
Comment #31
wodenx commented#26: 1865102-26-services_entity-access-bundle.patch queued for re-testing.
Comment #33
wodenx commentedRerolled to apply to HEAD.
Comment #34
wodenx commentedIs there anything still holding this up?
Comment #35
wodenx commented@joachim - would like to commit this - let me know if you have any objections.
Comment #36
joachim commentedJust a few minor things:
entity_access needs a () on it.
This case doesn't cover node_access() due to the workaround above.
Can you add a comment to explain why 'create' gets special handling?
Missing terminal newline.
Comment #37
wodenx commentedhttp://drupalcode.org/project/services_entity.git/commit/038618c