I made a Jmeter script like one thread in it login then my transaction and logout. I have put login n only once controller and transaction in loop controller. But when I execute concurrent thread some threads are failing as csrf token is not matching sequentially. I extract csrf token using regular expression. For 1-2 users it is working fine but more threads it is failing.
Try adding some debug logging to your test, i.e.
Save CSRF Token value into .jtl results file using Sample Variables property
Save all the responses into the .jtl results file, you can do this by adding the next lines to user.properties file:
jmeter.save.saveservice.output_format=xml
jmeter.save.saveservice.response_data=true
jmeter.save.saveservice.response_data.on_error=true
Inspect the response and the CSRF Token variable value using Debug Sampler and View Results Tree listener combination - it should be 100% match for each virtual user and different threads (virtual users) must have different CSRF Token values.
Related
Scenario:
We are using azure redis session provider. When page first loads, retrieves the data from external API and stores them in redish session.
The same session data is retrieved via different pages and components with in user session. The question is:
Does application gets the session data only once and stores locally http current context? Or everytime it goes to redis store?
What if we are encrypting the data on set and decrypt the data on Get operations?
Thanks.
Application gets the session-data from Redis everytime you ask for it... for the writing part, you'll have to wait until the dictionary key is unlocked. See https://msdn.microsoft.com/en-us/library/aa479041.aspx#aspnetsessionstate_topic3 assuming you are using asp.net for this
A page claims write access to the session state by setting the EnableSessionState attribute on the #Page directive to true. (This is the default setting.) A page, though, can also have read-only permissions on the session state, for example, when the EnableSessionState attribute is set to ReadOnly. In this case, the module will hold a reader lock on the session until the request for that page finishes. As a result, concurrent readings can occur.
If a page request sets a reader lock, other concurrently processed requests in the same session cannot update the session state but are at least allowed to read. This means that when a session read-only request is being served, awaiting read-only requests are given higher priority than requests needing a full access. If a page request sets a writer lock on the session state, all other pages are blocked, regardless of whether they have to read or write. For example, if two frames attempt to write to Session, one of them has to wait until the other finishes.
StackExchange.Redis is just a wrapper (or a abstraction) for the HttpSessionState Module
I'm developing a RestFul Apis for a mobile application (Android App). I'm using 2-Step auth using OTP and remember me token. For the remember me token I'm currently using Remember Me (any other similar strategy npm is welcome). The npm basically sets a unique token to a cookie which the App can use to verify itself. According to documentation in the above NPM, it recommended to re-generate the tokens after every request.
However in the event when the mobile App makes multiple parallel requests, all the parallel request use the same token. This undoubted give an auth error. I guess this is common situation. I wanted to know if there is a standard way to handle this ?
Current Workflow
Mobile App request authentication with a given OTP
Upon successful verification, the App is give a token which is
passed back in a cookie
For calls to protected APIs, the App calls
the API with cookie passed back in the previous step.
The server resets the token in the cookie and sends back the response to the App
Issue with the workflow
The App is successfully logged-in and has a valid cookie.
App makes a call to a protected API /protected_api_1
The server has reset the token in the cookie for the above call but has not yet completed the reponse
App makes a second call /protected_api_2, with the old cookies as the App does not have the new cookie with it.
Auth fails for (3)
Ok, checking your update I think of 3 workarounds for this. Let's say we have 3 actions, (a), (b) and (c) that requires the token to consume the API.
Token Store
With this just I mean a class, file, cookie or object where you can save your current token, and you can update with the new token after an action is completed.
The problem with this solution is that if you make (a), (b) and (c) at the same time with the same token, the first one who finishes would update the store, and the other 2 would fail. You would have run them synchronously or concurrently.
If you want to do it this way, maybe it would be a better idea to have a:
Lock: a boolean variable that indicates that the token is being used and that the current request must wait for the token to execute and update the token.
Queue: just a linked list where you push the requests and they are consumed asynchronously when the lock isn't set. You implement a service in another thread that handles the queue, may in a similar fashion to a reactor pattern.
Grouping The Requests
Let's suppose that your application executes (a), (b) and (c) very often. In that case, it would be a good idea to group them in just one action and execute it on the server with just one callback. This could be complicated in your case because it would require to create new resources or think about your modeling of the problem.
Managing token expiration
I've seen this in some projects. You set a soft expiration for the token, let's say 15 minutes (or even less). After the time has passed, you give the client a new token, before that time you keep the same token. (a), (b) and (c) would run at the same time with the same token. Problems would happen when you run the requests near the expiration time, depending on how long it takes to complete them.
I can't give you more details about implementation because I don't know in what language or framework you are implementing the client, and I've never made an Android Application, but I think it would be a good idea to try one of this ideas or a mix of them. Best wishes.
Original
I don't understand what do you mean by parallel in this context.
Try making a Token Store resource in your app which every parallel request consumes and updates after request is done.
If all requests are sent at the send time, maybe it would be a good idea to group them in just one operation, but that would maybe require API endpoint changes.
I'm creating flask web site that uses some API to retrieve data.
this API has basic authentication with tokens and each token is valid for X hours.
I'll probably will run this app behind nginx+uwsgi and the configuration will be something like that:
[uwsgi]
# Some other config....
master = true
processes = 2
enable-threads = true
threads = 4
So i'm trying to figure out what the best way to maintain updated Auth Token for my processes and their threads.
a common solution is to use a separate script that updates some memcache or some consul solutions and retrieve the data from there but is seems like a overkill for this specific task...
There is some nice way in flask to run some background thread that updates this token?
(just to be clear its ok if the same server will have couple of auth tokens, like one for each process running....)
Save the token to a db along with the creation time, every now and then check how long it's been and then ask for a new API token if the time has expired. If you are using multiple tokens then specify which token in the db is for what.
If you don't want to use a db then you could write the token and timestamp to a file instead.
In CherryPy, each request runs in a thread, and that thread has access to a session object via cherrypy.session. If, from that request thread, you launch another thread, thereby allowing the request to return, you no longer have access to that session object. Is there any way around this?
I have a function that runs when the user loads a specific page. Under certain circumstances, this function could take some time (say 10 seconds or so) to run. The results of this function aren't used directly in page rendering, rather they are stored in the users session object for later (instant) retrieval when the user clicks a button. Rather than make the user wait for the data to be compiled, I would like to offload this function to a background thread and let the main thread return the page to the user, but when I do that I no longer have access to the users session object to store the result. How can I work around this? Thanks.
In my specific situation, I am using a custom class for my session (a PostgreSQL session class), but I would think the same procedure would apply regardless. When the initial request comes in, I pull the session_id from the cherrypy.request.cookie object, and pass it to the function that I run in the child thread.
Then, in that function, when I need to access the session object, I instantiate a new session object myself using the session_id, and after setting the desired value call save() on the instance. Works perfectly for me!
I am trying to implement a simple cache where my cache will consist of just a latest token returned by authentication server to my application. There are different worker threads which try to login simultaneously to authentication server.This increases load on authentication server and also my application becomes slow as for each authentication thread there is a round trip involved with the server. Hence by implementing a simple token cache, a token will be cached at client side and will be updated only when one of the authentication thread fails to login. Whoever fails will go and fetch a new token from authentication server.
The problem I am getting is when any authentication thread fails and updates the token cache, there might be some threads who already have read the old token and will fail eventually and they also will try to update the cache. How can I stop these threads from updating the cache once it is already updated?
One possible solution is to assign a timestamp to the retrieved token. Time timestamp does not have to be "real", a sequence number suffices.
When a thread retrieves the token from the token cache, it also retrieves the sequence number associated with the token. When a thread fails to login, it first has to check the local cache again to see if the cache has been refreshed since it retrieved its token. If the sequence number of the current token is different from the one it currently has, it can try again with the token from the cache.
Updating the token cache is necessary only when login fails and the cache has not been refreshed either since the retrieval of the failing token.
There is a slight chance that the sequence number goes a full cycle wrapping around, and a task is mislead to think that the cache has not been refreshed when in fact it has a great number of times, but this is more of a theoretical possibility than a practical concern.
When a worker thread fails to log in, it should check the token cache to see if the token has changed from the one it was already issued. If the cached token has changed, it should use the new cached token instead of seeking a new token.
When a worker thread does seek a new token, it can also keep the old, no longer valid, token. Then before putting its new token in the cache, it can check if the currently cached token is the same as its old token.
The token cache of course needs to be thread safe and ensure that updates from one thread are seen immediately in other threads, for example by using a volatile reference to the cached token. This is simpler than keeping a separate time stamp with each token.
Assuming, your clients are acting quickly and often, and that time needed to get new token could be few times longer than few client requests, you must introduce some sort of locking.
If you assume, that token is received within 2 seconds, you could set up following rules:
use cache with keys "token" and "locked".
If there is not content for token, and locked is empty, set "lock" to True and try to get new token. As you are done, remove the lock and store new token.
If there is a token, try to use it.
If a token you have is failing, get from cache current token and if it differs, try to use new value. If there is no token, and "lock" is True, wait 2 seconds and try again. If no new token is found, try to get the token yourself (again, use "lock" True).
In short:
if "token" found, try using it
if "token" fails, delete it from cache and set up "lock", get new token, remove lock.
if no "token", check if there is a "lock", if yes, wait 2 seconds, get new token if available, if not available, try getting it on your own.