ZF2 module loading performance - php

As far as I understand, every enabled module in a ZF2 application is loaded for every request (unless one uses optimization methods such as that offered by the zf2-lazy-loading-module module). I've been keeping an eye on modules that get published on modules.zendframework.org and I've come across modules which offer extremely limited functionality, such as the AkrabatFormatUkTelephone module which purpose is to format phone numbers to UK format.
Whilst I understand development should focus on creating single purpose modules that are good at doing one thing (instead of modules which do many things but not in a very good way), I'm thinking if we start using modules which offer such limited functionality as the one mentioned, we will need to combine hundreds of modules in order to build a rich application which could be disastrous for performance. Instead I would expect this sort of functionality to be put in a class (e.g. Zend\I18n?) and loaded on demand which would be more optimized. But knowing Akrabat's reputation I'm thinking I must be missing something, hence my question:
Is the loading of modules such as the one I mentioned significantly worse for performance than loading the same functionality via PHP classes (or is it similar due to the way ZF2 has been designed)? Does anybody have any figures (i.e. is it 5%, 10%, 15% slower) about module vs class loading performance?

Don't take this comment as a final answer, as hopefully someone of the ZF2 devs will shed some more insight to it, but generally only Module.php and usually module.config.php will be actively loaded. Everything else will simply be registered and be called on demand. So as long as your Module.php and module.config.php are not TOO big in filesize, the performance shouldn't be THAT big of an issue
In the case of Akrabats example, all that's happening is, the registry of a new ViewHelper. Nothing else. The same with all other view helpers inside of Zend. Performance won't really matter a lot in these cases.
Personally the Skeleton loaded with 80ms on my Webspace and with BjyAuthorize, ZfcBase, ZfcUser and my own module, the loading time ramped up to 100ms. And this is without any sort of memory caching enabled!

Loading a module is not much more than loading any class, like Sam pointed out.
As long as you don't use anything from your module and do things right, it's just beeing registered.
Now what does "do things right" mean?
Just try to put a big nonsense loop inside your module classes bootstrap() method. You will see that this slows down every request on your application, because the bootstrap method of your module is called on every request and it should be used very carefully, only for light weight tasks. The purposes you usually use the bootstrap() method for, won't even slow down your app for a millisecond, but writing a file to the disk in this method could slow down your app for many seconds in each request.
If your app becomes really heavy, you should use the classmap_autoloader and some caching wherever you can. If you did "things right", you won't have any performance problems, just because you have many modules or many classes in your app. One could say, it's just all about algorithms.
Keep going on using best practices, like the one you mentioned. Usually these aren't the bottlenecks of your application, but your own algorithms and failures are.
edit:
When you're using modules from the community, you should always check them for performance issues. Even a module that seems to be very light could be a bottleneck for your application if it has bad algorithms. But the case that you're loading an additional module is not the point of it.

Good question. I would like to contribute a little bit to the reaction of Sam.
Module performance is not solely the loading of the module (which is, as pointed out quite fast), but also the communication of the modules in-between. So this question might boil down to: how slow/fast is the ServiceLocator and Event-driven system in comparison to traditional non-modulair systems?
I recall that ZF2 was build with performance in mind. For instance, the ServiceLocator registers factories, so that objects can be instantiated on-the-fly. So this requires only a few extra in-memory objects and instantiations, I guess this does not impact the total performance for your application much. The EventManager works in much the same way and I have not seen it being overloaded with registered events, even in large applications.
What might slow down, on the other hand, is the loading of the modules configuration. I figure that using a cache might solve this problem. I'm not sure but maybe Zend Optimizer might do this already.
So, in short, applications should scale pretty wel, provided that modules behave well, and do not over-register events or misuse the ServiceLocator.

