familyHub/api/people_update.php

97 lines
3.0 KiB
PHP

<?php
require_once __DIR__ . '/../includes/api_bootstrap.php';
if ($_SERVER['REQUEST_METHOD'] !== 'POST') {
sendJson(['success' => false, 'error' => 'Method not allowed'], 405);
}
$people = normalizePeopleList(readJsonFile('people.json'));
assertHoHCanManagePeople($people);
$body = readJsonBody();
$id = isset($body['id']) ? trim((string) $body['id']) : '';
if ($id === '') {
sendJson(['success' => false, 'error' => 'id is required'], 400);
}
$idx = null;
foreach ($people as $i => $p) {
if (($p['id'] ?? '') === $id) {
$idx = $i;
break;
}
}
if ($idx === null) {
sendJson(['success' => false, 'error' => 'Person not found'], 404);
}
if (isset($body['name'])) {
$name = trim((string) $body['name']);
if ($name === '') {
sendJson(['success' => false, 'error' => 'Name cannot be empty'], 400);
}
$people[$idx]['name'] = $name;
}
if (array_key_exists('icon', $body)) {
$people[$idx]['icon'] = trim((string) $body['icon']);
}
if (array_key_exists('description', $body)) {
$people[$idx]['description'] = trim((string) $body['description']);
}
if (array_key_exists('birthday', $body)) {
$birthday = trim((string) $body['birthday']);
if ($birthday !== '' && !preg_match('/^\d{4}-\d{2}-\d{2}$/', $birthday)) {
sendJson(['success' => false, 'error' => 'birthday must be YYYY-MM-DD'], 400);
}
$people[$idx]['birthday'] = $birthday;
}
if (array_key_exists('favoriteColor', $body)) {
$c = trim((string) $body['favoriteColor']);
if ($c !== '' && !preg_match('/^#[0-9A-Fa-f]{6}$/', $c)) {
sendJson(['success' => false, 'error' => 'favoriteColor must be a #RRGGBB value'], 400);
}
if ($c !== '') {
$people[$idx]['favoriteColor'] = $c;
}
}
if (array_key_exists('role', $body)) {
$newRole = (string) $body['role'];
$allowedRoles = [ROLE_HEAD, ROLE_ADULT, ROLE_CHILD];
if (!in_array($newRole, $allowedRoles, true)) {
sendJson(['success' => false, 'error' => 'Invalid role'], 400);
}
$wasHead = ($people[$idx]['role'] ?? '') === ROLE_HEAD;
if ($newRole === ROLE_HEAD && !$wasHead) {
$pin = isset($body['pin']) ? (string) $body['pin'] : '';
if (strlen($pin) < 4) {
sendJson(['success' => false, 'error' => 'PIN must be at least 4 characters when promoting to Head of Household'], 400);
}
$people[$idx]['pin_hash'] = password_hash($pin, PASSWORD_DEFAULT);
}
if ($newRole !== ROLE_HEAD && $wasHead) {
$people[$idx]['pin_hash'] = null;
}
$people[$idx]['role'] = $newRole;
}
$headCount = 0;
foreach ($people as $p) {
if (($p['role'] ?? '') === ROLE_HEAD) {
$headCount++;
}
}
if ($headCount < 1) {
sendJson(['success' => false, 'error' => 'At least one Head of Household is required'], 400);
}
if (!writeJsonFile('people.json', $people)) {
sendJson(['success' => false, 'error' => 'Failed to save people'], 500);
}
$safe = $people[$idx];
unset($safe['pin_hash']);
sendJson(['success' => true, 'person' => $safe]);