We hacked our client and here's what we learned from it
All online applications are at risk of being hacked, including the products we develop. But what exactly is that, "getting hacked," and what does it mean for our work? What do we and our customers actually need to consider? And how seriously should we take it? To answer questions like these, we organized an internal workshop in which we tried to hack the application of one of our customers.
The target of our hack
The approach of the workshop was to take a really practical and critical look at work that is just very typical work for us. So we chose a mobile app that we are currently developing for one of our clients. It is an app where users can register and view somewhat sensitive, personal information. Since the app is still under development and has not yet been announced to the public, unfortunately we cannot tell which client it is.
The app is developed in React Native with data being accessed via an API through a central backend. Users identify themselves with a combination of email address and password, provide some personal data, and gain insight into data processed by the client.
The backend that the app communicates with was also developed by us. The system is developed in Laravel and, as a central point, is directly connected to several other backend systems. Think ERP software, marketing systems and other external databases. The authentication layer in the API determines which data a user can access.
Potential security problems in online applications
The architecture of online applications almost always follow standard forms and therefore almost always have similarities with each other. This means that potential security problems have many similarities. For this reason, there is the OWASP top 10, a list of the most common problems surrounding online applications.
At the top of the top 10 is "Injection"; a method by which an attacker sends specific data to the server in order to perform actions that normally should not be performed. Injection would be covered but because this method is quite technical and we wanted our non-techies to participate as well, we would pay less attention to it.
In spot #2 is 'broken authentication'; a method where an attack aims to retrieve information that allows the user to impersonate someone else, or simply retrieve data that the user should not normally have access to. It's pretty close to number 5, "broken access control," a component we would definitely look at during the workshop.
Number 3 on the list is 'sensitive data exposure'; a method of retrieving data from other users, particularly personal data. Since the advent of AVG, this is something that fortunately has received a lot more attention and would get the same from us in the workshop.
The approach of the workshop
During the workshop we focused on the communication between application and backend, for us the most interesting part with the highest risk. 'Hacking' is just a rather broad term and the subject matter can be very technical. Therefore, because we wanted everyone to participate and to raise awareness about security not only among our techies, we started the workshop with a brief introduction of hacking and presented the workshop case study.
Our findings
During the workshop, attendees were divided into small teams, and each team went separately to try to figure out security problems, each using their own methods, to present at the end of the workshop. In summary, these were our findings.

Password guessing via Brute-force and Dictionary Attack
Several teams began simply trying to log in under someone else's account by trying email address and password combinations. It soon became apparent, of course, that this was impractical to do manually. The next step was to do this via a script with a number of test passwords. Again, it is impossible to try all passwords; the savvy developer grabbed a list of commonly used passwords. Within a short time, the passwords of several accounts were discovered and people were able to log in.
Such an attack can be secured just fine. First, you want to make sure that people use good passwords. You do this by checking the password at the registration screen, for example, for length and multiple characters. A great service for this is the API of Have I been Pwned that does a check on a password based on known data breaches. For the workshop, we made sure to secure some accounts with these commonly used passwords.
Second, you normally secure API endpoints with a "rate limiter. This ensures that you can make a maximum number of calls to the API endpoints, say 1 per second. This ensures that guessing passwords will take infeasibly long. This option was disabled before the test but is normally just on.
Retrieving privacy-sensitive information through a Timing Attack
The most complex and therefore the most interesting finding of the evening was a so-called Timing Attack. Originally, this attack comes from the corner of cryptography where an encryption can be circumvented by timing the trying out of different keys very precisely. This type of attack is possible if the failure of a (part of a) key is determined faster than its successful application. By measuring the time of both scenarios as an attacker can figure out the correct key much faster.
This method also applies well to online applications. Take for example the following piece of code:
function sendForgotPasswordEmail(email_address) {
user = UserService::findByEmail(email_address);
if (!user) {
return true;
}
EmailService::sendForgotPasswordEmail(email_address);
return true;
}
This is a simplified piece of code of a function that sends a password-forgotten email when a user is known to the system. The programmer of this piece of code was smart enough to provide a successful status even in case of failure (user is not known in the system), so that an attacker cannot immediately find out if a user is present in the database, which would give a data leak.
This piece of code consists of two parts: 1. checking if the user exists, and 2. sending an email to this user. However, sending an email takes time: a server must connect to an email server or enroll a process in a queue. However, if a user does not exist then this will never be performed and the process will finish faster. By precisely measuring the difference in time with a known and unknown mail address, the attacker can use this to determine whether or not a user exists in the system. This method was successfully deployed by one of the teams during the workshop.

Conclusion
Despite the relatively short time we had for this workshop, we gathered some interesting findings. They gave us more insight into the security of all our applications and the measures we need to take to improve it. It was also nice to see how even people without any experience in security came with their own insights and could actively participate in the workshop. So it is definitely something we will do more often.
Want to know more?
You can find the slides from our Hackathon presentation here: https://bit.ly/2K9Qwms. Would you like to talk through security with one of our specialists?