Website security is paramount! One authority on website security is OWASP. Their latest security vulnerability top-10 is already 2 years old and not always crystal-clear. What does the top-10 look like and how does it relate to PHP?
The issue discussed here is SQL injection. For safe handling of SQL queries to a database do not reinvent the wheel and rely on one of many PHP frameworks or database layers out there. Another matter is enforcing code discipline among the developers. Focus on the data that website users can generate!
Broken Authentication and Session Management
This vulnerability is actually a bunch of vulnerabilities. The most important one: unsafe password storage in the database. The solution is to encrypt passwords as described here. The key solution on planet PHP is bcrypt(). This is not the only defence. The best advice and an advice not mentioned by OWASP is simply not allowing users to choose a password in the first place. Let the website set a strong password for them. Users unhappy? tough luck! It is for their own interest.
Another attack vector is weak password recovery. It is nice to know you can regain access to a skype account by filling in a bunch of questions and let an algorithm decide if you is really you but it is not reassuring. The secret question solution is not reassuring at all. Best option: two-factor authentication. Example: conditionally resending a password via text messaging. Only the websites that matter will be able to afford the SMS subscription required but that is applied Darwinism.
The third attack vector mentioned by OWASP in this section it not worth mentioning: exposing a session ID in the url? What websites out there still rely on this method? I think I have once seen a Dodo but I have never come across a page like ?page=10&sessionid=0707 in a webbrowser. For the PHP crowd a thing to remember is a specific setting called
session.use_only_cookies. Problem solved.
Cross-Site Scripting (XSS)
The cross-site scripting page is particularly vague. As with SQL injection, rely on a framework and filter all user input data e.g. any data that is submitted with an online form. Also escape all output. The function htmlentities() is recommended over htmlspecialchars(). Note that in Zend Framework 2 the output filtering method escapeHtml() relies on htmlspecialchars() for some reason.
Insecure Direct Object References
What is this supposed to mean? The object reference here is a GET or POST variable for example a user ID that is used in the response of a request to collect and display data from the database. Example: hostname/profile/user/21. If you happen to be user 20 then an attempt with hostname/profile/user/22 should not produce any results because /profile authorises you as user 21. Better still the user ID is stored in a session and never exposed in a url or as a POST variable.
In the context of PHP measures are:
* ini_set(“display_errors”, 0); for the production environment to not display any errors
* Hide PHP by setting expose_php off in php.ini (link)
Not specifically mentioned but described by OWASP here are the risks of unrestricted file uploads.
* Set php_flag engine off in .htacess file to disallow php script execution in an upload folder
Sensitive Data Exposure
This is again about data management. Obviously credit card data are vulnerable. Problem is that any data is worth protection not just credit card information. Any user data stored on a server (even the home address) is an asset for identity theft. Only recourse then is encryption of all user data. Often overlooked is information exposed via access logs.
Missing Function Level Access Control
A lot of overlap here with the insecure direct object references mentioned earlier. Some OWASP advice worth repeating: not showing a button in a view does not mean the request can not be made directly in the browser.
Cross-Site Request Forgery
CSRF also made it to the OWASP list but should it? The main defence against CSRF attacks are CSRF tokens. All frameworks should provide them.
Using Components with Known Vulnerabilities
Most damaging in this context are things like WordPress plugins. Any WordPress site uses at least 10 of them and upgrading one to a newer safer version is not as straightforward as the specialists promise.
Invalidated Redirects and Forwards
Forget about this one, it describes a very specific vulnerability. Simply do not redirect users based on a url from a GET variable.