Files
Webgis-Class/api/helpers/response.php
T
Abimanyu Ridho 5ab7251f4f initial commit
2026-06-11 11:09:32 +07:00

100 lines
3.0 KiB
PHP

<?php
// api/helpers/response.php
function setCORSHeaders(): void {
header('Content-Type: application/json; charset=utf-8');
header('Vary: Origin');
header('Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS');
header('Access-Control-Allow-Headers: Content-Type, Authorization, X-API-Token');
header('X-Content-Type-Options: nosniff');
$origin = $_SERVER['HTTP_ORIGIN'] ?? '';
$allowed = false;
if ($origin !== '') {
$origin = trim($origin);
$allowedOrigins = parseAllowedOrigins(getenv('CORS_ALLOWED_ORIGINS') ?: '');
if (!empty($allowedOrigins)) {
$allowed = in_array($origin, $allowedOrigins, true);
} else {
$allowed = (bool)preg_match('/^https?:\/\/(localhost|127\.0\.0\.1)(:\d+)?$/', $origin);
}
if ($allowed) {
header('Access-Control-Allow-Origin: ' . $origin);
}
}
if (getMethod() === 'OPTIONS') {
http_response_code(($origin !== '' && !$allowed) ? 403 : 204);
exit;
}
}
function parseAllowedOrigins(string $raw): array {
$parts = array_map('trim', explode(',', $raw));
return array_values(array_filter($parts, static fn ($v) => $v !== ''));
}
function sendJSON(mixed $data, int $code = 200): void {
http_response_code($code);
echo json_encode($data, JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);
exit;
}
function sendSuccess(mixed $data = null, string $message = 'OK', int $code = 200): void {
sendJSON(['status' => 'success', 'message' => $message, 'data' => $data], $code);
}
function sendError(string $message, int $code = 400): void {
sendJSON(['status' => 'error', 'message' => $message], $code);
}
function requireWriteAuth(string $method): void {
if (!in_array($method, ['POST', 'PUT', 'DELETE'], true)) {
return;
}
$expected = (string)(getenv('API_WRITE_TOKEN') ?: '');
if ($expected === '') {
return;
}
$provided = (string)($_SERVER['HTTP_X_API_TOKEN'] ?? '');
if ($provided === '') {
$auth = (string)($_SERVER['HTTP_AUTHORIZATION'] ?? '');
if (preg_match('/Bearer\s+(.+)/i', $auth, $m)) {
$provided = trim($m[1]);
}
}
if ($provided === '' || !hash_equals($expected, $provided)) {
sendError('Unauthorized', 401);
}
}
function executeOrFail(mysqli_stmt $stmt, string $defaultMessage = 'Operasi database gagal'): void {
if ($stmt->execute()) {
return;
}
$errno = $stmt->errno;
$error = $stmt->error;
error_log('DB stmt error [' . $errno . ']: ' . $error);
if ($errno === 1062) {
sendError('Data duplikat terdeteksi', 409);
}
if ($errno === 1451 || $errno === 1452) {
sendError('Relasi data tidak valid', 422);
}
sendError($defaultMessage, 500);
}
function getBody(): array {
$raw = file_get_contents('php://input');
$data = json_decode($raw, true);
return is_array($data) ? $data : [];
}
function getMethod(): string {
return strtoupper($_SERVER['REQUEST_METHOD']);
}