3.5. Űrlapok használata

Az űrlapok a felhasználótól érkező információk klasszikus, és legfontosabb forrásai.

A PHP $_GET és $_POST változói használatosak az információ űrlapokból való továbbítására.

Minden HTML oldalon található űrlapelem automatikusan elérhető a PHP szkriptek számára.

3.5.1. A GET paraméterátadás

A $_GET változót arra használjuk, hogy értékeket gyűjtsünk az űrlapról a GET metódussal. A GET-tel mindenki számára látható módon tudunk adatokat küldeni az űrlapból (megjelenik a böngésző címsorában, az URL-ben).

Az elküldhető információ mennyisége korlátozva van. (A pontos korlát több szoftvertől is függ, de maximum 2.000 karakterrel érdemes számolni.)

Példa:

<form action="welcome.php" method="get">
  Név: <input type="text" name="name">
  Életkor: <input type="text" name="age">
  <input type="submit">
</form>

Amikor a felhasználó a submit gombra kattint, az URL-ben megjelennek az adatok:

http:// azenoldalam/welcome.php?name=Peter&age=37

A welcome.php fájl arra használja a $_GET változót, hogy elérje az űrlap adatait. Az űrlap mezők nevei automatikusan a $_GET tömb azonosítói lesznek:

<html>
<body>
  Üdvözöllek, <?php echo $_GET["name"]; ?>!<br>
  Te <?php echo $_GET["age"]; ?> éves vagy.
</body>
</html>

Miért használjuk a $_GET-et?

Amikor használjuk a $_GET változót, akkor az összes változó neve és értéke megjelenik az URL-ben. Tehát ennek a metódusnak a használata nem ajánlott jelszó és egyéb bizalmas információk küldésekor. Viszont pont emiatt lehetséges könyvjelző elhelyezése. Ez sok esetben hasznos, máskor kifejezetten hátrányos lehet.

A $_GET űrlap nélkül

Elsőre talán meglepőnek tűnik, de a $_GET tömb elemei nem csak űrlap kitöltésével jöhetnek létre. Semmi akadálya annak, hogy az URL eleve tartalmazzon kulcs-érték párokat, például a következő link eleve ilyen:

<a href=”index.php?id=23”>Másik oldal</a>

Ebben az esetben űrlap nélkül is lesz tartalma a $_GET tömbnek.

Hasonló okokból szokás űrlapba rejtett (hidden) mezőt elhelyezni. A kitöltött adatokkal együtt ezek az adatok is el fognak jutni a $_GET tömbbe.

URL-kódolás

Az URL egy erőforrások megcímzésére alkalmas eszköz kötött karakterkészlettel. Bizonyos karakterek (pl. ékezetes betűk, egyes írásjelek) közvetlenül nem szerepelhetnek az URL-ben, de kódolt formában már igen.

A kódolt karakterek egy % jellel és a két számjeggyel leírt hexadecimális értékükkel írhatók le. Például a szóköz kódolva %20.

Űrlapok adatainak GET metódussal való elküldése esetén az űrlap adatok az URL-ben kerülnek továbbításra. Ilyen esetben is fontos szerepet kap a kódolás, hiszen egy begépelt űrlapmezőben bármilyen karakter előfordulhat.

A $_REQUEST változó

A PHP $_REQUEST tartalmazza a $_GET, $_POST és $_COOKIE változók elemeit.

Arra használjuk, hogy megkapja a GET és POST metódussal történt adatküldés eredményét.

Példa:

Üdvözöllek, <?php echo $_REQUEST["name"]; ?>!<br>
Te <?php echo $_REQUEST["age"]; ?> éves vagy.

Biztonsági okokból a $_REQUEST használata általában kerülendő. Meg kell ugyanis győződnünk arról, hogy a fontos adatok tényleg onnan érkeztek-e, ahonnan mi várjuk, és nem valahonnan máshonnan.

3.5.2. A POST paraméterátadás

A $_POST változó neveket és értékeket tartalmazó tömb, melyek a HTTP POST metódussal lettek továbbítva. Az az információ, melyet egy űrlapról küldenek POST metódussal, láthatatlan a többi felhasználó részére, és nincs korlátozva az információ mennyiségét illetően. Példa:

<form action="welcome.php" method="post">
  Név: <input type="text" name="name">
  Életkor: <input type="text" name="age">
  <input type="submit">
</form>

Amikor a felhasználó a submit gombra kattint, az URL nem fog semmilyen űrlap adatot tartalmazni, és a valahogy így fog kinézni:

http:// azenoldalam/welcome.php

Így a welcome.php fájl most már használhatja a $_POST változót, hogy az űrlap adatokat elérhesse. Az űrlap mezők nevei automatikusan a $_POST tömb azonosító kulcsai lesznek:

<html>
<body>
  Üdvözöllek, <?php echo $_POST["name"]; ?>!<br>
  Te <?php echo $_POST["age"]; ?> éves vagy.
</body>
</html>

Miért használjunk $_POST–ot?

  • A HTTP POST-al küldött változók nem láthatók az URL-ben
  • A változóknak nincs hosszúsági korlátjuk

Egyébként, mivel az URL-ben nem láthatók a változók, nem lehetséges az oldalakat könyvjelzővel ellátni. (Ez általában nem is lenne praktikus.)

3.5.3. Adatfeldolgozás

A felhasználó által bevitt adatok érvényességét minden esetben vizsgálni kell. A kliens oldali vizsgálat (4.9.1 fejezet) a látogató számára gyorsabb, és csökkenti a szerver terheltségét, de önmagában sosem elegendő, hiszen egy rosszindulatú felhasználó azt könnyedén ki tudja játszani. Ezért az adatok szerver oldali vizsgálata is szükséges, különösen, ha az űrlapnak egy adatbázishoz kell hozzáférnie.

Mit is kaptunk?

Az egyes mezőtípusok esetén talán nem mindig triviális, hogy minek is kellene lennie az egyes szituációkban. Ezért egy egyszerű tesztelési lehetőség a print_r függvény használata:

<pre>
<?php
  print_r
($_GET);
?>

</pre>

Többes adatok

A select típusú űrlap elem és multiple tulajdonság használata esetén nem csak egy egyszerű értéket kellene visszakapunk, hanem egy tömböt. Ilyen esetben az űrlapot így érdemes felépítenünk:

<form action="form.php" method="post">
  <select name="test[]" multiple="multiple">
    <option value="one">egy</option>
    <option value="two">kettő</option>
    <option value="three">három</option>
    <option value="four">négy</option>
    <option value="five">öt</option>
  </select>
  <input type="submit" value="Küldés">
</form>

Ekkor a szerver oldalon minden adatot megkapunk, egy tömbként:

$test=$_POST['test'];
if ($test){
  foreach ($test as $t)
    echo 'Kiválasztva: ',$t,'<br>';
}

Ha get paraméterátadást használunk, az URL így fog kinézni:

form.php?test[]=two&test[]=three

Úrlapok kódolása

Ha UTF-8 karakterkódolással küldjük ki az oldalainkat, akkor célszerű az űrlapok esetén is megadni ezt az információt:

<form action="..." method="post" accept-charset="UTF-8">

Adatok érvényesítése

A felhasználótól érkező adatokban soha nem bízhatunk meg. Emiatt többféle ellenőrzést kell végeznünk a teljes biztonság érdekében.

Nézzünk meg egy egyszerű űrlapot:

<form action="myform.php" method="post">
  <p>Your Name: <input type="text" name="yourname"><br>
    E-mail: <input type="text" name="email"></p>
  <p>Do you like this website?
    <input type="radio" name="likeit" value="Yes" checked="checked"> Yes
    <input type="radio" name="likeit" value="No"> No
    <input type="radio" name="likeit" value="Not sure"> Not sure</p>
  <p>Your comments:<br>
    <textarea name="comments" rows="10" cols="40"></textarea></p>
  <p><input type="submit" value="Send it!"></p>
</form>

Ha az űrlap adatokat egyszerűen eltároljuk és/vagy később felhasználjuk, meglepetéseket tapasztalhatunk. Nézzük meg a myform.php egyszerű verzióját:

<html>
<body>
  Your name is: <?php echo $_POST['yourname']; ?><br>
  Your e-mail: <?php echo $_POST['email']; ?><br>
  <br>
  Do you like this website? <?php echo $_POST['likeit']; ?><br>
  <br>
  Comments:<br>
  <?php echo $_POST['comments']; ?>
</body>
</html>

Ekkor ilyen eredményre számítunk:

Your name is: John Doe
Your email: john@doe.com
Do you like this website? Yes
Comments:
This is my comment...

De mi történik akkor, ha a látogató egy kis JavaScript kódot ír be a beviteli mezőbe:

<script>location.href('http://www.SPAM.com')</script>

Ha ezt kiírjuk a fenti myform.php kóddal, az összes látogatót elküldjük a fenti webcímre. Ez megengedhetetlen. A következő kód a htmlspecialchars függvényt használja a támadások kivédésére:

<?php
  $yourname
= htmlspecialchars($_POST['yourname']);
 
$email    = htmlspecialchars($_POST['email']);
 
$likeit   = htmlspecialchars($_POST['likeit']);
 
$comments = htmlspecialchars($_POST['comments']);
?>

<html>
<body>
  Your name is: <?php echo $yourname; ?><br>
  Your e-mail: <?php echo $email; ?><br>
  <br>
  Do you like this website? <?php echo $likeit; ?><br>
  <br>
  Comments:<br>
  <?php echo $comments; ?>
</body>
</html>

Ekkor a fenti JavaScript kódból ez a közömbösített kód lesz:

&lt;script&gt;location.href('http://www.SPAM.com')&lt;/script&gt;

Ezen kívül további függvények is szóba jöhetnek az adatok megtisztítására. Ezek egységes használatára nézzünk egy példát:

function check_input($data) {
    $data = trim($data);
    $data = stripslashes($data);
    $data = htmlspecialchars($data);
    return $data;
}
$yourname = check_input($_POST['yourname']);
$email    = check_input($_POST['email']);
...

Kötelező mezők kezelése

Fejlesszük tovább a check_input függvényt. Ha egy mezőt kötelezően ki akarjuk töltetni, akkor ezt az opciót egy második paraméterrel beépíthetjük a függvénybe: ha átadjuk a szöveges paramétert, akkor ezzel jelezzük, hogy kötelező a kitöltés, és ekkor ez lesz a kiadandó hibaüzenet is:

function check_input($data, $problem='') {
    $data = trim($data);
    $data = stripslashes($data);
    $data = htmlspecialchars($data);
    if ($problem && strlen($data) == 0)     {
        die($problem);
    }
    return $data;
}

A következő felhasználás esetén az első és negyedik mező kitöltése kötelező, a középsőké nem:

$yourname = check_input($_POST['yourname'], "Enter your name");
$email    = check_input($_POST['email']);
$likeit   = check_input($_POST['likeit']);
$comments = check_input($_POST['comments'], "Write your comments");

Persze a hibaüzenetek lekezelésére (die függvény) ez csak egy első megoldás, tovább kell fejlesztenünk.

Reguláris kifejezések

A szintaxis-ellenőrzés régi bevált módszere a reguláris kifejezések használata. Itt most néhány példát fogunk megnézni. A hangsúly nem a reguláris kifejezések működésén, hanem azok PHP felhasználásán lesz.

Az e-mail cím ellenőrzésére egy lehetséges megoldás:

$email = htmlspecialchars($_POST['email']);
if (!preg_match("/([\w\-]+\@[\w\-]+\.[\w\-]+)/",$email)) {
    die("E-mail address not valid");
}

URL ellenőrzése:

$url = htmlspecialchars($_POST['website']);
if (!preg_match("/^(https?:\/\/+[\w\-]+\.[\w\-]+)/i",$url)) {
    die("URL address not valid");
}

Számjegyek:

if (preg_match("/\D/",$age)) {
    die("Please enter numbers only!");
}

Angol abc betűi:

if (preg_match("/[^a-zA-Z]/",$text)) {
    die("Please enter letters a-z and A-Z only!");
}

Űrlapok feldolgozása helyben

Az adatok ellenőrzésére bevett módszer, hogy az űrlap adatait az űrlapot is tartalmazó szkript dolgozza fel, így nincs szükség arra, hogy az adatokat egy újabb oldalra küldjük. Ebben az esetben a felhasználó a hibaüzeneteket ugyanazon az oldalon láthatja, ahol az űrlap található, így megkönnyítve a hiba felfedezését és kijavítását.
Nézzük az alapokat. Legyen az oldal neve form-action.php.

<?php
 
if(isset($_POST['submit'])) {
   
$name = $_POST['name'];
    echo
"User Has submitted the form and entered this name : <b> $name </b>";
    echo
"<br>You can use the following form again to enter a new name.";
}
?>

<html>
<head><title>Using PHP_SELF</title></head>
<body>
<form method="post" action="<?php echo $_SERVER['PHP_SELF']; ?>">
  <input type="text" name="name"><br>
  <input type="submit" name="submit" value="Submit Form"><br>
</form>
</body>
</html>

Először is meglepő, hogy nem az űrlappal kezdjük a forráskódot. Itt a háttérben már körvonalazódik az a – később egyre fontosabbá váló – logika, ami szerint a lehető legjobban válasszuk szét a program logikáját a megjelenítési részektől.

A kód elején el kell döntenünk, hogy most először akarja látni a látogató az oldalt, és üres űrlappal kell várnunk, vagy pedig az űrlap már kitöltve érkezett vissza a látogatótól. Az első esetben nem fog semmilyen POST adat érkezni. A második esetben viszont igen: a Submit Form gomb lenyomásakor már a POST adatok is elküldésre kerültek. Emiatt az isset függvény alkalmas a két eset megkülönböztetésére.

A form action paraméterét szokás a fenti módon kitölteni. A $_SERVER['PHP_SELF'] ugyanannak az oldalnak a címe, amely a fenti PHP kódot tartalmazza.

Itt is számítanunk kell azonban egy betörési lehetőségre. Ha a látogató a böngészője cím sorába beírja a következő címet, a $_SERVER['PHP_SELF'] változó egy ügyesen elhelyezett támadókódot tartalmaz.

A PHP futás eredménye ekkor:

<form name="test" method="post" action="form-action.php"/>
<script>alert('xss')</script><foo"">

Az XSS támadás elkerülése érdekében inkább így használjuk:

<form name="test"
  action="<?php echo htmlentities($_SERVER['PHP_SELF']); ?>"
  method="post">

Hibaüzenetek és javítási lehetőségek

A látogatók sokszor nem tudják hiba nélkül kitölteni az űrlapot. Emiatt fontos az alábbi elvek figyelembe vétele:

  1. az űrlap eleve tartalmazzon minden információt, ami a kitöltéssel kapcsolatos
  2. kliens oldalon ellenőrizzük az adatokat JavaScript segítségével
  3. beszédes hibaüzenetekkel lássuk el a látogatót, a hiba helyét könnyen beazonosítható módon
  4. adjuk vissza a látogatónak a megadott adatait, hogy ne kelljen mindent elölről kezdenie

A korábbi példáink a hibaüzeneteket eléggé mostohán kezelték. Többször használtunk olyan kódot, amely az első hibánál leáll. De a használhatóság miatt inkább össze kell gyűjtenünk a hibaüzeneteket, és a megfelelő helyen kiírni.

Nézzünk egy minimális példát a hibaüzenetek összegyűjtésére. A változók az űrlapról érkező adatokat tartalmazzák:

$errorMessage = '';
if(empty($varMovie)) {
  $errorMessage .= "<li>You forgot to enter a movie!</li>";
}
if(empty($varName)) {
  $errorMessage .= "<li>You forgot to enter a name!</li>";
}
if(empty($varGender)) {
  $errorMessage .= "<li>You forgot to select your Gender!</li>";
}

Jól látszik, hogy a futás végére az $errorMessage vagy üres marad, és ekkor nem volt probléma, vagy nem marad üres, és felsorolásként tartalmazza a hibaüzeneteket, és már csak ki kell írnunk egy ul elembe. Még szebb megoldás lenne, ha közvetlenül a mező mellett jelenne meg a hibaüzenet. (A 3.10.1 fejezetben látni fogunk erre is példát.)

Ha az űrlap feldolgozása során azt láttuk, hogy nem tökéletes, és újból a látogató felé kell továbbítani, akkor vissza kell küldenünk a korábban kitöltött adatokat. Erre egy egyszerű példa:

<input type="text" name="Coal"
  <?php if (isset($_POST['Coal'])) { ?>
    value="<?php echo $_POST['Coal']; ?>"
  <?php } ?>
/>

Ha a látogató már kitöltötte a Coal mezőt, az isset($_POST['Coal']) igaz lesz, és kiírjuk a value értékeként.

Érdemes azt is átgondolni, hogy az if-nek inkább olvashatósági jelentősége van, nélküle is megfelelő lenne a kimenet:

  • ha a feltétel teljesülne, akkor nincs változás,
  • ha a feltétel nem teljesül, akkor a value üres értékkel jelenik meg.

3.5.4. Állományok feltöltése

PHP-vel lehetséges fájlok szerverre történő feltöltése is. Leggyakrabban képeket szokás feltölteni, amelyek a szövegbe illesztve fognak fontos szerepet betölteni. De fájlmegosztás céljából (pl. egy PDF dokumentumot), vagy adminisztrációs célokból (adatok tömeges importálása CSV állományból) történő fájlfeltöltés is előfordulhat.
Fájlfeltöltő űrlap készítése

Nézzük meg az alábbi fájl feltöltésre használt HTML űrlapot:

<html>
<body>
  <form action="upload_file.php" method="post"
    enctype="multipart/form-data">
    <label for="file">Filename:</label>
    <input type="file" name="file" id="file">
    <br>
    <input type="submit" name="submit" value="Submit">
  </form>
</html>
</body>

Jegyezzük meg a következőket a HTML űrlappal kapcsolatban:

  • A form enctype attribútuma határozza meg, hogy melyik tartalom típust használjuk, amikor az űrlapot elfogadjuk. A multipart/form-data akkor használatos, ha az űrlap bináris adatot vár, mint pl. egy fájl tartalma feltöltéskor.
  • Az input elem file típusa határozza meg, hogy a függvény bemenete fájlként legyen feldolgozva. Például böngészőben való megjelenítéskor lesz egy Tallózás gomb a bemenet mező mellett.

Feltöltés engedélyezése felhasználók számára nagy kockázattal jár. Kizárólag megbízható felhasználók számára tegyük lehetővé fájlok feltöltést, és feltöltés után is ellenőrizzük a fájlt.

Feltöltő szkript készítése

Az upload_file.php fájl tartalmazza a fájl feltöltésére és az ellenőrzésre szolgáló programot:

if ($_FILES["file"]["error"] > 0) {
  echo "Error: " . $_FILES["file"]["error"] . "<br>";
} else {
  echo "Upload: " . $_FILES["file"]["name"] . "<br>";
  echo "Type: " . $_FILES["file"]["type"] . "<br>";
  echo "Size: " . ($_FILES["file"]["size"] / 1024)
       . " Kb<br>";
  echo "Stored in: " . $_FILES["file"]["tmp_name"];
}

A $_FILES globális PHP tömb használatával fájlokat tölthetünk fel egy kliens gépről a távoli szerverre. Az első index az űrlap mező neve, a második lehet name, type, size, tmp_name vagy error, a következőképpen:

  • $_FILES["file"]["name"]: a feltöltött fájl neve
  • $_FILES["file"]["type"]: a feltöltött fájl típusa
  • $_FILES["file"]["size"]: a feltöltött fájl mérete byte-okban
  • $_FILES["file"]["tmp_name"]: a szerveren tárolt fájl másolatának átmeneti neve
  • $_FILES["file"]["error"]: a fájl feltöltése során kapott hibakód

Ez a fájlfeltöltés egy nagyon egyszerű módja. Biztonsági okokból korlátozásokat kell bevezetni a felhasználóknál a feltöltésekre vonatkozóan.

A feltöltés korlátozása

Ebben a szkriptben a fájlfeltöltést korlátokhoz kötjük. A felhasználó kizárólag .gif vagy .jpeg fájlokat tölthet fel, és a fájlméretnek 20 Kb alatt kell maradnia:

if ((($_FILES["file"]["type"] == "image/gif")
    || ($_FILES["file"]["type"] == "image/pjpeg"))
      && ($_FILES["file"]["size"] < 20000)) {
  if ($_FILES["file"]["error"] > 0) {
    echo "Error: " . $_FILES["file"]["error"] . "<br>";
  } else {
    echo "Upload: " . $_FILES["file"]["name"] . "<br>";
    echo "Type: " . $_FILES["file"]["type"] . "<br>";
    echo "Size: " . ($_FILES["file"]["size"] / 1024)
         . " Kb<br>";
    echo "Stored in: " . $_FILES["file"]["tmp_name"];
  }
} else {
  echo "Invalid file";
}

A feltöltött fájl elmentése

A fenti példák elkészítik a szerveren a feltöltött fájlok egy-egy átmeneti másolatát a PHP temp mappában.

A temp mappa egy logikai kifejezés, ténylegesen a php.ini beállításától függ. XAMPP esetén c:\xampp\tmp.

Az átmeneti fájlok törlésre kerülnek, amint a szkript futása véget ér. Ahhoz, hogy a fájlt eltároljuk, át kell másolnunk máshová. Ehhez a move_uploaded_file függvényt kell használnunk:

if (($_FILES["file"]["type"] == "image/gif")
      || ($_FILES["file"]["type"] == "image/pjpeg")
    && ($_FILES["file"]["size"] < 20000)) {
  if ($_FILES["file"]["error"] > 0) {
    echo "Return Code: " . $_FILES["file"]["error"]
         . "<br>";
  } else {
    echo "Upload: " . $_FILES["file"]["name"] . "<br>";
    echo "Type: " . $_FILES["file"]["type"] . "<br>";
    echo "Size: " . ($_FILES["file"]["size"] / 1024)
         . " Kb<br>";
    echo "Temp file: " . $_FILES["file"]["tmp_name"]
         . "<br>";
    if (file_exists("upload/" . $_FILES["file"]["name"])) {
      echo $_FILES["file"]["name"] . " already exists. ";
    } else {
      move_uploaded_file($_FILES["file"]["tmp_name"],
      "upload/" . $_FILES["file"]["name"]);
      echo "Stored in: " . "upload/"
           . $_FILES["file"]["name"];
    }
  }
} else {
  echo "Invalid file";
}

A fenti szkript leellenőrzi, létezik-e már a fájl, ha pedig nem, bemásolja azt upload nevű mappába.

Ezzel a feltöltés folyamata eredményessé vált.

3.5.5. Levélküldés

A PHP lehetővé teszi, hogy közvetlenül szkriptből küldjünk e-maileket. Néhány ok, amiért e-mailt szoktunk küldeni egy weboldalról:

  • regisztráció, hírlevél feliratkozás stb. esetén megerősítő levél
  • hírlevél a feliratkozott látogatóknak
  • értesítés valamilyen esemény bekövetkezéséről

A PHP mail függvényt arra használják, hogy segítségével szkripten belül e-maileket küldjenek. Szintaxis:

mail(to, subject, message, headers, parameters)
  • to: Kötelezően megadandó. Az e-mail címzettjét/címzetteit határozza meg.
  • subject: Kötelezően megadandó. Az email témája. Ez a paraméter nem tartalmazhat új sor (LF, \n) karaktereket.
  • Message: Kötelezően megadandó. Az elküldendő üzenetet határozza meg. Minden új sort LF (\n) karakterrel kell elválasztani. Egy sor terjedelme nem haladhatja meg a 70 karaktert.
  • headers: Opcionális. További fejléceket adhatunk meg, mint például From, Cc és Bcc. A további fejléceket CRLF (\r\n) karakterrel kell elválasztani.
  • parameters: Opcionális. További paramétereket adhatunk meg a sendmail programnak

A mail függvény használatához a PHP-nek szüksége van egy feltelepített és működő levelezőrendszerre, vagy SMTP kapcsolatra. A használandó programot a php.ini fájl konfigurációs beállításai határozzák meg (3.1.2 fejezet).

Egyszerű megoldás

A legegyszerűbb levélküldési mód PHP-ben a szöveges levél küldése.

Az alábbi példában először deklaráljuk a változókat ($to, $subject, $message, $from, $headers), majd a mail függvényben felhasználjuk ezeket a változókat e-mailküldésre:

$to = "valaki@levele.com";
$subject = "Teszt levél";
$message = "Szia! Ez egy egyszerű levél.";
$from = "valakimas@levele.com";
$headers = "From: $from";
mail($to,$subject,$message,$headers);
echo "A levél elment.";

PHP levél űrlapból

A PHP segítségével létre tudunk hozni egy visszajelző (más néven kapcsolatfelévteli) űrlapot weboldalunkon. A következő példában egy szöveges üzenetet küldünk el a megadott e-mail címre.

<html>
<body>
<?php
if (isset($_POST['email'])) {
 
$email = $_POST['email'] ;
 
$subject = $_POST['subject'] ;
 
$message = $_POST['message'] ;
 
mail( "<a href="mailto:valaki@levele.com">valaki@levele.com</a>", "Subject: $subject",
 
$message, "From: $email" );
  echo
"Köszönjük üzenetét.";
} else {
  echo
"<form method='post' action='mailform.php'>
  Email: <input name='email' type='text'><br>
  Tárgy: <input name='subject' type='text'><br>
  Üzenet:<br>
  <textarea name='message' rows='15' cols='40'>
  </textarea><br>
  <input type='submit'>
</form>"
;
}
?>

</body>
</html>

Először megvizsgáljuk, hogy az email beviteli mező ki van-e töltve. Ha nincs (például ha ez az első látogatás az oldalon), akkor megjelenítjük a HTML űrlapot.

Ha ki van töltve, elküldjük az űrlapból az emailt. Ha az űrlap kitöltése után nyomják meg az elküld gombot, a lap újratöltődik, megnézi, hogy az email beviteli mező ki van-e töltve, majd elküldi az e-mailt.

Biztonságos levélküldés

Az előző fejezetben bemutatott mail függvénynek van egy gyenge pontja: lehetőséget ad befecskendezéses támadás (injection) megvalósítására. A probléma a fent bemutatott kóddal, hogy illetéktelen felhasználok be tudnak szúrni adatokat a levél fejlécébe a beviteli űrlapon keresztül.

Mi történik, ha a felhasználó a következő szöveget írja be az email beviteli mezőbe az űrlapon?

A mail függvény a szokott módon a fenti szöveget helyezi el a levél fejlécében, és így a fejléc többlet Cc:, Bcc:, és To: mezőket tartalmaz. Amikor a felhasználó az elküld gombra kattint, a fenti összes címre elküldi a levelet. Így a támadó olyan helyről küldött e-mailt, amely eddig nem volt letiltva spam gyanú miatt.

Emiatt mindenképpen célszerű reguláris kifejezésekkel ellenőrizni, hogy az egyes mezők megfelelnek-e a kívánalmaknak.