问题
I'd like to run several services from different .dll's in a isolated way. Basically, all services are derived from RoleEntryPoint
, and I want to load each one in a separated AppDomain
and run it there in a different thread.
So far, I can locate the service and get its type:
String pathToDll = @"C:\....\bin\Debug\ChildWorkerRole.dll";
Assembly assembly = Assembly.LoadFrom(pathToDll);
Type serviceType = assembly.GetTypes().SingleOrDefault(t => t.BaseType == typeof(RoleEntryPoint));
And also run it in the current AppDomain
and Thread
:
RoleEntryPoint myRole2 = (RoleEntryPoint)Activator.CreateInstance(serviceType);
if (myRole2.OnStart())
myRole2.Run();
But when I try to run it in a separate in different AppDomain I get an exception:
AppDomain domain = AppDomain.CreateDomain("MyNewDomain");
RoleEntryPoint myRole = (RoleEntryPoint)domain.CreateInstanceFromAndUnwrap(pathToDll, serviceType.FullName);
if (myRole.OnStart())
myRole.Run();
This exception:
System.Runtime.Serialization.SerializationException was unhandled
Message=Type 'ChildWorkerRole.WorkerRole' in assembly 'ChildWorkerRole, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null' is not marked as serializable.
Source=mscorlib
StackTrace:
at System.AppDomain.CreateInstanceFromAndUnwrap(String assemblyName, String typeName)
.......
The funny thing is that ChildWorkerRole
is actually marked with the SerializableAttribute
... but may be because RoleEntryPoint
is not, it cannot be done.
Any idea or workaround?
thanks!
回答1:
In order to work with a type in a separate AppDomain, it, and all of the types you directly use, need to be either marked as [Serializable]
, or you need to derive them from MarshalByRefObject.
If this is not possible, the only real option is to make a proxy class that you can use which does follow the above criteria, and allow it to manage your types internally.
来源:https://stackoverflow.com/questions/5380246/loading-services-from-other-dll-and-run-them-isolated