Getting Started with the SQL Server Driver for PHP

In this post, I’ll focus on the basics of using the SQL Server Driver for PHP to insert and retrieve data in a SQL Server Express database. I’ll build a web page that exposes enough of the driver functionality for you to understand the basics of connecting to a server, inserting and retrieving data, and handling errors.

 

A quick note about simplicity: The web page I’ll build in this post is very simple – it’s just a simple form, really. It collects information about people who are registering for some fictional event. I’m intentionally keeping it very simple so I can focus on the PHP code for using the driver. (Finally, I get to write some code. J) For a more complex example that demonstrates more of the driver features, see the Example Application that is part of the driver documentation.

 

Installation and Configuration

To execute the code in this post, you will need to have PHP, the SQL Server Driver for PHP, and SQL Server Express installed on your local machine. If you used the Web Platform Installer and followed the instructions in my last post, you are ready to go. J If you installed PHP manually, you will still need to install the driver and SQL Server Express:

 

· Download SQL Server Express here: SQL Server Express Download

· Download the SQL Server Driver for PHP here: Driver Download

 

After you have downloaded the driver, you need to move the appropriate driver .dll file into your PHP extension directory, add the corresponding entry in your php.ini file to enable the extension, and restart your Web server. The appropriate version of the driver depends on whether your PHP installation PHP 5.2 or 5.3, is thread-safe or non-thread-safe, and whether it was compiled with Visual C++ 6.0 or Visual C++ 9.0. For example, if you installed a non-thread-safe version of PHP 5.3 that was compiled with Visual C++ 9.0, you need to put the php_sqlsrv_53_nts_vc9.dll file into your PHP extension directory and add the following line to the extension section of your php.ini file (and then restart your Web server):

 

extension=php_sqlsrv_53_nts_vc9.dll

Creating the Database

The database I’ll use for this simple web application can be created by executing the PHP script that is attached to this post (CreateExampleDB.php). Of course, you’ll have to update the script with your SQL Server login and password. If you have SQL Server Management Studio installed, you can simply execute the following Transact-SQL:

 

SET ANSI_NULLS ON

SET QUOTED_IDENTIFIER ON

USE [master]

CREATE DATABASE ExampleDB

GO

USE ExampleDB

CREATE TABLE [dbo].[RegistrationTbl](

            [ID] [int] IDENTITY(1,1) NOT NULL,

            [Email] [nvarchar](50) NOT NULL,

            [LastName] [nvarchar](50) NOT NULL,

            [FirstName] [nvarchar](50) NOT NULL,

            [RegDate] [datetime] NOT NULL,

      CONSTRAINT [PK_RegistrationTbl] PRIMARY KEY CLUSTERED

      (

            [ID] ASC

      )ON [PRIMARY]

) ON [PRIMARY]

     

CREATE UNIQUE NONCLUSTERED INDEX [IX_UniqueEmail] ON [dbo].[RegistrationTbl]

(

      [Email] ASC

) ON [PRIMARY]

 

Building the Web Page

The web page I’ll build begins with the code below. In the following sections of this post, I’ll fill in the PHP code for connecting to the server, inserting and retrieving data, and handling errors. Copy this code into a file named ExampleForm.php and put it in your Web server’s root directory so you can test the page as we go. (The completed web page is in the .zip file that is attached to this post.)

 

<html>

<head>

<Title>Example Web Form</Title>

</head>

<body>

<form method="post" action="?action=add" enctype="multipart/form-data" >

      Last name <input type="text" name="lastName" id="lastName"/></br>

      First name <input type="text" name="firstName" id="firstName"/></br>

      E-mail address <input type="text" name="emailAddress" id="emailAddress"/></br>

      <input type="submit" name="submit" value="Submit" />

</form>

<?php

      //I’ll fill in the code here as we move through this tutorial.

?>

</body>

</html>

 

Connecting to the Server

Before I can insert or retrieve data, I need to establish a connection to the server. The SQL Server Driver for PHP API provides the sqlsrv_connect function for doing this. This function takes one required parameter ($serverName) and one optional parameter ($connectionOptions). The $connectionOptions parameter allows me to specify the database I want to connect to, my SQL Server login, my password, and other options.  (For a complete list of the connection options, see the sqlsrv_connect reference page.) So, here’s what I need to connect to my local instance of SQL Sever Express:

 

$serverName = ".\sqlexpress";

$connectionOptions = array("Database"=>"ExampleDB",

         "UID"=>"My_Login",

       "PWD" => "My_Password");

$conn = sqlsrv_connect($serverName, $connectionOptions);

if($conn === false)

{

      die(print_r(sqlsrv_errors(), true));

}

 

