As mentioned in my previous blog entry, I have undertaken a large project converting an existing application to PHP whith a MySQL back end (a LAMP stack type app). To do so, I have begun looking into PHP frameworks. I have settled on Zend Framework.
The reason I chose Zend is simple - it was the first framework I tried. After looking into Cake PHP, it seemed to be too strict in its requirements for this particular project. But after doing some initial work with Zend it became apparent that where Zend couldn't do what I need, plain old PHP could. So, I have begun coding with Zend.
The first challenge was to decide what directory structure to go with. There are many options here, and the directory structure has a dedicated posting on the ZF Wiki called Choosing Your Application's Directory Layout. This post nicely shows many options. After some talk on IRC (the #zftalk channel), I found another posting - Zend Framework: Zend Framework Default Project Structure Component Proposal. This posting shows what seems to be a good structure that will be extend-able as needed into the future. Specifically with regards to adding modules at a later date.
The idea of this directory structure is that the Internet users can only access files in the "public" directory. This assumes you have set up a virtual host on your web server that points to the public directory. All the processing code, configuration files, and documentation is outside the public directory to minimize security concerns. The directories do not need to be included, if they are not used. In my case, the "apis" directory is irrelevant (for now).
My next big challenge was to build a "bootstrap.php" file that was sufficient for what I need. For those who don't know, Zend uses a URL rewrite rule to filter all requests through a single file - index.php. This file then initializes the Zend environment, gets any needed data, and renders it to the page. The index.php file passes the request to the bootstrap code. The bootstrap also is where you would setup any global elements - database connections, configuration files, etc. However, there are different approaches to the bootstrap, and different needs. At a bare minimum, the bootstrap will set up a "Front Controller", and pass the request data to the front controller.
The bootstrap can be a simple PHP file setting up the environment you need, or it can be set up as a PHP Class, where you can compartmentalize code, and set up a reusable Bootstrap class. A sample Bootstrap class can be found here.
Following any of the many tutorials out there, I was able to get a simple controller/view running. However I needed to make use of many models. I set up my initial database and a model to access the first table. There was a slight flaw with my approach though - the models directory needs to be included. I chose to include this directory in the index.php file where we are already setting up some include directories:
set_include_path( $root . '/../application' . PATH_SEPARATOR . $root . '/../library' . PATH_SEPARATOR . $root . '/../application/models' . PATH_SEPARATOR . get_include_path() );
Once this is in place, my code works as expected. No more "require_once" commands to get each of my models.
Next challenge, talking to an Active Directory server. Turns out the Zend_Ldap class is only set up to handle the Zend_Auth authentication mechanisms at this time. So if you are looking to work with and LDAP or Active Directory server, you need to fall back to regular PHP code for this - ldap_connect(), ldap_bind(), ldap_search(), etc.
I'm onto my next challenge now - setting up access control utilizing the Active Directory user and groups. There IS a Zend_Acl class that should be helpful, but it doesn't tie directly to AD groups. So I'll have some custom work here.
Overall, I think Zend Framework is going to work out just fine. But there will be more challenges to overcome yet. Par for course with any project though. I'll be posting more about Zend as my project progresses.