Update car monitor asset reload and telemetry
This commit is contained in:
1 parent
6f965f8f3e
commit
5d75ad81bd
6 files changed
+128
-160
No files matched your search
+2
-3
@@ -59,12 +59,11 @@ $assets = [];
|
|||||||
foreach (collect_asset_files($root, $scanRoots) as $fullPath) {
|
foreach (collect_asset_files($root, $scanRoots) as $fullPath) {
|
||||||
$relativePath = ltrim(str_replace($rootPath ?: $root, '', $fullPath), DIRECTORY_SEPARATOR);
|
$relativePath = ltrim(str_replace($rootPath ?: $root, '', $fullPath), DIRECTORY_SEPARATOR);
|
||||||
$fileHash = is_readable($fullPath) ? (hash_file('sha256', $fullPath) ?: 'hash-failed') : 'unreadable';
|
$fileHash = is_readable($fullPath) ? (hash_file('sha256', $fullPath) ?: 'hash-failed') : 'unreadable';
|
||||||
$fileVersion = (string)filemtime($fullPath) . '-' . substr($fileHash, 0, 10);
|
$fileVersion = substr($fileHash, 0, 16);
|
||||||
$publicPath = '/car/' . str_replace(DIRECTORY_SEPARATOR, '/', $relativePath);
|
$publicPath = '/custom/car/' . str_replace(DIRECTORY_SEPARATOR, '/', $relativePath);
|
||||||
$fingerprints[] = implode('|', [
|
$fingerprints[] = implode('|', [
|
||||||
ltrim($publicPath, '/'),
|
ltrim($publicPath, '/'),
|
||||||
(string)filesize($fullPath),
|
(string)filesize($fullPath),
|
||||||
(string)filemtime($fullPath),
|
|
||||||
$fileHash,
|
$fileHash,
|
||||||
]);
|
]);
|
||||||
$assets[$publicPath] = $fileVersion;
|
$assets[$publicPath] = $fileVersion;
|
||||||
|
|||||||
@@ -214,20 +214,23 @@
|
|||||||
}).then(function (data) {
|
}).then(function (data) {
|
||||||
if (!data || data.result !== 'ok' || !data.version) return;
|
if (!data || data.result !== 'ok' || !data.version) return;
|
||||||
|
|
||||||
var token = data.version.slice(0, 12);
|
|
||||||
var previous = storeGet(storageKey);
|
var previous = storeGet(storageKey);
|
||||||
var mismatch = loadedAssetMismatch(data.assets);
|
var versionChanged = previous && previous !== data.version;
|
||||||
var forceReload = bfcacheReturn;
|
var latestToken = String(data.version).slice(0, 12);
|
||||||
|
var hasLatestToken = assetTokenFromLocation() === latestToken;
|
||||||
|
var mismatch = !hasLatestToken && loadedAssetMismatch(data.assets);
|
||||||
|
var wasBfcacheReturn = bfcacheReturn;
|
||||||
bfcacheReturn = false;
|
bfcacheReturn = false;
|
||||||
storeSet(storageKey, data.version);
|
storeSet(storageKey, data.version);
|
||||||
|
|
||||||
if (assetTokenFromLocation() !== token || mismatch || forceReload) {
|
if ((mismatch || wasBfcacheReturn) && !hasLatestToken) {
|
||||||
reloadWith(data.version, mismatch || forceReload);
|
reloadWith(data.version, true);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (previous && previous !== data.version) {
|
if (versionChanged) {
|
||||||
reloadWith(data.version, false);
|
reloadWith(data.version, false);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
}).then(function () {
|
}).then(function () {
|
||||||
running = false;
|
running = false;
|
||||||
|
|||||||
@@ -2,21 +2,21 @@
|
|||||||
"name": "Car Monitor",
|
"name": "Car Monitor",
|
||||||
"short_name": "Car Monitor",
|
"short_name": "Car Monitor",
|
||||||
"description": "Vehicle status monitor",
|
"description": "Vehicle status monitor",
|
||||||
"start_url": "/car/monitor.php?pwa=1",
|
"start_url": "/custom/car/monitor.php?pwa=1",
|
||||||
"scope": "/car/",
|
"scope": "/custom/car/",
|
||||||
"display": "standalone",
|
"display": "standalone",
|
||||||
"orientation": "portrait",
|
"orientation": "portrait",
|
||||||
"background_color": "#0f172a",
|
"background_color": "#0f172a",
|
||||||
"theme_color": "#0f172a",
|
"theme_color": "#0f172a",
|
||||||
"icons": [
|
"icons": [
|
||||||
{
|
{
|
||||||
"src": "/car/assets/icon-192.png",
|
"src": "/custom/car/assets/icon-192.png",
|
||||||
"sizes": "192x192",
|
"sizes": "192x192",
|
||||||
"type": "image/png",
|
"type": "image/png",
|
||||||
"purpose": "any maskable"
|
"purpose": "any maskable"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"src": "/car/assets/icon-512.png",
|
"src": "/custom/car/assets/icon-512.png",
|
||||||
"sizes": "512x512",
|
"sizes": "512x512",
|
||||||
"type": "image/png",
|
"type": "image/png",
|
||||||
"purpose": "any maskable"
|
"purpose": "any maskable"
|
||||||
|
|||||||
+73
-3
@@ -3,7 +3,7 @@ declare(strict_types=1);
|
|||||||
|
|
||||||
date_default_timezone_set('Asia/Seoul');
|
date_default_timezone_set('Asia/Seoul');
|
||||||
|
|
||||||
$carSecretFile = '/home/seo/secret/car.php';
|
$carSecretFile = __DIR__ . '/../../config/car.php';
|
||||||
if (!is_file($carSecretFile)) {
|
if (!is_file($carSecretFile)) {
|
||||||
throw new RuntimeException('Missing car secret config: ' . $carSecretFile);
|
throw new RuntimeException('Missing car secret config: ' . $carSecretFile);
|
||||||
}
|
}
|
||||||
@@ -40,6 +40,7 @@ define('ALLOWED_IPS', array_values(array_filter(
|
|||||||
const ALLOWED_CMD = ['se', 'ef', 'en', 'hn', 'hf', 'dl', 'du', 'tu'];
|
const ALLOWED_CMD = ['se', 'ef', 'en', 'hn', 'hf', 'dl', 'du', 'tu'];
|
||||||
const CONTROL_CMD = ['ef', 'en', 'hn', 'hf', 'dl', 'du', 'tu'];
|
const CONTROL_CMD = ['ef', 'en', 'hn', 'hf', 'dl', 'du', 'tu'];
|
||||||
const CARRIER_BILLING_UNIT_BYTES = 512;
|
const CARRIER_BILLING_UNIT_BYTES = 512;
|
||||||
|
const TCP_STALE_QUEUE_BATCH_LIMIT = 200;
|
||||||
|
|
||||||
const RAW_FULL_REGEX = '/(?<modem>\d{11})\/R:(?<r>[a-z])\/E:(?<E0>[io]{5}\d{3}[io])\/D:(?<D0>[oi]{7})\/L:(?<L0>o{5})\/F:(?<F0>[ots][oi]\d{4}[oi]{4})\/S:(?<S0>[^\/]+)/';
|
const RAW_FULL_REGEX = '/(?<modem>\d{11})\/R:(?<r>[a-z])\/E:(?<E0>[io]{5}\d{3}[io])\/D:(?<D0>[oi]{7})\/L:(?<L0>o{5})\/F:(?<F0>[ots][oi]\d{4}[oi]{4})\/S:(?<S0>[^\/]+)/';
|
||||||
|
|
||||||
@@ -271,7 +272,7 @@ function tcp_queue_update(PDO $pdo, string $requestId, array $values): void
|
|||||||
|
|
||||||
function tcp_queue_insert(string $cmd, string $usageSource, string $requestId): array
|
function tcp_queue_insert(string $cmd, string $usageSource, string $requestId): array
|
||||||
{
|
{
|
||||||
$pdo = db();
|
$pdo = db(true);
|
||||||
db_ensure_tcp_queue_schema($pdo);
|
db_ensure_tcp_queue_schema($pdo);
|
||||||
|
|
||||||
$now = microtime(true);
|
$now = microtime(true);
|
||||||
@@ -305,6 +306,25 @@ function tcp_queue_insert(string $cmd, string $usageSource, string $requestId):
|
|||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function tcp_queue_has_pending_collector_se(PDO $pdo): bool
|
||||||
|
{
|
||||||
|
db_ensure_tcp_queue_schema($pdo);
|
||||||
|
tcp_queue_expire_queued_before_send($pdo);
|
||||||
|
|
||||||
|
$stmt = $pdo->prepare("
|
||||||
|
SELECT 1
|
||||||
|
FROM car_tcp_request_queue
|
||||||
|
WHERE source = 'collector_se'
|
||||||
|
AND cmd = 'se'
|
||||||
|
AND status IN ('queued', 'processing', 'ui_timeout_pending')
|
||||||
|
AND usage_deadline_ts > :now
|
||||||
|
LIMIT 1
|
||||||
|
");
|
||||||
|
$stmt->execute([':now' => microtime(true)]);
|
||||||
|
|
||||||
|
return (bool)$stmt->fetchColumn();
|
||||||
|
}
|
||||||
|
|
||||||
function tcp_queue_get(string $requestId): ?array
|
function tcp_queue_get(string $requestId): ?array
|
||||||
{
|
{
|
||||||
$pdo = db();
|
$pdo = db();
|
||||||
@@ -323,7 +343,16 @@ function tcp_queue_claim_next(PDO $pdo): ?array
|
|||||||
|
|
||||||
$pdo->beginTransaction();
|
$pdo->beginTransaction();
|
||||||
try {
|
try {
|
||||||
$stmt = $pdo->query("SELECT * FROM car_tcp_request_queue WHERE status = 'queued' ORDER BY id ASC LIMIT 1 FOR UPDATE");
|
$stmt = $pdo->query("
|
||||||
|
SELECT *
|
||||||
|
FROM car_tcp_request_queue
|
||||||
|
WHERE status = 'queued'
|
||||||
|
ORDER BY
|
||||||
|
CASE WHEN cmd IN ('ef', 'en', 'hn', 'hf', 'dl', 'du', 'tu') THEN 0 ELSE 1 END,
|
||||||
|
id ASC
|
||||||
|
LIMIT 1
|
||||||
|
FOR UPDATE
|
||||||
|
");
|
||||||
$row = $stmt->fetch();
|
$row = $stmt->fetch();
|
||||||
if (!$row) {
|
if (!$row) {
|
||||||
$pdo->commit();
|
$pdo->commit();
|
||||||
@@ -356,8 +385,36 @@ function tcp_queue_has_usage(PDO $pdo, string $requestId): bool
|
|||||||
return (bool)$stmt->fetchColumn();
|
return (bool)$stmt->fetchColumn();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function tcp_queue_expire_queued_before_send(PDO $pdo): void
|
||||||
|
{
|
||||||
|
$stmt = $pdo->prepare("
|
||||||
|
UPDATE car_tcp_request_queue
|
||||||
|
SET status = 'expired_before_send',
|
||||||
|
updated_at = :updated_at,
|
||||||
|
tcp_ok = 0,
|
||||||
|
tcp_error = 'queue_expired_before_send',
|
||||||
|
sent_bytes = 0,
|
||||||
|
received_bytes = 0,
|
||||||
|
total_bytes = 0,
|
||||||
|
connect_ms = 0,
|
||||||
|
read_ms = 0,
|
||||||
|
tcp_ms = 0
|
||||||
|
WHERE status = 'queued'
|
||||||
|
AND ui_deadline_ts > 0
|
||||||
|
AND ui_deadline_ts < :now
|
||||||
|
ORDER BY id ASC
|
||||||
|
LIMIT " . TCP_STALE_QUEUE_BATCH_LIMIT
|
||||||
|
);
|
||||||
|
$stmt->execute([
|
||||||
|
':updated_at' => tcp_queue_now(),
|
||||||
|
':now' => microtime(true),
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
|
||||||
function tcp_queue_recover_stale(PDO $pdo): void
|
function tcp_queue_recover_stale(PDO $pdo): void
|
||||||
{
|
{
|
||||||
|
tcp_queue_expire_queued_before_send($pdo);
|
||||||
|
|
||||||
$now = microtime(true);
|
$now = microtime(true);
|
||||||
$stmt = $pdo->prepare("
|
$stmt = $pdo->prepare("
|
||||||
SELECT *
|
SELECT *
|
||||||
@@ -684,6 +741,19 @@ function tcp_request(
|
|||||||
$requestId = substr(bin2hex(random_bytes(16)), 0, 32);
|
$requestId = substr(bin2hex(random_bytes(16)), 0, 32);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ($cmd === 'se' && $usageSource === 'collector_se') {
|
||||||
|
try {
|
||||||
|
if (tcp_queue_has_pending_collector_se(db(true))) {
|
||||||
|
$tcpError = 'skipped_duplicate_pending_collector_se';
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
} catch (Throwable $e) {
|
||||||
|
$tcpError = 'queue_pending_check_failed';
|
||||||
|
record_tcp_usage($usageSource, $cmd, 0, 0, false, $tcpError, $requestId);
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
tcp_queue_insert($cmd, $usageSource, $requestId);
|
tcp_queue_insert($cmd, $usageSource, $requestId);
|
||||||
} catch (Throwable $e) {
|
} catch (Throwable $e) {
|
||||||
|
|||||||
+38
-142
@@ -3,7 +3,9 @@ declare(strict_types=1);
|
|||||||
|
|
||||||
date_default_timezone_set('Asia/Seoul');
|
date_default_timezone_set('Asia/Seoul');
|
||||||
|
|
||||||
$carSecretFile = '/home/seo/secret/car.php';
|
require_once __DIR__ . '/../common/auth.php';
|
||||||
|
|
||||||
|
$carSecretFile = __DIR__ . '/../../config/car.php';
|
||||||
if (!is_file($carSecretFile)) {
|
if (!is_file($carSecretFile)) {
|
||||||
throw new RuntimeException('Missing car secret config: ' . $carSecretFile);
|
throw new RuntimeException('Missing car secret config: ' . $carSecretFile);
|
||||||
}
|
}
|
||||||
@@ -19,8 +21,6 @@ define('DB_CHARSET', (string)($carDbConfig['charset'] ?? 'utf8mb4'));
|
|||||||
|
|
||||||
const LOG_LIMIT = 300;
|
const LOG_LIMIT = 300;
|
||||||
const CHART_LIMIT = 500;
|
const CHART_LIMIT = 500;
|
||||||
const CAR_MONITOR_COOKIE = 'car_monitor_access';
|
|
||||||
const CAR_MONITOR_AUTH_TTL = 2592000;
|
|
||||||
const CAR_MONITOR_SETTINGS_COOKIE = 'car_monitor_settings_access';
|
const CAR_MONITOR_SETTINGS_COOKIE = 'car_monitor_settings_access';
|
||||||
const CAR_MONITOR_SETTINGS_TTL = 900;
|
const CAR_MONITOR_SETTINGS_TTL = 900;
|
||||||
const CAR_MONITOR_SETTINGS_PASSWORD = '1026!)Corjs';
|
const CAR_MONITOR_SETTINGS_PASSWORD = '1026!)Corjs';
|
||||||
@@ -40,14 +40,13 @@ const DATA_CURRENT_BILLING_USAGE_BYTES = [
|
|||||||
|
|
||||||
function car_asset_url(string $path): string
|
function car_asset_url(string $path): string
|
||||||
{
|
{
|
||||||
$relativePath = preg_replace('#^/car/#', '', $path) ?? ltrim($path, '/');
|
$relativePath = preg_replace('#^/custom/car/#', '', $path) ?? ltrim($path, '/');
|
||||||
$fullPath = __DIR__ . '/' . ltrim($relativePath, '/');
|
$fullPath = __DIR__ . '/' . ltrim($relativePath, '/');
|
||||||
$version = 'dev';
|
$version = 'dev';
|
||||||
|
|
||||||
if (is_file($fullPath)) {
|
if (is_file($fullPath)) {
|
||||||
$mtime = filemtime($fullPath) ?: time();
|
$hash = is_readable($fullPath) ? substr(hash_file('sha256', $fullPath) ?: '', 0, 16) : '';
|
||||||
$hash = is_readable($fullPath) ? substr(hash_file('sha256', $fullPath) ?: '', 0, 10) : '';
|
$version = $hash !== '' ? $hash : 'unreadable';
|
||||||
$version = $mtime . ($hash !== '' ? '-' . $hash : '');
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return $path . '?v=' . rawurlencode($version);
|
return $path . '?v=' . rawurlencode($version);
|
||||||
@@ -879,62 +878,13 @@ function car_monitor_cookie_options(int $expires): array
|
|||||||
{
|
{
|
||||||
return [
|
return [
|
||||||
'expires' => $expires,
|
'expires' => $expires,
|
||||||
'path' => '/car/',
|
'path' => '/custom/car/',
|
||||||
'secure' => (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off'),
|
'secure' => (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off'),
|
||||||
'httponly' => true,
|
'httponly' => true,
|
||||||
'samesite' => 'Strict',
|
'samesite' => 'Strict',
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
function car_monitor_cookie_value(int $expires, bool $admin = false): string
|
|
||||||
{
|
|
||||||
$body = base64_encode(json_encode([
|
|
||||||
'exp' => $expires,
|
|
||||||
'iat' => time(),
|
|
||||||
'admin' => $admin,
|
|
||||||
], JSON_UNESCAPED_SLASHES));
|
|
||||||
$sig = hash_hmac('sha256', $body, car_monitor_cookie_secret());
|
|
||||||
|
|
||||||
return $body . '.' . $sig;
|
|
||||||
}
|
|
||||||
|
|
||||||
function car_monitor_issue_cookie(bool $admin = false): void
|
|
||||||
{
|
|
||||||
$expires = time() + CAR_MONITOR_AUTH_TTL;
|
|
||||||
setcookie(CAR_MONITOR_COOKIE, car_monitor_cookie_value($expires, $admin), car_monitor_cookie_options($expires));
|
|
||||||
}
|
|
||||||
|
|
||||||
function car_monitor_cookie_payload(): ?array
|
|
||||||
{
|
|
||||||
$cookie = $_COOKIE[CAR_MONITOR_COOKIE] ?? '';
|
|
||||||
if (!is_string($cookie) || strpos($cookie, '.') === false) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
[$body, $sig] = explode('.', $cookie, 2);
|
|
||||||
$expected = hash_hmac('sha256', $body, car_monitor_cookie_secret());
|
|
||||||
if (!hash_equals($expected, $sig)) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
$decoded = base64_decode($body, true);
|
|
||||||
if ($decoded === false) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
$payload = json_decode($decoded, true);
|
|
||||||
if (!is_array($payload)) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return (int)($payload['exp'] ?? 0) >= time() ? $payload : null;
|
|
||||||
}
|
|
||||||
|
|
||||||
function car_monitor_has_cookie(): bool
|
|
||||||
{
|
|
||||||
return is_array(car_monitor_cookie_payload());
|
|
||||||
}
|
|
||||||
|
|
||||||
function car_monitor_settings_cookie_value(int $expires): string
|
function car_monitor_settings_cookie_value(int $expires): string
|
||||||
{
|
{
|
||||||
$body = base64_encode(json_encode([
|
$body = base64_encode(json_encode([
|
||||||
@@ -993,74 +943,24 @@ function car_monitor_launcher_session(): array
|
|||||||
return $session;
|
return $session;
|
||||||
}
|
}
|
||||||
|
|
||||||
$cookieHeader = trim((string)($_SERVER['HTTP_COOKIE'] ?? ''));
|
if (custom_is_site_admin()) {
|
||||||
if ($cookieHeader !== '') {
|
custom_issue_auth_cookie(true);
|
||||||
$remoteSession = car_monitor_launcher_api_request('GET', 'https://chaegeon.com/custom/launcher/api.php?session=1', null, $cookieHeader);
|
$session = ['authenticated' => true, 'admin' => true];
|
||||||
if (is_array($remoteSession) && !empty($remoteSession['authenticated'])) {
|
|
||||||
car_monitor_issue_cookie();
|
|
||||||
$session = ['authenticated' => true];
|
|
||||||
return $session;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$cookiePayload = car_monitor_cookie_payload();
|
|
||||||
if (is_array($cookiePayload)) {
|
|
||||||
$session = ['authenticated' => true];
|
|
||||||
return $session;
|
return $session;
|
||||||
}
|
}
|
||||||
|
|
||||||
$session = ['authenticated' => false];
|
if (custom_has_auth_cookie()) {
|
||||||
|
$session = [
|
||||||
|
'authenticated' => true,
|
||||||
|
'admin' => custom_auth_cookie_is_admin(),
|
||||||
|
];
|
||||||
|
return $session;
|
||||||
|
}
|
||||||
|
|
||||||
|
$session = ['authenticated' => false, 'admin' => false];
|
||||||
return $session;
|
return $session;
|
||||||
}
|
}
|
||||||
|
|
||||||
function car_monitor_launcher_api_request(string $method, string $url, ?array $payload = null, string $cookieHeader = ''): ?array
|
|
||||||
{
|
|
||||||
$body = false;
|
|
||||||
|
|
||||||
if (function_exists('curl_init')) {
|
|
||||||
$ch = curl_init($url);
|
|
||||||
if ($ch !== false) {
|
|
||||||
$headers = ['User-Agent: car-monitor-auth/1.0'];
|
|
||||||
if ($cookieHeader !== '') {
|
|
||||||
$headers[] = 'Cookie: ' . $cookieHeader;
|
|
||||||
}
|
|
||||||
if ($payload !== null) {
|
|
||||||
$headers[] = 'Content-Type: application/json';
|
|
||||||
}
|
|
||||||
|
|
||||||
curl_setopt_array($ch, [
|
|
||||||
CURLOPT_RETURNTRANSFER => true,
|
|
||||||
CURLOPT_CONNECTTIMEOUT => 2,
|
|
||||||
CURLOPT_TIMEOUT => 4,
|
|
||||||
CURLOPT_CUSTOMREQUEST => strtoupper($method),
|
|
||||||
CURLOPT_HTTPHEADER => $headers,
|
|
||||||
]);
|
|
||||||
if ($payload !== null) {
|
|
||||||
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($payload, JSON_UNESCAPED_UNICODE));
|
|
||||||
}
|
|
||||||
$body = curl_exec($ch);
|
|
||||||
curl_close($ch);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if ($body === false) {
|
|
||||||
$context = stream_context_create([
|
|
||||||
'http' => [
|
|
||||||
'method' => strtoupper($method),
|
|
||||||
'timeout' => 4,
|
|
||||||
'header' => ($cookieHeader !== '' ? "Cookie: {$cookieHeader}\r\n" : '')
|
|
||||||
. "User-Agent: car-monitor-auth/1.0\r\n"
|
|
||||||
. ($payload !== null ? "Content-Type: application/json\r\n" : ''),
|
|
||||||
'content' => $payload !== null ? json_encode($payload, JSON_UNESCAPED_UNICODE) : '',
|
|
||||||
],
|
|
||||||
]);
|
|
||||||
$body = @file_get_contents($url, false, $context);
|
|
||||||
}
|
|
||||||
|
|
||||||
$data = is_string($body) ? json_decode($body, true) : null;
|
|
||||||
return is_array($data) ? $data : null;
|
|
||||||
}
|
|
||||||
|
|
||||||
function car_monitor_has_access(): bool
|
function car_monitor_has_access(): bool
|
||||||
{
|
{
|
||||||
$session = car_monitor_launcher_session();
|
$session = car_monitor_launcher_session();
|
||||||
@@ -1069,6 +969,10 @@ function car_monitor_has_access(): bool
|
|||||||
|
|
||||||
function car_monitor_require_access(bool $json = false): void
|
function car_monitor_require_access(bool $json = false): void
|
||||||
{
|
{
|
||||||
|
if (function_exists('custom_block_login_denied')) {
|
||||||
|
custom_block_login_denied($json);
|
||||||
|
}
|
||||||
|
|
||||||
if (car_monitor_has_access()) {
|
if (car_monitor_has_access()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -1101,7 +1005,7 @@ function car_monitor_require_access(bool $json = false): void
|
|||||||
window.addEventListener('DOMContentLoaded', function () {
|
window.addEventListener('DOMContentLoaded', function () {
|
||||||
window.CustomAuthPin && window.CustomAuthPin.render({
|
window.CustomAuthPin && window.CustomAuthPin.render({
|
||||||
mount: '#findMyShortcut',
|
mount: '#findMyShortcut',
|
||||||
apiUrl: '/car/monitor.php?mode=auth-login',
|
apiUrl: '/custom/car/monitor.php?mode=auth-login',
|
||||||
title: '비밀번호',
|
title: '비밀번호',
|
||||||
placeholder: '비밀번호',
|
placeholder: '비밀번호',
|
||||||
backLabel: '채건닷컴',
|
backLabel: '채건닷컴',
|
||||||
@@ -1127,20 +1031,16 @@ function car_monitor_issue_pwa_cookie_if_requested(): void
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
$cookieHeader = trim((string)($_SERVER['HTTP_COOKIE'] ?? ''));
|
header('Location: /custom/car/monitor.php', true, 302);
|
||||||
if ($cookieHeader !== '') {
|
|
||||||
$remoteSession = car_monitor_launcher_api_request('GET', 'https://chaegeon.com/custom/launcher/api.php?session=1', null, $cookieHeader);
|
|
||||||
if (is_array($remoteSession) && !empty($remoteSession['authenticated'])) {
|
|
||||||
car_monitor_issue_cookie();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
header('Location: /car/monitor.php', true, 302);
|
|
||||||
exit;
|
exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
function car_monitor_auth_api(): void
|
function car_monitor_auth_api(): void
|
||||||
{
|
{
|
||||||
|
if (function_exists('custom_block_login_denied')) {
|
||||||
|
custom_block_login_denied(true);
|
||||||
|
}
|
||||||
|
|
||||||
if ($_SERVER['REQUEST_METHOD'] === 'GET' && isset($_GET['failMessages'])) {
|
if ($_SERVER['REQUEST_METHOD'] === 'GET' && isset($_GET['failMessages'])) {
|
||||||
json_response(['failMessages' => ['비밀번호가 틀립니다.']]);
|
json_response(['failMessages' => ['비밀번호가 틀립니다.']]);
|
||||||
}
|
}
|
||||||
@@ -1155,12 +1055,8 @@ function car_monitor_auth_api(): void
|
|||||||
json_response(['result' => 'fail', 'message' => 'password_digits_only'], 401);
|
json_response(['result' => 'fail', 'message' => 'password_digits_only'], 401);
|
||||||
}
|
}
|
||||||
|
|
||||||
$remote = car_monitor_launcher_api_request('POST', 'https://chaegeon.com/custom/launcher/api.php', [
|
if (custom_verify_password($password)) {
|
||||||
'action' => 'login',
|
custom_issue_auth_cookie(false);
|
||||||
'password' => $password,
|
|
||||||
]);
|
|
||||||
if (is_array($remote) && ($remote['result'] ?? '') === 'ok') {
|
|
||||||
car_monitor_issue_cookie();
|
|
||||||
json_response(['result' => 'ok']);
|
json_response(['result' => 'ok']);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1350,13 +1246,13 @@ $carMonitorSession = car_monitor_launcher_session();
|
|||||||
<meta name="apple-mobile-web-app-status-bar-style" content="black-translucent">
|
<meta name="apple-mobile-web-app-status-bar-style" content="black-translucent">
|
||||||
<title>Car Monitor</title>
|
<title>Car Monitor</title>
|
||||||
|
|
||||||
<link rel="icon" href="<?= htmlspecialchars(car_asset_url('/car/assets/favicon.svg'), ENT_QUOTES, 'UTF-8') ?>" type="image/svg+xml">
|
<link rel="icon" href="<?= htmlspecialchars(car_asset_url('/custom/car/assets/favicon.svg'), ENT_QUOTES, 'UTF-8') ?>" type="image/svg+xml">
|
||||||
<link rel="shortcut icon" href="<?= htmlspecialchars(car_asset_url('/car/favicon.ico'), ENT_QUOTES, 'UTF-8') ?>">
|
<link rel="shortcut icon" href="<?= htmlspecialchars(car_asset_url('/custom/car/favicon.ico'), ENT_QUOTES, 'UTF-8') ?>">
|
||||||
<link rel="icon" href="<?= htmlspecialchars(car_asset_url('/car/assets/icon-32.png'), ENT_QUOTES, 'UTF-8') ?>" type="image/png" sizes="32x32">
|
<link rel="icon" href="<?= htmlspecialchars(car_asset_url('/custom/car/assets/icon-32.png'), ENT_QUOTES, 'UTF-8') ?>" type="image/png" sizes="32x32">
|
||||||
<link rel="icon" href="<?= htmlspecialchars(car_asset_url('/car/assets/icon-192.png'), ENT_QUOTES, 'UTF-8') ?>" type="image/png" sizes="192x192">
|
<link rel="icon" href="<?= htmlspecialchars(car_asset_url('/custom/car/assets/icon-192.png'), ENT_QUOTES, 'UTF-8') ?>" type="image/png" sizes="192x192">
|
||||||
<link rel="apple-touch-icon" href="<?= htmlspecialchars(car_asset_url('/car/assets/apple-touch-icon.png'), ENT_QUOTES, 'UTF-8') ?>">
|
<link rel="apple-touch-icon" href="<?= htmlspecialchars(car_asset_url('/custom/car/assets/apple-touch-icon.png'), ENT_QUOTES, 'UTF-8') ?>">
|
||||||
<link rel="manifest" href="<?= htmlspecialchars(car_asset_url('/car/assets/site.webmanifest'), ENT_QUOTES, 'UTF-8') ?>">
|
<link rel="manifest" href="<?= htmlspecialchars(car_asset_url('/custom/car/assets/site.webmanifest'), ENT_QUOTES, 'UTF-8') ?>">
|
||||||
<script src="<?= htmlspecialchars(car_asset_url('/car/assets/asset-reload.js'), ENT_QUOTES, 'UTF-8') ?>" data-service="car" defer></script>
|
<script src="<?= htmlspecialchars(car_asset_url('/custom/car/assets/asset-reload.js'), ENT_QUOTES, 'UTF-8') ?>" data-service="car" defer></script>
|
||||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||||
<link href="https://fonts.googleapis.com/css2?family=Gowun+Dodum&display=swap" rel="stylesheet">
|
<link href="https://fonts.googleapis.com/css2?family=Gowun+Dodum&display=swap" rel="stylesheet">
|
||||||
|
|||||||
+2
-2
@@ -26,11 +26,11 @@ register_shutdown_function(static function () use ($lockFp): void {
|
|||||||
@fclose($lockFp);
|
@fclose($lockFp);
|
||||||
});
|
});
|
||||||
|
|
||||||
db_ensure_tcp_queue_schema(db());
|
db_ensure_tcp_queue_schema(db(true));
|
||||||
|
|
||||||
while (true) {
|
while (true) {
|
||||||
try {
|
try {
|
||||||
$job = tcp_queue_claim_next(db());
|
$job = tcp_queue_claim_next(db(true));
|
||||||
if (!$job) {
|
if (!$job) {
|
||||||
usleep(WORKER_IDLE_SLEEP_USEC);
|
usleep(WORKER_IDLE_SLEEP_USEC);
|
||||||
continue;
|
continue;
|
||||||
|
|||||||
Reference in new issue
Block a user