Cleaned
This commit is contained in:
19
.gitignore
vendored
19
.gitignore
vendored
@@ -1,13 +1,20 @@
|
|||||||
# Environnement local
|
# ============================================
|
||||||
|
# Environnement & Configuration
|
||||||
|
# ============================================
|
||||||
.env
|
.env
|
||||||
|
|
||||||
# Composer
|
# ============================================
|
||||||
|
# Dépendances Composer
|
||||||
|
# ============================================
|
||||||
/vendor/
|
/vendor/
|
||||||
composer.lock
|
composer.lock
|
||||||
|
|
||||||
# Base de données SQLite
|
# ============================================
|
||||||
/database/*.sqlite
|
# Base de données
|
||||||
/database/*.db
|
# ============================================
|
||||||
|
/database/
|
||||||
|
|
||||||
# Cache et logs
|
# ============================================
|
||||||
|
# Cache & Logs
|
||||||
|
# ============================================
|
||||||
/var/
|
/var/
|
||||||
@@ -15,7 +15,8 @@
|
|||||||
"slim/psr7": "*",
|
"slim/psr7": "*",
|
||||||
"twig/twig": "*",
|
"twig/twig": "*",
|
||||||
"slim/twig-view": "^3.4",
|
"slim/twig-view": "^3.4",
|
||||||
"catfan/medoo": "2.*"
|
"catfan/medoo": "2.*",
|
||||||
|
"vlucas/phpdotenv": "^5.6"
|
||||||
},
|
},
|
||||||
"autoload": {
|
"autoload": {
|
||||||
"psr-4": {
|
"psr-4": {
|
||||||
|
|||||||
@@ -4,6 +4,12 @@ declare(strict_types=1);
|
|||||||
|
|
||||||
require __DIR__ . '/../vendor/autoload.php';
|
require __DIR__ . '/../vendor/autoload.php';
|
||||||
|
|
||||||
|
use Dotenv\Dotenv;
|
||||||
|
|
||||||
|
// Charger les variables d'environnement
|
||||||
|
$dotenv = Dotenv::createImmutable(__DIR__ . '/..');
|
||||||
|
$dotenv->load();
|
||||||
|
|
||||||
use Slim\Factory\AppFactory;
|
use Slim\Factory\AppFactory;
|
||||||
use Slim\Views\TwigMiddleware;
|
use Slim\Views\TwigMiddleware;
|
||||||
use Slim\Views\Twig;
|
use Slim\Views\Twig;
|
||||||
@@ -18,9 +24,12 @@ $env = $_ENV['APP_ENV'] ?? 'production';
|
|||||||
$isDev = strtolower($env) === 'development';
|
$isDev = strtolower($env) === 'development';
|
||||||
|
|
||||||
// Dossier de cache Twig (false en dev, chemin en prod)
|
// Dossier de cache Twig (false en dev, chemin en prod)
|
||||||
$twigCache = $isDev ? false : __DIR__ . '/../var/cache/twig';
|
$twigCache = false;
|
||||||
if ($twigCache && !is_dir($twigCache)) {
|
if (!$isDev) {
|
||||||
|
$twigCache = __DIR__ . '/../var/cache/twig';
|
||||||
|
if (!is_dir($twigCache)) {
|
||||||
@mkdir($twigCache, 0755, true);
|
@mkdir($twigCache, 0755, true);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Chemin base de données
|
// Chemin base de données
|
||||||
@@ -76,6 +85,7 @@ $app->add(TwigMiddleware::create($app, $twig));
|
|||||||
$controller = new PostController($twig, $db);
|
$controller = new PostController($twig, $db);
|
||||||
|
|
||||||
$app->get('/', [$controller, 'index']);
|
$app->get('/', [$controller, 'index']);
|
||||||
|
$app->get('/article/{slug}', [$controller, 'show']);
|
||||||
$app->get('/admin', [$controller, 'admin']);
|
$app->get('/admin', [$controller, 'admin']);
|
||||||
$app->get('/admin/edit/{id}', [$controller, 'form']);
|
$app->get('/admin/edit/{id}', [$controller, 'form']);
|
||||||
$app->post('/admin/create', [$controller, 'create']);
|
$app->post('/admin/create', [$controller, 'create']);
|
||||||
|
|||||||
@@ -30,6 +30,33 @@ class PostController
|
|||||||
return $this->view->render($res, 'pages/home.twig', ['posts' => $posts]);
|
return $this->view->render($res, 'pages/home.twig', ['posts' => $posts]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Affiche un article complet par son slug.
|
||||||
|
*/
|
||||||
|
public function show(Request $req, Response $res, array $args): Response
|
||||||
|
{
|
||||||
|
$slug = (string)($args['slug'] ?? '');
|
||||||
|
|
||||||
|
// Récupérer tous les posts et chercher celui qui correspond au slug
|
||||||
|
$rows = $this->db->select('post', '*', ['ORDER' => ['id' => 'DESC']]);
|
||||||
|
$post = null;
|
||||||
|
|
||||||
|
foreach ($rows ?: [] as $row) {
|
||||||
|
$postObj = Post::fromArray($row);
|
||||||
|
if ($postObj->getSlug() === $slug) {
|
||||||
|
$post = $postObj;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!$post) {
|
||||||
|
$res->getBody()->write('Article non trouvé');
|
||||||
|
return $res->withStatus(404);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $this->view->render($res, 'pages/post_detail.twig', ['post' => $post]);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Affiche la page d'administration.
|
* Affiche la page d'administration.
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -135,18 +135,6 @@ final class Post
|
|||||||
return trim($slug, '-');
|
return trim($slug, '-');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Indique si l'article a été créé récemment.
|
|
||||||
*
|
|
||||||
* @param int $days Nombre de jours
|
|
||||||
* @return bool
|
|
||||||
*/
|
|
||||||
public function isRecent(int $days = 7): bool
|
|
||||||
{
|
|
||||||
$limit = new DateTime("-{$days} days");
|
|
||||||
return $this->createdAt > $limit;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Retourne les données prêtes à persister en DB.
|
* Retourne les données prêtes à persister en DB.
|
||||||
*
|
*
|
||||||
|
|||||||
@@ -25,9 +25,6 @@
|
|||||||
<tr>
|
<tr>
|
||||||
<td>
|
<td>
|
||||||
<strong>{{ post.title }}</strong>
|
<strong>{{ post.title }}</strong>
|
||||||
{% if post.isRecent(7) %}
|
|
||||||
<span class="badge badge-new">Nouveau</span>
|
|
||||||
{% endif %}
|
|
||||||
</td>
|
</td>
|
||||||
<td>{{ post.createdAt|date("d/m/Y H:i") }}</td>
|
<td>{{ post.createdAt|date("d/m/Y H:i") }}</td>
|
||||||
<td>{{ post.updatedAt|date("d/m/Y H:i") }}</td>
|
<td>{{ post.updatedAt|date("d/m/Y H:i") }}</td>
|
||||||
|
|||||||
@@ -9,9 +9,6 @@
|
|||||||
|
|
||||||
<div class="post-meta">
|
<div class="post-meta">
|
||||||
<small>Publié le {{ post.createdAt|date("d/m/Y à H:i") }}</small>
|
<small>Publié le {{ post.createdAt|date("d/m/Y à H:i") }}</small>
|
||||||
{% if post.isRecent(7) %}
|
|
||||||
<span class="badge badge-new">Nouveau</span>
|
|
||||||
{% endif %}
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<p>{{ post.getExcerpt(200) }}</p>
|
<p>{{ post.getExcerpt(200) }}</p>
|
||||||
|
|||||||
29
views/pages/post_detail.twig
Normal file
29
views/pages/post_detail.twig
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
{% extends "layout.twig" %}
|
||||||
|
|
||||||
|
{% block title %}{{ post.title }} – Mon Blog{% endblock %}
|
||||||
|
|
||||||
|
{% block content %}
|
||||||
|
<article class="post">
|
||||||
|
<h1>{{ post.title }}</h1>
|
||||||
|
|
||||||
|
<div class="post-meta">
|
||||||
|
<small>Publié le {{ post.createdAt|date("d/m/Y à H:i") }}</small>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
{% if post.updatedAt != post.createdAt %}
|
||||||
|
<div class="post-updated">
|
||||||
|
<small><em>Mis à jour le {{ post.updatedAt|date("d/m/Y à H:i") }}</em></small>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
|
<div class="post-content">
|
||||||
|
{{ post.content|raw }}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<hr>
|
||||||
|
<p>
|
||||||
|
<a href="/">← Retour aux articles</a>
|
||||||
|
</p>
|
||||||
|
</article>
|
||||||
|
{% endblock %}
|
||||||
Reference in New Issue
Block a user