Što gradimo
Knjigu gostiju: obrazac u Reactu šalje poruku tvom serveru, server je sprema i prikazuje svakom budućem posjetitelju. Sjećaš li se obrasca iz razine 2 koji nije imao kamo poslati poruku? Danas vraćamo taj dug.
Pokazat ću ti: backend knjige gostiju
U mapi my-server prvo instaliraj još jedan paket:
npm install cors
I uredi server.js:
const express = require("express");
const cors = require("cors");
const app = express();
app.use(cors()); // allow the frontend on a different port to ask questions
app.use(express.json()); // understand JSON in incoming requests
const messages = [
{ name: "Martin", text: "First message! Long live the guestbook. 📖" },
];
// GET – hand out messages
app.get("/api/messages", (request, response) => {
response.json(messages);
});
// POST – accept a new message
app.post("/api/messages", (request, response) => {
const { name, text } = request.body;
// Never trust input: check it on the server too!
if (!name || !text || name.length > 50 || text.length > 500) {
return response.status(400).json({ error: "Invalid message." });
}
messages.push({ name, text });
response.json({ saved: true });
});
app.listen(3900, () => {
console.log("Server running at http://localhost:3900");
});
Novo:
cors()– frontend radi na portu 3901, server na 3900. Preglednici inače blokiraju takve “cross-origin” zahtjeve (sigurnosno pravilo CORS); ovako to dopuštaš na serveru.app.post(...)– tvoj prvi POST endpoint! Podaci obrasca dolaze urequest.body.- Provjera na serveru – frontend već provjerava obrazac, ali napadač može zaobići obrazac i poslati zahtjev izravno. Zato vrijedi željezno pravilo: backend uvijek provjerava i nikad ne vjeruje frontendu.
status(400)znači “loš zahtjev.”
Pokazat ću ti: frontend knjige gostiju
U React projektu napravi src/GuestBook.jsx:
import { useState, useEffect } from 'react';
function GuestBook() {
const [messages, setMessages] = useState([]);
const [name, setName] = useState("");
const [text, setText] = useState("");
// On first render: download the messages from the server
useEffect(() => {
fetch("http://localhost:3900/api/messages")
.then((response) => response.json())
.then((data) => setMessages(data));
}, []);
function submit(event) {
event.preventDefault();
fetch("http://localhost:3900/api/messages", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ name, text }),
})
.then((response) => response.json())
.then(() => {
setMessages([...messages, { name, text }]); // add it to the screen too
setName("");
setText("");
});
}
return (
<div>
<h2>Guestbook 📖</h2>
{messages.map((message, index) => (
<div className="card" key={index}>
<strong>{message.name}</strong>
<p>{message.text}</p>
</div>
))}
<form onSubmit={submit}>
<input
value={name}
onChange={(event) => setName(event.target.value)}
placeholder="Your name"
/>
<textarea
value={text}
onChange={(event) => setText(event.target.value)}
placeholder="Write a message..."
/>
<button type="submit">Send</button>
</form>
</div>
);
}
export default GuestBook;
Tri posljednje nove stvari u Reactu:
useEffect(() => {...}, [])– “pokreni ovo jednom, kad se komponenta prvi put prikaže.” Idealno mjesto za preuzimanje podataka.fetchsmethod: "POST"– šaljemo podatke;JSON.stringifyih pakuje u JSON.- Povezani obrasci – polje čita vrijednost iz statea (
value={name}) i piše je natrag tijekom tipkanja (onChange). Obrazac i state uvijek su usklađeni.
Sad si ti na redu 💪
- Pokreni oboje: server u jednom terminalu (
node server.js), React u drugom (npm run dev -- --port 3901). Dva terminala, dva programa – dobrodošao u full-stack! - Dodaj
<GuestBook />u aplikaciju i isprobaj: napiši poruku, osvježi stranicu – poruka je još tu (dok server radi). - Prilagodi knjigu gostiju svom projektu: 🏫 poruke za školu · 🙋 oglasna ploča za prijatelje · 🌍 savjeti posjetitelja “kamo bismo trebali” · ⚽ navijački skandici.
- Pokušaj poslati praznu poruku – frontend je pusti (nema provjere), ali server je odbije. Zatim dodaj provjeru i na frontend, da obrazac bude pristojan kao u razini 2.
Poruke nestaju kad se server ponovo pokrene – žive samo u nizu u memoriji. Prave aplikacije spremaju ih u bazu podataka, koja preživljava sve. To je prva stvar za naučiti nakon ove razine – ključne riječi: SQLite, PostgreSQL.
Provjeri sam sebe: Poruka iz obrasca putuje do servera, sprema se i vraća nakon ponovnog učitavanja stranice. Upravo si izgradio full-stack aplikaciju – frontend, backend, API. Točno to profesionalni programeri rade svaki dan.
Što ćeš ponijeti iz ove lekcije
useEffect(..., [])preuzima podatke pri prvom prikazu;fetchs POST šalje ih.- Željezno pravilo sigurnosti: server provjerava svaki unos, čak i kad frontend provjerava.
- Full-stack = dva pokrenuta programa (3901 + 3900) koji razgovaraju preko API-ja.
© 2026 Ing. Martin Polak / AlgoRhino · Uvjeti korištenja sadržaja