commit 8fbfd7ffeba547542b641fd55bd91fa621b7a2c1 Author: mrcwlnd Date: Mon Apr 21 22:06:17 2025 +0000 Dateien nach "/" hochladen diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..9580a39 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,13 @@ +# Basisimage +FROM node:20 + +# Arbeitsverzeichnis setzen +WORKDIR /app + +# Dateien kopieren +COPY package*.json ./ +RUN npm install +COPY . . + +# Startbefehl +CMD ["node", "index.js"] diff --git a/index.js b/index.js new file mode 100644 index 0000000..affc4d5 --- /dev/null +++ b/index.js @@ -0,0 +1,264 @@ +const express = require("express"); +const { Pool } = require("pg"); + +const cors = require('cors'); +const app = express(); +const port = process.env.PORT || 3000; + +const bcrypt = require('bcryptjs'); +const jwt = require('jsonwebtoken'); + +const JWT_SECRET = "supergeheimes_tg_cms_secret"; + +// Bodyparser fĂŒr JSON aktivieren +app.use(cors({ + origin: ["http://localhost:8080", "http://192.168.50.65:8080"], + methods: ["GET", "POST", "PUT", "DELETE"], + credentials: true +})); + +app.use(express.json()); + +// PostgreSQL Verbindung aufbauen +const pool = new Pool({ + user: "tgadmin", + host: "db", // Docker Container Name! + database: "tg-cms", + password: "secretpass", + port: 5432, +}); + +// Testroute API-Check +app.get("/api/hello", (req, res) => { + res.send("Hello World from TG CMS API! 🚀"); +}); + +// Testroute DB-Check +app.get("/api/test-db", async (req, res) => { + try { + const result = await pool.query("SELECT NOW()"); + res.json({ time: result.rows[0].now }); + } catch (err) { + console.error(err); + res.status(500).send("Fehler bei DB-Verbindung"); + } +}); + +// Alle News abrufen +app.get("/api/news", async (req, res) => { + try { + const result = await pool.query('SELECT * FROM news ORDER BY created_at DESC'); + res.json(result.rows); + } catch (err) { + console.error(err); + res.status(500).send("Fehler beim Abrufen der News"); + } +}); + +// Neue News anlegen +app.post("/api/news", async (req, res) => { + const { title, description, image_url, team } = req.body; + + if (!title || !description) { + return res.status(400).send("Titel und Beschreibung sind Pflichtfelder"); + } + + try { + const result = await pool.query( + 'INSERT INTO news (title, description, image_url, team) VALUES ($1, $2, $3, $4) RETURNING *', + [title, description, image_url, team] + ); + res.status(201).json(result.rows[0]); + } catch (err) { + console.error(err); + res.status(500).send("Fehler beim Anlegen der News"); + } +}); + +// News bearbeiten +app.put("/api/news/:id", async (req, res) => { + const { id } = req.params; + const { title, description, image_url, team } = req.body; + + try { + const result = await pool.query( + 'UPDATE news SET title = $1, description = $2, image_url = $3, team = $4 WHERE id = $5 RETURNING *', + [title, description, image_url, team, id] + ); + + if (result.rowCount === 0) { + return res.status(404).send("News-Eintrag nicht gefunden"); + } + + res.json(result.rows[0]); + } catch (err) { + console.error(err); + res.status(500).send("Fehler beim Aktualisieren der News"); + } +}); + +// News löschen +app.delete("/api/news/:id", async (req, res) => { + const { id } = req.params; + + try { + const result = await pool.query( + 'DELETE FROM news WHERE id = $1', + [id] + ); + + if (result.rowCount === 0) { + return res.status(404).send("News-Eintrag nicht gefunden"); + } + + res.send("News-Eintrag erfolgreich gelöscht"); + } catch (err) { + console.error(err); + res.status(500).send("Fehler beim Löschen der News"); + } +}); + +// Neuen Benutzer anlegen +app.post("/api/users", async (req, res) => { + const { username, password, role, email } = req.body; + + if (!username || !password || !email) { + return res.status(400).send("Username, Email & Passwort sind Pflicht"); + } + + try { + // Passwort hashen + const hashedPassword = await bcrypt.hash(password, 10); + + // In DB speichern + const result = await pool.query( + 'INSERT INTO users (username, password, role, email) VALUES ($1, $2, $3, $4) RETURNING id, username, role, email, created_at', + [username, hashedPassword, role ||'user', email] + ); + + res.status(201).json(result.rows[0]); + } catch (err) { + console.error(err); + res.status(500).send("Fehler beim Anlegen des Benutzers"); + } +}); + +// Benutzer Login +app.post("/api/login", async (req, res) => { + const { username, password } = req.body; + + if (!username || !password) { + return res.status(400).send("Username und Passwort erforderlich"); + } + + try { + const result = await pool.query( + 'SELECT * FROM users WHERE username = $1', + [username] + ); + + const user = result.rows[0]; + + if (!user) { + return res.status(400).send("Benutzer existiert nicht"); + } + + // Passwort prĂŒfen + const validPassword = await bcrypt.compare(password, user.password); + + if (!validPassword) { + return res.status(401).send("Passwort falsch"); + } + + await pool.query( + 'UPDATE users SET last_logged = NOW() WHERE id = $1', + [user.id] + ); + + // JWT Token erzeugen + const token = jwt.sign( + { id: user.id, username: user.username, role: user.role }, + JWT_SECRET, + { expiresIn: "6h" } + ); + + res.json({ token }); + } catch (err) { + console.error(err); + res.status(500).send("Fehler beim Login"); + } +}); + + +// Alle Benutzer abrufen +app.get("/api/users", async (req, res) => { + try { + const result = await pool.query( + 'SELECT id, username, role, email, created_at FROM users ORDER BY created_at DESC' + ); + res.json(result.rows); + } catch (err) { + console.error(err); + res.status(500).send("Fehler beim Abrufen der Benutzer"); + } +}); + +// Benutzer lĂloeschen +app.delete("/api/users/:id", async (req, res) => { + const { id } = req.params; + + try { + // PrĂŒfen, ob der Benutzer existiert + const checkResult = await pool.query('SELECT * FROM users WHERE id = $1', [id]); + if (checkResult.rowCount === 0) { + return res.status(404).send("Benutzer nicht gefunden"); + } + + // Benutzer löschen + await pool.query('DELETE FROM users WHERE id = $1', [id]); + + res.send("Benutzer erfolgreich gelöscht"); + } catch (err) { + console.error(err); + res.status(500).send("Fehler beim Löschen des Benutzers"); + } +}); + +// Benutzer bearbeiten +app.put("/api/users/:id", async (req, res) => { + const { id } = req.params; + const { username, password, role } = req.body; + + try { + // Passwort optional neu setzen + let query = 'UPDATE users SET username = $1, role = $2'; + let params = [username, role, id]; + + if (password) { + const hashedPassword = await bcrypt.hash(password, 10); + query = 'UPDATE users SET username = $1, password = $2, role = $3 WHERE id = $4'; + params = [username, hashedPassword, role, id]; + } else { + query += ' WHERE id = $3'; + } + + const result = await pool.query(query, params); + + if (result.rowCount === 0) { + return res.status(404).send("Benutzer nicht gefunden"); + } + + res.send("Benutzer erfolgreich aktualisiert"); + } catch (err) { + console.error(err); + res.status(500).send("Fehler beim Aktualisieren des Benutzers"); + } +}); + + + + +// Server starten +app.listen(port, () => { + console.log(`Server lĂ€uft auf Port ${port}`); +});