I just read this blog post by Wim Leers and apparently each entity type should have a bunch of test cases attached that test its REST functionality – even config entity types.
So, since we define three entity types, we should add such tests for all of them. (Whether it really makes sense for tasks is a bit of a question, but then again, why not? We should at least make sure they have proper access restrictions in place (don't want anonymous users to create tasks) and I guess it's at least theoretically possible that someone will want to review existing tasks via REST.)
(Note: Great instructions for how to add such tests are in the EntityResourceTestBase
class doc comment – and in the blog post linked above, of course.)
Comment | File | Size | Author |
---|---|---|---|
#29 | Screen Shot 2018-03-30 at 20.47.00.png | 136.16 KB | borisson_ |
#26 | 2929603.patch | 22.99 KB | borisson_ |
#19 | 2929603.patch | 7.99 KB | borisson_ |
|
Comments
Comment #2
drunken monkeyComment #3
borisson_Tagging this as novice, as there isn't really an "intermediate"-type of tag. Because of all the examples in core, it should be easy to resolve this.
Comment #4
borisson_We can only do this for content entities, so that means only for the task entity type. We should be able to do this for config entities in the future.
This doesn't work yet, and I don't know why that is, but at least this is a start.
Comment #6
borisson_Looks like that last-minute change before the patch upload got us some messages that were easier to test. Fixing this now
Comment #7
borisson_I can't reproduce those fails locally, I keep getting this:
I don't understand why that is happening.
We should be getting more errors now, I copied these tests from media, and looks like I didn't rename all of them correctly.
I also added 2
@group
annotations to the tests, because that makes it a little easier to run these:./vendor/bin/phpunit -c core/ modules/globalignore/search_api --group rest
Comment #8
borisson_Comment #10
drunken monkeyMakes sense for now, but would you say we should also commit it like this? Not sure what the consequences of that would be (if any, apart from making testing those easier).
Also: Why not just
./vendor/bin/phpunit -c core/ modules/globalignore/search_api/tests/src/Functional/EntityResource
?Would be a nice simplification – but are you sure about that? It seems like Core provides tests for all config entity types as well.
Regarding the patch itself: Seems like a great start, thanks! Unfortunately, I also couldn't figure out why the tests are failing. (Also, I had completely different fails with not a single passing test method, so even worse.) Or what's going on at all.
I don't really think tagging this as "Novice" is fair, I'd feel bad for any actual novice trying to take this on. It seems more like we'd need a REST expert to work on this, not a Search API expert.
Comment #11
borisson_Probably not.
I was wrong, this can be done for config as well, but let's fix Task first, before we do the other entities.
I agree, if both of us can't figure it out yet, asking a novice to work on this wouldn't be great. I'll did review a couple of the issues that went into drupal core regarding this, but even that knowledge isn't enough to help me figure out the fails.
Comment #12
Wim Leers❤️
Comment #13
Wim Leers+1. Especially when using https://www.drupal.org/project/jsonapi this is important (and we want to move that into core in 8.6), because that exposes all entities by default, and relies on entity access to ensure access is given to only those who should be allowed to access it!
That's not quite true — it's possible to view (
GET
) config entities. Run e.g.\Drupal\Tests\rest\Functional\EntityResource\NodeType\NodeTypeJsonBasicAuthTest
and observe :)#7: I cannot reproduce those failures locally (on Drupal 8.6.x + PHP 7 + latest
search_api
8.x-1.x
). I can reproduce the failures that testbot is showing.Patch review:
Nit: I'd suggest moving these into a
Rest
directory rather thanEntityResource
. That'll make 10x more sense for you as a contrib module :)(That's also the location that
\Drupal\Tests\rest\Functional\EntityResource\EntityResourceRestTestCoverageTest
checks, in case this module ever makes into core, or in case that test gets somehow generalized to run for contrib modules.)Unused, can be removed. (There are no
timestamp
fields in theTask
content entity type.)😀
C/P remnant.
These need to be updated too.
Test failures:
Seems to be the most complex/puzzling test failure. It's caused by the fact that the
Task
entity type … does NOT specify anadmin_permission
annotation key! So this is pointless:The reason can be found in
\Drupal\Core\Entity\EntityAccessControlHandler::checkAccess()
:It ends up executing the last branch, and hence there's no cacheability to be associated, hence no
user.permissions
cache context.Adding an
admin_permission
annotation key fixes that. Tests then fail just a little bit further, because then bothurl.site
andurl.permissions
are expected.url.site
is expected by default because 99% of entity types specify link relations. And link relations causeLink
response headers to be generated, containing absolute URLs, and those then of course vary by which site in a multi-site setup is being accessed. That's not the case here, so we need to override that default expectation.From then onward, the failures are more obvious, and I think you'll be easily able to drive them to completion :)
Comment #15
borisson_I still have those same failures locally - which makes it really hard to see if the things I'm doing are actually improving the patch. (php7.1, drupal 8.6 and latest search api 8.x-1.x)
Comment #17
drunken monkeyThanks for your continued work here, and thanks for jumping in, Wim!
With the additional hints, I was able to get a bit further, but now I'm stuck again (and out of time for today): apparently there is an unavoidable test during POST (
EntityResourceTestBase.php:857
) which ensures you can't add a second value to the label field – but we don't have a label field for tasks, so not sure if that will even work. But it fails with an unexpected 403 response anyways, so couldn't even find out if it does.Comment #19
borisson_I reinstalled mamp and now am running on php7.2, this made it so that I could reproduce the errors and I fixed them.
I'm not sure if we should add new issues for the other entities or if we should do that in one go.
Comment #20
drunken monkeyOh, that's all that was needed? Awesome, great job, thanks!
As per your request, I'm leaving this open for the index/server tests.
But thanks again, in any case!
Comment #21
borisson_Not sure if that was the big thing, but at least that made it so that I could reproduce the failures.
I added the work I did on the Index and Server, but this needs a fix in core tests.
@Wim Leers, do you think this is something sane to be added in core tests or should we try to fix this in Search API? The problem is that the not all links that we add to the Index class trough the annotation don't exist in the link relation type plugin manager.
Comment #23
borisson_That was the problem that is fixed with the core patch.
The problem that we see with the Anon test is something that I don't know how to fix:
Comment #24
borisson_Comment #26
borisson_Comment #28
borisson_The core patch I added in #21 was wrong and I fixed that by adding the correct link_relation_types in #26. Now all we need to to is figure out the 6 remaining failures, but I don't have a clue why they are happening and how to resolve them.
Comment #29
borisson_I asked @tedbow for help on this in slack.
As expected, his assesment is correct, the expected cache tags are:
The actual cache tags (
$response->getHeader('X-Drupal-Cache-Tags')
) are empty (array(0) {}
).I've tried figuring out why this happens, but I can't seem to find the reason.
I tried doing this by just getting the same page with Insomnia, but it looks like not getting the correct result is actually the correct response. At least it looks like that is what is happening.
Comment #30
drunken monkeyI've also tried looking into it, but I'm stumped as well. I did uncover some useful information (I think/hope), but wasn't able to convert it to any actual change that would make this pass:
4xx-response
,config:user.role.anonymous
,http_response
.user.permissions
cache context on the access result (since it's caused by the (anonymous) user not having the Search API admin permission). As I see it, this would lead to the second cache tag being correctly applied via\Drupal\Core\Cache\Context\AccountPermissionsCacheContext::getCacheableMetadata()
. The other two just seem to specify the kind of response, so would likely be added at some other point in the process.AccessDeniedHttpException
, not a DrupalCacheableAccessDeniedHttpException
. This leads to a responce object that also doesn't contain any cache metadata (see\Drupal\serialization\EventSubscriber\DefaultExceptionSubscriber::on4xx()
).\Drupal\Core\Routing\AccessAwareRouter::checkAccess()
, not in\Drupal\rest\Plugin\rest\resource\EntityResource::get()
(which throws the correct exception).Comment #31
borisson_I tried all afternoon to figure out why these failures were happening, but I didn't get one any closer. We're going to need help on this one.