I’ll explain the error handling later, but I’ll try to anticipate other questions you might have about this code here:

· What is the “.” in the server name? This is just shorthand for specifying the local server. You could also use “(local)\sqlexpress” or “yourServerName\sqlexpress”.

·  If I have to specify the database in the connection string, how do I change databases later? You simply need to use the sqlsrv_query function to execute a statement that changes the database. The Transact-SQL command for this is USE databaseName.

 

Inserting Data

Next I’ll write code that will take data from the submitted form and insert it into the database. To do this, I’ll use the sqlsrv_query function that executes an INSERT command. (There are three lines of code to focus on here, just below the /*Insert data*/ comment.) First, I’ll need to define the SQL that I want to execute ($insertSql). Second, I define an array ($params) that contains the parameter values from the $_POST variable. And last, I pass the connection resource, the SQL string, and the parameter array to the sqlsrv_query function.

 

if(isset($_GET['action']))

{

      if($_GET['action'] == 'add')

      {

            /*Insert data.*/

            $insertSql = "INSERT INTO RegistrationTbl (LastName, FirstName, Email, RegDate)

                          VALUES (?,?,?,?)";

            $params = array(&$_POST['lastName'],

                            &$_POST['firstName'],

                            &$_POST['emailAddress'],

                            date("Y-m-d"));

            $stmt = sqlsrv_query($conn, $insertSql, $params);

            if($stmt === false)

            {

                  /*Handle the case of a duplicte e-mail address.*/

                  $errors = sqlsrv_errors();

                  if($errors[0]['code'] == 2601)

                  {

                        echo "The e-mail address you entered has already been used.</br>";

                  }

                  /*Die if other errors occurred.*/

                  else

                  {

                        die(print_r($errors, true));

                  }

            }

            else

            {

                  echo "Registration complete.</br>";

            }

      }

}

 

As in the previous section, I’ll explain the error handling later, but I’ll try to anticipate other questions now:

· Why does the SQL string contain question marks? I’m using question marks (?) in place of the parameter values instead of concatenating parameter values with the SQL string to avoid SQL injection attacks. I wrote a post about why this is important some time back: How and Why to Use Parameterized Queries.

· Why are the variables in the $params array references? This is the recommended approach for constructing parameter arrays. Not using references in the parameter array can lead to unexpected results if the query is executed multiple times.

 

Retrieving Data

Now I want to display a table that contains information about all the people who have registered for my fictional event. Again, I’ll use the sqlsrv_query function, but this time I’ll use it to execute a SELECT statement. To access rows of returned data, I’ll use the sqlsrv_fetch_array function. (By default, this function returns an array with both numeric and associative indexes.) Notice that I’m using the sqlsrv_has_rows function to display the table only when the executed query actually returns rows (i.e. there are actually results to display).

 

$sql = "SELECT * FROM RegistrationTbl ORDER BY LastName";

$stmt = sqlsrv_query($conn, $sql);

if($stmt === false)

{

      die(print_r(sqlsrv_errors(), true));

}

if(sqlsrv_has_rows($stmt))

{

      print("<table border='1px'>");

      print("<tr><td>Last Name</td>");

      print("<td>First Name</td>");

      print("<td>E-mail Address</td>");

      print("<td>Registration Date</td></tr>");

     

      while($row = sqlsrv_fetch_array($stmt))

      {

            $regDate = date_format($row['RegDate'], 'Y-m-d');

            print("<tr><td>".$row['LastName']."</td>");

            print("<td>".$row['FirstName']."</td>");

            print("<td>".$row['Email']."</td>");

            print("<td>".$regDate."</td></tr>");

      }

      print("</table>");

}

 

Handling Errors

OK, now for the promised discussion of the error handing code. The sqlsrv_errors function returns error information about the last operation performed by the driver. In most cases, I simply use the PHP die function and print the error array. Obviously, this would only be OK for a development environment. But notice in the Inserting Data section above, I am actually checking for a particular SQL Server error code: 2601. This error occurs when I try to enter a duplicate entry into a field that doesn’t allow duplicates. Since the Email column in my database doesn’t allow duplicates (specified by the UNIQUE constraint), I can use this error information to inform the user that the entered e-mail address has already been used.

 

You may also wonder why I use the triple equals operator (===) to check for errors. This is simple a precaution. Since the triple equals operator compares both value and type, I make sure that an integer value of zero (that could be returned by a function) is not evaluated as the Boolean value false.

 

OK, that’s it for now. Look for posts soon that drill down into some of the features of the SQL Server Driver for PHP. As always, please comments and questions are welcome.

Thanks.

-Brian

Share this on Twitter

 

GetStartedPHPDriver.zip