Overview

When making changes to overrides within the code editor, the updates do not take effect in preview unless the changes are published. This results in confusion for users who expect to verify changes to overrides after making changes.

Steps to reproduce

  1. Ensure xb_dev_js_blocks as this provide block overrides which you can't make from the UI yet
  2. Open XB and open code editor for one of the overrides (e.g., branding)
  3. Make changes to the override
  4. Drag the dynamic component being overridden to the page
  5. Observe that the modified overrides are not applied
  6. Publish the project, and then note that the override changes finally appear

Proposed resolution

User interface changes

Command icon Show commands

Start within a Git clone of the project using the version control instructions.

Or, if you do not have SSH keys set up on git.drupalcode.org:

Comments

lauriii created an issue. See original summary.

balintbrews’s picture

I started seeing this problem with regular code components as well. Before updating the issue title and summary, can you please confirm, @lauriii? This seems like a regression after 0.2.0-alpha1.

wim leers’s picture

Component: Page builder » Component sources
Assigned: Unassigned » lauriii
Status: Active » Postponed (maintainer needs more info)
Issue tags: +Needs steps to reproduce
Related issues: +#3512385: Changes to code components are not visible in global regions until published

LOL, I independently found the same bug at #3512385-5: Changes to code components are not visible in global regions until published while digging into #3512385: Changes to code components are not visible in global regions until published — they both have the same root cause.

Actually, the issue summary is way too ambiguous:

the updates do not take effect in preview

Which preview?

  1. The one in the code component editor?
  2. The one when hovering the component list?
  3. The XB canvas' preview of a content entity's component tree?

It kinda sounds like it's #1, but then the STR make it sound like it's #3.

If it's #3: does that "block override code component" (which is highly experimental!) happen to be placed in a page region, or in the content entity's XB field? If it's in a page region, this is a duplicate of #3512385: Changes to code components are not visible in global regions until published.

lauriii’s picture

Assigned: lauriii » Unassigned
Status: Postponed (maintainer needs more info) » Active
Issue tags: -Needs steps to reproduce

It is number 3, the XB canvas' preview. This is different from #3512385: Changes to code components are not visible in global regions until published because with overrides, the block doesn't have to be placed in a page region for this bug to occur.

wim leers’s picture

Title: Changes to overrides are not loaded unless published » Auto-saved changes to the (highly experimental) "block override" code components are not visible until published
Priority: Critical » Major
Issue tags: +sprint

Thanks for confirming/clarifying.

The culprit is \Drupal\experience_builder\Plugin\ExperienceBuilder\ComponentSource\BlockComponent::renderComponent()'s:

    // ⚠️ Highly experimental: allow a Block plugin's Twig template to be
    // overridden and rendered using an XB JavaScriptComponent instead.
    $js_overrides = $this->entityTypeManager
      ->getStorage(JavaScriptComponent::ENTITY_TYPE_ID)
      ->loadByProperties([
        'block_override' => $block->getBaseId(),
        'status' => TRUE,
      ]);
    // ⚠️ This assumes that all such overrides are accessible to all users! If
    // that were not the case, presentation of the same block would vary between
    // users, which is unacceptable.
    // Therefore, this assumes that every user, even anonymous users, can access
    // the rendered result of the found JavaScriptComponent.
    // @see \Drupal\experience_builder\Element\AstroIsland::preRenderIsland()
    // @see https://www.drupal.org/project/experience_builder/issues/3508694
    if (count($js_overrides) == 1) {
      $js_component_for_block_base_plugin = reset($js_overrides);
      assert($js_component_for_block_base_plugin instanceof JavaScriptComponent);
      $build['#theme'] = 'block__' . strtr($build['#base_plugin_id'], '-', '_') . '__as_js_component';
      $build['#js_component'] = $js_component_for_block_base_plugin;
      // Update cacheability.
      $build['#cache']['tags'] = $js_component_for_block_base_plugin->getCacheTags();
      $build['#cache']['contexts'] = $js_component_for_block_base_plugin->getCacheContexts();
      $build['#cache']['max-age'] = $js_component_for_block_base_plugin->getCacheMaxAge();
    }

… because that doesn't perform auto-save checking, because everything that #3505993: Code Components as Block Overrides, step 1 did was a highly experimental hack 😅

Which is why to make this code component auto-save load, we're now needing to modify the block ComponentSource! 🤪

