Scheduler form alter doesn't apply to custom entity form displays

Created on 12 September 2023, over 1 year ago

Problem/Motivation

The Scheduler fields on a custom form display don't appear in the sidebar as expected.

Steps to reproduce

  1. Create a custom form display for an entity.
  2. Display the scheduler fields on the new form display.
  3. Ensure the role you are using has permissions to schedule publishing of this entity.
  4. Compare the default entity add/edit form to the new form display and see the scheduler fields appear differently.

Proposed resolution

In SchedulerPluginBase.php, entityFormIdsByType() custom form displays aren't being added to the returned array of possible form ids to alter in scheduler.module, scheduler_form_alter(). The entity_display.repository service can be used to retrieve these possible displays and include them in the array.

🐛 Bug report
Status

Active

Version

2.0

Component

Code

Created by

🇺🇸United States weekbeforenext Asheville, NC

Live updates comments and jobs are added and updated live.
Sign in to follow issues

Merge Requests

Comments & Activities

  • Issue created by @weekbeforenext
  • Status changed to Needs review over 1 year ago
  • Open in Jenkins → Open on Drupal.org →
    Core: 10.1.x + Environment: PHP 8.1 & MySQL 8
    last update over 1 year ago
    227 pass
  • 🇺🇸United States weekbeforenext Asheville, NC
  • First commit to issue fork.
  • 🇬🇧United Kingdom jonathan1055

    Hi weekbeforenext,
    Thanks for reporting this and for providing a patch. Can you give a little more detail on step 1 'Create a custom form display for an entity' so that I can follow exactly what you are doing. Can you provide a screen shot of the custom display and show how you'd like the fields to appear?

    The addition might need test coverage, are you able to add that? You can use one of the test modules to provide the custom display in case that is easier than making one during the test.

  • Open in Jenkins → Open on Drupal.org →
    Core: 10.1.x + Environment: PHP 8.1 & MySQL 8
    last update over 1 year ago
    227 pass
  • 🇺🇸United States weekbeforenext Asheville, NC

    Maybe this link is helpful: https://www.drupal.org/docs/drupal-apis/entity-api/display-modes-view-mo...

    You can create custom display modes for content view and form modes. Once the display mode exists, you can enable it for the content type and then configure it.

  • 🇬🇧United Kingdom jonathan1055

    Thanks. I have created a custom form mode, ticked the 'custom settings' checkbox on the article 'manage form display' tab, and can customise the fields. That all seems OK, but how do I get to actually use the display when editing content? I just get the default form.

  • 🇺🇸United States weekbeforenext Asheville, NC

    Ah, good question. I'm not 100% sure, but on the site I work on, I can access the custom edit form by visiting /node/[nid]/edit/[form-display]. Let me know if that doesn't work and I can do some further digging.

  • 🇬🇧United Kingdom jonathan1055

    I tried that, and get 'page not found'. I presume [form-display] is the machine name of the form display as shown in admin/structure/display-modes/form when you edit the display. I tried both with and without the leading 'node.'

    I also tried to create a route using the example in entity-api/display-modes-view-modes-and-form-modes#s-form-operations but could not get it right.

    entity.node.custom_edit:
      path: '/node/{id}/custom_edit'
      defaults:
        _entity_form: node.custom_form_mode_for_content
        _title: 'Edit article using custom form mode'
      requirements:
        _permission: 'edit node entities'
    
  • 🇺🇸United States weekbeforenext Asheville, NC

    So it seems it's not very straightforward :\

    I found some resources:
    Adding a display form mode

    In the site I maintain, we are using an EventSubscriber listening for 'onRequest' and redirecting to the form display based on the user's roles.

    It looks something like this, where
    is the machine name of the custom display and is the content type machine name:

    $form_url = Url::fromRoute('node.add.<form-display>', ['node_type' => '<type>']);
    $event->setResponse(new RedirectResponse($form_url->toString()));
    

    Alternatively, it looks like a custom module can provide a link to the route in a menu with something like this in the *.links.menu.yml file, where is the module machine name and is the menu machine name:

    <module-name>.custom_form_display:
      title: 'Add <type>'
      description: 'Create <type>'
      route_name: node.add.<form-display>
      menu_name: <menu-name>
      weight: 0
      route_parameters:
        node_type: '<type>'
      options: []
    

    Why is this so hard?

  • 🇺🇸United States weekbeforenext Asheville, NC

    If we are just looking for a way to manually reproduce/test, we could use this contrib module: https://www.drupal.org/project/form_mode_control

    I would expect that the route is already available within Drupal for an automated test. It's just hard to test manually.

  • Open in Jenkins → Open on Drupal.org →
    Core: 10.1.x + Environment: PHP 8.1 & MySQL 8
    last update over 1 year ago
    227 pass
  • Open in Jenkins → Open on Drupal.org →
    Core: 10.2.x + Environment: PHP 8.1 & MySQL 8
    last update about 1 year ago
    227 pass
  • Open in Jenkins → Open on Drupal.org →
    Core: 10.2.x + Environment: PHP 8.1 & MySQL 8
    last update about 1 year ago
    227 pass
  • Open in Jenkins → Open on Drupal.org →
    Core: 10.2.x + Environment: PHP 8.1 & MySQL 8
    last update about 1 year ago
    227 pass
  • Open in Jenkins → Open on Drupal.org →
    Core: 10.2.x + Environment: PHP 8.1 & MySQL 8
    last update about 1 year ago
    227 pass
  • Open in Jenkins → Open on Drupal.org →
    Core: 10.2.x + Environment: PHP 8.1 & MySQL 8
    last update about 1 year ago
    227 pass
  • 🇬🇧United Kingdom jonathan1055

    Rebased the MR

  • 🇬🇧United Kingdom jonathan1055

    I don't really want to add another 3rd-party module into the testing requirements, we already have lots of those :-)

    I would expect that the route is already available within Drupal for an automated test. It's just hard to test manually.

    I don't follow, can you explain what you mean? Thanks

  • Open in Jenkins → Open on Drupal.org →
    Core: 10.2.x + Environment: PHP 8.1 & MySQL 8
    last update about 1 year ago
    227 pass
  • Open in Jenkins → Open on Drupal.org →
    Core: 10.2.x + Environment: PHP 8.1 & MySQL 8
    last update 12 months ago
    227 pass
  • Status changed to Needs work 5 months ago
  • 🇬🇧United Kingdom jonathan1055

    There is another associated bug when using custom form displays. When the entity type Scheduler settings are modified, for example enabling or disabling scheduled publishing, only the default form mode is updated to add or remove the field. The custom form is not changed, which is a problem. I think a solution is to add the custom form mode(s) into the entityFormDisplayModes() array. I will push an update.

  • 🇬🇧United Kingdom jonathan1055

    Currently when enabling publishing, on save, in _scheduler_form_entity_type_submit(), we get

    $all_display_modes plus DEFAULT_DISPLAY_MODE => Array (
        [0] =&gt; custom_content_fm
        [1] =&gt; default
    )
    $supported_display_modes => Array (
        [0] =&gt; default
    )
    Loop for display_mode 'custom_content_fm'
    Removing publish_on because publishing not enabled or display mode not supported
    Loop for display_mode 'default'
    *** Setting publish_on component
    

    The field is not added to the custom form, becuase the id does not appear in the supported_display_modes array. This is built in the pluginBase entityFormDisplayModes() function.

  • 🇬🇧United Kingdom jonathan1055

    With the change to entityFormDisplayModes() we get

    $supported_display_modes => Array(
        [0] =&gt; default
        [1] =&gt; custom_content_fm
    )
    Loop for display_mode custom_content_fm
    *** Setting publish_on component
    Loop for display_mode default
    *** Setting publish_on component
    

    But is there any downside to adding any/all custom form modes into the the 'supported' array? PluginBase entityFormDisplayModes() was added in 📌 Disable fields in form displays by default Fixed

Production build 0.71.5 2024