bottleneck running task.run on asp net mvc - async-await

I have doubts regarding The legacy ASP.NET Synchronization-Context,
If I run the following methods in an ASP.Net MVC Application:
`Task.Run(async () => await httpClient.getContentAsync()).Result
var response= Task.Run(() => methodAsync(model));
var other = response.Result
var response= await Task.Run(() => methodAsync(model));`
those calls can generate a bottleneck?
all this in an mvc application that is not .net core

You should not use Task.Run in ASP.NET at all (classic or core). You also shouldn't be using Result to block on asynchronous code; that can cause a deadlock with ASP.NET Classic.
For async code, just use plain async and await:
var result = await httpClient.getContentAsync();
var other = await methodAsync(model);

Related

Process.all(array.map(... doesn't work in parallel with page.goto(

I am using the pupperteer library for my bot and I would like to perform some operations in parallel.
In many articles, it is advised to use this syntax :
await Promise.all(array.map(async data => //..some operations))
I've tested this on several operations and it works but when I embed the code below in my .map promise
await page.goto(..
It did not work during Operation Promise and it considers this to be a synchronous operation.
I would like to know why it reacts like this?
I believe your error comes from the fact that you're using the same page object.
The following should work:
const currentPage = browser.pages().then(allPages => allPages[0]);
const anotherPage = await browser.newPage();
const bothPages = [currentPage, anotherPage];
await Promise.all(
bothPages.map(page => page.goto("https://stackoverflow.com"))
);

C# async calls and realm instances

I am using Realm with a Xamarin Forms project, and I have read about how realm entity instances can't be shared across threads.
Given the following code, is using the route obtained in line 100, and then accessed again on line 109 after the awaited call on 104, dangerous?
I am new to using Realm, but if this is true, then one must get a new instance of the Realm and any object being worked with after any/every awaited call. Seems onerous...
is using the route obtained in line 100, and then accessed again on line 109 after the awaited call on 104, dangerous?
Yes, on the next foreach iteration, you will end up with a different managed thread, and Realm will throw an different thread access exception.
The key is to use a SynchronizationContext so your await continuations are on the same thread (and, of course, since you will be in a different thread, skip the use of the Realm-based async methods)
Using Stephen Cleary's Nito.AsyncEx (he is the king of sync contexts 😜)
re: how can i force await to continue on the same thread?
var yourRealmInstanceThread = new AsyncContextThread();
await yourRealmInstanceThread.Factory.Run(async () =>
{
var asyncExBasedRealm = Realm.GetInstance();
var routes = asyncExBasedRealm.All<UserModel>();
foreach (var route in routes)
{
// map it
// post it
await Task.Delay(TimeSpan.FromMilliseconds(1)); // Simulate some Task, i.e. a httpclient request....
// The following continuations will be executed on the proper thread
asyncExBasedRealm.Write(() => route.Uploaded = true);
}
});
Using SushiHangover.RealmThread
I wrote a simple SynchronizationContext for Realm awhile back, it works for my needs and has a specialized API for Realm.
using (var realmThread = new RealmThread(realm.Config))
{
await realmThread.InvokeAsync(async myRealm =>
{
var routes = myRealm.All<UserModel>();
foreach (var route in routes)
{
// map it
// post it
await Task.Delay(TimeSpan.FromMilliseconds(1));
// The following continuations will be executed on the proper thread
myRealm.Write(() => route.Uploaded = true);
}
});
}
Note: For someone that does not understand SynchronizationContext well, I would highly recommend using Nito.AsyncEx as a generic solution that is well supported and due to the fact that is from Stephen Cleary... I use it in a vast majority of my projects.

Asp.net Web Api [duplicate]

This question already has answers here:
Why should I create async WebAPI operations instead of sync ones?
(2 answers)
Closed 5 years ago.
I was going through some code to learn how to Consume a web API.
public async Task<List<TodoItem>> RefreshDataAsync ()
{
// RestUrl = http://developer.xamarin.com:8081/api/todoitems/
var uri = new Uri (string.Format (Constants.RestUrl, string.Empty));
var response = await client.GetAsync (uri);
if (response.IsSuccessStatusCode) {
var content = await response.Content.ReadAsStringAsync ();
Items = JsonConvert.DeserializeObject <List<TodoItem>> (content);
}
}
I found this code.All i want to know is why we use Async and Await.
As i observed Await is mandatory in method body when function is encapsulated as Async keyword.
It depends on your application. For GUI apps, it keeps the user interface from freezing and allows this thread to do other things while the call is being made. For apis, it can allow for scalability if you have blocking IO operations. Here is a similar question with some great explanations: Why should I create async WebAPI operations instead of sync ones?

ASP.Net Core 1.1 MiddleWare response

I am replacing a HttpHandler with a middleware service. I have all the code working except for returning the actual image. All the existing samples are for asp.net Core (or earlier) , but with asp.net core 1.1 the response object has change?
public async Task Invoke(HttpContext context)
{
var mediaType = new MediaTypeHeaderValue("image/jpeg");
mediaType.Encoding = System.Text.Encoding.UTF8;
context.Response.ContentType = mediaType.ToString();
byte[] results = some process that generates a byte array
Stream stream = new MemoryStream(results);
context.Response.Body = stream;
await _next.Invoke(context);
}
So how do we attach the byte array to the response object?
There is couple of methods which you can use on .NET Core 1.1:
httpContext.Response.Body.WriteAsync([BUFFER], [OFFSET], [COUNT]);
httpContext.Response.Body.Write([BUFFER], [OFFSET], [COUNT]);
httpContext.Response.Body.WriteByte([BYTE]);
httpContext.Response.WriteAsync([TEXT])

MVC3 request delay needed

I have a MVC3 application. I have to add a delay in one uri request. I know the simplest way to do is an sleep, but the application in production has a big number of request and i'm afraid that let the iis without threads to response to other request.
I'm looking at the async controller/action for the solution.
Is better for the iis thead pool to do the thread.sleep inside the "actionSync" method?
How can i solve this delay? Maybe an async action that calls a new Web Service that does the thread.sleep inside?
AsyncManager.OutstandingOperations.Increment();
DelayService delayService = new DelayService();
delayService.GetDelayCompleted += (sender, e) =>
{
AsyncManager.Parameters["result"] = e.Value;
AsyncManager.OutstandingOperations.Decrement();
};
newsService.GetDelayAsync(seconds);
In this case if i will deploy this web service to the same IIS that the mvc3 app affects the iis available threads for the mvc3 app? what if is deployed in a different application pool?
What can ido?
Can you consider using the new ASP.NET MVC 4 bits which were released by Microsoft?
If so, this might be a possible solution:
public class TestController : AsyncController {
public async Task<ActionResult> GetData() {
await Task.Delay(5000);
return Content("Done");
}
}

Resources