Cast Task<T> to Task<object> in C# without having T

cast task object to task t
c# task return void
c# parallel task with return value
system threading tasks task 1(system string c#)
c# task result
async task return value c#
c# task then
static async task

I have static class full of extension methods where each of the methods is asynchronous and returns some value - like this:

public static class MyContextExtensions{
  public static async Task<bool> SomeFunction(this DbContext myContext){
    bool output = false;
    //...doing stuff with myContext
    return output;
  }

  public static async Task<List<string>> SomeOtherFunction(this DbContext myContext){
    List<string> output = new List<string>();
    //...doing stuff with myContext
    return output;
  }
}

My goal is to be able to invoke any of these methods from a single method in another class and return their result as an object. It would look something like this:

public class MyHub: Hub{
  public async Task<object> InvokeContextExtension(string methodName){
    using(var context = new DbContext()){
      //This fails because of invalid cast
      return await (Task<object>)typeof(MyContextExtensions).GetMethod(methodName).Invoke(null, context);
    }
  }
}

The problem is that the cast fails. My dilemma is that I cannot pass any type parameters to the "InvokeContextExtension" method because it is part of a SignalR hub and is invoked by javascript. And to a certain extent I don't care about the return type of the extension method because it is just going to get serialized to JSON and sent back to the javascript client. However I do have to cast the value returned by Invoke as a Task in order to use the await operator. And I have to supply a generic parameter with that "Task" otherwise it will treat the return type as void. So it all comes down to how do I successfully cast Task with generic parameter T to a Task with a generic parameter of object where T represents the output of the extension method.


You can do it in two steps - await the task using the base class, then harvest the result using reflection or dynamic:

using(var context = new DbContext()) {
    // Get the task
    Task task = (Task)typeof(MyContextExtensions).GetMethod(methodName).Invoke(null, context);
    // Make sure it runs to completion
    await task.ConfigureAwait(false);
    // Harvest the result
    return (object)((dynamic)task).Result;
}

Here is a complete running example that puts in context the above technique of calling Task through reflection:

class MainClass {
    public static void Main(string[] args) {
        var t1 = Task.Run(async () => Console.WriteLine(await Bar("Foo1")));
        var t2 = Task.Run(async () => Console.WriteLine(await Bar("Foo2")));
        Task.WaitAll(t1, t2);
    }
    public static async Task<object> Bar(string name) {
        Task t = (Task)typeof(MainClass).GetMethod(name).Invoke(null, new object[] { "bar" });
        await t.ConfigureAwait(false);
        return (object)((dynamic)t).Result;
    }
    public static Task<string> Foo1(string s) {
        return Task.FromResult("hello");
    }
    public static Task<bool> Foo2(string s) {
        return Task.FromResult(true);
    }
}

How to convert a Task<TDerived> to a Task<TBase>?, Since C#'s Task is a class, you obviously can't cast a Task<TDerived> to a Task<​TBase> . However, you can do: public async Task<TBase>  A unique casting resin that is very strong when cast in Ultra-Thin sections ranging from 0.03” to 0.50” (0.075cm to 1.27cm). TASK™ 4 exhibits very low shrinkage which is why this plastic has become a favorite of precision prototype and design professionals throughout the world.


In general, to convert a Task<T> to Task<object>, I would simply go for the straightforward continuation mapping :

Task<T> yourTaskT;

// ....

Task<object> yourTaskObject = yourTaskT.ContinueWith(t => (object) t.Result);

(documentation link here)


However, your actual specific need is to invoke a Task by reflection and obtain its (unknown type) result .

For this, you can refer to the complete dasblinkenlight's answer, which should fit your exact problem.

Casting a Task<T> to a Task<DerivedT>, Easy way is use async\await pattern: public static async Task<TResponse> ExecuteAsync<TResponse>(Request request) where TResponse : Response { var  Whether you manage a large team or are an entrepreneur with many roles, Screencast-O-Matic’s video platform can save time and streamline business needs. From training videos to product demos and video walkthroughs, Screencast-O-Matic makes it easy for you to quickly create videos, manage content and share your ideas. Solutions for work.


You cannot cast Task<T> to Task<object>, because Task<T> is not covariant (it's not contravariant, either). The simplest solution would be to use some more reflection:

var task   = (Task) mi.Invoke (obj, null) ;
var result = task.GetType ().GetProperty ("Result").GetValue (task) ;

This is slow and inefficient, but usable if this code is not executed often. As an aside, what is the use of having an asynchronous MakeMyClass1 method if you are going to block waiting for its result?

and Another possibility is to write an extension method to this purpose:

  public static Task<object> Convert<T>(this Task<T> task)
    {
        TaskCompletionSource<object> res = new TaskCompletionSource<object>();

        return task.ContinueWith(t =>
        {
            if (t.IsCanceled)
            {
                res.TrySetCanceled();
            }
            else if (t.IsFaulted)
            {
                res.TrySetException(t.Exception);
            }
            else
            {
                res.TrySetResult(t.Result);
            }
            return res.Task;
        }
        , TaskContinuationOptions.ExecuteSynchronously).Unwrap();
    }

It is none-blocking solution and will preserve original state/exception of the Task.

How to: Return a Value from a Task, Tasks.Task<TResult> type to return a value from the Result property. It requires that the C:\Users\Public\Pictures\Sample Pictures\ directory  Dim fruits As New System.Collections.ArrayList() fruits.Add("mango") fruits.Add("apple") fruits.Add("lemon") ' Call Cast(Of String) to cast the ArrayList elements to strings. Dim query As IEnumerable(Of String) = fruits.Cast(Of String)().OrderBy(Function(fruit) fruit).Select(Function(fruit) fruit) '' The following code, without the cast, doesn't compile.


Async Return Types (C#), The Task (2011) cast and crew credits, including actors, actresses, directors, writers and more. CAST is a nonprofit 501 (c) (3) organization composed of scientific societies and many individual, student, company, nonprofit, and associate society members. CAST's Board is composed of representatives of the scientific societies, commercial companies, and nonprofit or trade organizations, and a Board of Directors. CAST was established in 1972


The most efficient approach would be custom awaiter:

struct TaskCast<TSource, TDestination>
    where TSource : TDestination
{
    readonly Task<TSource> task;

    public TaskCast(Task<TSource> task)
    {
        this.task = task;
    }

    public Awaiter GetAwaiter() => new Awaiter(task);

    public struct Awaiter
        : System.Runtime.CompilerServices.INotifyCompletion
    {
        System.Runtime.CompilerServices.TaskAwaiter<TSource> awaiter;

        public Awaiter(Task<TSource> task)
        {
            awaiter = task.GetAwaiter();
        }

        public bool IsCompleted => awaiter.IsCompleted;    
        public TDestination GetResult() => awaiter.GetResult();    
        public void OnCompleted(Action continuation) => awaiter.OnCompleted(continuation);
    }
}

with the following usage:

Task<...> someTask = ...;
await TaskCast<..., object>(someTask);

The limitation of this approach is that the result is not a Task<object> but an awaitable object.

The Task (2011) - Full Cast & Crew, It would be nice if there were an implicit conversion from T to Task ; it and thought the first cast from ViewResult to ActionResult wouldn't  Rest of cast listed alphabetically: Abdullah Abbas Taskmaster (uncredited) Gorgen Raymond Aghayan Hebrew at Golden Calf (uncredited) Ahmed Salah Sayed Ahmed Slave (uncredited)


Implicit conversion from T to Task<T> · Issue #15892 · dotnet/runtime , You cannot even return a type, which can be implicitly cast to Task/Task<T> because you'll get a compiler warning So far the only thing that works is adding a​  using System; using System.Linq; using System.Threading.Tasks; class Program { static void Main() { // Return a value type with a lambda expression Task<int> task1 = Task<int>.Factory.StartNew(() => 1); int i = task1.Result; // Return a named reference type with a multi-line statement lambda.


Async requiring you return Task/Task<T>/void =( Trying to make Get , And BadRequest can be cast to IHttpActionResult , so what gives? Well, a few key discoveries/refreshers: C# Tasks are Futures (what?) which  // Return statement specifies an integer result. return hours; } // Calls to TaskOfTResult_MethodAsync Task<int> returnedTaskTResult = TaskOfTResult_MethodAsync(); int intResult = await returnedTaskTResult; // or, in a single statement int intResult = await TaskOfTResult_MethodAsync(); You cannot cast a task to the result.


Task and Async: Magically Wrapping Returned Objects into Tasks , Overview. TASK® 7 is a low viscosity, fast set flame resistant plastic ideal for making fire Duration: 1:27 Posted: Jun 5, 2013 In this example we will see how to return Task in asynchronous function. If we return Task then we can use await keyword to call any long process function. Have a look on below code. using System; using System.Collections.Generic; using System.Linq; using System.Runtime.CompilerServices; using System.Text; using System.Threading; using System.Threading.Tasks; using System.Diagnostics; namespace Asynchronious { class TestAsync { public Task LongTask()