From the MVC component's perspective there are no modules at all! There's one big configuration file - a result of merge of every module's configuration. Unless your modules don't have a onBootstrap method or don't do much, module loading is as fast as invoking new Module on every one of them, which is painless and memory inexpensive.
The configuration merge procedure, which I mentioned above, happens only in DEV mode which is enabled by default.
There are number of tricks also to speed up your ZF2 application, like:
Enable merged config cache
Use EdpSuperluminal module
Return the ViewModel objects from actions, not arrays
Explicitly set the template name on the ViewModel
Use template maps instead of template path stack alone
Route order in the config matters! Its a LIFO queue (last in-first out).
Make sure you don't load Console modules in HTTP context.
Let the Composer do the autoloading, not ZF2
... and more. There's a quite good talk by Gary Hockin on the ZF2 app performance.
Authorization modules will surely slow down your app. There are number of things going down under the hood: the identity of the user needs to be fetched (from the database?), user needs to be authenticated agains your rules. Surely you can speed things up by using memcached or such, but this requires to have some knowledge about the lifecycle of the ZF2 application, about the modules you use, etc.
Also there is Zend Framework 3 going to be released soon, some things will go faster, but don't expect much. A lot of overhead is a result of your lack of knowledge about ZF2 - no offense!

Related

Understanding the impact of autoloaded packages

I'm having difficulty understanding the impact of having packages included (for example with composer), and autoloaded. For example, I'm currently trying to build an API with Lumen and hitting a bunch of roadblocks, because of poor documentation and a small userbase. People have suggested I use Laravel instead and comment out the services/middleware/functionality I wont use. But at the same time, if the packages are being autoloaded, how much of an inpact does that make?
On the surface, I'd think autoloading everything in my vendor directory would lead to a bunch of stuff in memory that would never be used. However, I'd doubt that it works by loading everything (I assume it builds some sort of reference system so when the code is called, it can be executed).
Looking online, it seems that Laravel is only 2-3 times slower than Lumen, though it has far more packages. If I start disabling functionality, I can put that on the lower end, if not much closer. But from a lower level, what impact is loading all the packages in the framework having? How much should I let it impact my decision on what framework to use?

Migrate to Zend Framework 2 from Zend Framework 1

We have pretty big application which has about 8 modules (big modules) written using Zend framework 1 and it has been developed for more than 3 years by couple of developers. Also it has a high traffic everyday. We use Amozon s3, Sphinx, Memcache, and some other third party services as well.
Is it a good idea to migrate it to Zend framework 2 ? Because as we went through the doc briefly, it seems Zend framework 2 has been re-written completely. Therefore we think we won't be able to migrate the application easily rather than re-writing the application according to ZF 2.
Valuable ideas would be highly appreciated.
You are correct that ZF2 is a completely different animal. So different, in fact, that there's no one-size-fits-all migration plan/strategy.
However, I recently did a similar migration. It's a fairly complex line-of-business application originally written over approximately 18 months, with a bunch of varied functionality. The main drivers for the decision were the improvements in the module and event systems.
In our case, it turned into a major point release for the product, which ended up including a bunch of UI changes along with all the plumbing.
Assuming you liked ZF1, the good news is that ZF2 is much better framework (as a framework). The ModuleManager, EventManager, Di, and ServiceManager components (and the general MVC-related stuff) are really great, once you grok them. The bad news is that they're a complete departure from ZF1. So you're at the very least signing up to completely overhaul your dispatch and routing, you'll be saying goodbye to Zend_Registry (ServiceManager/ServiceLocator are a huge improvement).
The other bit of good news is that you can almost certainly keep all the old ZF1-type components around for as long as you need them. So if you're relying on Zend_Cache, Zend_Log, Zend_Mail, etc, a little bit of fiddling with autoloader configs should make that possible.
What I'm suggesting is that if you do take the plunge, consider just migrating to ZF2-as-a-framework first, and worry about ZF2-as-a-component-library later.
If you've stuck with the fat-model/skinny-controller paradigm, it's probably feasible to just replace the Controllers, Front-Controller, Zend_Application stuff in a fairly straight-forward way. Once you get that into production, you can then work on removing dependencies on ZF1 components as time permits. In my case, there wasn't much of that, as things were pretty well factored and wrapped (so, for example, moving from Zend_Cache to Zend\Cache was trivial)
Finally, you should know up-front that View-layer stuff (mostly the helper-related stuff) is different too. If you have a bunch of complicated view-related stuff (partials, custom view-helpers, etc) all over the place, you need to anticipate either rewriting them, or finding a way to use the old Zend_View stuff in ZF2 so you can migrate piecemeal. I didn't really deal with this because our interfaces were fairly simple and we took it as an opportunity to overhaul the UI.
Just my $0.02, but I hope it helps.
There is no quick and easy way to migrate because ZF2 is very different from ZF1.
Related: Step by step migration from Zend Framework 1 to 2