We can hack this further for now, but we really need to work to refactor all the ⚠️ Highly experimental comments away: they're there for a reason!

Demoting priority, because such experimental features cannot be critical.

wim leers’s picture

Status: Active » Needs work

The fix is:

diff --git a/experience_builder.block_overrides.inc b/experience_builder.block_overrides.inc
index 1b396acf4..f41b45c38 100644
--- a/experience_builder.block_overrides.inc
+++ b/experience_builder.block_overrides.inc
@@ -172,7 +172,7 @@ function _experience_builder_render_js_component_from_block_element(array $block
   //   through an intermediary ephemeral Component entity?
   $source = JsComponent::createConfigEntity($js_component)->getComponentSource();
 
-  $build = $source->renderComponent(['props' => $props], $instance_uuid);
+  $build = $source->renderComponent(['props' => $props], $instance_uuid, TRUE);
   assert($source instanceof JsComponent);
   $source->setSlots($build, $slots);
   return $build;

… except that the TRUE cannot be hardcoded, but should happen only when appropriate, as described over at #3512385-4: Changes to code components are not visible in global regions until published.

IMHO it's fine to hard-code this as-is, which would result in the auto-saved "block override" code component to be visible even OUTSIDE XB's UI. IMHO that's fine because this is a highly experimental feature that needs to be rewritten anyway into its own component source plugin, which means it's a waste of time to work on passing "XB preview or not" context into this. If we can figure it out in <30 mins, we can do that, otherwise should just commit that one-liner IMHO.

wim leers’s picture

tedbow’s picture

Issue summary: View changes

updating summary to mention xb_dev_js_blocks as I think you need that because you can't make overrides from the UI yet

tedbow’s picture

Assigned: Unassigned » tedbow

working on this

tedbow’s picture

Assigned: tedbow » Unassigned
Status: Needs work » Needs review

I have test coverage that proves the auto-saved version is used in the layout preview but not elsewhere.

I am not sure if the best place for the test coverage but it works

wim leers’s picture

Assigned: Unassigned » wim leers
wim leers’s picture

Assigned: wim leers » Unassigned
Status: Needs review » Reviewed & tested by the community

  • wim leers committed 0f6f5ac2 on 0.x authored by tedbow
    Issue #3513144 by wim leers, tedbow, lauriii, balintbrews: Auto-saved...
wim leers’s picture

Status: Reviewed & tested by the community » Fixed
nagwani’s picture

Issue tags: -sprint
mayur-sose’s picture

Status: Fixed » Needs review

The issue still persists. I followed the same steps as mentioned in the overview. Please refer to the attached video for a detailed walkthrough of the issue:
https://drive.google.com/file/d/1Tvq2zRr-N6bZYwma8nrFgmjfquoJoBUu/view?u...

wim leers’s picture

@mayur-sose The video is inaccessible, can you make it publicly available? 🙏

wim leers’s picture

Assigned: Unassigned » tedbow
Status: Needs review » Needs work
tedbow’s picture

Assigned: tedbow » mayur-sose
Status: Needs work » Needs review
StatusFileSize
new19.64 MB
new18.73 MB

Investigating.

@mayur-sose, small point but the video shows the steps in slightly different order than the summary

From the summary

  1. Ensure xb_dev_js_blocks as this provide block overrides which you can't make from the UI yet
  2. Open XB and open code editor for one of the overrides (e.g., branding)
  3. Make changes to the override
  4. Drag the dynamic component being overridden to the page
  5. Observe that the modified overrides are not applied
  6. Publish the project, and then note that the override changes finally appear

In the video, step 4, dragging the component on, was done before step 2 and 3, editing the override.

In any case both orders should work.

I tested both orders and they worked for me. I have attached screen recordings.

It very well could be that something in the last 18 days since @mayur-sose posted his screen recording that some other commit fixed this.

@mayur-sose can you test this again with both editing the override and then dragging it on, as the summary says and dragging it on and then editing it.

Thanks

tedbow’s picture

Since #3508922: Regression after #3500386: import map scope mismatch when previewed code component's JS is a 307 due to it not having an auto-save/draft just landed another merge request I test this again because it does relate to auto-save. Both situations I described in #20 still work

mayur-sose’s picture

Assigned: mayur-sose » Unassigned
Status: Needs review » Fixed

This issue has been fixed and working as expected. Thanks @tedbow !

Status: Fixed » Closed (fixed)

Automatically closed - issue fixed for 2 weeks with no activity.