December 11, 2008

creole is dead

Tags: , , , , ,
Filed under: PHP,ZenMagick — DerManoMann @ 11:40 pm

Yesterday I checked the creole homepage for updates and to my horror I discovered that the project is being abandoned.

While I can understand the reasons behind this step to a degree, I still feel sad on different levels. I’ve picked creole as alternative to the current Zen Cart database code as it seemed mature and, at least to me, rather promising.

Also, the style it is coded in is very close to my ideas about how PHP code should look like. Seeing that the repository is going to exist, maybe there is still hope that someone else will pick up the project.

For ZenMagick, nothing really is going to change. I’ll be trying to convert the current 1.2 beta code into a single file as I’ve done with the 1.1.0 release (I had a go at that in some spare minutes, but there have been changes that make the current import code break, so it’ll take some time).

I am glad that I took the time to write my own (thin) database layer for ZenMagick to avoid depending on a single external project. This is proof that it was time well spend, even though the circumstances are very unfortunate.

I might evaluate another database API for the future, although this is very low priority and will be far in the future. Suggestions are, of course, welcome.

December 9, 2008

memcache stats/admin

Tags: , , , ,
Filed under: PHP,ZenMagick — DerManoMann @ 4:38 am

I’ve been playing around with implementing new ZMCache provider. xcache is nice and easy to test, in particular since it comes with a simple admin interface to dump the cache entries.

I just found something similar for memcache and it was really a big help.

Besides being able to verify that adding/removing from memcache worked, it helped figuring out how to retreive the stored items and, more importantly, the cache keys.
Since ZMCache supports grouping of entries the only way to handling this is to iterate over all entries and compare prefixes.

Initially I implemented some internal tracking. However, I wasn’t sure whether that would stay in sync over time. Iterating over entries might not be the most performant operation, but considering that this is ever going to happen from within the admin interface of ZenMagick this should be fine.

November 18, 2008

zend

Tags:
Filed under: PHP,ZenMagick — DerManoMann @ 2:16 am

I’ve finally had the time to download and install ZendOptimizer and ZendGuard.

Both seem to work fine with ZenMagick and in particular in combination with core.php help speeding things up a lot.

I haven’t got any numbers to compare, but relative to running the store without any optimisation make up for perhaps 40% performance gain.

So, this might be time well spend invetigating PHP acceleration, unless your hosting provider does that already for you.

June 18, 2008

Events and why using references is so nice

Filed under: PHP,ZenMagick — DerManoMann @ 1:58 am

I just checked in a couple changes that fire new events in case of a new account being created. The really nice things is now that event listener have a chance of modifying the account directly without having to change a single line of core code (or globals!).

For example, the following code would change the default authentication status for all new accounts:

class Blocker {
public function onZMCreateAccount($args) {
$account = $args['account'];
$account->setAuthorization(ZM_ACCOUNT_AUTHORIZATION_BLOCKED);
}
}

ZMEvents::instance()->attach(new Blocker());

I guess it couldn’t be any easier than that (other than re-defining the default authentication value ;)

June 11, 2008

compressing PHP packages

Tags: ,
Filed under: PHP,ZenMagick — DerManoMann @ 2:03 am

I have written before about how I managed to compress Creole into a single file. Now, I have extracted the more generic bits of code into a single utility class. The class has a couple callback methods to cope with custom handling. Actually, I implemented those callbacks exactly the way I needed them to implement the creole specific code, but it should the typical exceptions.

To use this, I added the first CLI script to ZenMagick. I do not expect a lot of user to require to run it, but it makes for a nice example of how to use the class.

For those interested in all the gory details, here is the source of the script:


// load ZenMagick core
$coreDir = dirname(dirname(__FILE__)) . '/core/';
require $coreDir.'ZMLoader.php';
ZMLoader::instance()->addPath($coreDir);
ZMLoader::resolve('ZMObject');
ZMLoader::resolve('ZMPhpPackagePacker');

/**
* Custom class for Creole specific dependency handling.
*/
class CreolePacker extends ZMPhpPackagePacker {
/**
* {@inheritDoc}
*/
public function isResolved($class, $level, $files) {
// Record does have circular references
return (‘Record’ == $class && 1 == $level);
}

/**
* {@inheritDoc}
*/
public function finalizeDependencies($dependencies, $files) {
// there is no explicit include/require for this
$dependencies['DebugConnection'][] = ‘Connection’;
return $dependencies;
}
}

