feat: clean URLs + fix addFileMeta silent failure
This commit is contained in:
+1
-1
@@ -85,7 +85,7 @@ ob_start();
|
||||
<div class="card mb-4">
|
||||
<div class="card-body">
|
||||
<p class="mb-0">
|
||||
Vous pouvez me joindre via le <a href="/?action=contact">formulaire de contact</a>.
|
||||
Vous pouvez me joindre via le <a href="/contact">formulaire de contact</a>.
|
||||
Je lis tous les messages, même si je ne réponds pas toujours vite.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
@@ -4,7 +4,7 @@ $existingFiles = $articles->getFiles($addFilesArticle['uuid']);
|
||||
?>
|
||||
|
||||
<div class="d-flex align-items-center gap-3 mb-4">
|
||||
<a href="/?action=edit&uuid=<?= rawurlencode($addFilesArticle['uuid']) ?>" class="btn btn-secondary btn-sm">← Retour</a>
|
||||
<a href="/edit/<?= rawurlencode($addFilesArticle['uuid']) ?>" class="btn btn-secondary btn-sm">← Retour</a>
|
||||
<h1 class="h4 mb-0">Ajouter des fichiers</h1>
|
||||
</div>
|
||||
|
||||
@@ -19,7 +19,7 @@ $existingFiles = $articles->getFiles($addFilesArticle['uuid']);
|
||||
<div class="card">
|
||||
<div class="card-body">
|
||||
<form method="POST"
|
||||
action="/?action=add_files&uuid=<?= rawurlencode($addFilesArticle['uuid']) ?>"
|
||||
action="/files/<?= rawurlencode($addFilesArticle['uuid']) ?>/add"
|
||||
enctype="multipart/form-data">
|
||||
|
||||
<div class="mb-3">
|
||||
@@ -34,7 +34,7 @@ $existingFiles = $articles->getFiles($addFilesArticle['uuid']);
|
||||
|
||||
<div class="d-flex gap-2">
|
||||
<button type="submit" class="btn btn-primary">Uploader</button>
|
||||
<a href="/?action=edit&uuid=<?= rawurlencode($addFilesArticle['uuid']) ?>"
|
||||
<a href="/edit/<?= rawurlencode($addFilesArticle['uuid']) ?>"
|
||||
class="btn btn-outline-secondary">Annuler</a>
|
||||
</div>
|
||||
|
||||
|
||||
+7
-7
@@ -17,7 +17,7 @@ function adminStatusBadge(array $a, int $now): string
|
||||
|
||||
<div class="d-flex justify-content-between align-items-center mb-4">
|
||||
<h1 class="h3 mb-0">Administration</h1>
|
||||
<a href="/?action=create" class="btn btn-primary btn-sm">+ Nouvel article</a>
|
||||
<a href="/new" class="btn btn-primary btn-sm">+ Nouvel article</a>
|
||||
</div>
|
||||
|
||||
<!-- Onglets -->
|
||||
@@ -25,24 +25,24 @@ function adminStatusBadge(array $a, int $now): string
|
||||
<?php if (isAdmin()): ?>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link <?= $tab === 'dashboard' ? 'active' : '' ?>"
|
||||
href="/?action=admin&tab=dashboard">Tableau de bord</a>
|
||||
href="/admin/dashboard">Tableau de bord</a>
|
||||
</li>
|
||||
<?php endif; ?>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link <?= $tab === 'articles' ? 'active' : '' ?>"
|
||||
href="/?action=admin&tab=articles"><?= isAdmin() ? 'Articles' : 'Mes articles' ?></a>
|
||||
href="/admin/articles"><?= isAdmin() ? 'Articles' : 'Mes articles' ?></a>
|
||||
</li>
|
||||
<?php if (isAdmin()): ?>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link <?= $tab === 'users' ? 'active' : '' ?>"
|
||||
href="/?action=admin&tab=users">Utilisateurs</a>
|
||||
href="/admin/users">Utilisateurs</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link <?= $tab === 'roles' ? 'active' : '' ?>"
|
||||
href="/?action=admin&tab=roles">Rôles</a>
|
||||
href="/admin/roles">Rôles</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/?action=categories">Catégories</a>
|
||||
<a class="nav-link" href="/categories">Catégories</a>
|
||||
</li>
|
||||
<?php endif; ?>
|
||||
</ul>
|
||||
@@ -132,7 +132,7 @@ function adminStatusBadge(array $a, int $now): string
|
||||
<?= htmlspecialchars(date('d/m/Y', strtotime((string)($a['published_at'] ?? $a['created_at'] ?? '')))) ?>
|
||||
</td>
|
||||
<td class="text-end text-nowrap">
|
||||
<a href="/?action=edit&uuid=<?= htmlspecialchars($a['uuid']) ?>"
|
||||
<a href="/edit/<?= htmlspecialchars($a['uuid']) ?>"
|
||||
class="btn btn-outline-secondary btn-sm">Modifier</a>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
<div class="col-lg-8 col-xl-7">
|
||||
|
||||
<div class="d-flex align-items-center gap-3 mb-4">
|
||||
<a href="/?action=import_image&uuid=<?= rawurlencode($ackArticle['uuid']) ?>"
|
||||
<a href="/import/<?= rawurlencode($ackArticle['uuid']) ?>"
|
||||
class="btn btn-secondary btn-sm">← Retour</a>
|
||||
<h1 class="h4 mb-0">Confirmation — droits d'auteur</h1>
|
||||
</div>
|
||||
@@ -99,7 +99,7 @@
|
||||
|
||||
<div class="d-flex gap-2">
|
||||
<button type="submit" class="btn btn-primary">Télécharger et insérer</button>
|
||||
<a href="/?action=import_image&uuid=<?= rawurlencode($ackArticle['uuid']) ?>"
|
||||
<a href="/import/<?= rawurlencode($ackArticle['uuid']) ?>"
|
||||
class="btn btn-outline-secondary">Annuler</a>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
+1
-1
@@ -4,7 +4,7 @@ $revMeta = $revisions[$revIndex] ?? [];
|
||||
?>
|
||||
|
||||
<div class="d-flex align-items-center gap-3 mb-3 flex-wrap">
|
||||
<a href="/?action=edit&uuid=<?= htmlspecialchars($article['uuid']) ?>" class="btn btn-secondary btn-sm">← Retour</a>
|
||||
<a href="/edit/<?= htmlspecialchars($article['uuid']) ?>" class="btn btn-secondary btn-sm">← Retour</a>
|
||||
<div>
|
||||
<strong><?= htmlspecialchars($article['title']) ?></strong>
|
||||
— révision #<?= (int)($revMeta['n'] ?? $revIndex + 1) ?>
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<?php ob_start(); ?>
|
||||
|
||||
<div class="d-flex align-items-center gap-3 mb-4">
|
||||
<a href="/?action=edit&uuid=<?= rawurlencode($importArticle['uuid']) ?>" class="btn btn-secondary btn-sm">← Retour</a>
|
||||
<a href="/edit/<?= rawurlencode($importArticle['uuid']) ?>" class="btn btn-secondary btn-sm">← Retour</a>
|
||||
<h1 class="h4 mb-0">Importer un fichier depuis une URL</h1>
|
||||
</div>
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
</div>
|
||||
<div class="d-flex gap-2">
|
||||
<button type="submit" class="btn btn-primary">Suivant →</button>
|
||||
<a href="/?action=edit&uuid=<?= rawurlencode($importArticle['uuid']) ?>"
|
||||
<a href="/edit/<?= rawurlencode($importArticle['uuid']) ?>"
|
||||
class="btn btn-outline-secondary">Annuler</a>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
@@ -40,7 +40,7 @@ $preSource = $step2Meta['canonical'] ?? $step2Meta['source'] ?? $step2Url;
|
||||
?>
|
||||
|
||||
<div class="d-flex align-items-center gap-3 mb-4">
|
||||
<a href="/?action=import_image&uuid=<?= rawurlencode($step2Article['uuid']) ?>" class="btn btn-secondary btn-sm">← Retour</a>
|
||||
<a href="/import/<?= rawurlencode($step2Article['uuid']) ?>" class="btn btn-secondary btn-sm">← Retour</a>
|
||||
<h1 class="h4 mb-0">Importer un fichier</h1>
|
||||
</div>
|
||||
|
||||
@@ -192,7 +192,7 @@ if ($visibleRows): ?>
|
||||
|
||||
<div class="d-flex gap-2">
|
||||
<button type="submit" class="btn btn-primary">Valider</button>
|
||||
<a href="/?action=edit&uuid=<?= rawurlencode($step2Article['uuid']) ?>"
|
||||
<a href="/edit/<?= rawurlencode($step2Article['uuid']) ?>"
|
||||
class="btn btn-outline-secondary">Annuler</a>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
@@ -100,11 +100,11 @@
|
||||
|
||||
<ul class="navbar-nav">
|
||||
<?php if (function_exists('isLoggedIn') && isLoggedIn()): ?>
|
||||
<li class="nav-item"><a class="nav-link" href="/?action=admin">Admin</a></li>
|
||||
<li class="nav-item"><a class="nav-link" href="/admin">Admin</a></li>
|
||||
<?php endif; ?>
|
||||
<?php if (function_exists('isLoggedIn') && isLoggedIn()): ?>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="/?action=profile">
|
||||
<a class="nav-link" href="/profile">
|
||||
<?= htmlspecialchars(function_exists('currentUserName') ? currentUserName() : (currentUserEmail() ?? '')) ?>
|
||||
</a>
|
||||
</li>
|
||||
@@ -133,10 +133,10 @@
|
||||
<small>© <?= date('Y') ?> — <a href="https://creativecommons.org/licenses/by/4.0/" target="_blank" rel="noopener">CC BY 4.0</a></small>
|
||||
</div>
|
||||
<nav class="footer-nav" aria-label="Liens du site">
|
||||
<a href="/?action=about">À propos</a>
|
||||
<a href="/?action=contact">Contact</a>
|
||||
<a href="/?action=legal">Mentions légales</a>
|
||||
<a href="/?action=licenses">Licences</a>
|
||||
<a href="/about">À propos</a>
|
||||
<a href="/contact">Contact</a>
|
||||
<a href="/legal">Mentions légales</a>
|
||||
<a href="/licenses">Licences</a>
|
||||
</nav>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+3
-3
@@ -35,7 +35,7 @@ ob_start();
|
||||
<div class="card-body">
|
||||
<p class="mb-1"><strong>Responsable de publication :</strong> Cédric Abonnel</p>
|
||||
<p class="mb-1"><strong>Qualité :</strong> Particulier — site personnel non commercial</p>
|
||||
<p class="mb-0"><strong>Contact :</strong> <a href="/?action=contact">formulaire de contact</a></p>
|
||||
<p class="mb-0"><strong>Contact :</strong> <a href="/contact">formulaire de contact</a></p>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
@@ -74,7 +74,7 @@ ob_start();
|
||||
</p>
|
||||
<p class="mb-0">
|
||||
Les composants tiers (Bootstrap, PHPMailer, police Inter…) sont soumis à leurs licences respectives,
|
||||
détaillées sur la <a href="/?action=licenses">page des licences</a>.
|
||||
détaillées sur la <a href="/licenses">page des licences</a>.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
@@ -99,7 +99,7 @@ ob_start();
|
||||
<p class="mb-0">
|
||||
Conformément au RGPD (règlement UE 2016/679), vous disposez d'un droit d'accès, de rectification
|
||||
et de suppression des données vous concernant. Pour exercer ces droits :
|
||||
<a href="/?action=contact">formulaire de contact</a>.
|
||||
<a href="/contact">formulaire de contact</a>.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+113
-102
@@ -102,96 +102,6 @@ $dateValue = isset($published_at)
|
||||
</div>
|
||||
<?php endif; ?>
|
||||
|
||||
<?php if (!empty($existingFiles)): ?>
|
||||
<?php $coverFile = $article['cover'] ?? ''; ?>
|
||||
<?php $filesMeta = $article['files_meta'] ?? []; ?>
|
||||
<div class="mb-3">
|
||||
<p class="form-label fw-semibold">Fichiers existants</p>
|
||||
<div class="list-group">
|
||||
<?php foreach ($existingFiles as $i => $f): ?>
|
||||
<?php
|
||||
$fileUrl = '/file?uuid=' . rawurlencode($uuid) . '&name=' . rawurlencode($f['name']);
|
||||
$fmeta = $filesMeta[$f['name']] ?? [];
|
||||
$isCoverFile = ($f['name'] === $coverFile);
|
||||
?>
|
||||
<div class="list-group-item py-2">
|
||||
<div class="d-flex align-items-center gap-3">
|
||||
<!-- Miniature -->
|
||||
<?php if ($f['is_image']): ?>
|
||||
<a href="<?= htmlspecialchars($fileUrl) ?>" target="_blank" rel="noopener" class="flex-shrink-0">
|
||||
<img src="<?= htmlspecialchars($fileUrl) ?>" alt=""
|
||||
style="width:56px;height:56px;object-fit:cover;border-radius:4px;<?= $isCoverFile ? 'outline:2px solid #0d6efd' : '' ?>">
|
||||
</a>
|
||||
<?php else: ?>
|
||||
<span style="width:56px;text-align:center;font-size:1.6rem;flex-shrink:0">
|
||||
<?= match(true) {
|
||||
str_starts_with($f['mime'], 'video/') => '🎬',
|
||||
str_starts_with($f['mime'], 'audio/') => '🎵',
|
||||
$f['mime'] === 'application/pdf' => '📑',
|
||||
default => '📄',
|
||||
} ?>
|
||||
</span>
|
||||
<?php endif; ?>
|
||||
|
||||
<!-- Infos + méta -->
|
||||
<div class="flex-grow-1 overflow-hidden">
|
||||
<div class="d-flex align-items-center gap-2 mb-1">
|
||||
<code class="text-truncate small"><?= htmlspecialchars($f['name']) ?></code>
|
||||
<small class="text-muted text-nowrap"><?= number_format($f['size'] / 1024, 1) ?> Ko</small>
|
||||
<?php if ($isCoverFile): ?>
|
||||
<span class="badge bg-primary">cover</span>
|
||||
<?php endif; ?>
|
||||
</div>
|
||||
<?php if ($f['is_image']): ?>
|
||||
<div class="d-flex gap-2 flex-wrap">
|
||||
<input type="hidden" name="fmeta_name[]" value="<?= htmlspecialchars($f['name']) ?>">
|
||||
<input type="text" name="fmeta_author[]"
|
||||
class="form-control form-control-sm"
|
||||
style="max-width:220px"
|
||||
placeholder="Auteur / crédit"
|
||||
value="<?= htmlspecialchars($fmeta['author'] ?? '') ?>">
|
||||
<input type="url" name="fmeta_source[]"
|
||||
class="form-control form-control-sm font-monospace"
|
||||
style="max-width:280px"
|
||||
placeholder="URL source"
|
||||
value="<?= htmlspecialchars($fmeta['source_url'] ?? '') ?>">
|
||||
</div>
|
||||
<?php endif; ?>
|
||||
</div>
|
||||
|
||||
<!-- Actions -->
|
||||
<div class="d-flex flex-column gap-1 flex-shrink-0 align-items-end">
|
||||
<?php if ($f['is_image'] && !$isCoverFile): ?>
|
||||
<div class="form-check mb-0">
|
||||
<input class="form-check-input" type="radio"
|
||||
name="cover_file" id="cover_<?= $i ?>"
|
||||
value="<?= htmlspecialchars($f['name']) ?>">
|
||||
<label class="form-check-label small" for="cover_<?= $i ?>">Cover</label>
|
||||
</div>
|
||||
<?php elseif ($isCoverFile): ?>
|
||||
<input type="hidden" name="cover_file" value="<?= htmlspecialchars($f['name']) ?>">
|
||||
<small class="text-primary">✓ Cover</small>
|
||||
<?php endif; ?>
|
||||
<div class="d-flex gap-1">
|
||||
<button type="button" class="btn btn-sm btn-outline-secondary"
|
||||
data-copy-md-name="<?= htmlspecialchars($fmeta['title'] ?? $f['name']) ?>"
|
||||
data-copy-md-is-image="<?= $f['is_image'] ? '1' : '0' ?>">
|
||||
MD
|
||||
</button>
|
||||
<button type="submit" form="del-file-<?= $i ?>"
|
||||
class="btn btn-sm btn-outline-danger"
|
||||
data-confirm="Supprimer « <?= htmlspecialchars($f['name']) ?> » ?">
|
||||
✕
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<?php endforeach; ?>
|
||||
</div>
|
||||
</div>
|
||||
<?php endif; ?>
|
||||
|
||||
<?php if ($action === 'edit'): ?>
|
||||
</div><!-- /col-lg-8 -->
|
||||
|
||||
@@ -285,6 +195,91 @@ $dateValue = isset($published_at)
|
||||
|
||||
<hr class="my-3">
|
||||
|
||||
<?php if (!empty($existingFiles)): ?>
|
||||
<?php $coverFile = $article['cover'] ?? ''; ?>
|
||||
<?php $filesMeta = $article['files_meta'] ?? []; ?>
|
||||
<div class="mb-3">
|
||||
<p class="form-label fw-semibold small mb-2">Fichiers existants</p>
|
||||
<div class="list-group">
|
||||
<?php foreach ($existingFiles as $i => $f): ?>
|
||||
<?php
|
||||
$fileUrl = '/file?uuid=' . rawurlencode($uuid) . '&name=' . rawurlencode($f['name']);
|
||||
$fmeta = $filesMeta[$f['name']] ?? [];
|
||||
$isCoverFile = ($f['name'] === $coverFile);
|
||||
?>
|
||||
<div class="list-group-item py-2 px-2">
|
||||
<div class="d-flex align-items-start gap-2">
|
||||
<!-- Miniature -->
|
||||
<?php if ($f['is_image']): ?>
|
||||
<a href="<?= htmlspecialchars($fileUrl) ?>" target="_blank" rel="noopener" class="flex-shrink-0">
|
||||
<img src="<?= htmlspecialchars($fileUrl) ?>" alt=""
|
||||
style="width:48px;height:48px;object-fit:cover;border-radius:4px;<?= $isCoverFile ? 'outline:2px solid #0d6efd' : '' ?>">
|
||||
</a>
|
||||
<?php else: ?>
|
||||
<span style="width:48px;text-align:center;font-size:1.4rem;flex-shrink:0;line-height:48px">
|
||||
<?= match(true) {
|
||||
str_starts_with($f['mime'], 'video/') => '🎬',
|
||||
str_starts_with($f['mime'], 'audio/') => '🎵',
|
||||
$f['mime'] === 'application/pdf' => '📑',
|
||||
default => '📄',
|
||||
} ?>
|
||||
</span>
|
||||
<?php endif; ?>
|
||||
|
||||
<!-- Infos + méta -->
|
||||
<div class="flex-grow-1 overflow-hidden" style="min-width:0">
|
||||
<div class="d-flex align-items-center gap-1 mb-1 flex-wrap">
|
||||
<code class="text-truncate small" style="max-width:100%"><?= htmlspecialchars($f['name']) ?></code>
|
||||
<small class="text-muted text-nowrap"><?= number_format($f['size'] / 1024, 1) ?> Ko</small>
|
||||
<?php if ($isCoverFile): ?>
|
||||
<span class="badge bg-primary">cover</span>
|
||||
<?php endif; ?>
|
||||
</div>
|
||||
<div class="d-flex gap-1 mb-1">
|
||||
<input type="hidden" name="fmeta_name[]" value="<?= htmlspecialchars($f['name']) ?>">
|
||||
<input type="text" name="fmeta_author[]"
|
||||
class="form-control form-control-sm"
|
||||
placeholder="Auteur / crédit"
|
||||
value="<?= htmlspecialchars($fmeta['author'] ?? '') ?>">
|
||||
<input type="url" name="fmeta_source[]"
|
||||
class="form-control form-control-sm font-monospace"
|
||||
placeholder="URL source"
|
||||
value="<?= htmlspecialchars($fmeta['source_url'] ?? '') ?>">
|
||||
</div>
|
||||
<div class="d-flex align-items-center gap-1 flex-wrap">
|
||||
<?php if ($f['is_image'] && !$isCoverFile): ?>
|
||||
<div class="form-check mb-0">
|
||||
<input class="form-check-input" type="radio"
|
||||
name="cover_file" id="cover_<?= $i ?>"
|
||||
value="<?= htmlspecialchars($f['name']) ?>">
|
||||
<label class="form-check-label small" for="cover_<?= $i ?>">Cover</label>
|
||||
</div>
|
||||
<?php elseif ($isCoverFile): ?>
|
||||
<input type="hidden" name="cover_file" value="<?= htmlspecialchars($f['name']) ?>">
|
||||
<small class="text-primary">✓ Cover</small>
|
||||
<?php endif; ?>
|
||||
<div class="d-flex gap-1 ms-auto">
|
||||
<button type="button" class="btn btn-sm btn-outline-secondary"
|
||||
data-copy-md-name="<?= htmlspecialchars($fmeta['title'] ?? $f['name']) ?>"
|
||||
data-copy-md-is-image="<?= $f['is_image'] ? '1' : '0' ?>">
|
||||
MD
|
||||
</button>
|
||||
<button type="submit" form="del-file-<?= $i ?>"
|
||||
class="btn btn-sm btn-outline-danger"
|
||||
data-confirm="Supprimer « <?= htmlspecialchars($f['name']) ?> » ?">
|
||||
✕
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<?php endforeach; ?>
|
||||
</div>
|
||||
</div>
|
||||
<hr class="my-3">
|
||||
<?php endif; ?>
|
||||
|
||||
<?php $sidebarImages = array_filter($existingFiles ?? [], fn ($f) => $f['is_image']); ?>
|
||||
|
||||
<?php if ($sidebarImages): ?>
|
||||
@@ -341,17 +336,17 @@ $dateValue = isset($published_at)
|
||||
<?php endif; ?>
|
||||
|
||||
<div class="d-flex flex-column gap-2">
|
||||
<a href="/?action=add_files&uuid=<?= rawurlencode($uuid) ?>" class="btn btn-outline-secondary btn-sm">
|
||||
<a href="/files/<?= rawurlencode($uuid) ?>/add" class="btn btn-outline-secondary btn-sm">
|
||||
+ Ajouter des fichiers
|
||||
</a>
|
||||
<a href="/?action=import_image&uuid=<?= rawurlencode($uuid) ?>" class="btn btn-outline-secondary btn-sm">
|
||||
<a href="/import/<?= rawurlencode($uuid) ?>" class="btn btn-outline-secondary btn-sm">
|
||||
+ Importer depuis une URL
|
||||
</a>
|
||||
<?php
|
||||
$hasSources = !empty($article['external_links']) || !empty($existingFiles);
|
||||
if ($hasSources):
|
||||
?>
|
||||
<a href="/?action=sources&uuid=<?= rawurlencode($uuid) ?>" class="btn btn-outline-secondary btn-sm">
|
||||
if ($hasSources):
|
||||
?>
|
||||
<a href="/sources/<?= rawurlencode($uuid) ?>" class="btn btn-outline-secondary btn-sm">
|
||||
Sources & métadonnées
|
||||
</a>
|
||||
<?php endif; ?>
|
||||
@@ -373,10 +368,18 @@ $dateValue = isset($published_at)
|
||||
<?php if (!empty($article['revisions'])): ?>
|
||||
<hr class="my-4">
|
||||
<div>
|
||||
<button class="btn btn-sm btn-link text-secondary text-decoration-none p-0 fw-semibold"
|
||||
type="button" data-bs-toggle="collapse" data-bs-target="#historyPanel">
|
||||
▸ Historique des révisions (<?= count($article['revisions']) ?>)
|
||||
</button>
|
||||
<div class="d-flex align-items-center gap-3 mb-1">
|
||||
<button class="btn btn-sm btn-link text-secondary text-decoration-none p-0 fw-semibold"
|
||||
type="button" data-bs-toggle="collapse" data-bs-target="#historyPanel">
|
||||
▸ Historique des révisions (<?= count($article['revisions']) ?>)
|
||||
</button>
|
||||
<form method="POST" action="/?action=delete_all_revisions&uuid=<?= rawurlencode($uuid) ?>" class="d-inline ms-auto">
|
||||
<button type="submit" class="btn btn-sm btn-outline-danger"
|
||||
data-confirm="Supprimer tout l'historique des révisions ?">
|
||||
Tout supprimer
|
||||
</button>
|
||||
</form>
|
||||
</div>
|
||||
<div class="collapse mt-3" id="historyPanel">
|
||||
<table class="table table-sm table-hover align-middle">
|
||||
<thead>
|
||||
@@ -384,8 +387,9 @@ $dateValue = isset($published_at)
|
||||
</thead>
|
||||
<tbody>
|
||||
<?php foreach (array_reverse($article['revisions']) as $rev): ?>
|
||||
<?php $revN = (int)($rev['n'] ?? 0); ?>
|
||||
<tr>
|
||||
<td class="text-muted small"><?= (int)($rev['n'] ?? 0) ?></td>
|
||||
<td class="text-muted small"><?= $revN ?></td>
|
||||
<td class="small text-nowrap">
|
||||
<?= htmlspecialchars(date('d/m/Y H:i', strtotime((string)($rev['date'] ?? '')))) ?>
|
||||
</td>
|
||||
@@ -395,11 +399,18 @@ $dateValue = isset($published_at)
|
||||
<td class="small text-muted">
|
||||
<?= htmlspecialchars($rev['comment'] ?? '') ?: '<span class="text-muted">–</span>' ?>
|
||||
</td>
|
||||
<td>
|
||||
<a href="/?action=diff&uuid=<?= rawurlencode($uuid) ?>&rev=<?= (int)($rev['n'] ?? 0) ?>"
|
||||
<td class="text-nowrap">
|
||||
<a href="/diff/<?= rawurlencode($uuid) ?>/<?= $revN ?>"
|
||||
class="btn btn-outline-secondary btn-sm" target="_blank">
|
||||
Diff
|
||||
</a>
|
||||
<form method="POST" action="/?action=delete_revision&uuid=<?= rawurlencode($uuid) ?>" class="d-inline">
|
||||
<input type="hidden" name="rev_n" value="<?= $revN ?>">
|
||||
<button type="submit" class="btn btn-sm btn-outline-danger"
|
||||
data-confirm="Supprimer la révision #<?= $revN ?> ?">
|
||||
✕
|
||||
</button>
|
||||
</form>
|
||||
</td>
|
||||
</tr>
|
||||
<?php endforeach; ?>
|
||||
|
||||
@@ -54,10 +54,10 @@ ob_start();
|
||||
<?php if ($isAvantPremiere): ?>
|
||||
<span class="text-muted">Disponible le <?= htmlspecialchars(date('d/m/Y \à H\hi', strtotime((string)($post['published_at'] ?? '')))) ?></span>
|
||||
<?php else: ?>
|
||||
<span><?= htmlspecialchars(date('d/m/Y', strtotime((string)($post['created_at'] ?? '')))) ?></span>
|
||||
<span><?= htmlspecialchars(date('d/m/Y', strtotime((string)($post['published_at'] ?? $post['created_at'] ?? '')))) ?></span>
|
||||
<?php endif; ?>
|
||||
<?php if (function_exists('isAdmin') && isAdmin()): ?>
|
||||
<a href="/?action=edit&uuid=<?= htmlspecialchars($post['uuid']) ?>" class="post-entry-edit">modifier</a>
|
||||
<a href="/edit/<?= htmlspecialchars($post['uuid']) ?>" class="post-entry-edit">modifier</a>
|
||||
<?php endif; ?>
|
||||
<?php if (!$isLocked): ?>
|
||||
<a href="<?= htmlspecialchars($postUrl) ?>" class="post-entry-read">→ lire</a>
|
||||
|
||||
+18
-6
@@ -32,7 +32,7 @@ if ($files) {
|
||||
$externalLinks = $article['external_links'] ?? [];
|
||||
$hasLeftSidebar = !empty($categorySidebar ?? []);
|
||||
?>
|
||||
<div class="row g-4 align-items-start flex-nowrap-lg">
|
||||
<div class="row g-4 align-items-start flex-lg-nowrap">
|
||||
|
||||
<?php if ($hasLeftSidebar): ?>
|
||||
<div class="post-sidebar-col order-2 order-lg-1">
|
||||
@@ -87,8 +87,8 @@ $hasSources = (!empty($externalLinks) || !empty($files))
|
||||
<div class="article-hero-top">
|
||||
<a href="/" class="hero-btn">← Retour</a>
|
||||
<?php if (function_exists('isAdmin') && isAdmin()): ?>
|
||||
<a href="/?action=edit&uuid=<?= rawurlencode($article['uuid']) ?>" class="hero-btn ms-auto">✎ Modifier</a>
|
||||
<a href="/?action=delete&uuid=<?= rawurlencode($article['uuid']) ?>"
|
||||
<a href="/edit/<?= rawurlencode($article['uuid']) ?>" class="hero-btn ms-auto">✎ Modifier</a>
|
||||
<a href="/delete/<?= rawurlencode($article['uuid']) ?>"
|
||||
class="hero-btn hero-btn--danger"
|
||||
data-confirm="Supprimer cet article définitivement ?">🗑 Supprimer</a>
|
||||
<?php endif; ?>
|
||||
@@ -111,7 +111,7 @@ $hasSources = (!empty($externalLinks) || !empty($files))
|
||||
</div>
|
||||
<div class="article-hero-right">
|
||||
<?php if ($hasSources): ?>
|
||||
<a href="/?action=sources&uuid=<?= rawurlencode($article['uuid']) ?>" class="hero-btn">ℹ Sources</a>
|
||||
<a href="/sources/<?= rawurlencode($article['uuid']) ?>" class="hero-btn">ℹ Sources</a>
|
||||
<?php endif; ?>
|
||||
<?php if (function_exists('isLoggedIn') && isLoggedIn()): ?>
|
||||
<form method="post" action="/?action=rate" class="d-flex align-items-center gap-2">
|
||||
@@ -162,10 +162,14 @@ $hasSources = (!empty($externalLinks) || !empty($files))
|
||||
<aside class="related-sidebar">
|
||||
|
||||
<?php if (!empty($attachments)): ?>
|
||||
<?php $filesMeta = $article['files_meta'] ?? []; ?>
|
||||
<h6 class="related-sidebar-title">Pièces jointes</h6>
|
||||
<div class="d-flex flex-column gap-2 mb-4">
|
||||
<?php foreach ($attachments as $file):
|
||||
$fileUrl = '/file?uuid=' . rawurlencode($article['uuid']) . '&name=' . rawurlencode($file['name']);
|
||||
$fileUrl = '/file?uuid=' . rawurlencode($article['uuid']) . '&name=' . rawurlencode($file['name']);
|
||||
$fmeta = $filesMeta[$file['name']] ?? [];
|
||||
$fAuthor = trim($fmeta['author'] ?? '');
|
||||
$fSource = trim($fmeta['source_url'] ?? '');
|
||||
?>
|
||||
<a href="<?= htmlspecialchars($fileUrl) ?>" target="_blank" rel="noopener" class="source-card">
|
||||
<?php if ($file['is_image']): ?>
|
||||
@@ -179,7 +183,15 @@ $hasSources = (!empty($externalLinks) || !empty($files))
|
||||
<?php endif; ?>
|
||||
<div class="source-card-body">
|
||||
<div class="source-card-title"><?= htmlspecialchars($file['name']) ?></div>
|
||||
<div class="source-card-meta"><?= htmlspecialchars(number_format($file['size'] / 1024, 1)) ?> Ko</div>
|
||||
<div class="source-card-meta">
|
||||
<?= htmlspecialchars(number_format($file['size'] / 1024, 1)) ?> Ko
|
||||
<?php if ($fAuthor !== ''): ?>
|
||||
· <?= htmlspecialchars($fAuthor) ?>
|
||||
<?php endif; ?>
|
||||
<?php if ($fSource !== ''): ?>
|
||||
· <?= htmlspecialchars(parse_url($fSource, PHP_URL_HOST) ?: $fSource) ?>
|
||||
<?php endif; ?>
|
||||
</div>
|
||||
</div>
|
||||
</a>
|
||||
<?php endforeach; ?>
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
<div class="alert alert-danger py-2 small mb-3"><?= htmlspecialchars($profileError) ?></div>
|
||||
<?php endif; ?>
|
||||
|
||||
<form method="post" action="/?action=profile">
|
||||
<form method="post" action="/profile">
|
||||
<div class="mb-3">
|
||||
<label class="form-label fw-semibold" for="display_name">Nom affiché</label>
|
||||
<input type="text" id="display_name" name="display_name"
|
||||
|
||||
@@ -38,7 +38,7 @@ function renderMetaCell(string $key, mixed $val, array $row = []): string
|
||||
?>
|
||||
|
||||
<div class="d-flex align-items-center gap-3 mb-1">
|
||||
<a href="/?action=edit&uuid=<?= rawurlencode($article['uuid']) ?>" class="btn btn-secondary btn-sm">← Modifier</a>
|
||||
<a href="/edit/<?= rawurlencode($article['uuid']) ?>" class="btn btn-secondary btn-sm">← Modifier</a>
|
||||
<h1 class="h4 mb-0">Sources & médias</h1>
|
||||
</div>
|
||||
<p class="text-muted small mb-4"><?= htmlspecialchars($article['title']) ?></p>
|
||||
|
||||
Reference in New Issue
Block a user