In the introduction, I mentioned the neat capabilities offered by the PHP Reflection API without explaining in detail what it is. So before I move on and start writing any code samples, a more precise explanation is in order here. Basically, this API is comprised of a set of methods that allow you to analyze the inner structure of classes and interfaces very easily, thus making it possible to determine, for example, if a reflected class defines a given method or not, or if the class declares a specified property, in addition to checking whether that property is public, protected or private. A similar level of reflection can be reached with interfaces as well, but this simple example should give you a clue to all the things that can be achieved with the API. Of course, it’s possible to accomplish much more than determining the visibility of a specific class property. However, as this is a work in progress, I’m going to start covering, for the moment, the API’s basic functionality. Therefore, to begin showing you the actual power behind the PHP 5’s reflection capabilities, I’m going to define a sample interface along with a basic class, which will be progressively stripped down to their bare bones via pure reflection. Now that I have explained my plan for this article series, below you'll find the definitions of the sample interface and its implementing class. They look like this: interface Identifier { public function setId($id);
public function getId();
}
/** * A sample user class * * @param id fname lname email */ class User implements Identifier { private $id = NULL; private $fname = 'Alejandro'; private $lname = 'Gervasio'; private $email = 'alejandro@domain.com'; const HEADING = 'Using the Reflection API in PHP 5';
// constructor (not implemented) public function __construct(){}
//setter for id property public function setId($id) { if (!is_numeric($id)) { throw new Exception('ID must be a numeric value'); } $this->id = $id; }
// getter for id property public function getId() { return $this->id; }
// setter for fname property public function setFirstName($fname) { if (empty($fname) OR !is_string($fname)) { throw new Exception('First name must be a non-empty string.'); } $this->fname = $fname; }
// getter for fname property public function getFirstName() { return $this->fname; }
// setter for lname property public function setLastName($lname) { if (empty($fname) OR !is_string($fname)) { throw new Exception('Last name must be a non-empty string.'); } $this->lname = $lname; }
// getter for lname property public function getLastName() { return $this->lname; }
// setter for email property public function setEmail($email) { if (empty($email) OR !is_string($email) OR strpos($email, '@') === FALSE) { throw new Exception('Email must be a well-formatted email address.'); } $this->email = $email; }
// getter for email property public function getEmail() { return $this->email; } } As you can see above, I defined a trivial interface called “Identifier” along with an implementing “User” class. The interface is so simple that it doesn’t bear any further discussion, so I suggest that you pay attention to the class. It implements not only the unique method declared by the interface, but a few additional ones, which allow you to set and retrieve the values assigned to its $fname, $lname and $email properties. Logically, in this case the class does nothing particularly useful; it behaves like a simple data container. However, the purpose of coding a class like this is to use it for demonstrating how to dissect its structure via the reflection API. So far, so good. Now that there’s a basic class and an interface available for immediate testing, the next thing we must do is start coding some examples that show how to put the API to work. The first of these examples will be coded in the section to come. So click on the link below and keep reading.
blog comments powered by Disqus |
|
|
|
|
|
|
|