asdsad
This commit is contained in:
@@ -42,17 +42,23 @@ foreach ($fields as $field) {
|
||||
}
|
||||
$isFxRatesSetup = $moduleName === 'fx-rates';
|
||||
$current = modules()->settings($moduleName);
|
||||
$intervalTaskStatuses = modules()->intervalTaskStatuses($moduleName);
|
||||
$intervalTaskStatuses = [];
|
||||
$cronTaskDefinitions = modules()->cronTasks($moduleName);
|
||||
$cronTaskStatuses = modules()->cronTaskStatuses($moduleName);
|
||||
$cronTaskStatuses = [];
|
||||
$cronTaskStatusGroups = [];
|
||||
foreach ($cronTaskStatuses as $cronTaskStatus) {
|
||||
$cronGroupName = trim((string) ($cronTaskStatus['job_name'] ?? $cronTaskStatus['name'] ?? ''));
|
||||
if ($cronGroupName === '') {
|
||||
continue;
|
||||
$refreshSchedulerState = static function () use ($moduleName, &$intervalTaskStatuses, &$cronTaskStatuses, &$cronTaskStatusGroups): void {
|
||||
$intervalTaskStatuses = modules()->intervalTaskStatuses($moduleName);
|
||||
$cronTaskStatuses = modules()->cronTaskStatuses($moduleName);
|
||||
$cronTaskStatusGroups = [];
|
||||
foreach ($cronTaskStatuses as $cronTaskStatus) {
|
||||
$cronGroupName = trim((string) ($cronTaskStatus['job_name'] ?? $cronTaskStatus['name'] ?? ''));
|
||||
if ($cronGroupName === '') {
|
||||
continue;
|
||||
}
|
||||
$cronTaskStatusGroups[$cronGroupName][] = $cronTaskStatus;
|
||||
}
|
||||
$cronTaskStatusGroups[$cronGroupName][] = $cronTaskStatus;
|
||||
}
|
||||
};
|
||||
$refreshSchedulerState();
|
||||
$setupActions = modules()->hasFunction($moduleName, 'setup_actions')
|
||||
? (array) module_fn($moduleName, 'setup_actions')
|
||||
: [];
|
||||
@@ -134,6 +140,8 @@ $driverOptions = [
|
||||
'sqlite' => 'SQLite',
|
||||
];
|
||||
|
||||
$timezoneOptions = modules()->timezones();
|
||||
|
||||
$describeDbConfig = static function (array $dbConfig): string {
|
||||
$driver = (string)($dbConfig['driver'] ?? '');
|
||||
$host = (string)($dbConfig['host'] ?? '');
|
||||
@@ -281,18 +289,72 @@ $normalizeDriver = static function (mixed $value): mixed {
|
||||
};
|
||||
};
|
||||
|
||||
$formatRunTimestamp = static function (?string $value): string {
|
||||
$formatRunTimestamp = static function (?string $value, ?string $timezone = null): string {
|
||||
$value = trim((string) $value);
|
||||
if ($value === '') {
|
||||
return '-';
|
||||
}
|
||||
|
||||
$ts = strtotime($value);
|
||||
if ($ts === false) {
|
||||
return $value;
|
||||
try {
|
||||
$dt = new DateTimeImmutable($value, new DateTimeZone('UTC'));
|
||||
$targetTz = trim((string) $timezone) !== '' ? new DateTimeZone((string) $timezone) : new DateTimeZone(date_default_timezone_get());
|
||||
return $dt->setTimezone($targetTz)->format('Y-m-d H:i:s');
|
||||
} catch (\Throwable) {
|
||||
$ts = strtotime($value);
|
||||
if ($ts === false) {
|
||||
return $value;
|
||||
}
|
||||
return date('Y-m-d H:i:s', $ts);
|
||||
}
|
||||
};
|
||||
|
||||
$extractSchedulerJobs = static function (array $postedSchedulerJobs, array $cronTaskDefinitions, array $current): array {
|
||||
$schedulerJobs = [];
|
||||
foreach ($cronTaskDefinitions as $cronTask) {
|
||||
if (!is_array($cronTask)) {
|
||||
continue;
|
||||
}
|
||||
$cronName = trim((string) ($cronTask['name'] ?? ''));
|
||||
if ($cronName === '') {
|
||||
continue;
|
||||
}
|
||||
|
||||
$jobPayload = is_array($postedSchedulerJobs[$cronName] ?? null) ? $postedSchedulerJobs[$cronName] : [];
|
||||
$entriesPayload = is_array($jobPayload['entries'] ?? null) ? $jobPayload['entries'] : [];
|
||||
$entries = [];
|
||||
foreach (array_values($entriesPayload) as $entryPayload) {
|
||||
if (!is_array($entryPayload)) {
|
||||
continue;
|
||||
}
|
||||
$cronExpression = trim((string) ($entryPayload['cron_expression'] ?? ''));
|
||||
$timezone = trim((string) ($entryPayload['timezone'] ?? ($current['schedule_timezone'] ?? 'UTC')));
|
||||
if ($cronExpression === '' && $timezone === '') {
|
||||
continue;
|
||||
}
|
||||
$entries[] = [
|
||||
'enabled' => !empty($entryPayload['enabled']),
|
||||
'cron_expression' => $cronExpression,
|
||||
'timezone' => $timezone !== '' ? $timezone : 'UTC',
|
||||
'builder' => [
|
||||
'mode' => trim((string) ($entryPayload['builder']['mode'] ?? 'builder')),
|
||||
'kind' => trim((string) ($entryPayload['builder']['kind'] ?? 'daily')),
|
||||
'time' => trim((string) ($entryPayload['builder']['time'] ?? '18:00')),
|
||||
'interval_days' => max(1, (int) ($entryPayload['builder']['interval_days'] ?? 2)),
|
||||
'weekday' => trim((string) ($entryPayload['builder']['weekday'] ?? '1')),
|
||||
'month_day' => max(1, min(31, (int) ($entryPayload['builder']['month_day'] ?? 1))),
|
||||
'interval_hours' => max(1, min(23, (int) ($entryPayload['builder']['interval_hours'] ?? 6))),
|
||||
],
|
||||
];
|
||||
}
|
||||
|
||||
if ((string) ($cronTask['mode'] ?? 'single') !== 'multi' && $entries !== []) {
|
||||
$entries = [array_values($entries)[0]];
|
||||
}
|
||||
|
||||
$schedulerJobs[$cronName] = ['entries' => $entries];
|
||||
}
|
||||
|
||||
return date('Y-m-d H:i:s', $ts);
|
||||
return $schedulerJobs;
|
||||
};
|
||||
|
||||
$cronWeekdays = [
|
||||
@@ -338,6 +400,8 @@ $renderField = function (array $field) use (&$current, $getNested, $driverOption
|
||||
<textarea name="<?= e($postKey) ?>" rows="3" <?= $required ? 'required' : '' ?>><?= e($value) ?></textarea>
|
||||
<?php elseif ($type === 'checkbox'): ?>
|
||||
<input type="checkbox" name="<?= e($postKey) ?>" value="1" <?= $value === '1' ? 'checked' : '' ?>>
|
||||
<?php elseif ($name === 'schedule_timezone' || str_ends_with($name, '_timezone') || str_ends_with($name, '.timezone')): ?>
|
||||
<input type="text" name="<?= e($postKey) ?>" value="<?= e($value) ?>" list="timezone-options" autocomplete="off" <?= $required ? 'required' : '' ?>>
|
||||
<?php else: ?>
|
||||
<input type="<?= e($type) ?>" name="<?= e($postKey) ?>" value="<?= e($value) ?>" <?= $required ? 'required' : '' ?>>
|
||||
<?php endif; ?>
|
||||
@@ -349,6 +413,7 @@ $renderField = function (array $field) use (&$current, $getNested, $driverOption
|
||||
};
|
||||
|
||||
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
|
||||
$isSchedulerAutosave = isset($_POST['scheduler_autosave']) && (string) $_POST['scheduler_autosave'] === '1';
|
||||
$payload = [];
|
||||
|
||||
foreach ($fields as $field) {
|
||||
@@ -393,53 +458,25 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST') {
|
||||
|
||||
if ($cronTaskDefinitions !== []) {
|
||||
$postedSchedulerJobs = is_array($_POST['scheduler_jobs'] ?? null) ? $_POST['scheduler_jobs'] : [];
|
||||
$schedulerJobs = [];
|
||||
foreach ($cronTaskDefinitions as $cronTask) {
|
||||
if (!is_array($cronTask)) {
|
||||
continue;
|
||||
}
|
||||
$cronName = trim((string) ($cronTask['name'] ?? ''));
|
||||
if ($cronName === '') {
|
||||
continue;
|
||||
}
|
||||
|
||||
$jobPayload = is_array($postedSchedulerJobs[$cronName] ?? null) ? $postedSchedulerJobs[$cronName] : [];
|
||||
$entriesPayload = is_array($jobPayload['entries'] ?? null) ? $jobPayload['entries'] : [];
|
||||
$entries = [];
|
||||
foreach (array_values($entriesPayload) as $entryPayload) {
|
||||
if (!is_array($entryPayload)) {
|
||||
continue;
|
||||
}
|
||||
$cronExpression = trim((string) ($entryPayload['cron_expression'] ?? ''));
|
||||
$timezone = trim((string) ($entryPayload['timezone'] ?? ($current['schedule_timezone'] ?? 'UTC')));
|
||||
if ($cronExpression === '' && $timezone === '') {
|
||||
continue;
|
||||
}
|
||||
$entries[] = [
|
||||
'enabled' => !empty($entryPayload['enabled']),
|
||||
'cron_expression' => $cronExpression,
|
||||
'timezone' => $timezone !== '' ? $timezone : 'UTC',
|
||||
'builder' => [
|
||||
'mode' => trim((string) ($entryPayload['builder']['mode'] ?? 'builder')),
|
||||
'kind' => trim((string) ($entryPayload['builder']['kind'] ?? 'daily')),
|
||||
'time' => trim((string) ($entryPayload['builder']['time'] ?? '18:00')),
|
||||
'interval_days' => max(1, (int) ($entryPayload['builder']['interval_days'] ?? 2)),
|
||||
'weekday' => trim((string) ($entryPayload['builder']['weekday'] ?? '1')),
|
||||
'month_day' => max(1, min(31, (int) ($entryPayload['builder']['month_day'] ?? 1))),
|
||||
'interval_hours' => max(1, min(23, (int) ($entryPayload['builder']['interval_hours'] ?? 6))),
|
||||
],
|
||||
];
|
||||
}
|
||||
|
||||
if ((string) ($cronTask['mode'] ?? 'single') !== 'multi' && $entries !== []) {
|
||||
$entries = [array_values($entries)[0]];
|
||||
}
|
||||
|
||||
$schedulerJobs[$cronName] = ['entries' => $entries];
|
||||
}
|
||||
$schedulerJobs = $extractSchedulerJobs($postedSchedulerJobs, $cronTaskDefinitions, $current);
|
||||
$current['scheduler_jobs'] = $schedulerJobs;
|
||||
}
|
||||
|
||||
if ($isSchedulerAutosave) {
|
||||
modules()->saveSettings($moduleName, $current);
|
||||
$current = modules()->settings($moduleName);
|
||||
$refreshSchedulerState();
|
||||
|
||||
header('Content-Type: application/json; charset=utf-8');
|
||||
echo json_encode([
|
||||
'ok' => true,
|
||||
'message' => 'Scheduler gespeichert.',
|
||||
'scheduler_jobs' => $current['scheduler_jobs'] ?? [],
|
||||
'statuses' => $cronTaskStatuses,
|
||||
], JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);
|
||||
return;
|
||||
}
|
||||
|
||||
$postedTestGroup = (string)($_POST['test_db'] ?? '');
|
||||
$postedResetGroup = (string)($_POST['reset_db'] ?? '');
|
||||
$postedSetupAction = trim((string)($_POST['module_setup_action'] ?? ''));
|
||||
@@ -524,6 +561,7 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST') {
|
||||
module_fn($moduleName, 'save_runtime_settings', $payload);
|
||||
$current = modules()->settings($moduleName);
|
||||
}
|
||||
$refreshSchedulerState();
|
||||
if (empty($payload['debug_enabled'])) {
|
||||
module_debug_clear($moduleName);
|
||||
}
|
||||
@@ -554,6 +592,11 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
<?php endif; ?>
|
||||
|
||||
<form method="post" class="setup-form">
|
||||
<datalist id="timezone-options">
|
||||
<?php foreach ($timezoneOptions as $timezoneOption): ?>
|
||||
<option value="<?= e((string) $timezoneOption['value']) ?>"><?= e((string) $timezoneOption['label']) ?></option>
|
||||
<?php endforeach; ?>
|
||||
</datalist>
|
||||
<?php if ($isFxRatesSetup): ?>
|
||||
<?php
|
||||
$fxCatalog = is_array($current['currency_catalog'] ?? null) ? $current['currency_catalog'] : [];
|
||||
@@ -686,7 +729,7 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
<div class="setup-grid">
|
||||
<label class="setup-field muted">
|
||||
<span>Scheduler-Zeitzone</span>
|
||||
<input type="text" name="schedule_timezone" value="<?= e((string) ($current['schedule_timezone'] ?? 'Europe/Berlin')) ?>">
|
||||
<input type="text" name="schedule_timezone" value="<?= e((string) ($current['schedule_timezone'] ?? 'Europe/Berlin')) ?>" list="timezone-options" autocomplete="off">
|
||||
<small class="muted">Diese Zeitzone wird fuer Cron-Jobs und die lokale Zeitberechnung verwendet.</small>
|
||||
</label>
|
||||
</div>
|
||||
@@ -852,10 +895,9 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
<input type="number" min="1" max="31" name="scheduler_jobs[<?= e($cronName) ?>][entries][<?= e((string) $entryIndex) ?>][builder][month_day]" value="<?= e((string) ($builder['month_day'] ?? 1)) ?>" data-cron-builder-month-day>
|
||||
<input type="number" min="1" max="23" name="scheduler_jobs[<?= e($cronName) ?>][entries][<?= e((string) $entryIndex) ?>][builder][interval_hours]" value="<?= e((string) ($builder['interval_hours'] ?? 6)) ?>" data-cron-builder-interval-hours>
|
||||
</div>
|
||||
<small class="muted">Letzter Start: <?= e($formatRunTimestamp((string) ($task['state']['last_started_at'] ?? ''))) ?></small>
|
||||
<small class="muted">Letzter Erfolg: <?= e($formatRunTimestamp((string) ($task['state']['last_success_at'] ?? ''))) ?></small>
|
||||
<small class="muted">Naechster Lauf UTC: <?= e($formatRunTimestamp((string) ($task['next_due_at'] ?? ''))) ?></small>
|
||||
<small class="muted">Naechster Lauf lokal: <?= e((string) (($task['next_due_at_local'] ?? '') !== '' ? $task['next_due_at_local'] : '-')) ?></small>
|
||||
<small class="muted">Letzter Start: <?= e($formatRunTimestamp((string) ($task['state']['last_started_at'] ?? ''), (string) ($task['timezone'] ?? 'UTC'))) ?></small>
|
||||
<small class="muted">Letzter Erfolg: <?= e($formatRunTimestamp((string) ($task['state']['last_success_at'] ?? ''), (string) ($task['timezone'] ?? 'UTC'))) ?></small>
|
||||
<small class="muted">Naechster Lauf lokal: <?= e(!empty($task['enabled']) ? (string) (($task['next_due_at_local'] ?? '') !== '' ? $task['next_due_at_local'] : '-') : '-') ?></small>
|
||||
<small class="muted">Status: <?= e((string) (($task['state']['last_status'] ?? '') !== '' ? $task['state']['last_status'] : '-')) ?></small>
|
||||
<?php if (trim((string) ($task['parse_error'] ?? '')) !== ''): ?>
|
||||
<small class="muted" style="color:#b42318;">Cron-Fehler: <?= e((string) $task['parse_error']) ?></small>
|
||||
@@ -1228,10 +1270,9 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
<input type="number" min="1" max="31" name="scheduler_jobs[<?= e($cronName) ?>][entries][<?= e((string) $entryIndex) ?>][builder][month_day]" value="<?= e((string) ($builder['month_day'] ?? 1)) ?>" data-cron-builder-month-day>
|
||||
<input type="number" min="1" max="23" name="scheduler_jobs[<?= e($cronName) ?>][entries][<?= e((string) $entryIndex) ?>][builder][interval_hours]" value="<?= e((string) ($builder['interval_hours'] ?? 6)) ?>" data-cron-builder-interval-hours>
|
||||
</div>
|
||||
<small class="muted">Letzter Start: <?= e($formatRunTimestamp((string) ($task['state']['last_started_at'] ?? ''))) ?></small>
|
||||
<small class="muted">Letzter Erfolg: <?= e($formatRunTimestamp((string) ($task['state']['last_success_at'] ?? ''))) ?></small>
|
||||
<small class="muted">Naechster Lauf UTC: <?= e($formatRunTimestamp((string) ($task['next_due_at'] ?? ''))) ?></small>
|
||||
<small class="muted">Naechster Lauf lokal: <?= e((string) (($task['next_due_at_local'] ?? '') !== '' ? $task['next_due_at_local'] : '-')) ?></small>
|
||||
<small class="muted">Letzter Start: <?= e($formatRunTimestamp((string) ($task['state']['last_started_at'] ?? ''), (string) ($task['timezone'] ?? 'UTC'))) ?></small>
|
||||
<small class="muted">Letzter Erfolg: <?= e($formatRunTimestamp((string) ($task['state']['last_success_at'] ?? ''), (string) ($task['timezone'] ?? 'UTC'))) ?></small>
|
||||
<small class="muted">Naechster Lauf lokal: <?= e(!empty($task['enabled']) ? (string) (($task['next_due_at_local'] ?? '') !== '' ? $task['next_due_at_local'] : '-') : '-') ?></small>
|
||||
<small class="muted">Status: <?= e((string) (($task['state']['last_status'] ?? '') !== '' ? $task['state']['last_status'] : '-')) ?></small>
|
||||
<?php if (trim((string) ($task['parse_error'] ?? '')) !== ''): ?>
|
||||
<small class="muted" style="color:#b42318;">Cron-Fehler: <?= e((string) $task['parse_error']) ?></small>
|
||||
@@ -1410,7 +1451,7 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
</label>
|
||||
<label class="setup-field muted">
|
||||
<span>Zeitzone</span>
|
||||
<input type="text" value="UTC" data-modal-timezone>
|
||||
<input type="text" value="UTC" data-modal-timezone list="timezone-options" autocomplete="off">
|
||||
</label>
|
||||
|
||||
<div class="scheduler-builder">
|
||||
@@ -1517,6 +1558,7 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
minute: '00',
|
||||
weekday: '1',
|
||||
};
|
||||
const form = modal.closest('form');
|
||||
|
||||
const modalFields = {
|
||||
enabled: modal.querySelector('[data-modal-enabled]'),
|
||||
@@ -1642,6 +1684,78 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
};
|
||||
|
||||
const getEntryField = (entry, selector) => entry.querySelector(selector);
|
||||
const findStatusNode = (entry, label) => Array.from(entry.querySelectorAll('small')).find((node) => node.textContent.includes(label));
|
||||
const setStatusText = (entry, label, value) => {
|
||||
const node = findStatusNode(entry, label);
|
||||
if (node) {
|
||||
node.textContent = `${label}: ${value}`;
|
||||
}
|
||||
};
|
||||
|
||||
const applyStatusUpdates = (statuses) => {
|
||||
if (!Array.isArray(statuses)) return;
|
||||
const statusMap = new Map();
|
||||
statuses.forEach((status) => {
|
||||
statusMap.set(`${status.job_name}#${status.entry_index}`, status);
|
||||
});
|
||||
|
||||
jobs.forEach((job) => {
|
||||
const jobName = job.dataset.jobName || '';
|
||||
job.querySelectorAll('[data-scheduler-entry]').forEach((entry) => {
|
||||
const key = `${jobName}#${entry.dataset.entryIndex || '0'}`;
|
||||
const status = statusMap.get(key);
|
||||
if (!status) return;
|
||||
const enabledNode = getEntryField(entry, '[data-enabled]');
|
||||
if (enabledNode) {
|
||||
enabledNode.checked = !!status.enabled;
|
||||
}
|
||||
setStatusText(entry, 'Letzter Start', status.last_started_at_local || status.state?.last_started_at || '-');
|
||||
setStatusText(entry, 'Letzter Erfolg', status.last_success_at_local || status.state?.last_success_at || '-');
|
||||
setStatusText(entry, 'Naechster Lauf lokal', status.enabled ? (status.next_due_at_local || '-') : '-');
|
||||
setStatusText(entry, 'Status', status.state?.last_status || '-');
|
||||
updateEntrySummary(entry);
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
const collectSchedulerPayload = () => {
|
||||
const payload = new FormData();
|
||||
payload.append('scheduler_autosave', '1');
|
||||
jobs.forEach((job) => {
|
||||
job.querySelectorAll('[data-scheduler-entry]').forEach((entry) => {
|
||||
entry.querySelectorAll('[name]').forEach((field) => {
|
||||
if (field instanceof HTMLInputElement && field.type === 'checkbox') {
|
||||
if (field.checked) {
|
||||
payload.append(field.name, field.value || '1');
|
||||
}
|
||||
return;
|
||||
}
|
||||
payload.append(field.name, field.value);
|
||||
});
|
||||
});
|
||||
});
|
||||
return payload;
|
||||
};
|
||||
|
||||
const persistScheduler = async () => {
|
||||
if (!form) return true;
|
||||
const response = await fetch(window.location.href, {
|
||||
method: 'POST',
|
||||
body: collectSchedulerPayload(),
|
||||
headers: {
|
||||
'X-Requested-With': 'XMLHttpRequest',
|
||||
},
|
||||
});
|
||||
if (!response.ok) {
|
||||
throw new Error(`Scheduler konnte nicht gespeichert werden (${response.status}).`);
|
||||
}
|
||||
const data = await response.json();
|
||||
if (!data || data.ok !== true) {
|
||||
throw new Error(data?.message || 'Scheduler konnte nicht gespeichert werden.');
|
||||
}
|
||||
applyStatusUpdates(data.statuses || []);
|
||||
return true;
|
||||
};
|
||||
|
||||
const updateEntrySummary = (entry) => {
|
||||
const enabled = getEntryField(entry, '[data-enabled]')?.checked ?? false;
|
||||
@@ -1683,11 +1797,11 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
entry.appendChild(statusNode);
|
||||
}
|
||||
|
||||
const lastStart = Array.from(entry.querySelectorAll('small')).find((node) => node.textContent.includes('Letzter Start'));
|
||||
const lastSuccess = Array.from(entry.querySelectorAll('small')).find((node) => node.textContent.includes('Letzter Erfolg'));
|
||||
const nextLocal = Array.from(entry.querySelectorAll('small')).find((node) => node.textContent.includes('Naechster Lauf lokal'));
|
||||
const status = Array.from(entry.querySelectorAll('small')).find((node) => node.textContent.includes('Status:'));
|
||||
const parseError = Array.from(entry.querySelectorAll('small')).find((node) => node.textContent.includes('Cron-Fehler'));
|
||||
const lastStart = findStatusNode(entry, 'Letzter Start');
|
||||
const lastSuccess = findStatusNode(entry, 'Letzter Erfolg');
|
||||
const nextLocal = findStatusNode(entry, 'Naechster Lauf lokal');
|
||||
const status = findStatusNode(entry, 'Status');
|
||||
const parseError = findStatusNode(entry, 'Cron-Fehler');
|
||||
|
||||
summaryNode.innerHTML = `
|
||||
<strong>${summary}</strong>
|
||||
@@ -1755,7 +1869,7 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
document.body.classList.remove('scheduler-modal-open');
|
||||
};
|
||||
|
||||
const saveModal = () => {
|
||||
const saveModal = async () => {
|
||||
const entry = modalState.entry;
|
||||
if (!entry) return;
|
||||
|
||||
@@ -1794,7 +1908,12 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
}
|
||||
|
||||
updateEntrySummary(entry);
|
||||
closeModal();
|
||||
try {
|
||||
await persistScheduler();
|
||||
closeModal();
|
||||
} catch (error) {
|
||||
alert(error instanceof Error ? error.message : 'Scheduler konnte nicht gespeichert werden.');
|
||||
}
|
||||
};
|
||||
|
||||
const createEntry = (job, values = {}) => {
|
||||
@@ -1850,6 +1969,7 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
const reindexJob = (job) => {
|
||||
const jobName = job.dataset.jobName || 'job';
|
||||
job.querySelectorAll('[data-scheduler-entry]').forEach((entry, index) => {
|
||||
entry.dataset.entryIndex = String(index);
|
||||
const setName = (selector, suffix) => {
|
||||
const node = entry.querySelector(selector);
|
||||
if (node) {
|
||||
@@ -1886,9 +2006,14 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
}
|
||||
|
||||
actions.querySelector('[data-entry-edit]')?.addEventListener('click', () => openModal(entry));
|
||||
actions.querySelector('[data-remove-scheduler-entry]')?.addEventListener('click', () => {
|
||||
actions.querySelector('[data-remove-scheduler-entry]')?.addEventListener('click', async () => {
|
||||
entry.remove();
|
||||
reindexJob(job);
|
||||
try {
|
||||
await persistScheduler();
|
||||
} catch (error) {
|
||||
alert(error instanceof Error ? error.message : 'Scheduler konnte nicht gespeichert werden.');
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
@@ -1997,7 +2122,7 @@ $activeDbGroup = $testGroup !== null && array_key_exists($testGroup, $dbGroups)
|
||||
.scheduler-modal__backdrop {
|
||||
position: absolute;
|
||||
inset: 0;
|
||||
background: rgba(10, 18, 28, 0.45);
|
||||
background: #ffffff;
|
||||
}
|
||||
|
||||
.scheduler-modal__dialog {
|
||||
|
||||
Reference in New Issue
Block a user