To my understanding, we should do database calls async since it will block IOLoop, and I also found some library/tools that working on this.
But recently I just found lots of posts about this question on stackoverflow
Tornado Asynchronous Handler
How does async work in Tornado?
and something from wiki https://github.com/tornadoweb/tornado/wiki/Threading-and-concurrency
Do it synchronously and block the IOLoop. This is most appropriate for
things like memcache and database queries that are under your control
and should always be fast. If it's not fast, make it fast by adding
the appropriate indexes to the database, etc.
So should we do database calls async?
and a related question: as I know, there are two methods to do database calls async
For sync database(mysqldb), we can
executor = ThreadPoolExecutor(4)
result = yield executor.submit(mysqldb_operation)
For async database(motor), we can use it directly.
what's the different of them based on tornado?
I had a similar doubt and went through some research and digging and finally have some grip over this.
Short Answer - Yes, Do it Asynchronously.
Long Answer :
Database calls are generally blocking calls. Tornado is best suited as a framework when we do async/Non-blocking I/O calls to completely utilize its full potential.
Now, You can do Database Calls in Tornado in the following ways, I am giving the How and Why for each method.
Method 1 : Synchronous Database Calls - Start a number of Tornado instances behind a load balancer like for example nginx, and make synchronous database calls(as mentioned in the wiki). In this case, the process with the particular request making the blocking database call will block. So nginx will load balance the other requests by directing them to the other running tornado instances to handle the requests.
NOTE : That wiki is old, and hasn't been updated so that method mentioned is prior to the addition of coroutines in the newer versions of Tornado as mentioned by Ben Darnell, one of the lead developers of Tornado.
Update : The wiki has been updated by Ben recently and you can check it now.
Method 2 : By using multiprocessing or multithreading, concurrent.futures, similar to what you have mentioned:
For sync database(mysqldb), we can
executor = ThreadPoolExecutor(4)
result = yield executor.submit(mysqldb_operation)
Method 3 : By using Async libraries, like for instance if you are using MySql, then you can use libraries like TorMySql, Tornado-MySQL, other links given here-Tornado 3rd-party libraries, go to the MySql section. These libraries are to be used with Tornado's async decorators, tornado.gen.coroutine or tornado.web.asynchronous. Similarly, you need to use other async libraries for different databases.
NOTE : You cannot use blocking libraries otherwise its all the same as Method 1.
CONCLUSION : Method 3 is what I mentioned as my Short Answer. Method 2 is the next best solution, followed by Method 1. This is in accordance with your performance requirements. If you requirement is for not-so-heavy(few to moderate) request processing per second or per minute, than going for the easy and general Method 1 will suffice.
Related
How do I invalidate a resource created by react-cache?
I can fetch data from API:
const FooResource = createResource(id => fetch(`/foo/${id}`)); // return a promise, or async/await
// inside render...
const fooResponse = FooResource.read(id); // suspends if not in cache; renders if in cache
return <div> {fooResponse} </div>;
However, when I update the data on the backend I am unable to refetch the data on the frontend.
This is the only somehow official documentation that I was able to find: https://github.com/sw-yx/fresh-concurrent-react/blob/master/apis/react-cache.md
Is there some undocumented API that I can use? 🤔
In general — you can't, and this is why it's "unstable". Don't use it for anything except demos and tinkering. We'll likely replace the whole thing with a different API.
As of now react-cache uses LRU (least recently used) caching policy. By this policy, the least recently used entries are invalidated first.
The size of the cache can be set using function unstable_setGlobalCacheLimit.
I couldn't find a function for explicit cache invalidation in the project. I also think that it is good news, 'cause dealing with cache is generally a hassle. It seems like LRU is going to make it easier for most React users.
Manual cache control might find its way in the future versions of react-cache as more developers embrace the technology and discover new use cases that need a custom approach, but I doubt it's something one should consider for now.
There is a lot more control over the cache is required using react-cache. It seems it is written considering only client-side rendering(though it works on both csr and ssr).
On the server, there are high chances that only a few specific API's need to be cached for a given interval. All user-specific API's or data should not be cached in react-cache.
react-cache should give control to differentiate caching behavior on both client and server as both environments have completely different use cases.
Currently, the react-cache source code doesn't point to any invalidation capability. It makes sense to need invalidation, to update the results for example after you've added a new comment or post, as well as use suspense with post/put/delete requests, which should not be cached by default in the first place.
I am learning cucumber through some tutorials and there is something that I don't know how to do.. I need to make a scenario that depends on another scenario (for example log out scenario I have to be logged in first before logging out) so what should I do? should I write steps of login at log out scenario (at the feature file) or there is a way to call the whole log in scenario at the log out scenario
also I need to know should I set up driver before each scenario and quit the driver after each scenario?
There is no support for creating a scenario that depends on another scenario in Cucumber-JVM. I think still is supported in the Ruby implementation in Cucumber. It is, however, a practice that is dangerous. The support for calling a scenario from another scenario will not be supported in future versions of Cucumber.
That said, how do you solve your problem when you want to reuse functionality? You mention logout, how do you handle that when many scenarios requires the state to be logged out for a user?
The solution is to implement the functionality in a helper method or helper class that each step that requires a user to be logged out calls.
This allow each scenario to be independent of all other scenarios. This in turn will allow you to run the scenarios in a random order. I don't think the execution order for the scenarios is guaranteed. I definitely know that it is discussed to have the JUnit runner to run scenarios in a random order just to enforce the habit of not having scenarios depend on other scenarios.
Your other question, how to set up WebDriver before a scenario and how to tear it down, is solved using the Before and After hooks in Cucumber. When using them, be careful not to import the JUnit version of Before and After.
Take a look into cucumber hooks, this allows you to set up global 'before' and 'after' steps, which will run for every scenario without having to specify them in your feature files.
Because they run for every scenario, they're ideal for something like initialising the driver at the start of each test. It may be suitable for running your logon, but if there's a chance you'll have a scenario which doesn't involve logging on then it wouldn't be the way to go (alternative further down). The same applies for the after scenario, which is where you could perform the log off and shut down your driver. As an example:
/**
* Before each scenario, initialise webDriver.
*/
#Before
public void beforeScenario() {
this.application.initialiseWebDriver();
}
/**
* After each scenario, quit the web driver.
*/
#After
public void afterScenario() {
this.log.trace("afterScenario");
this.application.quitBrowser();
}
In my example, I'm simply starting the driver in the before scenario, and closing it in the after, But in theory these before and after methods could contain anything, you just need to have them in your step definitions class and annotate them with the '#Before' and '#After' tags as shown.
As well as these, you can also have multiple before and after tags which you can call by tagging the scenario. As an example:
/**
* Something to do after certain scenarios.
*/
#After("#doAfterMethod")
public void afterMethod() {
this.application.afterThing();
}
You can set up something like this in your step defs, and as standard it won't run. However, you can tag your scenario with '#doAfterMethod' and it will run for the tagged scenarios, which makes this good for a common scenario that you will need at the end of tests, but not all of them. The same would work for methods to run before a scenario, just change the '#After' to '#Before'.
Bear in mind that if you do use these, the global Before and After (so in this example the driver initialisation and quitting) will always be the first and last things to run, with any other before/afters in between them and the scenario.
Further Reading:
https://github.com/cucumber/cucumber/wiki/Hooks
https://zsoltfabok.com/blog/2012/09/cucumber-jvm-hooks/
You can set test dependency with qaf bdd. You can use dependsOnMethods or dependsOnGroups in scenario meta-data to set dependency same as in TestNG, because qaf-BDD is TestNG BDD implementation.
Pleeeeease help me... :- )
"You are my only hope".
I need to execute an action asynchronously several thousand times. The action is supposed to fetch email content from external API and it is located in the different controller, so I use requestAction to get it. When I get all the results, then these 1000 email contents are sent as 1000 emails during one request, using other API.
Unfortunately, when run sequentially, it takes a lof of time, so I need to run these request asynchronously.
My question is:
Can I execute
$this->requestAction($myUrl)
...parallelly? For example 100 requests at one time? I've seen a bit of asynchronous examples in PHP, but they all used static files and I need to preserve CakePHP structure to be able to use requestAction.
Thanks to all who can help!
EDIT: By the way, when I tried to run requests via fopen($url, 'r'); and then stream get contents the efficiency was worse than worst, but maybe it could be improved. Don't know, but the requestAction seems to be definitely better option (I think).
Is there any reason why you wouldn't use a shell for this?
Please take a look at: CakePHP Shells
"Deferred Execution" is probably what you are after here, basically you want to send one command not have the user waiting around for it? If so then you can use a Message Queue to handle this pretty easily.
We use CakeResque and Redis to send 1000's of emails and perform other API calls
CakeResque - Deferred Processing for CakePHP
There are other message queues that are available but this is really simple to get working and probably wont need much of a change to your code.
In the end, I wasn't able to find a solution that would use requestAction, but I was able to extract the code to a standalone php file, which then is processed using include method.
And the most interesting part, asynchronous requests, was done using great library called cURL-easy and with help of my utility function. You can read about it (how to install and how to use it) here:
Is making asynchronous HTTP requests possible with PHP?
I'm not really sure how to handle the scenario I have in a good code manner.
The basic of the criteria of my work is this:
A WPF application that consumes a WCF service
The service uses per session instancing
The session starts soon after application is started and should live through the application lifetime (with small exceptions)
Some method calls in a session must precede and be finished before others are called
This means I will have to be able to have one instance of a proxy client throughout the whole application. I will also have to be able to handle async calls, so the client won't hang up, but at the same time ensure they are finished.
My technical understanding go WCF is limiting enough to not know if certain scenarios would work as intended. So I'm going to list my uncertainties:
When does a session start and when does it end. Is it based on the creation of clients or could a separate client instance access the same session if the first would go faulted.
What is the best way to handle exceptions through a WCF service
Is ChannelFactory something I should look at to help me put here.
So what I did in the first iteration to try to solve some of these problems.
I used dependency injection to inject the client instance throughout the classes of my WPF application (I'm using MVVM) to ensure the same instance is everywhere.
I made the service reference using the asynchronous generation method to get the Begin and End versions of all methods to ensure the calls would be async
I used the Coroutine (IResult interface) feature of the Caliburn.Micro framework to ensure one async action is finished before the other begins (have no idea if this is a proper usage or if it is a smart move at all).
Problems I still have is of course how to handle a faulted state of the client. I'm assuming right now that I could reinstance the client and either rescue the session or I could actually just set it up again as it was. I now need to reinstance it everyplace I injected it in with the same new instance.
So I though perhaps it would be best to create a ClientManager class that would wrap the Client. That way I could inject this ClientManager and reinstance inside of him if needed. I guess I should expose him outwards to be able to make method calls but it would be great if I could error handle inside him in somehow. I'm just having a hard time testing my methods and I'm never certain it will work properly in integration because I don't understand all of the inner workings of WCF, coroutines and threading.
Is there anyone out there with more experience then me in these matters that could give me a few pointers or at least tell me how WCF works in these situations ( per session ) and what I'm doing wrong and what right.
WCF supports sessions out-of-box, so I would recommend starting with this MSDN article.
At a very high level, first you set SessionMode=SessionMode.Required in your ServiceContract. And then, set the IsInitiating=True and IsTerminating=True properties on your OperationContract's to mark the start and end of each session.
However, note that WCF limits concurrent sessions by default to 16 to prevent DOS attacks, but you can always up the value. Also, you would have realized that the session is valid as long as its host (IIS / Windows Service / other) is not recycled.
On a related note, I have used WCF Durable Services earlier - which are meant to persist the state of your WCF service in a data-store (default is SQL Server). Ofcourse, there is a performance hit here. Suggest reading further to see if this is the right choice for you.
Hope this helps.
The big picture is:
I want to use eventlet in some application that does asynchronous IO while working with Django models externally. Working with Django externally is simple (see Django: How can I use my model classes to interact with my database from outside Django?) but it's not the main problem.
I presume (I haven't tested) that using Django from greenlets is dangerous. Actually, in the case of psycopg2, we have this warning (see http://www.initd.org/psycopg/docs/advanced.html#support-to-coroutine-libraries):
Psycopg connections are not green
thread safe and can’t be used
concurrently by different green
threads
In Django there is one db connection per thread (right?) and as such it may lead to scary scenarios when used. Is it possible to provide a connection object manually somehow? Or make it "greenlet-local"?
My motivation is to use connection pool from eventlet (http://eventlet.net/doc/modules/db_pool.html) so that I could speed up my IO-bound application.
There are some projects out there to make Django work well with greenlet. I would check out psycogreen which uses the coroutines support in Psycopg >= 2.2. There is a good blog post on using gevent, gunicorn, and psycogreen together with Django: http://dbinit.com/blog/going-green/.