passbolt/passbolt_api · error · BadRequestException
The record model is not valid.
Error message
The record model is not valid.
What it means
BadRequestException thrown by DirectoryIgnoreController::toggle when the foreignModel path argument, after normalization, is not one of the allowed values Groups, Users, or DirectoryEntries. normalizeForeignModel singularizes/pluralizes the URL segment, so only the canonical model names are accepted; anything else is rejected as an invalid record model.
Solutions
- Use exactly one of the supported model names in the URL: Groups, Users, or DirectoryEntries (case-sensitive).
- Verify the foreignModel argument in the client/script matches the route template and isn't truncated or altered by encoding.
- Confirm the entity type you intend to ignore is actually supported; map custom types to one of the three before calling.
- Check normalizeForeignModel in the controller to see which input forms are accepted, and align the caller with it.
Example fix
// before PUT /directoryignore/group/<uuid>.json // after PUT /directoryignore/groups/<uuid>.json
Defensive patterns
Strategy: validation
Validate before calling
$allowed = ['Groups', 'Users', 'DirectoryEntries'];
if (!in_array(ucfirst($model), $allowed, true)) {
throw new InvalidArgumentException("Unsupported foreignModel '$model'; use one of: " . implode(', ', $allowed));
} Type guard
function isSupportedForeignModel(string $m): bool { return in_array($m, ['Groups', 'Users', 'DirectoryEntries'], true); } Try / catch
try {
$apiClient->put('/directoryignore/' . $model . '/' . $id . '.json');
} catch (BadRequestException $e) {
if ($e->getMessage() === 'The record model is not valid.') {
// correct the model segment to Groups|Users|DirectoryEntries
}
} Prevention
- Keep the supported model list in a shared constant on both client and route definitions.
- Never hand-build URLs with singular/casual model names; validate segments before the call.
- Consult DirectoryIgnoreController::normalizeForeignModel for accepted input forms.
- Write an integration test covering all three valid model values.
When it happens
Trigger: Calling the toggle route with a mistyped or unsupported model segment, e.g. /directoryignore/group/<uuid>.json (singular not normalized as expected), /directoryignore/User/<uuid>, or a model that has no ignore support such as 'Gpgkeys'.
Common situations: Hand-written curl scripts using singular forms; API docs from older plugin versions listing different model names; clients iterating over directory entity types beyond the three supported ones; URL-encoding or trailing-slash artifacts changing the segment.
Understand the failure class
Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.
Related errors
- Invalid request. New key or passwords are not required.
- The identifier should be a valid UUID.
- The metadata key ID should be a valid UUID.
- The metadata key ID should be a valid UUID.
- The metadata key identifier should be a UUID.
AI-assisted analysis of passbolt/passbolt_api@31c1bbc10f (2026-09-17).
Data as JSON: /api/errors/e902b472f5aa4e79.
Report an issue: GitHub.
Appendix: source
Thrown at plugins/PassboltEe/DirectorySync/src/Controller/DirectoryIgnoreController.php:68
/**
* Check if a record is ignored
*
* @param string $foreignModel foreign model
* @param string $foreignKey foreign key
* @throws \App\Error\Exception\ValidationException If the model name or id is not valid
* @throws \Cake\Http\Exception\ForbiddenException if the current user is not an admin
* @return void
*/
public function toggle(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.'));
}
$ignored = null;
try {
$ignored = $this->DirectoryIgnore->get($foreignKey);
$this->DirectoryIgnore->delete($ignored);
} catch (RecordNotFoundException $exception) {
}
$this->success(__('The record is currently ignored as part of directory synchronization.'), $ignored);
}
/**
* Check if a record is ignored
*
* @param string $foreignModel foreign model
* @param string $foreignKey foreign key
* @throws \App\Error\Exception\ValidationException If the model name or id is not valid
* @throws \Cake\Http\Exception\ForbiddenException if the current user is not an adminView on GitHub (pinned to 31c1bbc10f)