Skip to content

Commit 0dcaa1d

Browse files
Preserve retention metadata for non-admins
Replace inline unsets with restoreProcessRetentionPropertiesFromOriginal. For non-administrator updates, reapply retention-related keys (retention_updated_by, retention_updated_at, retention_period) from the original model snapshot—decoding string-encoded properties if needed—and restore or remove keys to match the original state. This prevents non-admins from adding or modifying retention metadata and handles different properties formats robustly.
1 parent 4192138 commit 0dcaa1d

1 file changed

Lines changed: 36 additions & 4 deletions

File tree

ProcessMaker/Http/Controllers/Api/ProcessController.php

Lines changed: 36 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -601,11 +601,9 @@ public function update(Request $request, Process $process)
601601
}
602602
}
603603

604-
// Prevent non-administrators from updating the retention period
604+
// Non-administrators cannot change retention metadata: persist pre-request values.
605605
if (!auth()->user()->is_administrator) {
606-
unset($process->properties['retention_updated_by']);
607-
unset($process->properties['retention_updated_at']);
608-
unset($process->properties['retention_period']);
606+
$this->restoreProcessRetentionPropertiesFromOriginal($process, $original);
609607
}
610608

611609
// Catch errors to send more specific status
@@ -677,6 +675,40 @@ private function validateMaxManagers(Request $request)
677675
return $managerIds;
678676
}
679677

678+
/**
679+
* Re-apply retention-related keys on $process->properties from the model snapshot taken before fill().
680+
* Non-admins cannot add these keys if absent originally, or change values if present.
681+
*
682+
* @param array<string, mixed> $original
683+
*/
684+
private function restoreProcessRetentionPropertiesFromOriginal(Process $process, array $original): void
685+
{
686+
$originalProperties = $original['properties'] ?? null;
687+
if (is_string($originalProperties)) {
688+
$decoded = json_decode($originalProperties, true);
689+
$originalProperties = is_array($decoded) ? $decoded : [];
690+
}
691+
if (!is_array($originalProperties)) {
692+
$originalProperties = [];
693+
}
694+
695+
$properties = $process->properties;
696+
if (!is_array($properties)) {
697+
$properties = [];
698+
}
699+
700+
$keys = ['retention_updated_by', 'retention_updated_at', 'retention_period'];
701+
foreach ($keys as $key) {
702+
if (array_key_exists($key, $originalProperties)) {
703+
$properties[$key] = $originalProperties[$key];
704+
} else {
705+
unset($properties[$key]);
706+
}
707+
}
708+
709+
$process->properties = $properties;
710+
}
711+
680712
/**
681713
* Validate the structure of stages.
682714
*

0 commit comments

Comments
 (0)