PHP can also create, append to, and read files on the server. You can use this to store simple data, or to log access information, for long-term retrieval. For example, let’s say we want to have a poll and keep track of the results.
Make a new web page with a simple poll in it. Call this file “poll.php”.
<html>
<head>
<title>The Best Imaginary Character</title>
</head>
<body>
<h1>Imaginary Fight to the Finish</h1>
<form method="post" action="poll.php">
<p>
Please choose your favorite imaginary imaginary character:
<select name="imagine">
<option value="">Choose:</option>
<option value="rabbit">The White Rabbit</option>
<option value="scarecrow">The Scarecrow</option>
<option value="tinman">The Tin Man</option>
<option value="neo">Neo</option>
</select>
<input type="submit" value="Submit your answer" />
</p>
</form>
</body>
</html>
This is fairly simple and mostly useless. It doesn’t remember anything yet, but it should let you make the choice. Once you have the HTML in the page working, we can go ahead and remember the poll data.
Before you do anything else, you need to create a folder to store your poll data. If you are logged in via your desktop, you can make a folder in your home directory as normal. Call it “data”. If you have command line access to your account, you might use:
mkdir ~/data
cd ~/data
pwd
The ‘mkdir’ command creates a directory. The ‘pwd’ command tells you where you currently are. Where the example code says “/path/to/data”, replace that with the results of the ‘pwd’ command. It might well say, for example, “/home/username/data”. If so, where it says “/path/to/data/choices.txt” in the example below, use “/home/username/data/choices.txt”.
Now that you have the folder for storing the data, add the PHP. At the very top of the page, even before the <html>, add:
<?
$filename = "/path/to/data/choices.txt";
IF ($choice = $_POST["imagine"]):
//let’s append this to a file
IF ($choicefile = fopen($filename, "a")):
fwrite($choicefile, "$choice\n");
fclose($choicefile);
ELSE:
echo "<p><b>Unable to append to file choices.</b></p>\n";
ENDIF;
ENDIF;
?>
What this should do is, first, open the file called “choices.txt” in the specified directory. The first item in the list is the filename. The second item is what we want to do with the file. In this case, we want to “append” to the file. If we are able to open it, we write the choice and a new line to the file. Then, we close the file.
It is important to close the file as soon as you are done with it, because you can have many different people coming in to view your web page at the same time. Your PHP scripts can be running multiple times all at the same time, but only one of them can write to your file. The rest have to wait until the file is available again.
When you try to use this program, you will almost certainly get an error that looks like:
Warning : fopen(choices.txt) [ function.fopen ]: failed to create stream: Permission denied in /home/jerry/public_html/php/poll.php on line 4
This is a typical, and useful, PHP error message. It tells you exactly which line the error occurred on, and it tells you why the error occurred. In this case, “permission” was “denied” for whatever that line tried to do. Count up to line four in our code, and you’ll see that’s the line that tries to open the file.
The web server does not have permission to create files. That would be a major security flaw. You will need to create the file by hand, and then you will need to give the web server permission to write to that file.
Go to the command line (in Mac OS X, the ‘terminal’) and get to the folder where you are storing your PHP files. In Mac OS X, you can easily switch to a folder you’re looking at by opening the terminal, typing the letters ‘cd’ and a space, and then dragging that folder onto the terminal. Go into the terminal and press return to complete the command. Your typing will look something like this:
cd ~/data (for example, or drag and drop as described above)
touch choices.txt
chmod ugo+rw choices.txt
This will create an empty file called “choices.txt”. You can look at it by typing “more choices.txt”. Nothing should happen, because it should be empty. But if you then go back to your web page, make a selection, and submit it, you should be able to type “more choices.txt” and see the choice that you made. Keep making choices, and you’ll see additional lines show up in the file.
If you did not receive that error (and if PHP still did not work) it may be that you do not have error reporting turned on. At the very top of your web page, in the php, add:
error_reporting(E_ALL ^ E_NOTICE);
This turns on all errors, and then turns off notices. See the php.net manual for more information about errors and notices.
If you are using PHP to add information to a file in your account, you need to give PHP access to “write to” the file. In general, it is best to create this directory outside of your web area.
These two commands will, in Unix, create a folder and then ensure that nobody but you has access to see what is in that folder or make new things in that folder:
mkdir ~/data
chmod go-rw ~/data
chmod go+x ~/data
This ensures that your data folder is neither readable nor writable by the web server, but that the web server can get in that directory to modify and read files there. Only files that you specifically make readable or writable will be able to be read from or written to by the server.
Before the web server can write to a file, you need to create that file. The usual way to create a file on Unix is to use the ‘touch’ command, such as:
touch ~/data/choices.txt
chmod go+rw ~/data/choices.txt
The web server runs as a user (often ‘nobody’ or ‘www’) and is part of a group (which may be anything). So if you have particularly sensitive information, you can set your file to be readable and writeable only by the web server’s user or group. Look up the ‘chmod’ command in Unix for more information.
It will usually be best to use either ‘g’ or ‘o’ but not both. Only one of them should be necessary, but which one depends on your server.
You can use the ‘ls -l’ command to see files and their permissions, and the “more” command to see what a file contains.
Whenever you create a file that the web server can write to, you are reducing the security of your system. If someone not on the system can determine the name of that file, and if they can trick your code or someone else’s code into writing to that file, they might be able to write a computer program to that file. That computer program now runs as you. So you want to be very careful about not letting people list directories that contain writable files.