dev/api/post.php

112 lines
3.3 KiB
PHP

<?php
session_start();
header('Content-Type: application/json');
require '../config/db.php';
require '../lib/RateLimit.php';
require '../lib/FileValidator.php';
$env = require '../config/env.php';
$rateLimit = new RateLimit($pdo);
$fileValidator = new FileValidator();
$userId = $_SESSION['user_id'] ?? null;
if (!$userId) {
http_response_code(401);
echo json_encode(['success' => false, 'message' => 'Vous devez être connecté']);
exit;
}
// Rate limiting : 1 post par minute par utilisateur
if ($rateLimit->isBlocked($userId, 'post', 1, 60)) {
http_response_code(429);
echo json_encode(['success' => false, 'message' => 'Vous ne pouvez poster qu\'une fois par minute']);
exit;
}
$content = trim($_POST['content'] ?? '');
if (empty($content)) {
http_response_code(400);
echo json_encode(['success' => false, 'message' => 'Le message ne peut pas être vide']);
exit;
}
if (strlen($content) > 5000) {
http_response_code(400);
echo json_encode(['success' => false, 'message' => 'Le message ne doit pas dépasser 5000 caractères']);
exit;
}
// Insérer le message
$stmt = $pdo->prepare(
"INSERT INTO `{$env['TABLE_MESSAGES']}` (id_utilisateur, contenu, date_creation)
VALUES (?, ?, NOW())"
);
$stmt->execute([$userId, $content]);
$messageId = $pdo->lastInsertId();
// Traiter les fichiers
if (!empty($_FILES['image']['tmp_name'])) {
$file = $_FILES['image'];
// Valider le fichier avec un max de 2 Mo
$validationResult = $fileValidator->validate($file, 2 * 1024 * 1024);
if (!$validationResult['valid']) {
http_response_code(400);
echo json_encode(['success' => false, 'message' => $validationResult['error']]);
exit;
}
// Vérifier la sécurité du fichier (avant de le déplacer)
if (!$fileValidator->isSafe($file['tmp_name'])) {
http_response_code(400);
echo json_encode(['success' => false, 'message' => 'Le fichier contient du contenu dangereux']);
exit;
}
// Créer le répertoire uploads s'il n'existe pas
$uploadDir = __DIR__ . '/../uploads/';
if (!is_dir($uploadDir)) {
mkdir($uploadDir, 0755, true);
}
// Générer un nom de fichier sécurisé
$fileName = uniqid('post_', true) . '.' . $validationResult['ext'];
$filePath = $uploadDir . $fileName;
// Vérifier les permissions
if (!is_writable($uploadDir)) {
http_response_code(500);
echo json_encode(['success' => false, 'message' => 'Erreur serveur']);
exit;
}
// Déplacer le fichier
if (!move_uploaded_file($file['tmp_name'], $filePath)) {
http_response_code(500);
echo json_encode(['success' => false, 'message' => 'Erreur lors de l\'upload']);
exit;
}
// Sauvegarder dans la DB le chemin du fichier (pas le base64)
$stmt = $pdo->prepare(
"INSERT INTO `{$env['TABLE_FILES']}`
(id_message, nom_fichier, chemin_fichier, taille, type_mime, date_upload)
VALUES (?, ?, ?, ?, ?, NOW())"
);
$stmt->execute([
$messageId,
$file['name'],
'/uploads/' . $fileName, // Chemin relatif au web
$file['size'],
$validationResult['mime']
]);
}
// Enregistrer l'activité
$rateLimit->recordAttempt($userId, 'post');
echo json_encode(['success' => true, 'message' => 'Post publié avec succès']);