Appearance
Kapitel 17: Häufig verwendete Funktionen entwickeln
17.1 E-Mail senden
E-Mail senden mit mail()-Funktion
php
<?php
// Einfache E-Mail senden
$an = "empfaenger@example.com";
$betreff = "Test-E-Mail";
$nachricht = "Dies ist eine Test-E-Mail von PHP.";
$header = "From: absender@example.com" . "\r\n" .
"Reply-To: absender@example.com" . "\r\n" .
"X-Mailer: PHP/" . phpversion();
if (mail($an, $betreff, $nachricht, $header)) {
echo "E-Mail erfolgreich gesendet!";
} else {
echo "Fehler beim Senden der E-Mail.";
}
?>E-Mail senden mit PHPMailer (empfohlen!)
PHPMailer: Eine beliebte Bibliothek für E-Mail-Versand in PHP.
1. PHPMailer installieren (mit Composer)
bash
composer require phpmailer/phpmailer2. E-Mail senden mit PHPMailer (SMTP)
php
<?php
// PHPMailer verwenden
require_once 'vendor/autoload.php';
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\Exception;
$mail = new PHPMailer(true);
try {
// Servereinstellungen
$mail->SMTPDebug = 0; // Debug-Ausgabe (0 = aus)
$mail->isSMTP(); // SMTP verwenden
$mail->Host = 'smtp.example.com'; // SMTP-Server
$mail->SMTPAuth = true; // SMTP-Authentifizierung
$mail->Username = 'absender@example.com'; // SMTP-Benutzername
$mail->Password = 'passwort'; // SMTP-Passwort
$mail->SMTPSecure = PHPMailer::ENCRYPTION_SSTART; // Verschlüsselung
$mail->Port = 587; // SMTP-Port
// Empfänger
$mail->setFrom('absender@example.com', 'Absender Name');
$mail->addAddress('empfaenger@example.com', 'Empfänger Name');
$mail->addReplyTo('absender@example.com', 'Absender Name');
// Inhalt
$mail->isHTML(true); // HTML-E-Mail
$mail->Subject = 'Test-E-Mail von PHPMailer';
$mail->Body = '<h1>Test-E-Mail</h1><p>Dies ist eine Test-E-Mail von PHPMailer.</p>';
$mail->AltBody = 'Dies ist eine Test-E-Mail von PHPMailer.'; // Text-Version
// Anhang
// $mail->addAttachment('/pfad/zu/datei.pdf');
$mail->send();
echo 'E-Mail erfolgreich gesendet!';
} catch (Exception $e) {
echo "E-Mail konnte nicht gesendet werden. Fehler: {$mail->ErrorInfo}";
}
?>17.2 Captcha
Was ist Captcha?
Captcha: Ein Test, um zu überprüfen, ob ein Benutzer ein Mensch ist (und kein Bot).
Einfaches Captcha (matematisches Rätsel)
php
<?php
session_start();
// Captcha generieren
if (!isset($_SESSION['captcha_antwort'])) {
$zahl1 = rand(1, 10);
$zahl2 = rand(1, 10);
$_SESSION['captcha_antwort'] = $zahl1 + $zahl2;
}
// Formular
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
$captcha_eingabe = (int) ($_POST['captcha'] ?? 0);
if ($captcha_eingabe === $_SESSION['captcha_antwort']) {
echo "Captcha korrekt!";
unset($_SESSION['captcha_antwort']); // Captcha zurückseten
} else {
echo "Captcha falsch!";
}
}
?>
<!DOCTYPE html>
<html lang="de">
<head>
<meta charset="UTF-8">
<title>Captcha-Beispiel</title>
</head>
<body>
<form method="post" action="">
<p>Captcha: Was ist <?php echo $zahl1 . " + " . $zahl2; ?>?</p>
<label>Antwort:<br>
<input type="text" name="captcha" required>
</label><br><br>
<button type="submit">Senden</button>
</form>
</body>
</html>Google reCAPTCHA v3 (empfohlen!)
1. reCAPTCHA-Keys erhalten
- Gehen Sie zu Google reCAPTCHA
- Registrieren Sie Ihre Webseite
- Erhalten Sie Site Key und Secret Key
2. reCAPTCHA in Formular einbinden
html
<!-- formular.html -->
<!DOCTYPE html>
<html lang="de">
<head>
<meta charset="UTF-8">
<title>reCAPTCHA-Beispiel</title>
<script src="https://www.google.com/recaptcha/api.js?render=DEIN_SITE_KEY"></script>
</head>
<body>
<form id="meinFormular" method="post" action="verarbeite.php">
<label>Name:<br>
<input type="text" name="name" required>
</label><br><br>
<button type="submit">Senden</button>
</form>
<script>
grecaptcha.ready(function() {
grecaptcha.execute('DEIN_SITE_KEY', {action: 'senden'}).then(function(token) {
// Token in verstecktes Feld einfügen
var input = document.createElement('input');
input.type = 'hidden';
input.name = 'g-recaptcha-response';
input.value = token;
document.getElementById('meinFormular').appendChild(input);
});
});
</script>
</body>
</html>3. reCAPTCHA auf Server-Seite verifizieren
php
<?php
// verarbeite.php
session_start();
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
$name = trim($_POST['name'] ?? '');
$recaptcha_token = $_POST['g-recaptcha-response'] ?? '';
// reCAPTCHA verifizieren
$secret_key = 'DEIN_SECRET_KEY';
$url = 'https://www.google.com/recaptcha/api/siteverify';
$daten = [
'secret' => $secret_key,
'response' => $recaptcha_token,
'remoteip' => $_SERVER['REMOTE_ADDR']
];
$options = [
'http' => [
'header' => "Content-type: application/x-www-form-urlencoded\r\n",
'method' => 'POST',
'content' => http_build_query($daten)
]
];
$context = stream_context_create($options);
$result = file_get_contents($url, false, $context);
$result_json = json_decode($result);
if ($result_json->success && $result_json->score >= 0.5) {
// Captcha bestanden
echo "Captcha bestanden! Name: " . htmlspecialchars($name);
} else {
// Captcha nicht bestanden (Bot-Verdacht)
echo "Captcha nicht bestanden! (Bot-Verdacht)";
}
}
?>17.3 Paginierung (Seitenaufteilung)
Was ist Paginierung?
Paginierung: Eine Methode, um grosse Datenmengen auf mehrere Seiten aufzuteilen.
Einfache Paginierung
php
<?php
// Paginierung
$conn = new mysqli("localhost", "root", "", "meine_datenbank");
$conn->set_charset("utf8mb4");
// Seitennummer aus URL holen (Standard: Seite 1)
$seite = (int) ($_GET['seite'] ?? 1);
$seite = max(1, $seite); // Mindestens Seite 1
// Anzahl Einträge pro Seite
$eintraege_pro_seite = 10;
// Offset berechnen
$offset = ($seite - 1) * $eintraege_pro_seite;
// Gesamtanzahl der Einträge
$sql_gesamt = "SELECT COUNT(*) as gesamt FROM artikel";
$result_gesamt = $conn->query($sql_gesamt);
$row_gesamt = $result_gesamt->fetch_assoc();
$gesamteintraege = $row_gesamt['gesamt'];
// Gesamtanzahl der Seiten
$gesamteiten = ceil($gesamteintraege / $eintraege_pro_seite);
// Artikel für aktuelle Seite abfragen
$sql = "SELECT * FROM artikel ORDER BY erstellt_am DESC LIMIT ? OFFSET ?";
$stmt = $conn->prepare($sql);
$stmt->bind_param("ii", $eintraege_pro_seite, $offset);
$stmt->execute();
$result = $stmt->get_result();
// Artikel anzeigen
while ($row = $result->fetch_assoc()) {
echo "<h3>" . htmlspecialchars($row['titel']) . "</h3>";
echo "<p>" . htmlspecialchars($row['inhalt']) . "</p>";
echo "<hr>";
}
// Paginierungs-Links anzeigen
echo "<div class='paginierung'>";
// Zurück-Button
if ($seite > 1) {
echo "<a href='?seite=" . ($seite - 1) . "'>Zurück</a> ";
}
// Seitennummern
for ($i = 1; $i <= $gesamteiten; $i++) {
if ($i === $seite) {
echo "<strong>$i</strong> ";
} else {
echo "<a href='?seite=$i'>$i</a> ";
}
}
// Weiter-Button
if ($seite < $gesamteiten) {
echo "<a href='?seite=" . ($seite + 1) . "'>Weiter</a> ";
}
echo "</div>";
$stmt->close();
$conn->close();
?>Paginierung mit Bootstrap (responsive)
html
<!-- In <head> -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css" rel="stylesheet">
<!-- Paginierung -->
<nav aria-label="Paginierung">
<ul class="pagination justify-content-center">
<li class="page-item <?php echo $seite <= 1 ? 'disabled' : ''; ?>">
<a class="page-link" href="?seite=<?php echo $seite - 1; ?>">Zurück</a>
</li>
<?php for ($i = 1; $i <= $gesamteiten; $i++): ?>
<li class="page-item <?php echo $i === $seite ? 'active' : ''; ?>">
<a class="page-link" href="?seite=<?php echo $i; ?>"><?php echo $i; ?></a>
</li>
<?php endfor; ?>
<li class="page-item <?php echo $seite >= $gesamteiten ? 'disabled' : ''; ?>">
<a class="page-link" href="?seite=<?php echo $seite + 1; ?>">Weiter</a>
</li>
</ul>
</nav>17.4 API-Entwicklung (JSON-Rückgabe)
Was ist eine API?
API (Application Programming Interface): Eine Schnittstelle, über die Anwendungen miteinander kommunizieren können.
Einfache JSON-API erstellen
php
<?php
// api/artikel.php
header('Content-Type: application/json; charset=utf-8');
require_once '../config.php';
$conn = db_connect();
// Alle Artikel abfragen
$sql = "SELECT * FROM artikel ORDER BY erstellt_am DESC";
$result = $conn->query($sql);
$artikel = [];
while ($row = $result->fetch_assoc()) {
$artikel[] = [
'id' => $row['id'],
'titel' => $row['titel'],
'inhalt' => $row['inhalt'],
'erstellt_am' => $row['erstellt_am']
];
}
// JSON ausgeben
echo json_encode($artikel, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE);
$conn->close();
?>API mit Parametern (GET/POST)
php
<?php
// api/artikel.php?id=1
header('Content-Type: application/json; charset=utf-8');
require_once '../config.php';
$conn = db_connect();
// ID aus URL holen
$id = (int) ($_GET['id'] ?? 0);
if ($id > 0) {
// Einzelnen Artikel abfragen
$sql = "SELECT * FROM artikel WHERE id = ?";
$stmt = $conn->prepare($sql);
$stmt->bind_param("i", $id);
$stmt->execute();
$result = $stmt->get_result();
if ($result->num_rows === 1) {
$row = $result->fetch_assoc();
$artikel = [
'id' => $row['id'],
'titel' => $row['titel'],
'inhalt' => $row['inhalt'],
'erstellt_am' => $row['erstellt_am']
];
echo json_encode($artikel, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE);
} else {
http_response_code(404);
echo json_encode(['fehler' => 'Artikel nicht gefunden']);
}
$stmt->close();
} else {
// Alle Artikel abfragen
$sql = "SELECT * FROM artikel ORDER BY erstellt_am DESC";
$result = $conn->query($sql);
$artikel = [];
while ($row = $result->fetch_assoc()) {
$artikel[] = [
'id' => $row['id'],
'titel' => $row['titel'],
'inhalt' => $row['inhalt'],
'erstellt_am' => $row['erstellt_am']
];
}
echo json_encode($artikel, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE);
}
$conn->close();
?>API mit POST (Daten speichern)
php
<?php
// api/artikel_speichern.php
header('Content-Type: application/json; charset=utf-8');
require_once '../config.php';
// Nur POST-Anfragen erlauben
if ($_SERVER['REQUEST_METHOD'] !== 'POST') {
http_response_code(405);
echo json_encode(['fehler' => 'Nur POST-Anfragen erlaubt']);
exit();
}
// JSON-Daten aus Request-Body lesen
$json_daten = file_get_contents('php://input');
$daten = json_decode($json_daten, true);
if (!$daten) {
http_response_code(400);
echo json_encode(['fehler' => 'Ungültige JSON-Daten']);
exit();
}
$titel = trim($daten['titel'] ?? '');
$inhalt = trim($daten['inhalt'] ?? '');
// Validierung
if (empty($titel) || empty($inhalt)) {
http_response_code(400);
echo json_encode(['fehler' => 'Titel und Inhalt dürfen nicht leer sein']);
exit();
}
$conn = db_connect();
// Artikel speichern
$sql = "INSERT INTO artikel (titel, inhalt, benutzer_id) VALUES (?, ?, ?)";
$stmt = $conn->prepare($sql);
$benutzer_id = 1; // Beispiel
$stmt->bind_param("ssi", $titel, $inhalt, $benutzer_id);
if ($stmt->execute()) {
http_response_code(201);
echo json_encode([
'erfolg' => true,
'id' => $stmt->insert_id,
'nachricht' => 'Artikel erfolgreich gespeichert'
]);
} else {
http_response_code(500);
echo json_encode(['fehler' => 'Fehler beim Speichern: ' . $stmt->error]);
}
$stmt->close();
$conn->close();
?>17.5 AJAX-Interaktion (ohne Neuladen)
Was ist AJAX?
AJAX (Asynchronous JavaScript and XML): Eine Methode, um Daten im Hintergrund (asynchron) zu senden/empfangen, ohne die Seite neu zu laden.
Einfaches AJAX-Beispiel (mit Vanilla JavaScript)
html
<!-- index.html -->
<!DOCTYPE html>
<html lang="de">
<head>
<meta charset="UTF-8">
<title>AJAX-Beispiel</title>
</head>
<body>
<h2>AJAX-Beispiel</h2>
<button id="ladenButton">Artikel laden</button>
<div id="artikelListe"></div>
<script>
document.getElementById('ladenButton').addEventListener('click', function() {
// AJAX-Request (mit Fetch API)
fetch('api/artikel.php')
.then(response => response.json())
.then(daten => {
// Daten verarbeiten
let html = '';
daten.forEach(artikel => {
html += '<h3>' + artikel.titel + '</h3>';
html += '<p>' + artikel.inhalt + '</p>';
html += '<hr>';
});
document.getElementById('artikelListe').innerHTML = html;
})
.catch(fehler => {
console.error('Fehler:', fehler);
});
});
</script>
</body>
</html>AJAX mit jQuery (einfacher)
html
<!-- In <head> -->
<script src="https://code.jquery.com/jquery-3.7.0.min.js"></script>
<!-- AJAX mit jQuery -->
<script>
$(document).ready(function() {
$('#ladenButton').click(function() {
$.ajax({
url: 'api/artikel.php',
type: 'GET',
dataType: 'json',
success: function(daten) {
// Daten verarbeiten
let html = '';
daten.forEach(function(artikel) {
html += '<h3>' + artikel.titel + '</h3>';
html += '<p>' + artikel.inhalt + '</p>';
html += '<hr>';
});
$('#artikelListe').html(html);
},
error: function(xhr, status, fehler) {
console.error('Fehler:', fehler);
}
});
});
});
</script>AJAX-Formular (Daten senden ohne Neuladen)
html
<!-- formular.html -->
<!DOCTYPE html>
<html lang="de">
<head>
<meta charset="UTF-8">
<title>AJAX-Formular</title>
<script src="https://code.jquery.com/jquery-3.7.0.min.js"></script>
</head>
<body>
<h2>AJAX-Formular</h2>
<form id="meinFormular">
<label>Name:<br>
<input type="text" name="name" id="name" required>
</label><br><br>
<label>Nachricht:<br>
<textarea name="nachricht" id="nachricht" required></textarea>
</label><br><br>
<button type="submit">Senden</button>
</form>
<div id="ergebnis"></div>
<script>
$(document).ready(function() {
$('#meinFormular').submit(function(e) {
e.preventDefault(); // Formular-Submit verhindern
// Formulardaten sammeln
let name = $('#name').val();
let nachricht = $('#nachricht').val();
// AJAX-Request senden
$.ajax({
url: 'api/nachricht_speichern.php',
type: 'POST',
data: {
name: name,
nachricht: nachricht
},
success: function(antwort) {
$('#ergebnis').html('<p style="color: green;">' + antwort.nachricht + '</p>');
$('#meinFormular')[0].reset(); // Formular zurückseten
},
error: function(xhr, status, fehler) {
$('#ergebnis').html('<p style="color: red;">Fehler: ' + fehler + '</p>');
}
});
});
});
</script>
</body>
</html>php
<?php
// api/nachricht_speichern.php
header('Content-Type: application/json; charset=utf-8');
require_once '../config.php';
// Nur POST-Anfragen erlauben
if ($_SERVER['REQUEST_METHOD'] !== 'POST') {
http_response_code(405);
echo json_encode(['fehler' => 'Nur POST-Anfragen erlaubt']);
exit();
}
$name = trim($_POST['name'] ?? '');
$nachricht = trim($_POST['nachricht'] ?? '');
// Validierung
if (empty($name) || empty($nachricht)) {
http_response_code(400);
echo json_encode(['fehler' => 'Name und Nachricht dürfen nicht leer sein']);
exit();
}
$conn = db_connect();
// Nachricht speichern
$sql = "INSERT INTO nachrichten (name, nachricht) VALUES (?, ?)";
$stmt = $conn->prepare($sql);
$stmt->bind_param("ss", $name, $nachricht);
if ($stmt->execute()) {
echo json_encode([
'erfolg' => true,
'nachricht' => 'Nachricht erfolgreich gespeichert!'
]);
} else {
http_response_code(500);
echo json_encode(['fehler' => 'Fehler beim Speichern: ' . $stmt->error]);
}
$stmt->close();
$conn->close();
?>Zusammenfassung
In diesem Kapitel haben Sie:
- ✅ E-Mails mit
mail()und PHPMailer gesendet - ✅ Captcha (matematisches Rätsel und Google reCAPTCHA) implementiert
- ✅ Paginierung (Seitenaufteilung) erstellt
- ✅ JSON-API entwickelt (GET/POST, JSON-Rückgabe)
- ✅ AJAX-Interaktion (ohne Neuladen) implementiert
Nächstes Kapitel: Wir werden häufige Fehler und Lösungen lernen.
Übungsaufgaben:
- Erstellen Sie ein Kontaktformular mit E-Mail-Versand (PHPMailer)
- Implementieren Sie Google reCAPTCHA v3 in ein Formular
- Erstellen Sie eine Paginierung für eine Artikelliste
- Entwickeln Sie eine JSON-API für ein Blog-System
- Erstellen Sie ein AJAX-Formular für Benutzerregistrierung
Häufige Fehler:
- ❌
mail()in Produktion verwenden → Immer PHPMailer oder ähnliche Bibliotheken verwenden! - ❌ Captcha nicht validieren → Bots können Formulare automatisiert ausfüllen!
- ❌
LIMITundOFFSETin SQL-Abfragen vergessen → Paginierung funktioniert nicht! - ❌
header('Content-Type: application/json')vergessen → API gibt HTML statt JSON zurück! - ❌
e.preventDefault()in AJAX-Formularen vergessen → Seite wird neu geladen!
