Saturday, December 11. 2004
This week, two of my articles has been published. It started with issue 1.05 of the German "Java Magazin" for which I did a short introduction of to XUL. XUL is an XML language to model user interfaces for Mozilla, I did a PEAR class that allows you to create XUL applications with PHP.
Today I received the latest issue of the International PHP Magazine, which includes my article on XML_Serializer, I package I maintain in PEAR that is able to serialize almost any PHP structure to an XML document and vice versa.
Thursday, December 9. 2004
As I have finally had the time to look into the "cannot redeclare xmlrpc_decode()" bug, a new patSpiderizer release (v2.0.9) is now available from our site. This is just a bugfix release, but that one bug was very annoying, and only happened on PHP installations that had the xmlrpc extension included - the function names of our xmlrpc connectivity class simply were the same as those of the extension...
This is probably the last version for the v2 branch (except for bugfixes), as I have started writing up notes for the new v3. This new version will be rewritten from scratch, and synthesize the experience gained with patSpiderizer and its bigger brother XENA PolePosition (German) that I developed for my former employer, Metrix Internet Design GmbH, in one tool. The global concept will bring some fresh wind to the 'cloaking' scene, I think, as it will be the first NOT to cloak
Wednesday, December 8. 2004
I just released a new version of Services_Ebay, which fixes a small bug in the Item Model, allows you to change the language of the error messages and allows you to specify international shipping options for your items.
But the most important change is, that Adam Trachtenberg now has CVS karma to commit to the CVS repository. He already commited his first patch, hope there will be some more in the near future, when he started working with the package. So welcome aboard, Adam!
Tuesday, December 7. 2004
I just proposed a new package for inclusion in PEAR: HTTP_Cache. This package helps you creating ConditionalGet requests in your pages. This helps you keep the traffic low on your sites as it only sends the request body with the first request and a 304 (Not Modifed) header on subsequent requests. This is especially useful, if a page that is requested quite often is not changed a lot, but still is generated by PHP, so the browser will not cache it by default.
If you would like to implement this in your site, HTTP_Cache does all the work for you and even is able to work with output buffering. If using this feature, you only need to add two lines of code to the scripts you want to cache:
<?php
require_once 'HTTP/Cache.php';
$cache = &new HTTP_Cache(array('auto' => true));
echo "You now may send any data to the browser";
?>
HTTP_Cache will generate a unique id for the current browser and send the following headers:
Cache-Control: must-revalidate
Etag: e33b111743ff17c7829cd6bdad6815cb
On the next request the client will resend the ETag back to the server and HTTP_Cache will compare the client's ETag with the one that will be generated on the server. If both tags match, the data will not be send to the client, but a 304 header will be issued:
HTTP/1.x 304 Not Modified
The only drawback is that HTTP_Cache will need to create an MD5-sum of the content, which could slow your application down in some cases. But using the cache will speed up your site as your webserver does not have to send as much data as without the HTTP_Cache.
Furthermore you may supply the unique id so HTTP_Cache does not need to create use the md5() function. This is especially helpful, when you are already using a serverside cache system and already generated a unique cache key for the current page. In this case you may also check whether the browsercache is valid so you do not need to load the cache file from disk:
<?php
require_once 'HTTP/Cache.php';
$cache = &new HTTP_Cache();
// create an etag
$etag = 'hfhfhjfjddhfhjdshdddkjd33';
$cache->setEtag($etag);
// The browser cache is not valid
if (!$cache->isValid()) {
// create your content
$html = 'Do some expensive HTM creation....';
// pass it to the cache
$cache->setBody($html);
}
// send header or data
$result = $cache->send();
?>
If you are interested in this package, take a look at the package proposal or download the first version from out site.
Monday, December 6. 2004
While shopping for christmas presents on Saturday, I found Christian's and Tobias' new book PHP5 Kompendium standing on the shelves and until then I hadn't realized, that this already had been published. The German book deals with all you need to know about PHP5 and is the perfect christmas present for everybody who either wants to learn PHP from scratch or is looking for some advanced techniques.
While skipping through Christian's blog, I discovered that the book had been released nearly two weeks ago, I guess it's time that Christian's blog is included in Planet PHP.
Congratulations to Christian and Tobi.
I have added the patTemplate driver to the new Describer class included with patBBCode: this driver uses a patTemplate template file or loaded templates to generate the tag guide, leaving nearly total control in layout. The effect can best be seen by comparing the very simple HTML Driver output with the new patTemplate driver output.
In addition to making it possible to let patBBCode render its tag guide automatically directly in your site's design, the patTemplate driver has a series of options you can set, namely:
- injectContent: whether to inject the content into the loaded templates directly, or return the rendered list as a string. This is very useful if you want to inject the content directly in place into an existing template your application has already loaded.
- sortBy: sorting of the tags list. Possible values are 'tagName' to order by tag names alphabetically, 'attributes' to sort by tags with or without attributes, or set to 'null' to disable completely.
- sortDir: sorting direction. asc|desc
- containerTemplate: sets the name of the template containing the whole tags list
- entryTemplate: the name of the template for each tag
- attributesTemplate: the name of the template with the attributes list
- variablePrefix: a prefix prepended to all variables in the templates - use if some of the standard variable names collide with existing ones in your application
These changes are currently only available in CVS, so you can view the changes in our WebCVS or download the latest CVS snapshot.
Wednesday, December 1. 2004
In the latest issue of the PHP Barnstormer Aaron wrote a nice summary of Greg's tutorial on how to use those strange phpt-files and how to write your own tests. This currently is the best source of information on phpt files you can get (at least I could not find better information).
Together with the new PEAR_RunTest class, that Greg wrote, it will finally be a lot easier using these standard tests for your PEAR packages.
This reminded me, that a lot of my PEAR packages still are in need of some good unit tests, guess I'll give phpt a try.
Tuesday, November 30. 2004
I finally managed to release the stable version of my templating engine. It has been completely recoded for this release, as well as redesigned. Here's just a short list of the feature: - based on XML tags
- Very flexible architecture
- interchangable readers: read from files, string, other template formats
- input filters
- output filters
- variable modifiers
- easily extendible (bind PHP objects to tags)
- accepts strings, arrays and objects
- features conditions for special templates (odd, even, first or last repetition)
If you'd like to see a full list of features, you might want to take a look at the online examples or browse our blog.
If you're still not convinced to use patTemplate, maybe you should know, that the content management system Mambo started adopting patTemplate for their next major version.
To download the package, have a look at our site, or to be on the bleeding edge and give yourself some shivers, there's also the CVS snapshots.
I just released a new version of my PEAR package Services_Ebay, which is now marked as alpha as the API starts to stabilize.
This version includes some quite interesting new features: Services_Ebay now provides some kind of introspection, as you can get a list of all supported API calls using Services_Ebay::getAvailableCalls(). Furthermore it finally supports a changeable SiteId, that means it's not restricted to ebay.com anymore.
To help you debugging your application and to help me analysing the bug reports it's now also possible to capture the XML data that is sent to and recieved from the eBay webservice.
But the coolest new feature are the custom models, an idea I had in the Toby's and Lukas' powerworkshop. They used Services_Ebay in conjunction with some other PEAR packages, but wanted to store some additional information for the items in a database. To achieve this, they created a new object that stored a reference to a Services_Ebay_Model_Item object and the additional data that they wanted to store in the database. Although this worked, it did not look very nice and can get quite messy.
To achieve the same result, you may now create new model items to replace the ones provided by Services_Ebay. That means you can create classes for users, items, feedback etc. that will automatically created and filled with data by the Services_Ebay package. All you have to do is the following:
<?php;
require_once 'Services/Ebay.php';
// simple model class
// You may implement any additional methods you need
// in your custom models.
class myItem extends Services_Ebay_Model_Item
{
// Dummy method
// This does not really do anything, but you can implement whatever you like
// here...
public function StoreItem()
{
echo "Now you could store the item data in your local database...";
}
}
Services_Ebay::useModelClass('Item', 'myItem');
$session = Services_Ebay::getSession($devId, $appId, $certId);
$session->setToken($token);
$ebay = new Services_Ebay($session);
$item = $ebay->GetItem('4501296414');
$item->StoreItem();
?>
This is totally simple and allows you to add any functionality you need in your application without wrapping methods or duplicating code.
Inspired by Helgi's comment on patForms, I started a new approach to data filters in patForms.
patForms data filters are fore more powerful than input filters in other form processing tools, liek QuickForm. The possibilities of filters include: - Filters work in two directions, e.g. you can store seconds in database and let the user view and enter hours by applying a multiplier filter
- Filters can be applied before data is validated, I call these HTTP filters, as they sit between the browser and patForms
- Filters can be applied after data is validated, I call these PHP filters, as they sit between patForms and your application
Although this made filters an extremely cool feature, they are harder to use than filters in QuickForm, as each filter (indepentent of the real complexity) has to be an object and needs to be instantiated before it can be used, which led to the following code:
<?php
// create the trim filter
$filter =& patForms::createFilter( 'Trim' );
// get the element
$el =& $form->getElementByName( 'username' );
// apply the filter to the element
$el->applyFilter( $filter );
?>
Helgi complained that in most cases you'll probably just want to apply a built-in PHP function to the date that is sent from the user and that having to instantiate objects is overkill for this simple feature.
Today a nice idea popped to my mind: I created a new filter object that is able to apply any PHP function to the form data. Furthermore I created a wrapper function in the element base class which lets you instantiate and configure this object in a single method call. This reduces the necessary code while still maintaining the flexibilty we introduced by using filter objects:
<?php
// get the element
$el =& $form->getElementByName( 'username' );
// apply an HTTP filter for incoming data
$el->applySimpleFilter('strtolower');
?>
In addition to a function that filters incoming data, you may pass a second function that modifies the value before it is sent back to the browser. Of course applySimpleFilter() also accepts static methods or object methods instead of functions.
Monday, November 29. 2004
Our BBCode parser, patBBCode, ist available as v1.0.0beta. This small library is based on a SAX parser, and retrieves all tags with just one regular expression. The tag transformation is then done by filter objects, or patBBcode itself in case of 'basic' tags without attributes.
A complete documentation is available as well as a series of examples also included in the package for a quick start.
Some are already familiar with patBBCode, but with this release there are a few new things. Filter classes can now trigger their own user errors, e.g. if a vital attribute is missing. The biggest addition, however, is the Describer helper class: it enables you to describe an existing patBBCode object by retieving information about all available tags. This can be used to automatically generate a tag guide which you can retrieve in several output formats by means of a specific Driver object. The following bit of code generates an HTML table with a list of tags and their function:
// create the Describer
$descr =& patBBCode::createDescriber();
// create the driver
$driver =& $descr->createDriver( 'HTML' );
// tell the describer to use the driver
// $descr->setDriver( $driver );
// and display the documentation
echo $descr->describe( $BBCode );
You can view the result here - this is included in the examples collection of the package. For the moment, the HTML driver is very simple, but I intend to add a patTemplate driver which will give you total layout control. Another feature worth noting: the Describer respects the locale you set in the patBBCode object you describe
Friday, November 26. 2004
Today, Sebastian released the first public version of patForms. Here's what he wrote in his release announcement:
"Many were eagerly awaiting this moment, and this is it: patForms is out, It's only an alpha version, but that depends on the parts of patForms you will be using. In you don't know what our form abstraction class is or what it can do for you, have a look at the overview. Otherwise, download and test away! Just make sure you report any bugs you find via our patBugzilla."
So the next thing is to propose this package to PEAR as it would allow us a faster release cycle and provide a better infrastructure. And it would introduce this package to a broader audience.
If you haven't tried patForms yet, now's the perfect time for it.
In an entry in the Bitflux blog chregu writes, that they started integrating patForms in the Bitflux CMS.
So finally people start using this projects, which is great, as it hasn't even seen an official release yet. So if you wonder, how people can use this already, you may be interested in the latest CVS snapshot, API documentation or the examples.
I was really happy, that the guys at Bitflux like using patForms, as they developed a lot of things I really liked and chregu is one of the few people I really look up to, when it comes to XML knowledge.
The only feature they have been missing so far is multi-page support, but this is on my todo list, maybe I could work on this together with the Bitflux team.
This morning, Sebastian promised to prepare a first release and already applied for a PEAR account, as we would like to submit this project to PEAR (this has been requested by people like Toby, Lukas, Klaus, Arnaud, Carsten, Aaron, Markus and Christian). Hey, this should ensure our five votes, that we need...
So keep your eyes open for the first official patForms release, or get the latest snapshot, there are tons of (well documented) examples included, so it should not be too hard to get started with patForms. We are already using it in a lot of commercial projects, when will you start using it?
Tuesday, November 23. 2004
I just released the first public version of Services_Delicious, a PHP API for the REST based webservice of the social bookmarking site del.icio.us. If you've read my last blog entry on this topic, you already know, what it can do for you.
If you are not familiar with social bookmarking, here's an introduction for you:
Social bookmarking allows you to compile a list of categorized links that are accessible through a website by other users. This has the advantage that you can also browse the bookmarks of others and easily find interesting site. del.icio.us is a quite pouplar bookmarking site, which also offers a webservice to add new bookmarks or read your existing ones using HTTP and XML.
When using Services_Delicous you can easily manage your bookmarks using PHP: <?php
$dlc = &new Services_Delicious($username, $password);
$posts = $dlc->getRecentPosts('php', 10);
print_r($posts);
?>
Adding a new bookmark is not any harder:
<?php
$dlc = &new Services_Delicious($username, $password);
$result = $dlc->addPost('http://pear.php.net', 'PHP Extension and Application Repository', 'The home of Services_Delicious', array('php', 'pear'));
if (PEAR::isError($result)) {
die($result->getMessage());
} else {
echo "Success";
}
?>
Services_Delicious provides a lot of more methods, API documentation should show up on the PEAR website quite soon and I already started writing the end-user documentation for the PEAR manual.
Monday, November 22. 2004
Although my PEAR package Services_Ebay is still in devel state, I started writing documentation for it. So far I've finished the "Getting started" section which helps you setting up your developer account at the eBay developer program and gets you aquainted with the Auth&Auth procedures and the eBay sandbox.
These things got me stuck when I started working on the project and so I thought, I could attract more developers to the package by providing a shallow learning curve, as using Services_Ebay is a lot easier than understanding how the eBay webservice works.
I just committed the documentation the the PEAR website, but the manual is only rebuilt on Sunday, until then you may read it in my testing environment.
|