Prashant Tomar
Prashant Tomar

Reputation: 205

How to redirect to a page from async method in mvc

I want to redirect to an error page like "https://www.mydomain/Timeout" when the API is taking longer to response (e.g., 60seconds).

The logic of getting the response from the API is written in the async method present in the ServiceLayer project in the same VS solution.

That async method is being called in the non-asynchronous controller (Present in the Web project in same VS solution).

When I check the time in async method and on the basis of that I do Response.Redirect in controller then it works. But, I want to do this in the async method because this is the method which is being called by around 50 APIs. So rather doing the Response.Redirect in each controller I want to handle it from here so that it will be applicable for each API.

Now please help me how to do it?

  1. I tried to put the Response.Redirect("https://www.mydomain/timeout") in async method but that is not working.

  2. I also tried Server.Transfer but no luck. Is this due to async method.

Below is the code of getting response from API which is written in async method.

private async Task<T1> PostA<T1,T2>(string method, T2 request, string api,
            bool isPut)
{
  Stopwatch sw = new Stopwatch();
  sw.Start();

        var response = isPut ? 
               await client.PutAsync(parturl, 
                 body).ConfigureAwait(continueOnCapturedContext: false) :
               await client.PostAsync(parturl, 
                 body).ConfigureAwait(continueOnCapturedContext: false);

  sw.Stop();

  long elapsedTime = sw.ElapsedMilliseconds;

  if (elapsedTime >= 60000)
  {
     Response.Redirect("https://www.mydomain/timeout")
  }
}

In the method I have shown you only the required code, the rest of the logic has been removed.

Upvotes: 0

Views: 1435

Answers (1)

Prashant Tomar
Prashant Tomar

Reputation: 205

How I followed the approach on the basis of the comments above:

  1. I created a static dictionary as Dictionary<string, bool> d= new Dictionary<string, bool>(); in the class where my API calling method is written e.g., MyApiClass
  2. I put the code line client.timeout = [your time here in milliseconds]; for API sending the request.
  3. When API is time out then it throws TaskTimeoutException, so I caught the exception and put the code in catch block as d.Add("timeout", true);

  4. I created the custom action filter and applied the following code:

    public class CustomActionFilter : ActionFilterAttribute
    {
        public override void OnActionExecuted(ActionExecutedContext filterContext)
        {
            if(MyApiClass.d.ContainsKey("timeout") && d["timeout"])
            {
                throw new Exception();
            }
        }
    }
    
  5. I applied the [CustomActionFilter] on the action.

  6. when action is executed and enter the custom filter it throws Exception by checking the dictionary entry. Now, we have Application_Error() in Global.asax.cs that catches the exception.

  7. In the Application_Error() we have written the code for redirect to the required page.

NOTE: In step 4 you can create your custom exception to provide more precise detail for logging.

Upvotes: 0

Related Questions