🛠️ Ćwiczenia – Sklep internetowy z bazą danych

W tym ćwiczeniu stworzysz prostą aplikację sklepu internetowego w PHP z wykorzystaniem bazy danych MySQL.

1️⃣ Stwórz bazę danych i tabele

Utwórz bazę danych sklep oraz tabelę produkty z przykładowymi danymi:

CREATE DATABASE IF NOT EXISTS sklep;
USE sklep;

CREATE TABLE IF NOT EXISTS produkty (
    id INT AUTO_INCREMENT PRIMARY KEY,
    nazwa VARCHAR(100) NOT NULL,
    cena DECIMAL(10,2) NOT NULL
);

INSERT INTO produkty (nazwa, cena) VALUES
('Mysz gamingowa RGB', 79.99),
('Klawiatura mechaniczna', 199.99),
('Monitor 24"', 599.00),
('Słuchawki bezprzewodowe', 129.90),
('Laptop 15"', 2999.99);

2️⃣ Połącz się z bazą danych w PHP

Utwórz plik db.php z połączeniem do bazy danych:

<?php
$host = 'localhost';
$user = 'root';
$pass = '';
$db = 'sklep';

$conn = new mysqli($host, $user, $pass, $db);
if ($conn->connect_error) {
    die("Błąd połączenia: " . $conn->connect_error);
}
?>

3️⃣ Wyświetl listę produktów na stronie

W pliku index.php załaduj dane z bazy i wyświetl je użytkownikowi:

<?php include('db.php'); ?>
<!DOCTYPE html>
<html lang="pl">
<head>
  <meta charset="UTF-8">
  <title>Sklep internetowy</title>
</head>
<body>
  <h1>Lista produktów</h1>
  <?php
  $sql = "SELECT * FROM produkty";
  $result = $conn->query($sql);

  if ($result->num_rows > 0) {
    while($row = $result->fetch_assoc()) {
      echo "<div>";
      echo "<strong>" . $row['nazwa'] . "</strong> - " . $row['cena'] . " zł";
      echo "</div>";
    }
  } else {
    echo "Brak produktów.";
  }
  $conn->close();
  ?>
</body>
</html>

4️⃣ Dodaj przycisk „Dodaj do koszyka”

Uzupełnij kod o prosty formularz, który pozwoli dodać produkt do koszyka (symulacja):

<form method="post">
  <input type="hidden" name="produkt_id" value="<?php echo $row['id']; ?>">
  <button type="submit">Dodaj do koszyka</button>
</form>

<?php
if ($_SERVER["REQUEST_METHOD"] == "POST" && isset($_POST["produkt_id"])) {
    echo "Produkt został dodany do koszyka.";
}
?>

🧪 Zadanie dodatkowe

5️⃣ Rejestracja użytkownika (tabela klienci)

Stwórz tabelę użytkowników i prosty formularz rejestracyjny:

CREATE TABLE klienci (
    id INT AUTO_INCREMENT PRIMARY KEY,
    login VARCHAR(50) NOT NULL UNIQUE,
    haslo VARCHAR(255) NOT NULL
  );
<form method="post">
    Login: <input type="text" name="login"><br>
    Hasło: <input type="password" name="haslo"><br>
    <input type="submit" name="zarejestruj" value="Zarejestruj się">
  </form>
  
  <?php
  if (isset($_POST["zarejestruj"])) {
    $login = $_POST["login"];
    $haslo = password_hash($_POST["haslo"], PASSWORD_DEFAULT);
    $conn->query("INSERT INTO klienci (login, haslo) VALUES ('$login', '$haslo')");
    echo "Zarejestrowano!";
  }
  ?>

6️⃣ Logowanie użytkownika

<form method="post">
    Login: <input type="text" name="login"><br>
    Hasło: <input type="password" name="haslo"><br>
    <input type="submit" name="zaloguj" value="Zaloguj się">
  </form>
  
  <?php
  session_start();
  
  if (isset($_POST["zaloguj"])) {
    $login = $_POST["login"];
    $haslo = $_POST["haslo"];
  
    $res = $conn->query("SELECT * FROM klienci WHERE login='$login'");
    if ($res->num_rows == 1) {
      $u = $res->fetch_assoc();
      if (password_verify($haslo, $u["haslo"])) {
        $_SESSION["klient_id"] = $u["id"];
        echo "Zalogowano jako $login";
      } else {
        echo "Błędne hasło.";
      }
    } else {
      echo "Nie znaleziono użytkownika.";
    }
  }
  ?>

7️⃣ Koszyk i składanie zamówienia

Stwórz tabele:

