Problem/Motivation
In an entity reference field with at least one reference, and which has a target_bundles setting that lists multiple bundles, a reference whose target ceases to exist becomes impossible to determine the bundle for, and hence impossible to determine the JSON API resource type for.
A resource type requires both the entity type and bundle to be known. But in a Drupal entity reference, only the entity type is guaranteed to be known.
Proposed resolution
Omit dangling references from the normalization. A dangling reference is a reference that does have a target_id, but which does not have a corresponding loadable entity.
Remaining tasks
None.
User interface changes
None.
API changes
Dangling references omitted. CR to be created.
Data model changes
None.
| Comment | File | Size | Author |
|---|---|---|---|
| #24 | 2984647-24.patch | 12.25 KB | wim leers |
| #24 | interdiff.txt | 3.43 KB | wim leers |
| #22 | 2984647-22.patch | 12.11 KB | wim leers |
| #22 | interdiff.txt | 1.3 KB | wim leers |
| #19 | 2984647-19.patch | 11.43 KB | wim leers |
Comments
Comment #2
wim leersThanks for reporting this!
I wonder why
$target_entity === NULLever happens for this though. Can you also post steps to reproduce for creating content entities that trigger this problem?Comment #3
haihoi2 commentedThank for quick reply!
Steps to reproduce:
1. Add new media type for video embedded
2. Choose video embedded for media source
2. Create a content type, let say a story, reference to the media field with multi type
4. Create a new story, we can edit the story, but cannot view it.
Drupal Core 8.5.5 - Media Core
entity - Version - 8.x-1.0-beta4
inline_entity_form - Version: 8.x-1.0-rc1
entity_browser_entity_form - Version: 8.x-2.0-alpha3
video_embed_field - Version: 8.x-2.0
video_embed_media - Version: 8.x-2.0
jsonapi - Version: 8.x-1.22
jsonapi_extras - Version: 8.x-2.2
Comment #4
dawehnerI ran into the same problem when using the recipe from umami.
This content model has 4 references to taxonomy terms:
This error message is really confusing. I would suggest to maybe create a type exception and throw a message which actually helps in the context of Drupal.
One possible better message could be: "JSONAPI doesn't support having multiple entity reference to the same entity type in the same bundle", or well anything which is actually helpful.
Comment #5
wim leersThanks for reporting that @dawehner, that makes it easier to reproduce :)
This was added in #2940339: Port reference field support for non-empty entity reference fields not pointing to an entity from #2543726 to check a pretty fundamental assumption in the logic that was being added there to support the
<root>Taxonomy term parent. It was thought to be an impossible case. Clearly, as #3 and #4 show, that is not at all impossible! I'm glad we added that exception, because it made this bug report already much more precise than "fatal error in some weird place" :)This error message is thrown in case an entity reference items'
->entityproperty isNULL. How is it possible to have an entity reference that doesn't point to any entity? Understanding that is key to making sure nobody has to ever see this exception again.Comment #6
wim leersIf somebody has time to debug this (I don't have time right now, and will be going on vacation next week):
\Drupal\jsonapi\Normalizer\EntityReferenceFieldNormalizer::normalize()does$entity = $item->get('entity')->getValue();, and passes this to\Drupal\jsonapi\Normalizer\Relationship::__construct()which passes it to\Drupal\jsonapi\Normalizer\RelationshipItem::__construct(), which throws the exception.Comment #7
dawehnerI fear weakly typed languages will always have an infinite amount of edge cases :(
Comment #8
wim leers@dawehner I … agree. Not sure why exactly you're making that statement here though, I'm guessing because you are a bit sad by seeing this bug being reported here? :)
Comment #9
wim leersNow that 2.0-beta1 is released, I really would like to see this bug fixed at last :)
I tried to reproduce this with just Drupal core:

… but it normalizes just fine:
@dawehner reported to be able to reproduce this with just Drupal core. But @haihoi2 reported to be using https://www.drupal.org/project/video_embed_field. So I'll install that and try again.
Comment #10
wim leersI installed
video_embed_media(which requiresvideo_embed_field). I created an "embedded media" media type, just like in the screenshots in #3. And I changed the settings of my media reference field to allow "embedded media" to be referenced.Results:
That's what I was referring to when I wrote:
The code that is triggering the error only is executed for references to entities that cannot be loaded, because either they never existed (which is the case for Taxonomy Terms' virtual "root" term), or because they no longer exist.
@dawehner and @haihoi2, are you in your cases dealing with an entity reference field pointing to non-existing data?
Comment #11
wim leersIf I delete a media item (any of them, not
video_embed_media-related necessarily), then I can indeed reproduce this, because Drupal core does not clean up its dangling entity references … you need something like https://www.drupal.org/project/entity_reference_integrity to fix that, weirdly.Comment #12
wim leersThis means the logic introduced by #2940339: Port reference field support for non-empty entity reference fields not pointing to an entity from #2543726 in
\Drupal\jsonapi\Normalizer\EntityReferenceFieldNormalizer::normalize()is too naïve.This fixes it.
Comment #13
gabesulliceI thought we already considered this and decided that it was best to not omit those values because it misrepresents the field data and could lead a JS client to accidentally delete field data via a PATCH based on our response.
Comment #14
wim leersBetter title & IS.
This is technically a BC break, because in the 1.x any entity reference field which has a single target bundle will have its dangling references still show up in the JSON API normalization. With this patch in, they won't anymore, for the sake of consistency: see the comment that #12 adds.
Comment #15
wim leers#13: I think you're referring to #2968972: Cannot PATCH an entity with dangling references in an ER field? That's not what that patch did.
You wrote in #2968972-5: Cannot PATCH an entity with dangling references in an ER field:
This patch does amount to "correcting" the data.
Comment #16
wim leersFailing test-only patch is also the interdiff.
Comment #18
gabesulliceSomething about this just feels wrong. I can see why it's needed, but I don't like it.
I would feel better about this if there were a core issue to fix this "correctly".
Did you consider a "missing" resource identifier? Sorry, I know that explodes the size of the patch /me runs away.
Comment #19
wim leersI'd be fine with this, actually.
It's not that bad at all :)
Comment #20
wim leersNit: D'oh, stupid reformatting.
Comment #21
gabesulliceThis is my only nit. I wish this could be
'type' => 'unknown'.It'd be great if both the
typeand theidwere static and then could be more easily hardcoded into a client.I guess that would mean making
$type_namean argument toResourceType.Comment #22
wim leersWow, only one nit!?
I solved it in a different way than you suggested. Somewhat too clever, but requiring far fewer infra changes. And since it's
@internalanyway, we can change it later if we want.Comment #23
gabesullice😞you're right, I lied. I'm sorry!
This logic already exists in the resource type repository. Something like this will avoid it:
Comment #24
wim leers✔️
Comment #25
gabesullice👏
Comment #26
gabesulliceNeeds https://www.drupal.org/docs/8/modules/json-api/core-concepts#missing to exist :P
Comment #28
gabesulliceNeeds work per #26.
Comment #29
gabesulliceCR published: https://www.drupal.org/node/2996568
Still needs documentation.
Comment #30
wim leersDocs added: https://www.drupal.org/node/2803133/revisions/view/10989525/11107488
Comment #32
rpayanmMoving to Drupal core's issue queue.
I'm working on https://www.drupal.org/project/drupal/issues/3122113