Home

Linqpad: LINQPad.Util.Cache throws error if query file is modified, saved and re-run.

edited March 2022

Using the amazing LinqPad with a C# script. Get an error using the Util.Cache storing a custom class declared in the same script. How to resolve, other than restarting LinqPad please?

Reproduce error:

  1. Add any char to the comment
  2. save file
  3. run again

Error raised:

Cannot load type 'UserQuery+IPerson' from cache.
Data    
(0 items)
HelpLink    null
HResult -2146233088
InnerException  null
Message Cannot load type 'UserQuery+IPerson' from cache.
Source  LINQPad.Runtime
StackTrace     at LINQPad.Util.Cache[T](Func`1 dataFetcher, String key, Boolean& fromCache)
   at LINQPad.Util.Cache[T](Func`1 dataFetcher, String key)
   at UserQuery.Main(), line 3
TargetSite  
RuntimeMethodInfo•••
CacheConverter.CanConvert (Type sourceType, Type targetType, HashSet<TypeType> visitedTypes)

Linqpad query code

Here is the code being run:

void Main()
{
   IPerson p = Util.Cache<IPerson>(()=>new Person("Bob"), "person_bob9");
   p.Dump();
   // add any char after here, save re-run, error thrown: a
}

interface IPerson{string Name {get;init;}}
class Person:IPerson
{
   public Person(string name)=> Name = name;
   public string Name { get; init; }
}

Notes

Maybe this happens because the Person class is compiled by linqpad into a dll each time the file is modified and run. When an instance of Person is stored in a cache, this might differ from the current Person type declaration, hence the error.

Also placed onto
https://stackoverflow.com/questions/71457806

Comments

  • You need to make Person serializable. This will allow LINQPad to use the serialization engine to extract the type out of the previous DLL:

    [Serializable]
    class Person:IPerson
    {
       public Person(string name)=> Name = name;
       public string Name { get; init; }
    }
    

    You will also need to remove the IPerson type parameter when calling Cache (because interfaces cannot be marked as serializable):

    IPerson p = Util.Cache(()=>new Person("Bob"), "person_bob9");
    
    
  • Excellent thanks Joe, that works great

Sign In or Register to comment.