} else {
////////////////////////////////
// If they didn't include all the required fields set a variable
// and keep going.
////////////////////////////////
$notall = 1;
}
}
?>
This next section is the beginning of the standard HTML part of the page.
<!-- Start Page -->
<HTML>
<HEAD>
<TITLE>Add a Message</TITLE>
</HEAD>
<BODY BGCOLOR="white">
<H1>Add A Message</H1>
This next section is a good example of how to mix and match PHP and HTML. The first line is a standard HTML comment. The second line switches to PHP and sets an IF statement to detect if the $notall variable was set to indicate that the form was incomplete. If it was set, then output the next line which is HTML, not even PHP code, and continue. If it was not set the HTML is not returned to the browser. How about that?!
<!-- Let them know that they have to fill in all the blanks -->
<? if ($notall == 1) { ?>
<P><FONT COLOR="red">Please answer all fields</FONT></P>
<? } ?>
This is the section that creates the form on the browser. The things to note are the little snippets of PHP to fill in the fields on the form if the person submitted an incomplete form. This keeps them from having to input ALL the data in again.
<!-- The bits of PHP in the form allow the data that was already input
to be placed back in the form if it is filled out incompletely -->
<FORM METHOD="post" ACTION="guest.php">
<PRE>
Your Name: <INPUT
TYPE="text"
NAME="name"
SIZE="20"
MAXLENGTH="50"
VALUE="<? echo $name; ?>">
Your Email: <INPUT
TYPE="text"
NAME="email"
SIZE="20"
MAXLENGTH="50"
VALUE="<? echo $email; ?>">
Enter Message:
<TEXTAREA NAME="message" COLS="40" ROWS="8" WRAP="Virtual">
<? echo $message; ?>
</TEXTAREA>
<INPUT TYPE="submit" VALUE="Add">
</PRE>
</FORM>
<HR>
Here we have the same two lines that connect to the host and select the database as before. The query is defined and called.
<?
////////////////////////////////
// This is where we connect to the database for reading.
////////////////////////////////
mysql_pconnect("db2.pair.com","tator_r","password")
or die("Unable to connect to SQL server");
mysql_select_db("tator_awtrey") or die("Unable to select database");
This next section sends a query to the database to count the total number of records in the table that have data in them. This is an easy way to count records.
////////////////////////////////
// This is where we count the number of entries.
////////////////////////////////
$query = "SELECT COUNT(*) FROM guests";
$numguests = mysql_query($query) or die("Select Failed!");
$numguest = mysql_fetch_array($numguests);
?>
<!-- This is where we report the total messages. -->
<P>
<A HREF="guest.php?complete=1"><? echo $numguest[0]; ?> people</A> have
left me a message.
</P>
This query is set depending on whether the URL is set to retrieve all the records or not.
////////////////////////////////
// This is where we decide to get all the entries or just the last 20.
// This variable is set by just adding a '?complete=1' after the URL.
////////////////////////////////
if ($complete == 1) {
$query = "SELECT * FROM guests ORDER BY guest_time DESC";
} else {
$query = "SELECT * FROM guests ORDER BY guest_time DESC LIMIT 20";
}
$guests = mysql_query($query) or die("Select Failed!");
This next section is a loop that runs as long as there are records. The while statement returns each record to an array called $guest. It contains all the data selected from the table in array variables named for the field name. Therefore if you want the "guest_name" value, you can get it by refering to $guest['guest_name'] This is an incredibly powerful feature since it allows you to change the structure of a database without breaking the application.
<?
////////////////////////////////
// This will loop as long as there are records waiting to be processed.
// Notice the plain HTML inside the while loop structure. PHP is flexable
// enough to allow you to break into and out of the "code" at any point.
////////////////////////////////
while ($guest = mysql_fetch_array($guests)) {
?>
This is the actual beginning of the loop. Most of it is standard HTML with PHP inserted to supply the database fields.
<TABLE BORDER="1" WIDTH="500">
<TR><TD>
Name: <? echo $guest['guest_name']; ?>
</TD><TD>
Email: <A HREF="mailto:<? echo $guest['guest_email']; ?>">
<? echo $guest['guest_email']; ?></A>
</TD><TD>
Using the MySQL timestamp datatype in PHP requires a little coding. This next bit takes apart the MySQL data and generates a formated date. The substr function just grabs a substring from a given string. The mktime function generates a timestamp that the date function uses to generate the date and time in the format specified.
<?
////////////////////////////////
// The database has a timestamp record type that we can use to show the
// date the guestbook was filled out.
////////////////////////////////
$datefromdb = $guest['guest_time'];
$year = substr($datefromdb,0,4);
$mon = substr($datefromdb,4,2);
$day = substr($datefromdb,6,2);
$hour = substr($datefromdb,8,2);
$min = substr($datefromdb,10,2);
$sec = substr($datefromdb,12,2);
$orgdate = date("l F dS, Y h:i A",mktime($hour,$min,$sec,$mon,$day,$year));
?>
Date: <? echo $orgdate; ?>
The last bit just uses PHP to drop in the variables where needed. The closing } ends the while loop and once all the data is output, the page finishes up with standard HTML.
</TD></TR>
<TR><TD COLSPAN="3">
<? echo $guest['guest_message']; ?>
</TD></TR>
</TABLE>
<BR>
<? } ?>
</BODY>
</HTML>
Fgdgggggggggggggggggggg
Lllllllllllllllllllllllllllllllllllllllllll
Finally, we'll add the following PRIMARY KEY(id) a primary key is a unique key where each entry must be defined as not null, this is the main key that MySQL will use when refering to entries in the table.
Put It Together
Now that we have everything ready to create the table we need, all that's left is to put it together:
CODE
CREATE TABLE guestbook
(
id INT(10) not null AUTO_INCREMENT,
name VARCHAR(50),
email VARCHAR(50),
message TEXT,
date CHAR(10),
PRIMARY KEY(id)
);
Now that we have our table ready we can make a simple form to add the entries into the guestbook.
Often you'll find it easier to have a seperate page for your form that people fill out and for the code needed to add the data into your table, but i'll give an example of doing everything in one page because it's easier to explain that way.
Connecting
The first thing we need to do is check the form has been posted and connect to our database:
[php]<?php
if($_POST['submit'])
{
$db = mysql_connect('localhost','db_user','db_pass')
or die(mysql_errno().' : '.mysql_error());
mysql_select_db('db_name')
or die(mysql_errno().' : '.mysql_error());[/php]
Obviously you need to replace the database values (host, user, password and database name) with your own. The if($_POST['submit']) line means that the script will only connect once somebody submits the form, as there's no need to connect to the database everytime the page loads.
Now we can form the query that will add the information into our table.
[php]
$sql[addpost] = mysql_query("INSERT INTO guestbook (name, email, message, date)
VALUES ('$_POST[name]','$_POST[email]','$_POST[message]',time())");
mysql_close($db);
echo "Thanks ".$_POST['name']." your message has been added\n";
}
[/php]
When we put it all together it should look something like this:
[php]
<?php
if($_POST['submit'])
{
$db = mysql_connect('localhost','db_user','db_pass')
or die(mysql_errno().' : '.mysql_error());
mysql_select_db('db_name')
or die(mysql_errno().' : '.mysql_error());
$sql[addpost] = mysql_query("INSERT INTO guestbook (name, email, message, date)
VALUES ('$_POST[name]','$_POST[email]','$_POST[message]',time())");
mysql_close($db);
echo "Thanks ".$_POST['name']." your message has been added\n";
}
?>
[/php]
The time() function given for the date field returns a UNIX timestamp of the current time and date, later we'll convert this into a readable date format.
The Form
Now all that's really left is to create the form for the user to fill in.
I'm hoping that if you're reading about creating and submitting infomation to a database that you at least know how to create a basic form, so i wont explain this much.
CODE
<form method="post" action="./">
<table cellpadding="6" cellspacing="0">
<tr>
<td>Name :</td>
<td><input type="text" name="name" /></td>
</tr>
<tr>
<td>Email :</td>
<td><input type="text" name="email" /></td>
</tr>
<tr>
<td valign="top">Message :</td>
<td><textarea name="message" cols="30" rows="6"></textarea></td>
</tr>
<tr>
<td> </td>
<td>
<input type="submit" name="submit" value="Add Message" />
<input type="reset" name="reset" value="Clear Message" />
</td>
</tr>
</table>
</form>
We just have three inputs for our fields name, email and message.
That's all, aslong as you followed everything correctly when you submit the form, the details will be added to the database.
Now this is far from perfect, you would really want to firstly check that all the fields are completed before the form is submitted, otherwise you'll get people posting blank messages, check the query is successful before telling the user their message was posted and probally limit the amount of characters allowed in the name and message.
It would also be a good idea to strip out the slashes from peoples messages to stop them spamming your guestbook with urls or trying to post HTML code and Javascript but this is intended to cover only the very basics so that'll require some thought and research from you to put in place.
Obviously this part is quite important. There's no point having a database full of guestbook posts if you don't know how to show them on your page, though it's also very simple.
Connecting
Exactly the same way we did when adding the message we need to connect to the database so that we can print out the messages, and we'll use much of the same code as before:
CODE
$db = mysql_connect('localhost','db_user','db_pass')
or die(mysql_errno().' : '.mysql_error());
mysql_select_db('db_name')
or die(mysql_errno().' : '.mysql_error());
As before, change the values to connect to your own database. Then once we're connected, we can run a query to grab the information from the table.
$sql[getPosts] = mysql_query("SELECT name, email, message, date, FROM guestbook order by id DESC LIMIT 10");
Now this is slightly different from the query we used before, but it's quite easy to understand.
* SELECT name, email, message, date FROM guestbook this part just says that we want to 'select' the name, email, message and date from our table named 'guestbook'.
* order by id DESC LIMIT 10 This second part defines how we want to show the messages on our page order by id DESC if you remember when creating the table we added an "id" field that will give each entry a unique number, well this basically says we want to sort our messages in order according to their id number starting with the most recent first DESC = descending.
* LIMIT 10 The final part, is exactly what it says, it will limit the output to 10 entries, so using this means only the last 10 messages will be displayed on our page, obviously you can change that however you like, if you don't specify a limit then all entries will be shown.
Display The Messages
Now that we've grabbed the information from the database we just need to print it onto the page. We need to create a loop, because we're grabbing a number of entries and not just one. You can use a while loop to make an array of the information we grabbed from the table.
[php]
while($data = mysql_fetch_array($sql[getPosts]))
{
Then print out each entry from the array. This is also the point where we'll convert the UNIX timestamp in the date field to a readable format using PHP's date() function.
$post_date = date('D F jS Y @ g:ia', $data[date]);
echo "<div>On $post_date <a href=\"mailto:$data[email]\">$data[user]</a> said:</div>\n";
echo "<div>$data[message]</div>\n\n";
}
mysql_close($db);[/php]
After putting that together, you should have something like the following:
[php]
<?php
$db = mysql_connect('localhost','db_user','db_pass')
or die(mysql_errno()'. : .'mysql_error());
mysql_select_db('db_name')
or die(mysql_errno()'. : .'mysql_error());
$sql[getPosts] = mysql_query("SELECT name, email, message, date, FROM guestbook order by id DESC LIMIT 10");
while($data = mysql_fetch_array($sql[getPosts]))
{
$post_date = date('D F jS Y @ g:ia', $data[date]);
echo "<div>On $post_date <a href=\"mailto:$data[email]\">$data[user]</a> said:</div>\n";
echo "<div>$data[message]</div>\n\n";
}
mysql_close($db);
?>[/php]
And that's all you need, connect to the database, grab the entries from the table, put them into an array and use a loop to echo them one by one to the page.
Now you have your very own guestbook
Ssssssssssssssssssssssssssssssssss
FORM action=gb.php METHOD=POST>
Text: <TEXTAREA ROWS=4 COLS=40 name=text>ass</TEXTAREA><br>
Author: <INPUT TYPE=TEXT name=author><br>
Email: <INPUT TYPE=TEXT name=email><br>
Homepage: <INPUT TYPE=TEXT name=homepage><br>
<INPUT TYPE=SUBMIT>
</FORM>
See I wrote nothing special, just a set of the input types. And the method is POST cause we want user to post some data when he adds new message.
Now let me explain how the main script works.
The code shown below is to add new line to the file. Remember to use file locking functions if you want stable guestbook.
$fp=fopen($gbfile,'a+');
flock($fp, LOCK_EX);
fwrite($fp, $tmp. "\n");
flock($fp, LOCK_UN);
fclose($fp);
Another important thing is to read the contents of a file:
$i=1;
while($i<$start && !feof($fp)) {
$tmp=fgets($fp);
$i++;
}
while($i<=$end && !feof($fp)) {
$tmp=trim(fgets($fp));
if ($tmp) { array_push($records, $tmp); }
$i++;
}
The code above uses first "while" cycle to skip first lines and second "while" cycle reads the records to be shown. See how $start and $end variables are involved. These are for showing a certain number of records on the page.
Now I'll explain how the adding part works:
if ($REQUEST_METHOD=='POST' && $_POST['text']) {
$msg = str_replace($separator, '', htmlspecialchars($_POST['text']));
$author = str_replace($separator, '', htmlspecialchars($_POST['author']));
$email = str_replace($separator, '', htmlspecialchars($_POST['email']));
$homepage = str_replace($separator, '', htmlspecialchars($_POST['homepage']));
$tmp = implode($separator, array($msg, $author, $email, $homepage));
add($tmp);
}
This code checks if the form was submitted by POST method and then it adds all fields into the file as a string. Implode function is used to get single text line from a set of values.
I would not say much about the listing part and about the pagination code.
Just note this code:
?>
<HR>
Author: <?=$author?><br>
Email: <?=$email?><br>
Homepage: <?=$homepage?><br>
Text: <?=$msg?><br><br>
<?
It will output each record so you can write a better HTML code here.
Feel free to ask me in our if you get troubles when tuning any part of this script for your page.
Now I placed all this code into one file.
File gb.php
<?
$gbfile='gb.txt';
$separator= '^';
//====================================
//This function will add one line to
//the end of file
//====================================
function add($str){
global $gbfile;
$tmp = trim($str);
$fp=fopen($gbfile,'a+');
flock($fp, LOCK_EX);
fwrite($fp, $tmp. "\n");
flock($fp, LOCK_UN);
fclose($fp);
}
//====================================
//Function below gets specified number
//of lines and returns an array
//====================================
function get($start, $end){
global $gbfile;
$records=array();
$filename="gb.txt";
$fp=fopen($gbfile,'r');
flock($fp, LOCK_SH);
$i=1;
$tmp=TRUE;
while($i<$start && !feof($fp)) {
$tmp=fgets($fp);
$i++;
}
while($i<=$end && !feof($fp)) {
$tmp=trim(fgets($fp));
if ($tmp) { array_push($records, $tmp); }
$i++;
}
flock($fp, LOCK_UN);
fclose($fp);
return($records);
}
//=============================================
//Start of the script
//=============================================
//If the method is post then add new message
//to the guestbook file
if ($REQUEST_METHOD=='POST' && $_POST['text']) {
$msg = str_replace($separator, '', htmlspecialchars($_POST['text']));
$author = str_replace($separator, '', htmlspecialchars($_POST['author']));
$email = str_replace($separator, '', htmlspecialchars($_POST['email']));
$homepage = str_replace($separator, '', htmlspecialchars($_POST['homepage']));
$tmp = implode($separator, array($msg, $author, $email, $homepage));
add($tmp);
}
//Listing part
$start=$_GET['start'];
$end=$_GET['end'];
if (!$end || $start<=0) { $start=1; }
if (!$end) { $end=10; }
if ($end<$start) { $end=$start+1; }
$show=$end - $start;
//Get records from file into array
$records = get($start, $end);
//For each record get each field
foreach ($records as $rec) {
$tmp = explode($separator, $rec);
$msg = $tmp[0];
$author = $tmp[1];
$email = $tmp[2];
$homepage = $tmp[3];
//=================================
//Outputting
?>
<HR>
Author: <?=$author?><br>
Email: <?=$email?><br>
Homepage: <?=$homepage?><br>
Text: <?=$msg?><br><br>
<?
}
//Pagination
if ($start>$show) {
$start-=$show;
$end-=$show;
print "<a href=gb.php?start=$start&end=$end>Prev $show</a> ";
if (count($records)!=0) {
$start+=$show*2;
$end+=$show*2;
print "<a href=gb.php?start=$start&end=$end>Next $show</a>";
}
else {
print "No more records found !";
}
}
else {
$start+=$show;
$end+=$show;
print "<a href=gb.php?start=$start&end=$end>Next $show</a> ";
}
?>
How to use it...
First, remember to use HTML form that is shown in top part of this text. Second, to see the contents of the guestbook, you can create a regular link to the file:
<a href=gb.php>Guestbook</a>
If you want to have a certain number of records to be shown on each page of the guestbook, you can use this parameters for the script:
start: means number of the first record
end: means number of the last record
Example:
gb.php?start=1&end=10
If you want to configure this script with the design of your page you can insert any HTML code before the code (I mean before the first '<?'). And also you can add a footer after the last line of the file.