Upload via GUI (364 Dateien)
This commit is contained in:
@@ -13,7 +13,7 @@ RewriteRule ^ - [F,L]
|
||||
# RewriteRule ^ - [F,L]
|
||||
|
||||
# Clickjacking-Schutz
|
||||
Header always set X-Frame-Options "SAMEORIGIN"
|
||||
Header always set X-Frame-Options "DENY"
|
||||
Header always set X-Content-Type-Options "nosniff"
|
||||
|
||||
# Schützt interne Verzeichnisse vor direktem Web-Zugriff.
|
||||
|
||||
@@ -248,7 +248,7 @@ if ($action !== 'typing') {
|
||||
|
||||
if ($action === 'typing') {
|
||||
if ($activeTicket && $activeTicket['status'] !== 'closed') {
|
||||
$pdo->prepare('UPDATE tickets SET typing_customer_until = ? WHERE id = ?')
|
||||
$pdo->prepare('UPDATE tickets SET typing_customer_until = ?, updated_at = updated_at WHERE id = ?')
|
||||
->execute([date('Y-m-d H:i:s', time() + 6), $activeTicket['id']]);
|
||||
}
|
||||
chat_json(['ok' => true]);
|
||||
|
||||
@@ -0,0 +1,75 @@
|
||||
<?php
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* Prüft die Überwachung der Plugin-Webseite auf der Statusseite: Prüfadresse aus dem offiziellen Katalog, Standarddienst,
|
||||
* automatische Erkennung am Namen und dass ohne offiziellen Katalog nichts angelegt wird.
|
||||
*/
|
||||
|
||||
putenv('DESKHUB_TESTING=1');
|
||||
putenv('DESKHUB_CATALOG_DEFAULTS=' . __DIR__ . '/fixtures/no-catalog.php');
|
||||
putenv('DESKHUB_SQLITE_PATH=:memory:');
|
||||
require_once dirname(__DIR__) . '/includes/bootstrap.php';
|
||||
|
||||
$failures = [];
|
||||
$check = function (bool $ok, string $what) use (&$failures): void {
|
||||
if (!$ok) $failures[] = $what;
|
||||
};
|
||||
$pdo = get_db();
|
||||
$byName = fn(string $name) => $pdo->query("SELECT * FROM status_components WHERE name = " . $pdo->quote($name))->fetch(PDO::FETCH_ASSOC);
|
||||
|
||||
// Ohne offiziellen Katalog gibt es nichts zu prüfen
|
||||
$check(status_plugin_site_url() === '', 'ohne Katalog keine Prüfadresse');
|
||||
status_restore_core_components($pdo);
|
||||
$check(!$byName('Plugin-Webseite'), 'ohne Katalog wird kein Dienst "Plugin-Webseite" angelegt');
|
||||
|
||||
// Mit offiziellem Katalog
|
||||
$GLOBALS['deskhub_catalog_defaults'] = ['plugins_url' => 'https://plugins.example.test/seite/catalog.php?type=plugins', 'themes_url' => '', 'publisher_key' => 'x'];
|
||||
$check(status_plugin_site_url() === 'https://plugins.example.test/seite/health.php', 'Prüfadresse liegt neben dem Katalog: ' . status_plugin_site_url());
|
||||
$check(status_restore_core_components($pdo) >= 1, 'Standarddienste ergänzen den fehlenden Dienst');
|
||||
$c = $byName('Plugin-Webseite');
|
||||
$check((bool) $c && $c['monitor_type'] === 'plugin_site' && (int) ($c['is_enabled'] ?? 1) === 1, 'Dienst "Plugin-Webseite" ist angelegt und aktiv');
|
||||
$t = status_component_monitor_target($pdo, $c);
|
||||
$check($t && $t['type'] === 'plugin_site' && $t['target'] === 'https://plugins.example.test/seite/health.php', 'Prüfziel ist das health.php der Plugin-Webseite');
|
||||
$check(status_restore_core_components($pdo) === 0, 'ein zweiter Durchlauf legt nichts doppelt an');
|
||||
$check(isset(status_monitor_types()['plugin_site']) && status_set_component_monitor($pdo, (int) $c['id'], 'plugin_site', ''), 'Prüfart "Plugin-Webseite" lässt sich wählen');
|
||||
|
||||
// Automatische Erkennung am Namen (Dienst mit anderem Namen, Prüfart "auto")
|
||||
$id = status_save_component($pdo, null, 'Pluginseite von DeskHub', '', 900, null);
|
||||
$row = $pdo->query('SELECT * FROM status_components WHERE id = ' . (int) $id)->fetch(PDO::FETCH_ASSOC);
|
||||
$t = status_component_monitor_target($pdo, $row);
|
||||
$check($t && $t['type'] === 'plugin_site', 'Name mit "Plugin" und "seite" wird automatisch erkannt');
|
||||
$id2 = status_save_component($pdo, null, 'Plugin-Hersteller', '', 910, null);
|
||||
$row2 = $pdo->query('SELECT * FROM status_components WHERE id = ' . (int) $id2)->fetch(PDO::FETCH_ASSOC);
|
||||
$check(status_component_monitor_target($pdo, $row2) === null, 'ein anderer Name mit "Plugin" wird nicht fälschlich geprüft');
|
||||
|
||||
// Intern: wird geprüft, steht aber nicht öffentlich
|
||||
$check(status_has_internal($pdo), 'Spalte is_internal ist vorhanden');
|
||||
$check((int) $byName('Plugin-Webseite')['is_internal'] === 1, 'Plugin-Webseite ist standardmäßig intern');
|
||||
$cat = $pdo->query('SELECT name FROM status_categories WHERE id = ' . (int) $byName('Plugin-Webseite')['category_id'])->fetchColumn();
|
||||
$check($cat === 'Server & Datenbank', 'Kategorie ist "Server & Datenbank", nicht "Webseite": ' . var_export($cat, true));
|
||||
$pub = array_column(status_components($pdo, false, true), 'name');
|
||||
$all = array_column(status_components($pdo), 'name');
|
||||
$check(!in_array('Plugin-Webseite', $pub, true) && in_array('Plugin-Webseite', $all, true), 'öffentliche Liste ohne den internen Dienst, Mitarbeiterliste mit ihm');
|
||||
$check(in_array('plugin_site', array_map(fn($c) => (status_component_monitor_target($pdo, $c)['type'] ?? ''), status_components($pdo)), true), 'interner Dienst wird weiter geprüft');
|
||||
// Ausfall eines internen Dienstes ändert den öffentlichen Gesamtzustand nicht
|
||||
status_set_component($pdo, (int) $byName('Plugin-Webseite')['id'], 'outage');
|
||||
$check(status_overall($pdo)['key'] === 'operational', 'Ausfall eines internen Dienstes ändert den öffentlichen Gesamtzustand nicht: ' . status_overall($pdo)['key']);
|
||||
$check(status_set_component_internal($pdo, (int) $byName('Plugin-Webseite')['id'], false) && in_array('Plugin-Webseite', array_column(status_components($pdo, false, true), 'name'), true), 'als öffentlich markiert erscheint er wieder');
|
||||
$check(status_overall($pdo)['key'] === 'outage', 'öffentlich: der Ausfall zählt');
|
||||
status_set_component_internal($pdo, (int) $byName('Plugin-Webseite')['id'], true);
|
||||
status_set_component($pdo, (int) $byName('Plugin-Webseite')['id'], 'operational');
|
||||
// Störung an einem internen Dienst erscheint nicht öffentlich
|
||||
$inc = status_create_incident($pdo, 'Plugin-Webseite langsam', 'x', 'investigating', (int) $byName('Plugin-Webseite')['id'], null, null);
|
||||
$check(!empty($inc['ok']) && count(status_incidents($pdo, 14)) === 0 && count(status_incidents($pdo, 14, false, true)) === 1, 'Störung an einem internen Dienst steht nicht öffentlich, Mitarbeiter sehen sie');
|
||||
|
||||
// Eine http-Adresse (ohne https) wird nicht als Prüfadresse verwendet
|
||||
$GLOBALS['deskhub_catalog_defaults'] = ['plugins_url' => 'http://plugins.example.test/catalog.php', 'themes_url' => '', 'publisher_key' => 'x'];
|
||||
$check(status_plugin_site_url() === '', 'nur https wird verwendet');
|
||||
unset($GLOBALS['deskhub_catalog_defaults']);
|
||||
|
||||
if ($failures) {
|
||||
fwrite(STDERR, "Fehlgeschlagen:\n - " . implode("\n - ", $failures) . "\n");
|
||||
exit(1);
|
||||
}
|
||||
echo "Status plugin site checks passed.\n";
|
||||
@@ -216,10 +216,10 @@ try {
|
||||
[$s] = $call('GET', '/staff/ticket_view.php?n=T-OPEN-5', null, null, [], $jarChef, ['Sec-Fetch-Mode: navigate']);
|
||||
$check($s === 200 && (int) $assignee('T-OPEN-5') === $ids['Chef'], 'Auch im Browser: Öffnen weist das Ticket zu (HTTP ' . $s . ')');
|
||||
|
||||
// Ticketliste: Spalte mit dem Eingangsdatum
|
||||
// Ticketliste: Spalte mit der letzten Aktivität (Eingang im Tooltip)
|
||||
[$s, $list] = $call('GET', '/staff/tickets.php', null, null, [], $jarChef, ['Sec-Fetch-Mode: navigate']);
|
||||
$list = is_string($list) ? $list : '';
|
||||
$check($s === 200 && str_contains($list, '<th>Eingang</th>') && str_contains($list, date('d.m.Y ')), 'Ticketliste zeigt die Spalte „Eingang“ mit Datum und Uhrzeit (HTTP ' . $s . ', ' . strlen($list) . ' Zeichen, Tabelle: ' . (str_contains($list, '<table') ? 'ja' : 'nein') . ', leer: ' . (str_contains($list, 'Keine Tickets') ? 'ja' : 'nein') . ')');
|
||||
$check($s === 200 && str_contains($list, '<th>Letzte Aktivität</th>') && str_contains($list, date('d.m.Y ')), 'Ticketliste zeigt die Spalte „Letzte Aktivität“ mit Datum und Uhrzeit (HTTP ' . $s . ', ' . strlen($list) . ' Zeichen, Tabelle: ' . (str_contains($list, '<table') ? 'ja' : 'nein') . ', leer: ' . (str_contains($list, 'Keine Tickets') ? 'ja' : 'nein') . ')');
|
||||
|
||||
@unlink($jarChef);
|
||||
@unlink($jarOther);
|
||||
|
||||
@@ -132,7 +132,9 @@ $pdo->prepare('UPDATE staff SET is_on_vacation = 1, vacation_substitute_id = NUL
|
||||
[$h] = vacation_apply_change($pdo, $ben, [0, null], [1, null], true);
|
||||
$check($h === 0 && $owner($t6) === $ben, 'Ohne Vertretung bleibt alles beim Abwesenden');
|
||||
// Das Plugin „Urlaub und Vertretung“ hat Vorrang
|
||||
$pdo->exec('CREATE TABLE IF NOT EXISTS plugin_vertretung_absences (id INTEGER PRIMARY KEY AUTOINCREMENT, staff_id INTEGER, substitute_id INTEGER, start_date TEXT, end_date TEXT, note TEXT, status TEXT, created_by INTEGER, created_at TEXT)');
|
||||
$pdo->exec($pdo->getAttribute(PDO::ATTR_DRIVER_NAME) === 'sqlite'
|
||||
? 'CREATE TABLE IF NOT EXISTS plugin_vertretung_absences (id INTEGER PRIMARY KEY AUTOINCREMENT, staff_id INTEGER, substitute_id INTEGER, start_date TEXT, end_date TEXT, note TEXT, status TEXT, created_by INTEGER, created_at TEXT)'
|
||||
: 'CREATE TABLE IF NOT EXISTS plugin_vertretung_absences (id INT AUTO_INCREMENT PRIMARY KEY, staff_id INT, substitute_id INT, start_date VARCHAR(20), end_date VARCHAR(20), note TEXT, status VARCHAR(20), created_by INT, created_at VARCHAR(20))');
|
||||
$pdo->prepare("INSERT INTO plugin_vertretung_absences (staff_id, substitute_id, start_date, end_date, note, status, created_at) VALUES (?,?,?,?,?,?,?)")->execute([$ben, $anna, '2026-01-01', '2026-12-31', '', 'active', $now]);
|
||||
$pdo->prepare('UPDATE staff SET is_on_vacation = 1, vacation_substitute_id = ? WHERE id = ?')->execute([$anna, $ben]);
|
||||
[$h] = vacation_apply_change($pdo, $ben, [0, null], [1, $anna], true);
|
||||
|
||||
@@ -150,7 +150,7 @@ try {
|
||||
'/staff/custom_lists.php' => 'Listen', '/staff/custom_lists.php?new=1' => 'Einträge',
|
||||
'/staff/site_pages.php' => 'Seiten', '/staff/site_pages.php?new=1' => 'Seiteninformationen',
|
||||
'/staff/business_hours.php' => 'Feiertage', '/staff/business_hours.php?tab=holidays' => 'Feiertage',
|
||||
'/staff/update.php' => 'Datenbank aktualisieren', '/staff/plugins.php' => 'Plugin-Katalog', '/staff/login_log.php' => 'Anmelde-Wächter', '/staff/login_alert.php?t=abc' => 'ungültig, abgelaufen', '/staff/backup.php' => 'Vorhandene Backups', '/staff/security_check.php' => 'Sicherheitsprüfung', '/staff/import_osticket.php' => 'osTicket Import', '/staff/ticket_rules.php' => 'Ticket-Regeln', '/staff/ticket_rules.php?new=1' => 'Regelinformationen',
|
||||
'/staff/update.php' => 'Datenbank aktualisieren', '/staff/plugins.php' => 'Plugin-Katalog', '/staff/login_log.php' => 'Anmelde-Wächter', '/staff/problems.php' => 'Neues Problem', '/staff/reports.php' => 'Jetzt zu tun', '/staff/reports.php?tab=activity' => 'Ticketaktivität', '/staff/reports.php?tab=analysis' => 'Statistiken', '/staff/problems.php?tab=create' => 'Neues Problem erfassen', '/staff/login_alert.php?t=abc' => 'ungültig, abgelaufen', '/staff/backup.php' => 'Vorhandene Backups', '/staff/security_check.php' => 'Sicherheitsprüfung', '/staff/import_osticket.php' => 'osTicket Import', '/staff/ticket_rules.php' => 'Ticket-Regeln', '/staff/ticket_rules.php?new=1' => 'Regelinformationen',
|
||||
] as $path => $marker) {
|
||||
$response = browser_request($port, 'GET', $path, $cookies);
|
||||
assert_page($response, $marker);
|
||||
|
||||
Reference in New Issue
Block a user