ZF2 Trouble using dependancy injection in Vendor library

So I have the following dilemma. I want to have a common library that all my ZF2 applications will use. This library will contain all the business logic for my website. Each application will consume different parts of the library to properly display/perform whatever actions are necessary. Now so far I've managed to create a library. Lets call it Foo. Foo has a Module.php which does the basic autoloading required to load the entire library.
Now here is where I start to have problems. I want to take advantage of dependency injection, the service manager, etc from ZF2 inside Foo. The problem is I only have the one Module.php that loads Foo. This means as my library grows so will Module.php since as far as I can tell I can't have sub modules. Is there any way around this issue?
Essentially I want every app to just include Foo and Foo to have several Module.php so that at least the dependency stuff can be handled on a module by module basis.
You're probably swimming against the current to try and do sub-modules -- and you probably don't need to.
If you've written your module nicely, loading it won't be a very expensive operation. Remember, the whole point of the service manager is that all those services are lazily created. So if the calling code never asks for a particular service in a particular request, that service's classfile is never autoloaded, the object is never instantiated, etc. So you may be fine staying with a big, monolithic, module.
The one place that things might get a little tricky is if you're leaning heavily on the EventManager, and your module is attaching a bunch listeners. But you can probably get around that by setting up some module configuration directives, and then just conditionally attach listeners.
Having said that, it probably makes sense to try to split your module up. So you could have FooBar and FooBaz modules.
If you really, really, want sub-modules, you can dig into the ModuleManager and try to figure it out. I went a little ways down that road once -- and then got distracted. In my case, I was dealing with shipping physical items. I wanted a "Fulfillment" module that could be configured to load a bunch of similar shipping modules (Fulfillment\Courier\USPSModule, Fulfillment\Courier\FedExModule, etc), so that my main Fulfillment module could iterate over all loaded submodules, without specific knowledge about any of them. If I recall correctly, the best way to do it was to essentially mirror what ZF2 does, but inside my Fulfillment\Module class. However, I can't think of many situations where you'd want to do that, unless you want a set of similar submodules that all implement the same interface, and want them to be consumed by a super-module that has no specific knowledge of them. I also looked at this because was thinking about runtime enabling/disabling of those submodules by end-users (sort of like a plugin system).
If you're not doing that, I'd say stick to FooBarModule, FooBazModule, etc, so far as it makes sense. And remember even if your module contains a ton of code, the ServiceManager will only autoload, parse, and instantiate classes that are needed to satisfy the dependencies of any given request.

PHP front controller library with support for unit testing

