Choose a version here. If you've not already started the tutorial, just go with the latest one.

NB: There are several versions of this tutorial, each successive one containing additional improvements. If you're in the middle of working through it, please check the versions panel above, to ensure you're not mixing code from different versions.

Make your own blog

What is this?

It's a small, interactive course to teach beginners the PHP programming language.

Who's it for?

Anyone who wants to learn how to create simple database-powered web applications.

How much does it cost?

It's free of charge.

Do I need to sign up?

No, not at all.

How do I get started?

Click on the first chapter in the index.

How is each change introduced?

I use a visual device known as a diff. Related file changes are grouped into sets, like this example — explore by clicking on the tabs.

index.php index.php

install.php install.php

lib/common.php lib/common.php

view-post.php view-post.php Download 1 2 3 4 5 6 7 8 9 10 11 12 <?php // Work out the path to the database, so SQLite/PDO can connect $root = __DIR__; $database = $root . '/data/data.sqlite'; $dsn = 'sqlite:' . $database; // Connect to the database, run a query, handle errors $pdo = new PDO($dsn); $stmt = $pdo->query( 'SELECT id, title, created_at, body 1 2 3 4 5 6 7 8 <?php require_once 'lib/common.php'; // Connect to the database, run a query, handle errors $pdo = getPDO(); $stmt = $pdo->query( 'SELECT id, title, created_at, body Download 1 2 3 4 5 6 7 8 40 41 42 43 44 45 46 <?php // Get the PDO DSN string $root = realpath(__DIR__); $database = $root . '/data/data.sqlite'; $dsn = 'sqlite:' . $database; $error = ''; // Connect to the new database and try to run the SQL commands if (!$error) { $pdo = new PDO($dsn); $result = $pdo->exec($sql); if ($result === false) { 1 2 3 4 5 6 7 8 9 40 41 42 43 44 45 46 <?php require_once 'lib/common.php'; // Get the PDO DSN string $root = getRootPath(); $database = getDatabasePath(); $error = ''; // Connect to the new database and try to run the SQL commands if (!$error) { $pdo = getPDO(); $result = $pdo->exec($sql); if ($result === false) { Download 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 <?php /** * Gets the root path of the project * * @return string */ function getRootPath() { return realpath(__DIR__ . '/..'); } /** * Gets the full path for the database file * * @return string */ function getDatabasePath() { return getRootPath() . '/data/data.sqlite'; } /** * Gets the DSN for the SQLite connection * * @return string */ function getDsn() { return 'sqlite:' . getDatabasePath(); } /** * Gets the PDO object for database access * * @return \PDO */ function getPDO() { return new PDO(getDsn()); } Download 1 2 3 4 5 6 7 8 13 14 15 16 17 18 19 <?php // Work out the path to the database, so SQLite/PDO can connect $root = __DIR__; $database = $root . '/data/data.sqlite'; $dsn = 'sqlite:' . $database; // Get the post ID if (isset($_GET['post_id'])) } // Connect to the database, run a query, handle errors $pdo = new PDO($dsn); $stmt = $pdo->prepare( 'SELECT title, created_at, body 1 2 3 4 5 13 14 15 16 17 18 19 <?php require_once 'lib/common.php'; // Get the post ID if (isset($_GET['post_id'])) } // Connect to the database, run a query, handle errors $pdo = getPDO(); $stmt = $pdo->prepare( 'SELECT title, created_at, body

What, no framework?

Deliberately so. I think it's a good idea to learn what can be done with a language before using frameworks. Frameworks are good because they hide the nuts and bolts of applications from developers, but they can be bad, because they hide the nuts and bolts of applications from learners.

Is the tutorial finished?

Most tutorials are published and forgotten about, which is why there are so many on the web promoting old or insecure practices. This one is finished in the sense it is ready to use, but I intend to maintain it.

Will this work with the latest version of PHP?

Indeed it will. It will work on a version of PHP as low as 5.5, but since it was written with best practices to start off with, it works just fine with any PHP in the 7.x series as well.

How do I obtain assistance if I get stuck?

I have set up a support channel on Reddit, where you are welcome to post about any problems you may have with this material. As the author, I'll try to be around to help.

If I'm not around, PHPhelp is also worth a try. There are also plenty of other help forums and chat rooms on the web, which can be found with an internet search, and many of these will cater to beginners.

Can I offer some general feedback?

Of course. If you have some general remarks, then please post a new topic on the support channel. If you see a specific issue, or you can see something that could be done better, please raise a bug report on GitHub.

Any tips on how to break through beginner frustration?

Building a group of fellow programmers of a similar level of learning can be very helpful. You can do this in your local area, or reach out to people over the web via social media. You can use tools like instant messaging, perhaps meeting at an agreed weekly time, to chat whilst you learn.