Azure Function, EF Core, Can't load ComponentModel.Annotations 4.2.0.0

I would suggest running this function below once you start your Azure Function. It will redirect any assembly to an existing version.

public class FunctionsAssemblyResolver
{
    public static void RedirectAssembly()
    {
        var list = AppDomain.CurrentDomain.GetAssemblies().OrderByDescending(a => a.FullName).Select(a => a.FullName).ToList();
        AppDomain.CurrentDomain.AssemblyResolve += CurrentDomain_AssemblyResolve;
    }

    private static Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args)
    {
        var requestedAssembly = new AssemblyName(args.Name);
        Assembly assembly = null;
        AppDomain.CurrentDomain.AssemblyResolve -= CurrentDomain_AssemblyResolve;
        try
        {
            assembly = Assembly.Load(requestedAssembly.Name);
        }
        catch (Exception ex)
        {
        }
        AppDomain.CurrentDomain.AssemblyResolve += CurrentDomain_AssemblyResolve;
        return assembly;
    }

}

I followed the instructions here:

https://codopia.wordpress.com/2017/07/21/how-to-fix-the-assembly-binding-redirect-problem-in-azure-functions/

And added the following redirect:

"BindingRedirects": "[ { "ShortName": "System.ComponentModel.Annotations", "RedirectToVersion": "4.2.1.0", "PublicKeyToken": "b03f5f7f11d50a3a" } ]"

NOTE: Its not v 4.5.0.0 ... Its actually 4.2.1.0.


The accepted response will cause a CPU leak due to the += if it is misused, and will grind your function app to a halt. If you are using IoC, it is better to use a singleton. Here:

public class FunctionsAssemblyResolver
{
    static FunctionsAssemblyResolver()
    {
        AppDomain.CurrentDomain.AssemblyResolve += CurrentDomain_AssemblyResolve;
    }

    // At least one static member needs to be invoked in order to execute the static constructor,
    // but it will only run the constructor once.
    public static void StaticInstance() { }

    private static Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args)
    {
        var requestedAssembly = new AssemblyName(args.Name);
        try
        {
            // Feel free to resolve any other assemblies, but this will take care of Annotations
            return requestedAssembly.Name == "System.ComponentModel.Annotations"
                ? Assembly.Load(requestedAssembly.Name)
                : null;
        }
        catch
        {
            // do nothing
        }

        return null;
    }
}

To use, just call FunctionsAssemblyResolver.StaticInstance() prior to any IoC resolves. This can also be used for any non-IoC approach as well.