I am looking for a (small) library that helps me cleanly implement a front controller for my pet project and dispatches requests to single controller classes. The front controller/dispatcher and controller classes need to be fully unittestable without sending HTTP requests.
Requirements
PSR-0 compatible
installable via its own PEAR channel
support for unit testing:
checking if the correct HTTP headers are sent
catches output to allow inspection in unit tests
perferably PHPUnit helper methods to help inspecting the output (for different output types, i.e. HTML, XML, JSON)
allows setting of incoming HTTP headers, GET and POST parameters and cookies without actually doing HTTP requests
needs to be usable standalone - without the db abstraction, templating and so that the fat frameworks all provide
Background
SemanticScuttle, the application that is bound to get proper "C" support, is an existing, working application. The library needs to blend in it and needs to work with the existing structure and classes. I won't rewrite it to match a framework's specific required directory layout.
The application already has unittests, but based on HTTP requests which make them slow. Also, the current old way of having several dozens of .php files in the www directory isn't the most managable solution, which is why proper controller classes need to be introduced. All in all, there will be about 20-30 controllers.
Previous experience
In general, I was pretty happy with Zend Framework for some previous projects but it has several drawbacks:
not pear-installable, so I cannot use it as dependency in my pear-installble applications
only available as one fat download, so I manually need to extract the required bits from it - for each single ZF update.
while unit test support exists for ZF controllers, it's lacking some advanced utility functionality like assertions for json, HTTP status code and content type checks.
While these points seem to be nit-picking, they are important for me. If I have to implement them myself, I do not need to use an external libary but write my own.
What I don't want
StackOverflow has a million "what's the best PHP framework" questions (1, 2, 3, 4, 5), but I'm not looking for those but for a specific library that helps with controllers. If it's part of a modular framework, fine.
I also know the PHP framework comparison website, but it doesn't help answer my question since my requirements are not listed there.
And I know that I can build this all on my own and invent another microframework. But why? There are so many of them already, and one just has to have all that I need.
Related questions
What's your 'no framework' PHP framework?
How do you convert a page-based PHP application to MVC?
Knowing Symfony2 well, I can assure you it's definitely possible to use it just for the "C" in MVC. The models and templates are completely free and are typically executed from the Controllers anyway, so if you don't call Doctrine or Twig specifically, you can do what you want.
As for functional testing, which is really what you're talking about in your article, what you want to look at is the WebTestCase class, which is well complemented by the LiipFunctionalTestBundle bundle for more advanced cases.
That allows for some things like this example of testing a contact form that sends an email, where the entire HTTP request is done in process, since the framework is written to allow multiple requests per process and has no global state, this works very well and does not require a http server to be running or anything. As you can see I do assertions on the HTTP status code of the response too, and was able to capture the email without sending it since in test configuration sending of emails is disabled in the standard distro of Symfony2.
That being said, you could also just use the Request and Response classes from Symfony2's HttpFoundation component. It should allow you to test your code, but IMO you wouldn't get as many nice features as you could if you'd use the entire framework. Of course that's just my biased opinion ;)
I would recommend downloading the Symfony 2 framework Routing component: https://github.com/symfony/Routing
Documentation is found here: http://symfony.com/doc/current/book/routing.html
Perhaps it does not satisfy all you requirements, but it's the closest.
If you are familiar with symfony (which I think you are) you should check out silex From their website this is what they say about it:
A microframework provides the guts for building simple single-file apps. Silex aims to be:
Concise: Silex exposes an intuitive
and concise API that is fun to use.
Extensible: Silex has an extension
system based around the Pimple micro
service-container that makes it even
easier to tie in third party
libraries.
Testable: Silex uses
Symfony2's HttpKernel which abstracts
request and response. This makes it
very easy to test apps and the
framework itself. It also respects
the HTTP specification and encourages
its proper use.
I'd add Net_URL_Mapper, it doesn't have the assertions though. Is that why you ruled it out?
Another pretty interesting thing is silex. It also comes with controller tests. I'd use that over Symfony2. But that's my personal preference.
Quite a understandable wishlist. I think we all hate it in testing when we run into dependencies that make testing to havoc. Tests should be simple and short, having many things to solve before and after running each test can be a burden.
From the description of your question it looks like that you pretty specifically know what you're looking for.
My first reaction would be that you use PHPUnit for this. It does not qualify all your requirements, but it's a base you can build on. It's highly expendable and flexible, however it does not support PSR-0 but has an autoloader of it's own so probably that does not weight that hard.
From the information you give in your question I'm not sure if the design of your testsuite(s) or the design of your application are hindering in writing and performing the tests you would love to.
I smell sort of probably both. If your application code is not easily testable, then there is not much a testing framework like PHPUnit can do about. So for example, if your controllers do not use a request object with an interface, it's not so easy to inject some request that was not triggered by the HTTP request, but by your tests. As HTTP is most often the entry-point into a webapplication, it pays to abstract here for tests. There exist some suggestions apart from specific frameworks: Fig/Http. However this is just a pointer.
Similar is this with the database scenario you give: If your application code is depending on the database, then your tests will be as well. If you don't want to test against your database all the time, you need to have your controllers being able to work w/o the concrete database. This is comparable with the HTTP requests.
There exists numerous approaches to cope with these circumstances, but as I read you question you don't look uneducated, but it's more you're looking for a better solution than exisiting ones.
As with every own code, it's pretty hard to find something that matches the own design. The best suggestion I can give is to extend PHPUnit to add those suites and constraints you need to for your application while you use the support of automated tests to refactor your application to fit the needs of how you would like to test.
So you can start with the tests and then develop the controller like you need it. This will keep your controller light I assume and help you to find the solutions you need.
If you find something that is missing with PHPUnit, you can first extend it on your own and additionally the author is very helpful in adding missing features.
Keep in mind that if there does not exist what you need, you need to code it your own. However if you're able to share (part) of the work with others, you most often get a benefit than by doing everything alone. That's a point for an existing framework, be it for testing or the application.
So if as of yet there is no such controller / MVC that does support easy unit-testing out of the box that fits your needs, chime in and develop one TDD-wise. If done right it can exactly match your requirements. However I think you're not alone with this problem. So not a very concrete answer, but I can only say that I made very good experiences with PHPUnit and it's extendability. That includes output tests you're mentioning in your question.
And probably a little differentiation at the end: It's one thing to test code-units and another to test if they all work in concert in the application with it's various requests. The last most often requires larger test setups by nature. However, if you can separate units from each other and clearly define with which other units they interact, then you normally only need to test the interaction between those which can reduce the setup. This does not save you from infrastructure problems, but those are normally not tested with unit-tests anyway (albeit you can extend PHPUnit to perform other type of checks).
A popular framework - even with a bad design - has the big plus that components tend to be better tested by use. That normally helps to go over the first years of your application until design issues in a framework make you need to rewrite your whole code base (probably).
As controllers often are sort in the middle of everything, this can lead to the scenario that you tend to test the whole application while you only want to test the controller(s). So you should think about the design and role of the controllers and their place within the overall application, what you really want to test with your controllers, so you can really make them testable according to your needs. If you don't need to test the database, you don't need to test the models. So you could mock a model returning random data to take it to the extreme. But if you want to test if HTTP handling is right, then probably a unit that abstracts HTTP handling is needed at first. Each controller relying on this would not be needed to test (theoretically) as the HTTP processing has been tested already. It's a question of the level of abstraction as well. There is no overall solution, it's only that frameworks can offer something but you're then bound to those paradigms the framework expects. AFAIK testing in php is getting more and more popular but that doesn't mean that the existing frameworks have good support for it. I know from the zend framework that they are working on this to improve the situation since longer. So it's probably worth to look into the more recent developments in the more popular frameworks to what this leads to as well.
And for the very specifics, you need to test on your own always.
Opting to PHPUnit and own testcases however does look as a practically way to me. Code your controllers as you need them for your project in TDD and you should get what you need.
Probably the more component based approach of Symfony 2 is better fitting your needs than what you experienced with Zend Framework. However, I can not suggest you anything specific as needs highly differ within application design. What's a quick and solid solution for one application is a burden for the other. See Page Controller.
You could take a look at the http://ezcomponents.org/ witch is becoming apache zeta
There are three ways how to make eZ components available for your PHP environment, please read the whole of this article before continuing with the practical part:
Use PEAR Installer for convenient installation via command line
Download eZ components packaged in an archive
Get the latest sources from SVN
I haven't got my hands into it yet but looks like a good solution...
Seldaek: WebTestCase isn't quite the right thing - it's for testing a view directly, and a controller or model only indirectly.
A unit test case for a controller would invoke the controller, likely giving it a mock object for the templating engine (e.g. a mock Smarty object), then check the values that were assigned to that object for display: for example, if you invoked the controller for /countries/south-sudan, you could check that the template variable $continent was set to "Africa". This kind of unit testing wouldn't actually involve any template rendering in most cases.

