Files
jared 4ce64c7839
Deploy to git-pages / deploy (push) Successful in 20s
Fix CORS: add proxy support for browser-based API calls on git-pages
- Add VITE_PROXY_URL env var to route requests through a CORS proxy when
  deployed as static site (CRDC API doesn't send Access-Control-Allow-Origin)
- Update useApi.js, LoadingAnimation.jsx, and ChartPanel.jsx to respect proxy
- Add nginx.conf with /api/v1/ reverse proxy + CORS headers for Docker deployment
- Include proxy.php — simple PHP CORS proxy for git-pages hosts that support PHP
- Document CORS workaround in README

Without this fix, browser fetch() calls are blocked by same-origin policy and
the app shows a blank white screen despite serving correct HTML.
2026-08-10 11:22:44 -04:00

58 lines
1.8 KiB
PHP

<?php
/**
* Simple CORS proxy for CRDC Arrest Rate API.
*
* Deploy this file to your git-pages host alongside the static site (e.g., at /crdc-demo/proxy.php).
* Then set VITE_PROXY_URL=/crdc-demo/proxy.php in your build environment.
*
* Usage: GET /proxy.php?target=/api/v1/districts?q=Denver&state=CO
*/
// Allow cross-origin requests from any origin
header('Access-Control-Allow-Origin: *');
header('Access-Control-Allow-Methods: GET, OPTIONS');
header('Access-Control-Allow-Headers: *');
header('Content-Type: application/json');
if ($_SERVER['REQUEST_METHOD'] === 'OPTIONS') {
http_response_code(204);
exit;
}
// Extract and validate the target path from query string
$target = isset($_GET['target']) ? $_GET['target'] : '';
if (empty($target)) {
http_response_code(400);
echo json_encode(['error' => 'Missing "target" parameter']);
exit;
}
// Construct the full API URL — only allow requests to crdc-api.civilytics.org for security
$apiBase = 'https://crdc-api.civilytics.org';
$url = $apiBase . $target;
// Validate that we're not proxying arbitrary URLs (prevent SSRF)
if (!str_starts_with($url, $apiBase . '/api/v1/')) {
http_response_code(403);
echo json_encode(['error' => 'Invalid target — must be under /api/v1/']);
exit;
}
// Fetch the API response and return it with CORS headers
$ch = curl_init($url);
curl_setopt_array($ch, [
CURLOPT_RETURNTRANSFER => true,
CURLOPT_FOLLOWLOCATION => true,
CURLOPT_TIMEOUT => 30,
CURLOPT_SSL_VERIFYPEER => false,
]);
$response = curl_exec($ch);
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
// Forward the response with appropriate status code and CORS headers
http_response_code($httpCode);
header('Access-Control-Allow-Origin: *');
echo $response;