Not so long ago, on Habré, a
post about the emergence of a new PHP framework called Yii jumped.
After acquaintance, this framework seemed interesting, promising and worthy of attention.
Recently, Daniel Carrera posted on his blog an interesting article
“Comparison of PHP frameworks” about comparing CakePHP, CodeIgniter and Yii.
In order to popularize Yii among the Russian-speaking (and poorly in English-reading) population, I decided to make a translation.
Caution: there are really a lot of letters.
-
Content
- Simplicity
- Documentation
- Performance
- Flexibility
- Security
- Other notes
- Results
-
Simplicity
It is difficult to judge the simplicity of the framework before creating the application, but I can give a few comments based on the documentation:
')
Cakephp
Installation: I have problems with Apache that have not been documented. I had to edit three .htaccess files to add the “RewriteBase” commands.
Usage: Helpers, Actions, Behaviors, Layouts, Components ... Do I really need to know about all this to write my program? Looks like Cake
the highest threshold of entry and for the current moment I do not see any special features in it that the other frameworks would not provide.
All frameworks come with default styling and CSS. In order to test, I had to get rid of it so that each framework did only what was required. In the case of CakePHP, it turned out to be very difficult to find out which design files were used. It was an illogical place (inside my application directory).
Codeigniter
Installation: Trivial. Just unzip the files and everything is ready for work.
Use: CodeIgniter seems simple enough. Documentation does not give reason to doubt this. My hello-world app was ready much faster than using Cake. In general, the threshold of entry for CI is lower.
All frameworks come with default styling and CSS. In order to test, I had to get rid of it so that each framework did only what was required. In the case of CI, this happened automatically when I created a new view. CI does not insert a design unless it is asked for.
Yii
Installation: Easy. You must run yiic to create a root web directory. There is also a PHP version (yiic.php), which is good if you do not have ssh access. Yiic is well documented.
Usage: Yii also seems simple and understandable, perhaps a little less than CodeIgniter. My “hello-world” was created almost as quickly as in the case of CI.
All frameworks come with default styling and CSS. In order to test, I had to get rid of it so that each framework did only what was required. With Yii it was very simple. The design file is in a logical place and it is well documented.
I am happy to announce that none of the frameworks require learning a templating language, such as Smarty. PHP itself is a great template engine. I have used Smarty for several years and, to be honest, I think that there are more problems from him than good. Note that Yii and CodeIgniter come with
optional template engine, especially for those who like it. But, as I said, this is optional.
Result: CodeIgniter seems to be the easiest, followed closely by Yii.
I will postpone the final verdict until I write the application prototypes in the second part of the test.
-
Documentation
Please be critical. Documentation usually starts to look a little different when you are actually writing an application. If it is inaccurate or incomplete, you will not know about it until the start of work. Until now, the only application I wrote for testing frameworks is “hello world”.
Cakephp
My first impression was positive. Documentation looks complete and easy to read. The tutorials were hard enough to detect (they ended up in the “Example Applications” section). When I wrote my “hello world”, I ran into a problem (404 error) and it was not described in the documentation. I had to edit the .htacces files to solve this. I would like to see the “Troubleshooting” section in the documentation. In addition, it was very hard for me to figure out how to get rid of lotions (header, footer, styles) that are present in Cake by default.
Codeigniter
The first impression was again positive. I note that writing “hello world” took me a lot less time than in the case of Cake. I think the reason is that the CI is simpler, but I also believe that the documentation affected it.
Yii
And again my first impression was positive, I wrote “hello world” very quickly. After that, I got rid of the extra lotions that Yii connects to make the page pretty. Find how to do it was very easy and fast.
Result: At the moment it is difficult to judge.
It seems that all the frameworks have good documentation. I had a couple of problems with Cake, but so far I can not say anything firmly.
-
Performance
In this part, I want to discuss two performance tests. One held by me, the other - by the team Yii. I believe that both are worthy of attention.
Key similarities:
Both tests try to estimate the minimum overhead of each framework. The goal of the framework is to output “Hello World” and nothing else.
The main differences are:
I used the default configuration of each framework. The Yii team tried to optimize each framework to display “Hello World” as quickly as possible.
The test from Yii performs only die (). Mine uses MVC: the controller sets the value of the variable to “Hello World”, then it is passed to the view for output on the main HTML page.
Yii used a dedicated server for tests, and I - shared hosting, where I am going to host my real application.
So the Yii team tests are more technically honest, but mine better reflect behavior in the real world.
As always, all tests should be taken critically.
Results are expressed in requests per second (Requests Per Second, RPS), so higher values ​​are better.
Test details:
This page on the Yii website describes their test. In my test, each framework contained the following code in the view:
Where the
$ message variable is provided by the controller, and its value is “Hello World”. The number of requests per second was found using the ApacheBench utility with the following parameters: "ab-t 30 -c 10 URL". My test environment is shared hosting with the following parameters:
* CentOS 4 Enterprise Linux.
* Apache 2
* PHP 5.2.6
* CPU: Quad-Core AMD Opteron (tm) Processor 2350
* Memory: 8GB
Conclusions: Yii and CI both stood out in terms of speed. Perhaps Yii has some advantage, but it is hard to say for sure.
-
Flexibility
Cakephp
CakePHP is very tied to agreements. He expects from you a certain naming of files, classes, databases, methods, etc. I can not yet say whether this will be a problem for me, but this can happen.
CodeIgniter and Yii
CodeIgniter and Yii both look quite flexible. Looking at the documentation, it would be problematic to say that one is definitely more flexible than the other.
Both use the MVC pattern, but do not seem very strict in this regard. CakePHP is much more dependent on conventions than Yii and CI.
Some examples of similarities and differences:
* Each of the frameworks expects you to follow controller naming conventions.
* CakePHP requires the creation of models, databases and tables, even if they are not used in your program.
* Cake calls the view itself automatically, based on the controller name. In CI and Yii, you invoke the view explicitly, so in Cake, agreements more prevail over configuration. In turn, in CI and Yii, you can invoke several views.
Here is a sample code:
As you can see, the versions for CI and Yii do not seem more complicated than for CakePHP, besides they have an additional feature - you can load more than one view file. For example, you can load a special header, insert a widget, etc.
Result: CodeIgniter and Yii both look more flexible. At the moment I can not determine which one is more flexible.
-
Security
Security is a complex topic, as there are a large number of different types of attacks. This paragraph is quite voluminous, but I will try to stick to the topic. The paragraph is divided into parts according to the capabilities of frameworks and types of attacks.
Access control
Preliminary information here -
Authentication and
Authorization .
Cakephp
I found that the CakePHP access control system is difficult to understand. A code generator (“cake bake”) is
used to generate schema files and
access control lists (ACLs) —this process looks intricate. Some terms (ACOs, AROs, Requester) finished me off completely.
I expected access control to be difficult, but in Cake it turned out to be much more complicated than I thought. It looks quite powerful, but hard to use. I felt that I did not control the process and did not understand what was going on. And security is exactly what I would like to have control over and that I would like to understand well.
Quick test : I did not notice an obvious way to increase the
strength of passwords . The tutorial says that if you will hash passwords yourself, the application will not work.
Codeigniter
As far as I can tell, CI does not provide access control tools. Access control can be quite a challenge (groups, roles, etc.) and it would be nice if the framework helped with this.
Yii
I understood
the access control system in Yii much faster. I would not say that it is simple, but this is because access control itself is not easy. I would say that in Yii, the access control system is as simple as possible - but no more. After I read the documentation, it seemed to me that I understood the process and that I was able to change it to fit my needs.
Quick test : I could immediately find how to increase the
strength of passwords .
Some Yii chips I like
*
Flexibility: you may have access rules based on user IP address or request type (GET vs POST), or rules for anonymous and authorized users.
*
Return URL: You follow the link, but the session is already outdated. You are redirected to the login page. You login, and the system automatically brings you back to the page you were trying to access. As for me, it is very convenient.
Role Based Access Control : RBAC is more flexible and powerful than traditional
ACLs . With the Yii framework, you can write your application, not paying attention to RBAC, and use it only in cases where you need to solve a specific problem. So, the system is as flexible as it should be, but your access rules are no more complicated than what is required.
Dictionary Attacks
A dictionary attack consists of trying to guess a password using a list of the most commonly used words - a dictionary. In the case of web applications, such an attack can be very effective. A recent
Twitter attack was a dictionary attack.
There are many methods of interrupting a dictionary attack: account lockout after X unsuccessful authorization attempts, time delays, CAPTCHAs. Each of them has its advantages and disadvantages. Blocking accounts is easy and effective, but it provides an opportunity for
denial of service attacks : someone can make many authorization attempts, but not to gain access, but to cause other users to block. Here is one of the methods that I like: after 5 unsuccessful attempts, you should solve the captcha to get additional attempts. This allows you to control dictionary attacks, DoS and user convenience.
None of the frameworks has any tools related to the problems of dictionary attacks or denial of service, but I did not expect this. The real question is,
can you set up an authorization method in this framework exactly the way you need it ? This is a matter of control and flexibility. In CI and Yii, I'm sure I can do it. However, I'm not so sure about this in the case of CakePHP.
Cross-site scripting attacks (XSS )
XSS leads the buffer overflow in the ranking of the most common security problems. It works like this: Someone publishes a comment on your blog and this message includes malicious JavaScript code. When you view a blog, the code is executed. Since the code is taken from your domain, it is considered a “safe” browser. This code can read your cookies, or change the content of the page (for example, “The session has expired. Please enter your password.”).
CodeIgniter and Yii come with HTML filters that can remove JavaScript code from user input. Unfortunately, CakePHP does not have such filters.
Implementing SQL code ( SQL injection attacks )
The introduction of SQL-code is one of the most frequent attacks and gaps in the security of web applications (comics). This happens when the text entered by the user is interpreted as executable SQL code. For example:
Suppose a user has entered the password
foo 'OR 1 =' 1 . Then the request will be:
Since 1 = '1' is always true, the query will return a list of all users. The most frequent (and incorrect) solution is screening strings using
addslashes () or
mysql_real_escape_string () functions:
What is wrong with this decision?
* It is error prone since you must remember to do this for each parameter.
* It also depends on the fact that someone can find all possible characters that can be used for hacking. Good guys find all the holes, bad enough to find one. This is a game for losers.
Chris Shiflett shows how to embed SQL bypassing addslashes using a Chinese character. How can we know that there is no Tamil symbol that will allow to bypass
mysql_real_escape_string ?
Correct decision: prepared expressions (prepared statements)
The correct solution would be to solve the problem as a whole by compiling the SQL query separately from the user input, ie, use the prepared expressions (in other words, parameterized queries). The prepared expressions separate the logic of the SQL query from the user data (see
here and
here ).
Does the framework support prepared expressions?
Unfortunately, only one of the three frameworks - Yii -
provides such an opportunity . I think the lack of prepared expressions is the most serious problem of CakePHP and CodeIgniter.
Cross-site request forgery attacks, CSRF
Cross-site request forgery (CSRF) is used in a sense in addition to cross-site scripting (XSS) attacks. XSS abuses client trust server, CSRF - server trust client. Imagine that Bob visits a malicious site with the following image tag:
If Bob is currently logged in to his bank page, the bank’s server will receive a request from Bob to transfer $ 10,000 to Eve’s account.
So what can be done to protect against CSRF? In addition to reducing the life span of cookies, the main solution is to use the secret value to authenticate any GET and POST parameters that can change data on the server.
CakePHP and CodeIgniter do not seem to have the means to fight CSRF. Yii offers protection against CSRF for POST requests by using secret tokens (you must enable this feature). To fully protect against CSRF, you must be sure that GET requests cannot change data on the server.
Cookie hijacking attacks
Cookies are usually used to store sufficiently significant information, such as session IDs, usernames, password hashes. Cookie theft is when a third party gains access to your cookies. This can be done using XSS or packet sniffer.
How to protect against theft of cookies?
SSL protects you from sniffers, and you must take steps to prevent XSS attacks. You can make cookies less significant by discarding the long-term storage of relevant information in them. For example, instead of storing md5 (passwd) use hashes that expire - HMAC (date, md5 (passwd)).
As far as I know, CakePHP and CI do not have any protective mechanisms against theft of cookies. Yii has the ability to verify cookies, which uses HMAC to authenticate the data contained. The attacker will not be able to change the data of the expired cookie (for example, the expiration date) without being noticed.
Of course, all this will not help you if you make stupid mistakes - storing the password in clear text in cookies, for example.
Winner : Yii
Yii has a significant security advantage, with better access control and XSS protection, SQL injection, cross-site request forgery and cookie theft.
CakePHP and CodeIgniter are a bit disappointing in this regard. Since the CI is more flexible, it will be easier to add the required protections yourself.
-
Other notes
There are some things that I consider necessary to mention, although they do not fall under the criteria of this test.
Prototype
CakePHP uses the
Prototype library. I
dealt with the Prototype. Basically, it will pollute the global namespace and may break existing JavaScript code. Thus, Prototype does not behave well with your code or other libraries.
Scheduled Releases
Yii has
scheduled releases . I would like all open source projects to do this.
Input filtering
CodeIgniter has an excellent
Input class that cleans data. It destroys the GET array and all global variables except POST and COOKIE. This chip does not quite fit into my criteria, but contributes to a better code, and therefore worthy of mention. XSS- .
-
Results
— CakePHP , CI Yii. , -, , , CI Yii. , Cake CI Yii. , , Cake. , Cake , CI or Yii, .
Yii CodeIgniter . , — , . CodeIgniter , Yii . , , .
, . , , :
[1] . , .
[2] CodeIgniter XSS .
— Daniel Carrera,
«Comparison of PHP frameworks — Part I»