Cross-module Communication

Quite simply, it of course makes good sense to group parts of an application into appropriate modules.
Commonly, keeping these modules decoupled is not an issue, however it often arrises that data from the a user management module is required by other components.
It is substantially less than ideal by normal principles that these client modules would have knowledge of the user module's internal classes etc, which brings me to the question of how this cross-module communication is best architected.
My thoughts thus far are that a module could have a conventionally-named API class via which other modules could 'query' the module. This approach will still lead to a certain dependency, but at least only on the other module/its API.
Your thoughts on this would be greatly welcomed.
Thanks in advance,
James
You could call the user module a "library". This terminology change can help clarify which modules are supposed to be top-level, and which ones manage lower-level activities that are intended to be used by multiple other modules. The CodeIgniter PHP framework uses this approach.
Well, "module" is extremely vague - exactly what defines a module can vary greatly from system to system.
I'm actually confused by exactly what type of scenario you're trying to avoid. It's not uncommon at all for two classes or groups of classes to communicate with eachother. That's why we have stuff like interfaces in the first place.
I guess in your scenario you could have a controller-like class (as in the C from MVC) in between your modules that would know the guts of each and could serve as a communication bridge.
You might want to read up on "dependency injection". Symfony Components offers a solution for Dependency Injection and has lots of good reading/examples on the subject.

Categories