getConnection(); $db->exec(" CREATE TABLE articles ( id INTEGER PRIMARY KEY AUTOINCREMENT, title TEXT, content TEXT, author TEXT, category TEXT, tags TEXT, created TIMESTAMP DEFAULT CURRENT_TIMESTAMP );"); unset($db); } catch (PDOException $e) { throw new InternalServerErrorException($e->getMessage()); } } } /** * Baut die Verbindung zur Datenbank auf. * @throws InternalServerErrorException */ private function getConnection() { try { $user = 'root'; $pw = null; $dsn = 'sqlite:' . __DIR__ . '/../../db/articles.db'; return new PDO($dsn, $user, $pw); } catch (PDOException $e) { throw new InternalServerErrorException($e->getMessage()); } } /** * Gibt die DatabaseArticleManager-Instanz zurück. * @return DatabaseArticleManager */ public static function getInstance() { if (self::$instance == null) { self::$instance = new DatabaseArticleManager(); } return self::$instance; } public function addArticle($title, $content, $author, $category, $tags) { try { $db = $this->getConnection(); $sql = "INSERT INTO articles (title, content, author, category, tags) VALUES (:title, :content, :author, :category, :tags);"; $command = $db->prepare($sql); if (!$command) { throw new InternalServerErrorException("internal_error"); } // Verknüpft die übergebenen Parameter exakt mit den SQL-Platzhaltern $success = $command->execute([ ":title" => $title, ":content" => $content, ":author" => $author, ":category" => $category, ":tags" => $tags ]); if (!$success) { throw new InternalServerErrorException("internal_error"); } return intval($db->lastInsertId()); } catch (PDOException $e) { throw new InternalServerErrorException($e->getMessage()); } } public function updateArticle($id, $article, $author) { if (empty($article)) { throw new InternalServerErrorException("internal_error"); } // Berechtigungsprüfung analog zur lokalen Implementierung: if ($article->getAuthor() !== $author) { throw new UnauthorizedAccessException("unauthorized_access"); } try { $db = $this->getConnection(); $sql = "UPDATE articles SET title = :title, content = :content, author = :author, category = :category, tags = :tags WHERE id = :id;"; $command = $db->prepare($sql); if (!$command) { throw new InternalServerErrorException("internal_error"); } $success = $command->execute([ ":id" => $id, ":title" => $article->getTitle(), ":content" => $article->getContent(), ":author" => $author, ":category" => $article->getCategory(), ":tags" => $article->getTags() ]); // rowCount() prüft, ob eine Zeile mit dieser ID existierte und geändert werden konnte if (!$success || $command->rowCount() === 0) { // Falls die ID nicht existiert, prüfen wir, ob sie überhaupt da ist if (!$this->getArticle($id)) { throw new NotFoundException("missing_id"); } } } catch (PDOException $e) { throw new InternalServerErrorException("internal_error"); } } public function deleteArticle($id, $author) { $article = getArticle($id); if (empty($article)) { throw new NotFoundException("not_found_article"); } // Berechtigungsprüfung: if ($article->getAuthor() !== $author) { throw new UnauthorizedAccessException("unauthorized_access"); } try { $db = $this->getConnection(); $sql = "DELETE FROM articles WHERE id = :id;"; $command = $db->prepare($sql); if (!$command) { throw new InternalServerErrorException("internal_error"); } if (!$command->execute([":id" => $id])) { throw new InternalServerErrorException("internal_error"); } } catch (PDOException $exc) { throw new InternalServerErrorException("internal_error"); } } public function getArticle($id) { try { $db = $this->getConnection(); $sql = "SELECT * FROM articles WHERE id = :id;"; $command = $db->prepare($sql); if (!$command) { throw new InternalServerErrorException("internal_error"); } $command->execute([":id" => $id]); $row = $command->fetch(PDO::FETCH_ASSOC); if ($row) { return new Article( intval($row['id']), $row['title'], $row['content'], $row['author'], $row['category'], $row['tags'], $row['created'] ); } return null; } catch (PDOException $e) { throw new InternalServerErrorException("internal_error"); } } public function getAllArticles() { try { $db = $this->getConnection(); $sql = "SELECT * FROM articles;"; $command = $db->query($sql); if (!$command) { throw new InternalServerErrorException("internal_error"); } $rows = $command->fetchAll(PDO::FETCH_ASSOC); $articles = []; foreach ($rows as $row) { $articles[] = new Article( intval($row['id']), $row['title'], $row['content'], $row['author'], $row['category'], $row['tags'], $row['created'] ); } return $articles; } catch (PDOException $e) { throw new InternalServerErrorException("internal_error"); } } public function getArticlesByAuthor($author) { try { $db = $this->getConnection(); $sql = "SELECT * FROM articles WHERE author = :author;"; $command = $db->prepare($sql); if (!$command) { throw new InternalServerErrorException("internal_error"); } $command->execute([":author" => $author]); $rows = $command->fetchAll(PDO::FETCH_ASSOC); $filteredArticles = []; foreach ($rows as $row) { $filteredArticles[] = new Article( intval($row['id']), $row['title'], $row['content'], $row['author'], $row['category'], $row['tags'], $row['created'] ); } return $filteredArticles; } catch (PDOException $e) { throw new InternalServerErrorException("internal_error"); } } public function getArticlesByCategory($category) { try { $db = $this->getConnection(); $sql = "SELECT * FROM articles WHERE category = :category;"; $command = $db->prepare($sql); if (!$command) { throw new InternalServerErrorException("internal_error"); } $command->execute([":category" => $category]); $rows = $command->fetchAll(PDO::FETCH_ASSOC); $filteredArticles = []; foreach ($rows as $row) { $filteredArticles[] = new Article( intval($row['id']), $row['title'], $row['content'], $row['author'], $row['category'], $row['tags'], $row['created'] ); } return $filteredArticles; } catch (PDOException $exc) { throw new InternalServerErrorException("internal_error"); } } public function search(string $keyword): array { // TODO: implement search() return []; } }