I have an Azure function that deserializes a message from a topic:
#r "Lib.PosLog.dll" #r "Newtonsoft.Json" #r "Microsoft.ServiceBus" using System; using System.Threading.Tasks; using System.Configuration; using Microsoft.ServiceBus.Messaging; using Newtonsoft.Json; using Lib.PosLog; using System.Reflection; public static void Run(string message, TraceWriter log) { var settings = new JsonSerializerSettings { TypeNameHandling = TypeNameHandling.Auto }; var transaction = JsonConvert.DeserializeObject<TransactionDomainSpecific>(message, settings); }
The message has a type dependency from a custom Lib.PosLog DLL:
"$type":"Lib.PosLog.SaleBase, Lib.PosLog",
The DeserializeObject function will fail with the following internal exception:
InnerException: HResult=-2146233088 Message=Could not load assembly 'Lib.PosLog'. Source=Newtonsoft.Json StackTrace: at Newtonsoft.Json.Serialization.DefaultSerializationBinder.GetTypeFromTypeNameKey(TypeNameKey typeNameKey) at Newtonsoft.Json.Utilities.ThreadSafeStore`2.AddValue(TKey key) at Newtonsoft.Json.Utilities.ThreadSafeStore`2.Get(TKey key) at Newtonsoft.Json.Serialization.DefaultSerializationBinder.BindToType(String assemblyName, String typeName) at Newtonsoft.Json.Serialization.JsonSerializerInternalReader.ResolveTypeName(JsonReader reader, Type& objectType, JsonContract& contract, JsonProperty member, JsonContainerContract containerContract, JsonProperty containerMember, String qualifiedTypeName)
I checked the source code for GetTypeFromTypeNameKey and seemed to just call Assembly.LoadWithPartialName ("Lib.PosLog"), which returns null.
He then checks the current AppDomain for the type.
If I call Assembly.LoadWithPartialName ("Lib.PosLog") before calling DeserializeObject, then it works fine as it gets the type from AppDomain, for example:
public static void Run(string message, TraceWriter log) { var settings = new JsonSerializerSettings { TypeNameHandling = TypeNameHandling.Auto }; Assembly.LoadWithPartialName("Lib.PosLog") var transaction = JsonConvert.DeserializeObject<TransactionDomainSpecific>(message, settings); }
So my question is, why does LoadWithPartialName work when I call it in run.csx, but it doesnβt work when it calls Json.net internally? Probably I am missing something important. I am also sure that this was used to work on Azure before upgrading the run version to 1.
thanks