// pack; ideally path/version should be CLI args…
$creoleVersion = ‘creole-1.1.0′;
$packer = new CreolePacker(‘c:/temp/’.$creoleVersion.’/classes/’, ‘c:/temp/’.$creoleVersion.’.packed.php’);
$packer->setDebug(false);
$packer->packFiles();

The script extends the generic package packer class to implement custom callbacks. Creole is actually a quite easy to analyze, as almost all (except for one Connection) dependencies are covered by include and require statements.

So, executing the scirpt will result in the new file creole-1.1.0.pack.php which is about 187kb large and, at least for the default drivers, makes the custom class loading in Creole obsolete.

long term I hope to be able to extract the generic MVC code out of ZenMagick and compress is using the some similar code. This will require some more work, though, as the current class does not look at extends and implements of classes. Since all code depends on the loader, rather than import/require, analyzing those will be required in order to build a proper dependency map.

Should anyone use this for their own project, then it would be great to let me know.

May 8, 2008

Compressing Creole into a single file

Tags:
Filed under: PHP,ZenMagick — DerManoMann @ 5:28 am

Right, I am just about to check in some new code that makes will make it very easy to import/prepare Creole for the ZenMagick loader architecture. The new (mostly unused) class ZMPhpCompressor also allows to squezze a full Creole release (everything under classes) into a single 188kb file.

I am actually not sure if I should include that already with the next release, as right now there are probably about 3 or four queries per request done by the new API and I might as well stick with the existing code a bit longer – we’ll see.

The code depends on two other ZenMagick classes, so it’s not very portable (if anyone is interested), but apart from that it works fine ;)

The actual code to do the magic looks like this on my XP box:

$creole = 'creole-1.1.0';
zm_creole_import('C:/TEMP/'.$creole);

$comp = new ZMPhpCompressor();
$comp->setRoot(‘C:\Program Files\Apache Group\Apache2\htdocs\zen-cart\zenmagick\core\ext/’.$creole);
$comp->setOut(‘C:\Program Files\Apache Group\Apache2\htdocs\zen-cart\zenmagick\core\ext/’.$creole.’.php’);
$comp->setTemp(‘C:\Program Files\Apache Group\Apache2\htdocs\zen-cart\tmp’);
$comp->compress();

Not sure how often I’ll be using this, but it’s nice not having to try to remember these things once they are needed again!

The only caveeat is that compressing into a single file breaks the Creole ‘dot-path notation’, so in order to use the MySQL driver you’ll need to do something like:

Creole::registerDriver('mysql', 'MySQLConnection');

to avoid errors about missing drivers. Since all database access in ZenMagick is handled by a single database provider class that’s not really an issue, though.

That means the last open issue is to write some proper release notes – oh, well, babysteps ;)

April 2, 2008

writing a database abstraction layer…

Tags: ,
Filed under: PHP,ZenMagick — DerManoMann @ 4:24 am

Writing a database abstraction layer is definitely not something I had in mind when stating ZenMagick :) On the other hand I really enjoy this sort of work – in fact much more than working on new store features.

So far I have a single interface ZMDatabase that will eventually be used to access the database. Right now there are two implementations and the implementation class is configured via a setting.

The interface is not complete yet, I’ll add stuff as a go through the code and convert database access. Currently there is only ZMManufacturers upgraded to use the new code and it works perfect.

Only worry right now is that Creole may throw Exceptions. In itself that is not a problem – is’s actually a nice change to know whether things have worked or not. However, currently none of the code is the least exception aware.  I probably should change that before going to far down that way to avoid having to redo a lot of changes.

I just fear that by starting that can of worms I’ll end up rewriting most of the current dispatch code in order to properly handle exceptions throughout the request process… Oh, well, one step at a time…

March 31, 2008

*importing* creole into ZenMagick

Tags: ,
Filed under: PHP,ZenMagick — admin @ 3:41 am

Today I spend some time massaging Creole to properly load in ZenMagick using either ZMLoader or as part of core.php.

There were a number of issues I ran into:

  1. include and require statements in Creole sources rely on the PHP include_path
  2. Some files are missing the closing ‘?>’
  3. DebugConnection.php does not include/require Connection.php, breaking the otherwise perfect dependencies
  4. Record.php includes a require for QueryDataSet.php which actually creates some sort of circular dependency loop, since QueryDataSet.php also depends on Record.php

