Skip to content

CMSEditLinkExtension doesn't work with Hierarchy #1628

Open
@tiller1010

Description

@tiller1010
Original context We have a class that uses both the Hierarchy and CMSEditLinkExtension extensions. After the ParenID is changed, and the ContentLayout is saved, I get the error: `[Emergency] Uncaught LogicException: Could not produce an edit link for the passed object.`

It doesn't look like there is any support for DataObjects in a Hierarchy in the CMSEditLinkExtension. Instead, it looks like it only checks for has_many/has_one relationships: https://github.com/silverstripe/silverstripe-admin/blob/2/code/CMSEditLinkExtension.php#L62

class ContentLayout extends DataObject implements CMSPreviewable
{
  private static $cms_edit_owner = 'Parent';

  private static $extensions = [
    Hierarchy::class,
    CMSEditLinkExtension::class,
  ];

  /*
    CMSEditLink
    Returns the cms edit link for the content layout object
  */
  public function CMSEditLink()
  {
    // Get the value returned by the CMSEditLinkExtension
    return $this->extend('CMSEditLink')[0];
  }

  public function getCMSFields()
  {
    ...
    // Parent Container
    $Parent = TreeDropdownField::create('ParentID', 'Parent', ContentLayout::class)
      ->setEmptyString('Top Level');
    ...
  }
}

If a class has the Hierarchy extension it cannot rely on the Parent relation as the owner relation, because there is no corresponding has_many relation. Hierarchy relies on its own methods to get the related children records.

Developers could choose either of Children() or AllChildren() to put in the GridField so we'd need to check if either of these are editable, and if so return the link for it. They could also implement their own method to link back to the child records, though that would be out of scope.

Note that we also need to validate that the parent record and the child record both share the same hierarchical base class before getting a hierarchical link - otherwise you could have a has_one from MyRandomDataObject to SiteTree, and accidentally try to give a hierarchical link even though they don't share a hierarchical base class.

There's also no way to define what the edit owner is for the root level item in the hierarchy.

e.g:

some admin section
└─ root record
       └─ child record
               └─ grandchild record

The grandchild checks its parent and finds the child. The child checks its parent and finds the root. But the root will try to check its parent and find nothing...

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions