Zakładam, że skoro tutaj jesteś, masz swoją stronę www. Z pewnością chciałbyś wiedzieć, czy artykuły, które na niej umieszczasz, podobają się internautom, jak również chciałbyś im dać możliwość wzięcia udziału w dyskusji dotyczącej treści tego artykułu.
Aby to było możliwe, musisz mieć na stronie z tym artykułem formularz do wysyłania komentarzy, jak też skrypt obsługujący go (zapisywanie i odczytywanie komentarzy w bazie danych).
W tym artykule pokażę, jak go zrobić.
Jeżeli nie interesują Ciebie poszczególne kroki - przejdź do całego skryptu
Zacznijmy od samego formularza, czyli miejsca, gdzie internauci wpisywać będą tekst komentarza, podawać swój nick, czy tez inne dane. W przypadku serwisu www-4u.pl są to: nick i komentarz.
Stwórzmy więc formularz:
<form action="'.$adres.'" method="post"> <p><b>Twój Nick</b>: <br /><input type="text" name="nick" size="35" maxlength="35" /></p> <p class="email_h"><b>Twój e-mail</b>: <br /><input type="text" name="e_mail" /></p> <p><b>Twój Komentarz</b>:<br /><textarea name="komentarz" cols="77" rows="10" ></textarea></p> <input type="submit" name="wys_kom" value="Wyślij" class="przycisk"/> </form>
Wypada wyjaśnić znaczenie fragmentu w pierwszej linii kodu, a mianowicie: '.$adres.'.
Krótko mówiąc - jest to adres strony z komentowanym artykułem, na której znajduje się formularz. Aby było nam wygodnie, zamiast wpisywać go ręcznie na każdej stronie, pobierzemy go sobie automatycznie. Jak to zrobić wyjaśnię w dalszej części, opisującej obsługę formularza.
Zabezpieczenie przed robotami (spamem), będzie stanowić pole e_mail (trzecia linijka). Roboty sieciowe będą widzieć to pole i namiętnie wpisywać w nie swoje e-maile. Normalni użytkownicy z krwi i kości, nie będą widzieć tego pola (ukryte za pomocą CSS), więc siłą rzeczy go nie wypełnią. Skrypt, o którym za chwilę, wykryje to, i odpowiednio zareaguje.
Komentarze będą przechowywane w bazie danych - w tym przykładzie - bazie o nazwie baza_nr1. Stwórzmy wiec tabelę komentarze, w której będą przechowywane.
Za pomocą phpMyAdmin'a w oknie SQL wpisujemy i wykonujemy:
CREATE TABLE IF NOT EXISTS `komentarze` ( `id` int(7) unsigned NOT NULL AUTO_INCREMENT, `url` char(45) COLLATE utf8_polish_ci NOT NULL, `nick` char(35) COLLATE utf8_polish_ci NOT NULL, `data` datetime NOT NULL, `ip` char(15) COLLATE utf8_polish_ci NOT NULL, `komentarz` text COLLATE utf8_polish_ci NOT NULL, PRIMARY KEY (`id`), KEY `url` (`url`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8 COLLATE=utf8_polish_ci COMMENT='komentarze do artykułów' AUTO_INCREMENT=1 ;
Teraz zajmiemy się skryptem php, który obsłuży formularz - prześle dane (komentarz i nick) do bazy danych, oraz wyświetli komentarze, które znajdują się już w bazie i odnoszą się do tego artykułu.
// Pobieramy adres IP komentującego $IP = $_SERVER['REMOTE_ADDR']; // Pobieramy adres aktualnej strony bez nazwy domeny $adres = $_SERVER['REQUEST_URI']; /* Tutaj zastosuj swój skrypt połączenia z bazą danych */ // Jeżeli został wciśnięty przycisk "wyślij" if (isset ($_POST['wys_kom'])) { // Jeżeli nick jest pusty if (empty($_POST['nick'])) { $komunikat .= '<p>Podaj swój nick (imię).</p>'; } else { $nick = ($_POST['nick']); } // Jeżeli komentarz jest pusty if (empty($_POST['komentarz']) ) { $komunikat .= '<p>Napisz komentarz.</p>'; } else { $koment = stripslashes($_POST['komentarz']); } // Zabezpieczenie przed robotami if (!empty($_POST['e_mail'])) { $komunikat .= '<p>Według skryptu jesteś robotem. Twój komentarz został odzrzucony. Jeżeli nie jesteś tym za kogo wziął Cię nasz skrypt, skontaktuj się z administratorem strony.</p>'; } //Jeżeli nie ma żadnego błędu if (!isset($komunikat)) { $zapytanie = "INSERT INTO komentarze (url, nick, komentarz, data, ip) VALUES ( '$adres', '$nick', '$koment', NOW(), '$IP')"; if ($rezultat = mysql_query ($zapytanie)) { mysql_close(); header ("Location: http://" . $_SERVER['HTTP_HOST'] . $_SERVER['PHP_SELF']); exit(); } else { $komunikat = '<p>Przepraszamy za chwilowe usterki. Wysłanie komentarza nie było możliwe. Spróbuj później.</p>'; } } }
Dwie pierwsze linijki skryptu obsługi to przyporządkowanie zmiennym $IP i $adres - odpowiednio:
- adresu IP użytkownika wysyłającego komentarz (przydatne w przypadku banowania itp.)
- adresu aktualnej strony - w tabeli bazy danych komentarze będzie kolumna przechowująca adres strony z której wysłany został komentarz
(bez adresu URL domeny - w celu zaoszczędzenia miejsca w bazie danych). Będzie ona też potrzebna do wczytywania komentarzy dotyczących artykułu na danych stronach serwisu. Na tej stronie jest to: /skrypty-formularz-komentarze.php
Zabezpieczenie przed robotami stanowi wyrażenie warunkowe:
if (!empty($_POST['e_mail'])) {
$komunikat .= 'Według skryptu ...';
}
Jeżeli pole e_mail nie jest puste - skrypt wyświetli odpowiedni komunikat. Z kolei wyświetlenie jakiegokolwiek komunikatu, skrypt traktuje jako błąd i nie dodaje komentarza do bazy danych. Wyjaśniam to poniżej.
Wypadałoby się też zabezpieczyć przed wysyłaniem pustych komentarzy, jak też komentarzy bez nick'a. Służą temu wyrażenia warunkowe, okomentowane w powyższym skrypcie jako Jeżeli nick jest pusty i Jeżeli komentarz jest pusty.
Jeżeli skrypt wykryje, że komentarz, nick jest pusty, lub fakt, że został wpisany email, wyświetli komunikat - odpowiednio Podaj swój nick (imię), Napisz komentarz lub Według skryptu jesteś robotem. Twój ....
Dalej widzimy akcję dodania komentarza do bazy danych, poprzedzoną wyrażeniem warunkowym sprawdzającym, czy nie został wysłany komunikat. Jeżeli został wysłany, to znaczy, że nick lub komentarz jest pusty, ewentualnie w formularzu został wpisany email (ludzie nie widzą tego pola), bo tylko w tych trzech wypadkach jest on wysyłany.
Jeżeli nie ma komunikatu, skrypt dodaje rekord do bazy danych, zamyka połączenie z bazą i przekierowuje na tę stronę - aby pozbyć się "zmiennych POST" i tym samym zabezpieczyć stronę przed odświeżeniem i ponownym wysłaniem tego samego komentarza.
Jeżeli jest jakikolwiek komunikat(y), skrypt nie zapisze komentarza w bazie, tylko wyświetli ten komunikat (te komunikaty).
// Wyświetla wszystkie komentarze do tego artykułu $zapytanie2 = "SELECT * FROM komentarze WHERE url = '$adres' ORDER BY id"; $rezultat2 = mysql_query ($zapytanie2); while ($dane = mysql_fetch_array ($rezultat2, MYSQL_ASSOC)) { echo' <p><b>',$dane['nick'],'</b> (',$dane['data'],')</p> <p>',nl2br($dane['kom']),'</p>'; <hr />'; } // Jeżeli są jakieś komunikaty - wyświetl je if (isset($komunikat)) { echo $komunikat; } --- Tutaj formularz wysyłania komentarzy ---
Pierwsza część powyższego kodu odpowiada za wyświetlanie komentarzy dotyczących tego artykułu.
Druga część sprawdza, czy nie wysłany był komunikat o błędzie (pusty komentarz, nick, czy też błąd spowodowany usterkami - błąd skryptu, lub połączenia z bazą). Jeżeli był wysłany - wyświetla go.
<?php // Pobieramy adres IP komentującego $IP = $_SERVER['REMOTE_ADDR']; // Pobieramy pełny adres strony na której wysyłany jest komentarz $lokalizacja = 'http://'.$_SERVER['HTTP_HOST'].$_SERVER['REQUEST_URI']; // Pobieramy adres aktualnej strony bez nazwy domeny, czyli np.: "jakis-artykul.php", do bazy danych $adres = $_SERVER['REQUEST_URI']; /* Dane potrzebne do połączenia z bazą danych, oraz nawiązanie połączenia. Poniżej są domyślne dane do połączenia z serwerem WampServer (po instalacji). Więcej informacji o instalacji tego serwera na: http://www-4u.pl/instalacja-serwera.php Jeżeli masz lepszy sposób na łączenie z bazą mysql - zastosuj go zamiast poniższego */ DEFINE ('DB_USER', 'root'); DEFINE ('DB_PASSWORD', ''); // Jeżeli masz jakieś hasło to wpisz DEFINE ('DB_HOST', 'localhost'); DEFINE ('DB_NAME', 'baza_nr1'); // Jeżeli masz inną nazwę bazy danych - podaj swoją // Nawiązuje połączenie i wybiera bazę danych. $dbc = @mysql_connect(DB_HOST, DB_USER, DB_PASSWORD) OR die ('Nie mogłem połączyć się z MySQL-em: ' . mysql_error() ); @mysql_select_db(DB_NAME) OR die ('<b>Nie udało mi się wybrać bazy danych:</b> ' . mysql_error() ); // Jeżeli został wciśnięty przycisk "wyślij" if (isset ($_POST['wys_kom'])) { // Jeżeli nick jest pusty if (empty($_POST['nick'])) { $komunikat .= '<p>Podaj swój nick (imię).</p>'; } else { $nick = ($_POST['nick']); } // Jeżeli komentarz jest pusty if (empty($_POST['komentarz']) ) { $komunikat .= '<p>Napisz komentarz.</p>'; } else { $koment = stripslashes($_POST['komentarz']); } // Zabezpieczenie przed robotami if (!empty($_POST['e_mail'])) { $komunikat .= '<p>Według skryptu jesteś robotem. Twój komentarz został odzrzucony. Jeżeli nie jesteś tym za kogo wziął Cię nasz skrypt, skontaktuj się z administratorem strony.</p>'; } //Jeżeli nie ma żadnego błędu if (!isset($komunikat)) { $zapytanie = "INSERT INTO komentarze (url, nick, data, ip, komentarz) VALUES ('$adres', '$nick', NOW(), '$IP', '$koment')"; mysql_query("set names utf8;"); if ($rezultat = mysql_query ($zapytanie)) { mysql_close(); header ("Location: http://" . $_SERVER['HTTP_HOST'] . $_SERVER['PHP_SELF']); exit(); } else { $komunikat = '<p>Przepraszamy za chwilowe usterki. Wysłanie komentarza nie było możliwe. Spróbuj później.</p>'; } } } echo' <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="pl" lang="pl"> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/> <meta name="Description" content=" [wstaw tu opis strony] "/> <meta name="Keywords" content=" [wstaw tu slowa kluczowe] "/> <meta name="Author" content="www-4u.pl"/> <meta name="Copyright" content="Copyright (c) 2011 www-4u.pl"/> <title>Formularz wysyłania wiadomości</title> <!-- poniżej przykładowy styl CSS --> <!-- strona --> <style type=text/css> body { width: 660px; text-align: left; margin: 0 auto; background-color: #f9f8f0; font-family: Arial, tahoma, Verdana; font-size: 13px; color: #444; padding:10px; border-right: 1px solid #c7b467; border-left: 1px solid #c7b467; } h1 { color: #dd0000; margin: 10px 0; } h2 { color: #a28324; margin: 10px 0; } <!-- formularz --> .formularz { background-color: #f2e8c6; padding: 5px 10px; margin: 10px 0; border-right: 1px solid #999; border-bottom: 1px solid #999; border-left: 1px solid #fff; border-top: 1px solid #fff; } .komunikat { background-color: #ff0000; color: #fafafa; padding: 5px; margin: 10px 0; } .koment { color: #777; border: 2px solid #fdfdfd; padding: 0 5px; margin: 3px 0; background-color: #fdfdfd; border-left: 1px solid #bbb; border-top: 1px solid #bbb; } .koment_nag { font-size: 11px; background-color: #f7f0db; padding: 5px 0 5px 5px; margin:0 -5px; } /* ukrywanie przed robotami */ .email_h { display: none; } </style> </head> <body> <h1>Przykładowy artykuł:</h1> <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec gravida magna ac erat vestibulum laoreet. Aliquam suscipit, dui sed tempus aliquam, ligula neque pharetra justo, eget sodales velit ipsum id nisl. Suspendisse potenti. Praesent elit orci, placerat congue tempus non, suscipit eu nulla. Nulla at aliquet libero. Vestibulum pulvinar iaculis elit, nec elementum tellus malesuada ac. In pellentesque, erat non imperdiet vulputate, urna risus commodo nunc, vitae egestas tortor est sit amet ligula. Praesent auctor iaculis libero eget mattis. Nunc ac sem dolor. Donec at lacus dolor, a molestie lacus. Donec gravida malesuada nulla, vel pharetra elit pharetra eu. Aenean pretium eros ac nulla egestas at cursus magna bibendum. Aliquam pellentesque lobortis nulla sed tincidunt.</p>'; // Wyświetla wszystkie komentarze do tego artykułu echo'<h2>Wasze komentarze:</h2>'; $zapytanie2 = "SELECT * FROM komentarze WHERE url = '$adres' ORDER BY id"; mysql_query("set names utf8;"); $rezultat2 = mysql_query ($zapytanie2); while ($dane = @mysql_fetch_array ($rezultat2, MYSQL_ASSOC)) { echo' <div class="koment"> <p class="koment_nag"><b>',$dane['nick'],'</b> (',$dane['data'],')</p> <p>',nl2br($dane['komentarz']),'</p> </div>'; } // Jeżeli są jakieś komunikaty - wyświetl je if (isset($komunikat)) { echo '<div class="komunikat">'.$komunikat.'</div>'; } // Formularz wysyłania komentarza echo' <div class="formularz"> <h2>Napisz komentarz:</h2> <form action="'.$lokalizacja.'" method="post"> <p><b>Twój Nick</b>: <br /><input type="text" name="nick" size="35" maxlength="35" /></p> <p class="email_h"><b>Twój e-mail</b>: <br /><input type="text" name="e_mail" /></p> <p><b>Twój Komentarz</b>:<br /><textarea name="komentarz" cols="77" rows="10" ></textarea></p> <input type="submit" name="wys_kom" value="Wyślij" class="przycisk"/> </form> </div> </body> </html>'; ?>
Powyższy skrypt jest od razu gotowy do działania, oczywiście jeżeli nie ominąłeś kroku związanego z utworzeniem bazy danych. Umieściłem w nim kawałek kodu stylu CSS, żeby w przypadku kiedy go wkleisz do swojego dokumentu php, jakoś wyglądał (podgląd). Na jego końcu umieszczona jest klasa odpowiadająca za ukrycie pola e_mail przed użytkownikami. Roboty widzą kod html strony, więc i to pole będzie dla nich widoczne. Z pewnością z niego skorzystają, i to je zgubi.
Jeżeli chcesz - pobierz pliki do przetestowania na swoim roboczym serwerze.
W skład zestawu wchodzą:
A jak sprawa skryptu ma się do bootów spamujących przez takie formularze?
Gostoo, w powyższym skrypcie nie ma takiego zabezpieczenia. Na www-4u.pl jest.
Jeżeli podejrzysz źródło tej strony i plik css, zrozumiesz na czym polega.
To tak na szybko.
Niedługo zaktualizuję artykuł i dodam tę metodę do powyższego skryptu. Dzięki za sugestię.
Artykuł zaktualizowany. Dodałem w nim zabezpieczenie przed spamem botów sieciowych.
Mam w planach napisać więcej przykładów (sposobów) zabezpieczenia formularzy przed robotami sieciowymi, opartych na podchwytliwych pytaniach, które skutecznie wykryją "sztuczną inteligencję". Będą one dostępne w dziale Przydatne skrypty.
a czy komentarze sa sprawdzane przez admina a potem wstawiane na stronie...wlasnie chodzi mi o taki skrypt jak mozesz to prosze podaj.Pozdrawiam ,masz super stronke.
Witam, jak zrobić by komentarz wyświetlał się po wysłaniu na stronie, wraz z innymi?
dlaczego skrypt powraca do strony indeks przy dynamicznych urelach np
To zabezpieczenie przed botami to jakaś parodia. 99% komentarzy uważa, że są napisane przez bota!
Możesz podać kod bez tego zabezpieczenia? Bo jak go usuwam to wyskakuje błąd ;/
Odpowiedź na komentarz nr 12:
muszę sobie sam odpowiedzieć na to pytanie :-)
trzeba się nauczyć programowania w PHP i wszystko będzie jasne.
Skrypt jest super działa tylko trzeba pamiętać że używając "Location" przed nim nie może być ani kawałka kodu HTML. Najpierw skrypt z php a potem reszta.
Dziękuje za ten skrypt twórcy pozdrawiam!!!
Witam
Świetna stronka. Dużo mi pomógł zamieszczony tu skrypt, ale mam problem z jednym. Brakuje mi opcji usuwania komentarzy. Próbowałem robić przeszczepy z innych skryptów, ale ciągle coś jest nie tak. Jakby ktoś podrzucił tu rozwiązanie to byłbym wdzięczny.
Można to zrobić na trzy sposoby:
1. Zrobić stronę administracyjną ze wszystkimi komentarzami, umieścić na niej skrypt do ich usuwania.
2. Bezpośrednio na stronie z komentarzami zrobić przycisk "Usuń" widziany tylko przez administratora, wykorzystując do tego np. IP (jeżeli jest stałe, niezmienne) i kawałek skryptu php obsługującego ten przycisk.
3. Wejść do bazy danych "ręcznie", np. za pomocą PHPMyAdmin (każdy hostingodawca udostępnia coś takiego), odnaleźć dany komentarz i go usunąć.
© copyright: www-4u.pl