CREATE TABLE zamowienia (
    id INT AUTO_INCREMENT PRIMARY KEY,
    klient_id INT,
    data_zamowienia DATETIME DEFAULT CURRENT_TIMESTAMP
  );
  
  CREATE TABLE zamowienia_produkty (
    zamowienie_id INT,
    produkt_id INT,
    ilosc INT
  );

Przykład kodu dodania produktu do koszyka (symulacja):

<?php
  session_start();
  if (!isset($_SESSION["koszyk"])) {
    $_SESSION["koszyk"] = [];
  }
  
  if (isset($_POST["produkt_id"])) {
    $id = $_POST["produkt_id"];
    $_SESSION["koszyk"][$id] = ($_SESSION["koszyk"][$id] ?? 0) + 1;
    echo "Dodano produkt do koszyka.";
  }
  ?>

Wyświetlenie koszyka i składanie zamówienia:

<?php
  if (isset($_POST["zloz"])) {
    $klient_id = $_SESSION["klient_id"];
    $conn->query("INSERT INTO zamowienia (klient_id) VALUES ($klient_id)");
    $zamowienie_id = $conn->insert_id;
  
    foreach ($_SESSION["koszyk"] as $pid => $ilosc) {
      $conn->query("INSERT INTO zamowienia_produkty (zamowienie_id, produkt_id, ilosc)
                    VALUES ($zamowienie_id, $pid, $ilosc)");
    }
    echo "Zamówienie złożone!";
    $_SESSION["koszyk"] = [];
  }
  ?>
  
  <form method="post">
    <input type="submit" name="zloz" value="Złóż zamówienie">
  </form>

8️⃣ Panel administratora – przegląd klientów

Wyświetl listę zarejestrowanych klientów:

<?php
  $result = $conn->query("SELECT * FROM klienci");
  
  echo "<table><tr><th>ID</th><th>Login</th></tr>";
  while ($row = $result->fetch_assoc()) {
    echo "<tr><td>" . $row["id"] . "</td><td>" . $row["login"] . "</td></tr>";
  }
  echo "</table>";
  ?>

9️⃣ Panel administratora – zarządzanie produktami

Dodaj formularz do wstawiania nowych produktów:

<form method="post">
    Nazwa: <input type="text" name="nazwa"><br>
    Cena: <input type="number" name="cena" step="0.01"><br>
    <input type="submit" name="dodaj_produkt" value="Dodaj">
  </form>
  
  <?php
  if (isset($_POST["dodaj_produkt"])) {
    $nazwa = $_POST["nazwa"];
    $cena = $_POST["cena"];
    $conn->query("INSERT INTO produkty (nazwa, cena) VALUES ('$nazwa', $cena)");
    echo "Produkt dodany.";
  }
  ?>

Wyświetl produkty i umożliwiaj ich usuwanie:

<?php
  if (isset($_GET["usun"])) {
    $id = $_GET["usun"];
    $conn->query("DELETE FROM produkty WHERE id = $id");
    echo "Produkt usunięty.";
  }
  
  $produkty = $conn->query("SELECT * FROM produkty");
  while ($p = $produkty->fetch_assoc()) {
    echo $p["nazwa"] . " - " . $p["cena"] . " zł ";
    echo "<a href='?usun=" . $p["id"] . "'>Usuń</a><br>";
  }
  ?>

1️⃣0️⃣ Panel administratora – przegląd zamówień

Wyświetl wszystkie zamówienia z listą produktów i klientów:

<?php
  $q = "SELECT z.id, k.login, z.data_zamowienia, p.nazwa, zp.ilosc
  FROM zamowienia z
  JOIN klienci k ON z.klient_id = k.id
  JOIN zamowienia_produkty zp ON zp.zamowienie_id = z.id
  JOIN produkty p ON p.id = zp.produkt_id
  ORDER BY z.id DESC";
  
  $res = $conn->query($q);
  $last_id = null;
  
  while ($row = $res->fetch_assoc()) {
    if ($row["id"] != $last_id) {
      echo "<h3>Zamówienie #" . $row["id"] . " przez " . $row["login"] . " (" . $row["data_zamowienia"] . ")</h3>";
      $last_id = $row["id"];
    }
    echo "- " . $row["nazwa"] . " x " . $row["ilosc"] . "<br>";
  }
  ?>

1️⃣1️⃣ Generowanie raportów sprzedaży

Dodaj możliwość generowania raportów sprzedaży na podstawie złożonych zamówień. Stwórz zapytanie, które wyświetli wszystkie zamówienia z datą oraz nazwą produktu:

CREATE TABLE IF NOT EXISTS zamowienia (
    id INT AUTO_INCREMENT PRIMARY KEY,
    produkt_id INT,
    klient_id INT,
    data_zamowienia DATETIME DEFAULT CURRENT_TIMESTAMP,
    FOREIGN KEY (produkt_id) REFERENCES produkty(id),
    FOREIGN KEY (klient_id) REFERENCES klienci(id)
);

-- Przykładowe dane
INSERT INTO zamowienia (produkt_id, klient_id) VALUES
(1, 2),
(3, 1),
(2, 3);
<?php
$sql = "SELECT zamowienia.id, produkty.nazwa, zamowienia.data_zamowienia 
        FROM zamowienia 
        JOIN produkty ON zamowienia.produkt_id = produkty.id";
$result = $conn->query($sql);

if ($result->num_rows > 0) {
    while($row = $result->fetch_assoc()) {
        echo "Zamówienie ID: " . $row['id'] . " - Produkt: " . $row['nazwa'] . " - Data: " . $row['data_zamowienia'] . "<br>";
    }
} else {
    echo "Brak zamówień.";
}
?>

1️⃣2️⃣ Wyszukiwanie produktów w sklepie

Dodaj funkcjonalność wyszukiwania produktów po nazwie. Skopiuj poniższy kod do pliku search.php, aby umożliwić użytkownikom wyszukiwanie produktów w sklepie:

<form method="GET">
    Wyszukaj produkt: <input type="text" name="query">
    <button type="submit">Szukaj</button>
  </form>
<?php
if (isset($_GET['query'])) {
    $query = $_GET['query'];
    $sql = "SELECT * FROM produkty WHERE nazwa LIKE '%$query%'";
    $result = $conn->query($sql);

    if ($result->num_rows > 0) {
        while($row = $result->fetch_assoc()) {
            echo "<div>";
            echo "Produkt: " . $row['nazwa'] . " - Cena: " . $row['cena'] . " zł";
            echo "</div>";
        }
    } else {
        echo "Brak produktów spełniających kryteria.";
    }
}
?>

1️⃣3️⃣ System oceniania produktów

Umożliw użytkownikom ocenianie produktów. Zaktualizuj tabelę produktów o dodatkową kolumnę ocena oraz stwórz formularz umożliwiający wystawienie oceny:

ALTER TABLE produkty ADD COLUMN ocena DECIMAL(2,1) DEFAULT 0;
<form method="POST">
    Wybierz produkt:
    <select name="produkt_id">
        <?php
        $sql = "SELECT * FROM produkty";
        $result = $conn->query($sql);
        while($row = $result->fetch_assoc()) {
            echo "<option value='" . $row['id'] . "'>" . $row['nazwa'] . "</option>";
        }
        ?>
    </select>
    Ocena: <input type="number" name="ocena" min="0" max="5" step="0.1">
    <input type="submit" name="ocen" value="Wystaw ocenę">
  </form>

  <?php
  if (isset($_POST['ocen'])) {
      $produkt_id = $_POST['produkt_id'];
      $ocena = $_POST['ocena'];
      $conn->query("UPDATE produkty SET ocena = '$ocena' WHERE id = '$produkt_id'");
      echo "Ocena została zapisana.";
  }
  ?>

🔒 Zadanie: Zabezpieczenie przed CSRF

Dodaj zabezpieczenie przed atakami CSRF. Skopiuj poniższy kod do formularza, aby chronić go przed nieautoryzowanym dostępem:

<?php
session_start();
if (empty($_SESSION['csrf_token'])) {
    $_SESSION['csrf_token'] = bin2hex(random_bytes(32));
}
?>
<form method="POST">
    <input type="hidden" name="csrf_token" value="<?php echo $_SESSION['csrf_token']; ?>">
    ... reszta formularza ...
</form>
<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
    if ($_POST['csrf_token'] !== $_SESSION['csrf_token']) {
        die("Nieautoryzowany dostęp.");
    }
    // Przetwarzanie formularza...
}
?>

🔐 Zadanie: Hashowanie haseł

Przypisz odpowiednią funkcję do haszowania haseł przy rejestracji i logowaniu. Użyj funkcji password_hash() i password_verify() w celu zapewnienia bezpieczeństwa:

$haslo = password_hash($_POST["haslo"], PASSWORD_DEFAULT);
if (password_verify($_POST['haslo'], $u['haslo'])) {
    echo "Zalogowano!";
}

🔗 Zadanie: Optymalizacja zapytań SQL

Opracuj zapytanie, które wykorzystuje indeksy w bazie danych w celu optymalizacji przetwarzania dużych danych. Utwórz indeks na kolumnie nazwa w tabeli produkty:

CREATE INDEX idx_nazwa ON produkty (nazwa);

Portal edukacyjny © 2025 – Sklep PHP + SQL