Sean's Obsessions


  • I'm a happy Linode customer. This is a Linode 540 VPS. Linode periodically increases RAM and disk while keeping costs steady, which makes them the natural choice.
  • Archives

29 Jun

Load testing a Rails app with JMeter and the authenticity_token

I have been slowly learning how to use JMeter to load test the Small Payroll application. One of the problems has been getting around the CSRF protection that Rails puts in with the authenticity_token parameter.

Each form has a hidden form element:

<div style="margin:0;padding:0;display:inline">
<input name="authenticity_token" type="hidden" 
value="16iUP1J2tdSKyvHKgYR/I/og6K7NgPPmTHCZ+idQP4k=" />
</div>

The token is also encrypted in the session so that the response to the form has to match. This value changes every time the form is loaded and can’t be set to a known value, otherwise it would be easy to defeat the CSRF protection. This means that JMeter has to figure out the token and put it into the POST.

Googling around, I found some people that said they did it, and a lot of people who couldn’t get it to work, but no solid walkthroughs.

Here’s my solution:

There are three elements. The first is the HTTP request sampler that gets the login page. Under that is a regular expression extractor post processor that gets the authenticity token. The extractor uses a simple regexp to pull out the value parameter and saves it to the LOGIN_AUTH_TOKEN variable. The login is then done by making reference to the variable – ${LOGIN_AUTH_TOKEN}. Make sure you have the Encode? button checked, as the authenticity_token is not always base-64 friendly!

The final step, not pictured, is that you have an HTTP Cookie Manager in your thread group to take care of cookies. You probably already have one, though.

Sean

15 Responses to “Load testing a Rails app with JMeter and the authenticity_token”

  1. 1
    Phil Rosenstein Says:

    Works great! Thanks.

  2. 2
    Prodis a.k.a. Fernando Hamasaki de Amorim Says:

    It has worked for me to.
    Thank you.

  3. 3
    Aynat Says:

    It worked for me after I changed the regular expression to:

    <input\s+name=”authenticity_token”\s+type=”hidden”\s+value=”(.*?)”\s*\/>

    (\s+ instead of empty spaces)

  4. 4
    Elmatou Says:

    Logging works great for me, but the session is immediately reseted.
    I have set a cookie and a cache manager. (Rails 2.3.11 & Devise 1.0.9)
    If anybody have an idea ?!

  5. 5
    Priyanka Says:

    Great!!! This Post helped me a lot and saved my time.

  6. 6
    How to load test Ruby on Rails Applications with JMeter « Life Is Rails Says:

    [...] This article provides a detailed explanation how to do it. I only used s+ instead of empty spaces to make it work. [...]

  7. 7
    Abhijeet Says:

    Does not worked for me :(

    Is there anything we need to try?

  8. 8
    sean Says:

    Hello Abhijeet,

    Some people here have mentioned changes to the regular expression that might help. Also look at your Rails logs, is anything getting sent at all?

    This technique should work on any application but since it uses regexps to parse the HTML it can be brittle and might need tweaking in some environments.

  9. 9
    Fiona Says:

    Thank you for sharing this!

    The change to the regular expression suggested by Aynat worked for me.

  10. 10
    ALF Says:

    These instructions were extremely helpful and they got me past the rails login page, but other form posts are failing because of the authenticity_token. I am including the token from the page that contains the form in the same fashion as illustrated above for the rails login. I can clearly see the correct authenticity_token being extracted and posted in the form, but when I tail the logs it is failing because it cannot validate the token. I then end up back on the home page of the site with my user still logged in. Any ideas?

  11. 11
    Wai Says:

    Hi,

    I used the same regular expression to get the authenticity token.

    I have noticed a strange quirk with Jmeter, as sometimes my script will not run correctly. and It looks like everytime the authenticity token contains a “+” sign in it, Jmeter will substitute it this with a space.

    So for example the authenticity token is:
    htJ+IyYu5MCL+mUSfBTjyVK8vOQFsUn+TbWkGosqEE8=

    Then when I check what my script posted, I see this:
    htJ IyYu5MCL mUSfBTjyVK8vOQFsUn TbWkGosqEE8

    The strange thing is I’ve used the Regular Expression tester in Jmeter to check my RegEx and that returns the full value including the “+” signs.

    Slightly frustrating!

    I’m using Jmeter 2.8 btw.

  12. 12
    sean Says:

    + is also the HTML encoding of space, I’m wondering if there’s some decoding going on when you put it back out there?

  13. 13
    Wai Says:

    Thanks for the reply, that was helpful.

    I checked my settings and it looks like you need to make sure the encode? option is enabled, otherwise Jmeter doesn’t include the + character. So by enabling this for my authenticity token worked!

  14. 14
    Dzmitry Kashlach Says:

    In JMeter 2.9 they added CSS/jQuery extractor. Now it is possible to get tokens not only via XPath, but via CSS also.
    Later there will be JMeter 2.9 review in performance testing blog.

  15. 15
    Richard Zhang Says:

    Excellent Solution!It is works!
    The point is [get auth token] must be created in [log in page]!
    Thank you very much!

Leave a Reply

© 2014 Sean's Obsessions | Entries (RSS) and Comments (RSS)

Powered by Wordpress, design by Web4Sudoku, based on Pinkline byGPS Gazette