Problem/Motivation

This is kind of a strange bug where new block instances are overwriting existing block instances because we do not provide a mechanism for checking for these existing block instances when saving a new block instance.

Steps to Reproduce

To reproduce, simply go to /admin/structure/block/list/ and click on +Place blocks.

  1. Choose to place a block that already contains an instance in the current theme.
  2. For this example: System Help (Note that an instance of System Help with a machine name of 'help' already exists in the 'Help' region.)
  3. Put a new instance of System Help in the 'Header' region and make its machine_name 'help'
  4. After saving your new block instance, you'll see that you still only have one 'System Help' block, but now it is placed in the 'Header' region.

You could even do this with another block type - perhaps place a 'Syndicate' block in a region but make its machine_name equal to 'help' - saving this will remove your old 'System Help' block and replace it with a 'Syndicate' block.

Or watch this video to see this in action: http://screencast.com/t/zRvySXYffdV

Proposed resolution

Create a test that will check for an existing block with the same name, prevent the new block from saving if a duplicate is found, and provide an error message giving the user the opportunity to give the new block a different machine name and resave.

Support from Acquia helps fund testing for Drupal Acquia logo

Comments

saltednut’s picture

Priority: Normal » Critical
Issue tags: +Blocks-Layouts

xjm says this is critical. I concur.

xjm’s picture

Issue tags: +Needs tests
dcam’s picture

So what is the expected behavior in this scenario? I was thinking of writing tests for it, but I don't know what the result should be.

dcam’s picture

http://drupal.org/node/1427826 contains instructions for updating the issue summary with the summary template.

dnmurray’s picture

Assigned: Unassigned » dnmurray

Writing a test that will fail if a block with the same name already exists and it moves or disappears after the save. Assuming that the patch to fix the bug will prevent the save due to the duplicate block name.

jasonyarrington’s picture

Removed needs issue summary update tag

adamdicarlo’s picture

@dnmurray Please visit http://core.drupalofficehours.org/task/2362 (logged in) and indicate that you're working on this so those of us in the code sprint know this task isn't available.

Thanks!

saltednut’s picture

marcingy’s picture

Assigned: dnmurray » marcingy

Working on this hopefully will have test and fix up for review today, initial test will be appearing shortly.

marcingy’s picture

Status: Active » Needs review
FileSize
1.87 KB

Test only patch this should fail.

marcingy’s picture

FileSize
3.05 KB

This fixes the test but smells very wrong.

marcingy’s picture

FileSize
3.73 KB

A some what better version that allows for machine name to be given a prefix, which is the issue here as blocks are prefixed with theme name.

tim.plunkett’s picture

This sounds like a dupe of #1887654: Creating a config entity with an existing machine name shouldn't work, at least the underlying bug.

xjm’s picture

Status: Needs review » Reviewed & tested by the community
Issue tags: -Needs tests

Oh, that's where that issue went. Still, though, I think this can go in as-is to fix the data loss issue. We can generalize it later with #1887654: Creating a config entity with an existing machine name shouldn't work and #2019709: Add an option to machine name elements to increment with a delta instead of failing validation, but this seems fine to me to at least prevent the blithe overwriting through the UI.

xjm’s picture

#12: block-1998664-12.patch queued for re-testing.

xjm’s picture

FileSize
20.81 KB

Patch in action:

validation_error.png

tim.plunkett’s picture

Status: Reviewed & tested by the community » Needs work
Issue tags: +Needs tests
+++ b/core/includes/form.incundefined
@@ -3871,7 +3871,14 @@ function form_validate_machine_name(&$element, &$form_state) {
+    // Certain configuration entities prefix the machine name so add these if

I don't know that form.inc should know/care about "configuration entities".

And the test coverage for this API addition to FAPI should have standalone tests, not coupled to the block UI.

xjm’s picture

Well, such tests won't work since this fix is only FAPI validation...

xjm’s picture

Issue tags: -Needs tests

Ah, to clarify #17, I didn't notice that the validation is being done in form.inc. @tim.plunkett and I agreed that since the prefixing is a Block-only behavior that we probably want to remove anyway, let's just move the validation into the block form instead. (So the tests are correct, but the fix is too general.)

marcingy’s picture

So the patch in https://drupal.org/node/1998664#comment-7483306 instead? Which is a block only version of the validation patch.

tstoeckler’s picture

Field UI does this by adding a #field_prefix to the form element and then manually prepending that in the validate() step. Field UI also adds a < span dir="ltr" > because machine names are always English and, thus, should always be displayed in ltr regardless of the rest of the page. The fact that AFAIK only Field UI does this, however, is a hint IMO that #type machine_name should probably handle that automatically. So I would support adding an #id_prefix property (although it should probably be renamed, as the form type is machine_name) or re-using the #field_prefix for that, if that's possible (although probably not, because of the < span > thing). Field UI could be used as a sample implementation of that as well.

On the other hand, that does sort of seem like scope-screep, since this is a critical bug. Can't the Blocks UI simply add the prefix in validate() as well? Then we can figure out the broader issue in a follow-up.

tstoeckler’s picture

Ahh, I'm sorry I didn't read the issue properly. The Blocks UI already adds the prefix correctly. This is about the #exists callback not getting the correct ID....
Hmm...

sdboyer’s picture

note that, while this will still be a problem, this becomes vastly less of a user WTF when #2022897: Shift responsibility for creating unique config id/machine name off of (views) block plugins and onto BlockFormController goes in.

yched’s picture

xjm’s picture

tim.plunkett’s picture

Status: Needs work » Closed (duplicate)

Back in June, when this was close, it was fine to keep this separate. At this point, it's out of date enough that we should just mark it a dupe of #1887654: Creating a config entity with an existing machine name shouldn't work

tim.plunkett’s picture

Issue summary: View changes

Updated the issue summary.