I am developing a app that chooses a user and has a 15 sec. timer for that user to respond. The user app queries the db every 5 sec to see if that user is chosen. If so The mobile app begins a 15 sec. timer. The problem is that the timers will never match up because the user app can be on a different timer cycle that the backend and can query the db at a later time. I use Angular, NodeJS, and expressJS + MongoDB to develop this app.
any suggestion on how I can get the timers to be synchronized?
You need to create API for requesting current server time and use that server time as basis of your timer.
You also need to take into account condition when browser pauses javascript execution. This is true for mobile device. When mobile device is paused/sleep, browser stops javascript execution causing timer not sync anymore.
Every tick, check last tick millisecond with current tick millisecond. If difference is greater than some threshold value then assume timer not sync anymore and need to be sync by requesting current server time and recalculate timer value
Related
Google describes basic scaling like this:
I don't really have any other choice, as I'm using a B1 instance, so automatic scaling is not allowed.
That raises the question though, if I have an endpoint that takes a variable amount of time (could be minutes, could be hours), and I basically have to set an idle_timeout, will App Engine calculate idle_timeout from the time the request was made in the first place or when the app is done handling the request?
If the former is right, then it feels a bit unfair to have to guess how long requests will take when thread activity is a usable indicator of whether or not to initiate shutdown of an app.
Here you are mixing up two different terms.
idle_timeout is the time that the instance will wait before shutting down after receiving its last request
Request timeout is the amount of time that App Engine will wait for the return of a request from your app
As per the documentation:
Requests can run for up to 24 hours. A manually-scaled instance can
choose to handle /_ah/start and execute a program or script for many
hours without returning an HTTP response code. Task queue tasks can
run up to 24 hours.
My requirement is I want 10 users logging in(using login credentials from CSV) with simultaneous login of 5 users, with each user traversing different paths depending on which user has logged-in. Below is my Test Plan for the same:
Below is synchronizing timer settings which I have used:
I have clubbed my requests in a transaction controller since each main request has multiple concurrent sub-requests Plus i want to put requests for all JS, css, image files as one parent request. I am considering 1 request to include all the requests within each Transaction controller.:
As per my Test Plan, if my understanding is correct then, 1st user will login and the request continues to "If controller" of User1. Here requests will wait till 5 requests have been queued as per setting done in synchronizing timer and all the 5 requests will be sent to the server at one time. Then 2nd user will login and the requests of the second user will be processed and so on.
The above test plan executes successfully if synchronizing timer is not used. Once I use the synchronizing timer, my test plan execution continues indefinitely.
As per my understanding of synchronizing timer, the processing should continue since I have used timeout value of 200000 MilliSecs. I am unable to understand why on using synchronizing timer the Test Plan hangs.
What i actually want is first all 10 users should login with 5 simultaneous logins and then each user continue with their respective requests as per the condition specified in the If Controller(${__groovy(vars.get("username") == "user1" )}), with 10 simultaneous requests.
So, how do i design my Test Plan along with use of synchronizing timer to achieve the desired result?
I will greatly appreciate inputs from seasoned JMeter experts. Thanks!
It seems the you want the synchronizing timer to work specifically when 10 users are entering the if controller.
Because Timers are executed before every Samplet in scope,
timers are processed before each sampler in the scope in which they are found;
In your case you just need to move timer under request 1 inside controller.
Currently you are trying to sync all samplers in flow, and you don't need to wait on every sampler
I have a mobile app with a comment system, backed by App Engine. When user A replies to user B's comment, user B gets a notification. Everything works over HTTP.
Right now I have the client device polling App Engine every minute for updates. It works but on average, there's a 30-second delay before the notification appears.
I would like to close this gap by having App Engine send a packet to user B's device immediately after user A posts the reply. I can make this happen by moving the wait(60) command from the client to the server -- the client will run a tight loop, making another request as soon as it gets a response; App Engine sits on every request for 60 seconds before responding.
But if the user gets a notification, App Engine responds before the 60 seconds are up. Essentially, user A's request handler wakes up user B's sleeping request handler and causes it to return non-null data.
Is there a name for this technique as applied to HTTP? Can it be coded efficiently? If so, how can I implement the wait/notify code?
In lieu of sockets App Engine has the Channel API, which should be nearly instant without the need to poll.
docs
Consider implementing poker on Google App Engine. Suppose a player is allowed only 10 seconds to check/fold/raise.
That is, if 10 seconds pass with no response from the player then some timer should fire which executes code that writes to DataStore declaring that the player folded. What is the idiomatic way to implement this on Google App Engine.
The GAE has a feature called "Tasks". Sadly, they have no guaranteed resolution, so a task scheduled for now+10 seconds can execute in 10 seconds or any later time.
Solution: Write the current time-stamp along with the information about the current player into the database. If any of the players request updated information about the current game, you can check this time-stamp, compare it with the current one, and therefore determine if these 10 seconds have passed and update the database accordingly.
You can combine this solution with tasks to ensure, that even if nobody "watches" that game, its still updated sometime.
This needs to be done on a backend, as that's the only code that can persist outside of a request handler.
Player is dealt. Timer starts on backend. Timer expires. Player
status updated.
Backends are special App Engine instances that have no request deadlines, higher memory and CPU limits, and persistent state across requests. They are started automatically by App Engine and can run continously for long periods. Each backend instance has a unique URL to use for requests, and you can load-balance requests across multiple instances.
https://developers.google.com/appengine/docs/python/backends/
No need to act synchronously - i.e. do some action exactly 10 seconds after last user action.
Just record the time of last user action and act accordingly next time the user action happens: if <10s let user do next move, if >10s notify user he folded.
To keep things more responsive, e.g. to show user how much time he hes before folding, you should also track this on client.
Can we start a dynamic backend programatically? mean while when a backend is starting how can i handle the request by falling back on the application(i mean app.appspot.com).
When i stop a backend manually in admin console, and send a request to it, its not starting "dynamically"
Dynamic backends come into existence when they receive a request, and
are turned down when idle; they are ideal for work that is
intermittent or driven by user activity.
Resident backends run continuously, allowing you to rely on the state
of their memory over time and perform complex initialization.
http://code.google.com/appengine/docs/python/backends/overview.html
I recently started executing a long running task on a dynamic backend and noticed a dramatic increase in the performance of the frontends. I assume this was because the long running task was competing for resources with normal user requests.
Backends are documented quite thoroughly here. Backends have to be started and stopped with appcfg or the admin console, as documented here. A stopped backend will not handle requests - if you want this, you should probably be using the Task Queue instead.
It appears that a dynamic backend need not be explicitly stopped. The overvicew (http://code.google.com/appengine/docs/python/backends/overview.html) states that the billing for a dynamic backend stops 15 minutes after the last request is processed. So, if your app has a cron job, for example, that requires 5 minutes to complete, and needs to run every hour, then you could configure a backend to do this. The cost you'll incur is 15+5 minutes every hour, or 8 hours for the whole day. I suppose the free quota allows you 9 backend hours. So, this type of scenario would be free for you. The backend will start when you send your first request to it through a queue, and will stop 15 minutes after the last request you send is processed completely.