passbolt/passbolt_api · critical · Cake\Http\Exception\InternalErrorException
Could not save the user data. Please try again later.
Error message
Could not save the user data. Please try again later.
What it means
InternalErrorException thrown when UsersTable::save() returns false while persisting the edited user (with 'checkrules' => false since rules were already checked). This indicates an unexpected persistence failure — database error, avatar filesystem write failure (the filesystem adapter option is passed to save), or a save() event/behavior aborting — not a client input problem.
Solutions
- Check server logs for the underlying CakePHP/database error accompanying the 500.
- Verify database connectivity and that migrations are up to date (`ddev refresh` / passbolt migration status).
- If avatars are enabled, check the avatar filesystem adapter's storage path permissions and free space.
- Disable recently added plugins that hook into user save events and retry to isolate the aborting listener.
Example fix
// server-side: ensure storage is writable before retrying the request // before sudo chown www-data:www-data /var/www/html/webroot/img/public/Avatar // after sudo chown -R www-data:www-data /var/www/html/webroot/img/public/Avatar && sudo -u www-data test -w /var/www/html/webroot/img/public/Avatar
Defensive patterns
Strategy: retry
Try / catch
try { await api.editUser(id, data); } catch (e) { if (e.code === 500 && /Could not save the user data/.test(e.message)) { await sleep(1000); return retryWithBackoff(() => api.editUser(id, data), 3); } throw e; } Prevention
- Monitor server database health and migration status before bulk user operations.
- Ensure avatar storage has free space and correct permissions.
- Retry with backoff for transient 500s; alert on repeated failures instead of retrying forever.
When it happens
Trigger: PUT /users/{id}.json where validation and rules passed but save() fails: DB unreachable/locked, avatar storage adapter cannot write, an attached model event (e.g. from a plugin) returns false, or a race deleted the row mid-request.
Common situations: Database down or credentials changed; disk full or wrong permissions on the avatar storage path; a plugin's Users event listener aborts saves; migrations out of date so a column is missing.
Related errors
- Could not save the comment, please try again later.
- Could not save the SSO state, please try again later.
- The metadata private key could not be created. Please try…
- The metadata private keys could not be created.
- The SSO state could not be saved.
AI-assisted analysis of passbolt/passbolt_api@31c1bbc10f (2026-09-17).
Data as JSON: /api/errors/9d299f4e23e8e5be.
Report an issue: GitHub.
Appendix: source
Thrown at src/Controller/Users/UsersEditController.php:110
throw new ValidationException(__('Could not validate user data.'), $user, $this->Users);
}
$this->Users->checkRules($user);
if ($user->getErrors()) {
throw new ValidationException(__('Could not validate user data.'), $user, $this->Users);
}
$isBeingDisabled = $wasDisabledNull && !is_null($user->disabled);
// Used when sending after update event
// We need entity's dirty state to know which column values has been changed.
$userEntityWithDirtyState = clone $user;
// Save
$saveOptions = [
'checkrules' => false,
AvatarsTable::FILESYSTEM_ADAPTER_OPTION => $filesystemAdapter,
];
if (!$this->Users->save($user, $saveOptions)) {
throw new InternalErrorException('Could not save the user data. Please try again later.');
}
if ($isBeingDisabled) {
/** @var \App\Model\Table\SecretsTable $secretsTable */
$secretsTable = $this->fetchTable('Secrets');
$secretToExpire = $secretsTable->findByUserId($id)
->select(['id', 'user_id', 'resource_id'])->all()->toArray();
$resourcesExpireResourcesService->expireResourcesForSecrets($secretToExpire);
}
// Get the updated version (ex. Role needs to be fetched again if role_id changed)
try {
/** @var \App\Model\Entity\User $user */
$user = $this->Users->findView($id, $this->User->role())->firstOrFail();
} catch (Exception $exception) {
$msg = __('Could not find the user data after save. Maybe it has been deleted in the meantime.');
throw new InternalErrorException($msg, 500, $exception);
}View on GitHub (pinned to 31c1bbc10f)