#1 was to be expected in one form or another, so it wasn’t really an issue.
#2 is actually something I do not really understand, but then, I never had the time/energy to read the PHP specs to figure out why this is working at all. If you know, feel free to leave a comment…

#3 turned out to be a problem, because in order to be able to include all files in core.php I had to rearrange all source files based on dependency. A short script that build a simple dependency tree was easily done based on include/require statements, except for this one file (which I ended up hardcoding in the script…)

#4 was really annoying because it meant that initially I had to patch Record.php in order to get all files loaded at all using the include_path solution (which is the documented way of installing Creole!) . Eventually I changed my *import* script to load the files from a non ZenMagick folder, so no initial loading was done.

One thing that might come out of this exercise is that hopefully I will have time to split ZMCoreCompressor into a generic class and a ZenMagick specific subclass. That should allow me to easily build a single file Creole version that can then be included in ZenMagick versions instead of the full 90 odd single files (this is version 1.1). I might strip this down, though, excluding all non MySql drivers as there is currently no point loading them…

One really nice thing I discovered was that Creole follows a concept of filename-classname relationship very similar to ZenMagick. That definitely made it a lot easier!

March 26, 2008

database progress

Tags: ,
Filed under: PHP,ZenMagick — admin @ 5:14 am

As a first step of migrating to a more sophisticated database access system I have started with adding a simple layer (read: interface) that eventually will replace all $db usage. The interface will provide some simple methods to read/write the database using a lot of the ZenMagick binding code.

That should make it easy to replace the current $db based implementation with something different. The nice thing right now is that I can migrate services and other database access classes one by one without breaking anything.

Once all code is converted to using the new interface I’ll start investigating alternative implementations. I really like Creole, as it looks (intentinally) a lot like Java and the interface design is done with that in mind, so it will be easy enough to create an implementation using Creole…

March 13, 2008

CakePHP

Filed under: PHP — DerManoMann @ 10:05 pm

For a current project I joined the growing number of people using CakePHP.  Even though I didn’t use any of the bakery options if found it mostly very useful.

Of course, there is the time spend to figure out how all fits together and I pssobily haven’t even touched half of the features.

One thing that I noticed, though, is the lack of consistent documentation. I mean, there is lots out there, but usually the stuff that breaks is so specific that it really takes a while to find the answer. On the other hand the CakePHP newsgroup was more then helpful for me.

There were two big issues I had so far:

1) Upload progress bar.

Thi si snot really CakePHP specific, but it took me a while to figure out how to tell the controller to not use a layout and view. But then, I usually prefer to read sources rather than read documentation.

But before it came to all that there was the realization that PHP doesn’t really make it easy to do that at all. As of PHP5.2 there is basic support, but even then it requires to install an extension in order to be able to really doe something useful.

Further complications are that the code seems to be less reliable on Windows installations. After some late nights experimenting with the sample code of the extensions author I tried an alternative demo which finally worked.

Still, it took me a ling time to figure out why my upload form wasn’t working when the demo could do it.

Two things really stand out here:

  •  The form needs a (hidden) MAX_FILE_SIZE field.
    Interesting is that the value that works is 411353512 which I believe is the default value. It doesn’t matter if PHP is configured differently. Even though I was able to upload larger files, increasing the value broke the upload progress extension (or PHP)
  • Each file input field needs a (hidden)  UPLOAD_IDENTIFIER field with a unique value. That value is then used to track progress.
    Again some very interesing things here. First of all the identifier field has to be right before the field input, it’s no use putting them all at the begin or end.
    The secod thing which took a lot longer to realise was that in order to work an additional identifier field was required after the last field input.

2) Session handling

Once I had the progress tracking basically working I ran into the next problem. Even though everything was working fine when doing it manually, tracking progress using Ajax caused the session to expire.

More experimenting showed that parallel or overlapping requests would cause the same problem. So, hitting reload a few times would make the session invalid!

This is where the CakePHP newsgoup kicked into action. After some very speedy responses and quick testing it turned out that the setting Security.level was the culprit.

It seems that recently the code was changed so the high setting would regenerate the session id for each request! that means with parallel requests the session id gets lost!

To sum it all up: I think CakePHP is really useful and does a lot of stuff assuming (rightly so) that most web apps works pretty much the same (login, authentications, sessions, forms, htm you name it).

However, once you need something more individual it takes a while to dig out all the nitty gritty details needed to make it do exactly what you want.

« Previous PageNext Page »