Problem/Motivation

I ran into some issues with the version 8.x-4.x in context with the "Drupal Account Provisioning Events" settings.

Situation:
- Drupal 9.0.9
- drupal/ldap dev-4.x

- No checkbox selected at "Drupal Account Provisioning Events"
- LDAP Query configured. Test of query works successfully
- If I run the ldap_user_cron() then the users are updated correctly

Issue 1
At "Drupal Account Provisioning Events" I check "Create or Sync to Drupal user on successful authentication with LDAP credentials" and run the cron again. I get the error Integrity constraint violation: 1062 Duplicate entry 'XXXXXX' for key 'user__name'
This occurrs, because GroupUserUpdateProcessor::runQuery() calls the method drupalUserLogsIn(), which then calls syncToDrupalAccount(), because of this Drupal account provisioning setting.

Issue 2
I get the same "duplicate entry" error, if I check the other checkbox "Create or Sync to Drupal user anytime a Drupal user account is created or updated."
In this case, saving the user causes the ldap_user_user_presave() hook to be called. Which calls drupalUserUpdate() and this again leads into calling syncToDrupalAccount(). Therefore, we run into the same issue.
In this case it also effects the user handling in other places. For instance, I can reproduce the error with this:

$users = $this->entityTypeManager->getStorage('user')->loadMultiple([10, 11]);
foreach ($users as $user) {
   $user->save();
}

If I check the logs afterwards, the error occurs while saving the second user.
Example:
- User 10, username "foo"
- User 11, username "bar"

User 10 updated successfully. While saving user 11, the error appears with the username of user 10, but with uid of user 11.
Duplicate entry 'foo' for key 'user__name' ...... [uid_placeholder] => 11

Comments

marco-s created an issue. See original summary.

marco-s’s picture

I can also reproduce it with the hogwarts demo.

hpotter (uid 6)
hgranger (uid 7)

Integrity constraint violation: 1062 Duplicate entry 'hpotter-en' for key 'user__name': INSERT INTO {users_field_data} (uid, langcode, .... Array ( [:db_insert_placeholder_0] => 7 [:db_insert_placeholder_1] => en

I stepped a little deeper into the process and found out that via doSave() in SqlContentEntityStorage::mapToStorageRecord() the user entity of the second user (hgranger) has the correct values, but $entity->get('name')->value returns the wrong value (hpotter instead of hgranger). Could also be a Drupal related issue? I will analyse this in more detail soon if possible.

grahl’s picture

Status: Active » Fixed

I believe I've fixed this in another issue, unfortunately the DrupalUserProcessor wasn't being reset in the cron runs.

Please let me know if you can still reproduce this on latest dev.

fred r’s picture

Thank you @grahl.
The last dev version fix that bug for me.

Before update : each cron give this error :
Integrity constraint violation: 1062 Duplicate entry

After update :
i've deteled all users.
Run cron --> all users created
Run cron --> no error

Status: Fixed » Closed (fixed)

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

marco-s’s picture

I agree. The latest dev version has solved most of the issues.
Unfortunately, I can still reproduce issue 2, if I have "Create or Sync to Drupal user anytime a Drupal user account is created or updated" selected and save multiple users in a row somewhere in the code.

$users = $this->entityTypeManager->getStorage('user')->loadMultiple([10, 11]);
foreach ($users as $user) {
   $user->save();
}

This breaks user updates in other modules.

marco-s’s picture

The reason for the issue is the assignment of the user's name in DrupalUserProcessor::setLdapBaseFields().

grahl’s picture

marco-s’s picture

@Hendrik, thank you for the link. Drupal::service('ldap.drupal_user_processor')->reset() indeed solves that issue! :)