passbolt/passbolt_api · error · NotFoundException
AssociatedRecordExists
AssociatedRecordExists
Error message
$errors['id']['AssociatedRecordExists'] (dynamic validation error message)
What it means
Raised in add() when DirectoryIgnore->createOrFail() fails validation with the 'AssociatedRecordExists' rule on the id field. It means the referenced user/group/directory-entry does not exist in the main application tables, so an ignore row cannot be created; the controller converts this validation error into an HTTP 404 NotFoundException carrying the dynamic validation message.
Solutions
- Verify the entity exists first (GET /users/{uuid}, /groups/{uuid}) before marking it ignored
- Refresh the id from a current listing instead of a cached/stale source
- Check you are calling the correct environment's API for that uuid
- Handle 404 in the client as 'associated record missing' and resync directory entries
Example fix
// before: post with deleted user id → 404
$api->ignore('users', $deletedUserId);
// after: guard first
if ($api->userExists($userId)) { $api->ignore('users', $userId); } Defensive patterns
Strategy: validation
Validate before calling
try {
$api->get("/{$model}/{$id}.json");
} catch (NotFoundException $e) {
throw new \RuntimeException("cannot ignore $model $id: record does not exist");
} Try / catch
try {
$api->post("/directoryignore/{$model}/{$id}.json");
} catch (NotFoundException $e) {
// 404 with AssociatedRecordExists: referenced user/group/entry not found
// resync directory entries or fix the uuid
} Prevention
- Verify the target entity exists before marking it ignored
- Keep ids fresh from live listings, not cached exports
- Watch for cross-environment uuid mix-ups
When it happens
Trigger: POST /directoryignore/users/{uuid} where the uuid does not match any existing Users row (same for Groups/DirectoryEntries), e.g. a deleted entity id or a fabricated uuid.
Common situations: Syncing stale directory data whose linked passbolt user was deleted; ids taken from an old export; mixing uuids across environments (staging vs production); typos when hand-crafting requests.
Understand the failure class
Background: "Not found" and "does not exist" errors: why "Task not found", "No such folder", and "Can't find" fire when a lookup comes back empty — this error's family across 14 libraries.
Related errors
- group(s) returned by your directory are invalid and will be…
- users returned by your directory are invalid and will be…
- Could not validate directory entry data.
- Could not validate user data.
- Directory settings are invalid:
AI-assisted analysis of passbolt/passbolt_api@31c1bbc10f (2026-09-17).
Data as JSON: /api/errors/55d0046b16816f88.
Report an issue: GitHub.
Appendix: source
Thrown at plugins/PassboltEe/DirectorySync/src/Controller/DirectoryIgnoreController.php:134
* @return void
*/
public function add(string $foreignModel, string $foreignKey): void
{
if ($this->User->role() !== Role::ADMIN) {
throw new ForbiddenException(__('You are not authorized to access that location.'));
}
$this->assertDirectoryEnabled();
$foreignModel = $this->normalizeForeignModel($foreignModel);
if (!Validation::inList($foreignModel, ['Groups', 'Users', 'DirectoryEntries'])) {
throw new BadRequestException(__('The record model is not valid.'));
}
try {
$ignored = $this->DirectoryIgnore->createOrFail($foreignModel, $foreignKey);
} catch (ValidationException $exception) {
$errors = $exception->getEntity()->getErrors();
if (isset($errors['id']['AssociatedRecordExists'])) {
throw new NotFoundException($errors['id']['AssociatedRecordExists']);
}
throw $exception;
}
$this->success(__('The record will be ignored in the next directory synchronization.'), $ignored);
}
/**
* Delete
*
* @param string $foreignModel foreign model
* @param string $foreignKey foreign key
* @return void
*/
public function delete(string $foreignModel, string $foreignKey): void
{
if ($this->User->role() !== Role::ADMIN) {
throw new ForbiddenException(__('You are not authorized to access that location.'));
}View on GitHub (pinned to 31c1bbc10f)