Test the load that your Magento website can handle
Sizing your Magento can be tricky sometimes, and depending on the seasonality of your business, your shop might be experience idle period and sudden peaks of visit. Stress testing your Magento website becomes a MUST to have a proactive understanding of your site limits. This is mostly valid for sites which do not have auto scaling set up, however even when you have auto scaling you need to understand if the metrics you set up for scaling are correct and if your scaling is fast enough to handle sudden spikes of activity.
To do that, we will look at a open source tool provided by Apache: jMeter. We will go through 2 use cases: an easy one where your site already have an history of activity through access log, and a second case where we have a cold start, ie we don’t have logs we can use to simulate load and will have to generate our own.
I strongly suggest to install it on a separate instance than your servers. If you want to simulate high volume, I would suggest running it from an instance in the same network as your application. But you can also run it on an instance outside of your network if let’s say you also want to test your load balancer or other components. You can even install it on your laptop. The limitation here is that you will have only one network pipe between your laptop or instance, and your application server, so the faster this pipe is, the better you can simulate high load.
You can download it here (only 67Mb): https://jmeter.apache.org/download_jmeter.cgi
Take the binary package that is the easiest to use.
You need Java 8+ (JRE) installed on that instance/laptop before!
Unpack then simply run /bin/jmeter (or jmeter.bat depending on your environment)to verify the installation worked as intended.
Use Case 1: your shop is already in production since a while
Preparing the data:
Well, lucky you, there is a free set of data you can use to perfectly simulate the activity that you are expecting, your access logs! Wether it is Apache or Nginx, you will find them in /var/log/nginx or /var/log/apache2.
You can use the access log sampler out of the box feature of jMeter. If you want to do so please skip this charter but be aware that it is not always working perfectly when parsing logs. I like to simplify my logs and manipulate them. The output of the below process can be useful to more activities than just load testing.
Copy the latest access log that you have, or if you need more data you can copy the file ending on .log.1 or the logrotate archives (you’ll need to unpack them) looking like access.log.2.gz.
If you want to count the lines that a file have you can use:
less access.log | wc -l
Let’s say we want to simulate 200.000 calls to our website, but we only have 50.000 lines in our log file, we can augment the content of the log file by duplicating it. In this case we need to do it twice to get 200k. Let’s use the following command that append the content of a file to the end of a file:
cat access.log | tee -a access.log
The access logs contain a lot of metadata that we will not use (such as response code, browser, etc…). So we need to retain only the http call from each line. Let’s use the following command to do that:
sed -r “s/.*(GET|POST|HEAD|PROPFIND) (.*?) HTTP.*/\2/” access.log > test.log
It is outputing all the request paths and their parameter string if any to a test.log file.
Another useful command below let you append your website at the begining of each lines:
sed -i -e 's_.*_https://mywebsite.com&_' test.log
Done! We now have log file ready to be used by jMeter and simulate load.
We will do this using the GUI, but the same is achievable by command line if you put some efforts into it.
We need to set up a thread group. Right click on your test plan name on the left panel and select add->thread group
This element will determine how many concurrent virtual users will be used in the test plan, how many times you want to loop through the test and how long time do you want jMeter to take to ramp up to full capacity test. It basically simulates your users.
Let’s put 4 threads to start with, ramp up of 20s and one iteration.
Now we need to feed the thread group with the http requests we got in our access log. To do that right click on the thread group in the left panel and select add->Sampler->Access Log Sample
Enter the protocol, base url or hostname in the Server section, and port if needed.
For plugin class the TCLogParser is fine, you can additionally select a filter for better parsing depending on your file format. In our case there is no need.
And finally there select your access log file in the Log File section.
If you need to configure specific headers for your requests, if for example you test load an API, you can do so by adding a HTTP Header Manager to your thread group and enter the headers you need. There are plenty of options in jMeter, like authentication manager, etc… we’ll only cover the basics here but jMeter is a very flexible tool that can adapt to most of your testing scenarios.
Another good feature of jMeter to use is the cookie manager. You can for example enter your session ID cookie in it and test authentication based requests. Plenty of options.
Now there is only one thing left to do, setting up a listener to monitor the calls results. Right click your thread group and select Add -> Listener -> View Results Tree .
This component will allow you to have a detailed look at every call executed, the result, request and response. Be cautious here! If you test a limited dataset of logs with a few threads, no problem, but if you test hundreds of thousands of lines with tens of threads, this log will very quickly be enormous and your machine will struggle. In these cases you need to either log to file, or use an aggregate listener such as the Aggregate Graph. You will see that jMeter has a lot of listeners you can choose from.
You should end up with something like that:
Use case 2: you need to test a new instance
Your magento instance is new and you don’t have any relevant access logs history. Magento has a solution for you, the performance toolkit.
It allows you to generate testing content in your webshop (users, products, etc….) and provides you with a jMeter jmx testing template.
Let’s not reinvent the wheel, there is a very nice tutorial in Magento documentation that explains you in detail how to generate the mockup data and customize it to replicate what you expect your shop to have:
Generate data for performance testing
This is a beta release of documentation for Magento 2.4, published for previewing soon-to-be-released functionality…
Once your instance has the required data generated, have a look at the performance toolkit github page to get the .jmx template and run your jMeter properly:
All Submissions you make to Magento Inc. ("Magento") through GitHub are subject to the following terms and conditions…
Since you have generated a lot of mockup data, you’ll need to clean it up. I strongly advise you to do that perf testing on a test instance and use a clean install for your prod. Even after cleaning you bear the risk of having residual test data that will pollute your instance.
Whether you use the performance toolkit or your access log, jMeter can help you in generating calls to your website and monitor how well it responds. Though the goal of this article is to introduce you to jMeter, which is a very customizable tool, if you dig deeper you might be able to create very realistic testing scenarios.
Need help with your Magento installation, performances or strategy, I am also providing consulting and implementation services. Contact me by email firstname.lastname@example.org