public IMessageHandler Create(IMessageHandler handler, ICommonSerializer serializer, object service) { // subscribe to events on the service and forward them to the transport // generate a method that can handle incoming messages // it needs to send the results to the caller // do we need to tell the servive about the caller? no. nice but not required. we can still call a method to get current state var className = "WrapperFor" + service.GetType().Name; var assemblies = new HashSet <string>(); foreach (var loaded in AppDomain.CurrentDomain.GetAssemblies()) { if (!loaded.IsDynamic && loaded.FullName.StartsWith("System")) { assemblies.Add(loaded.Location); } } var requestTypes = new List <string>(); var returnTypes = new List <Type>(); var code = GenerateClassDefinition(className, assemblies, service, requestTypes, returnTypes); var assembly = CompileAndLoadClassDefinition(code, className, assemblies); foreach (var rType in returnTypes.Distinct()) { var inh = typeof(ResponseMessage <>).MakeGenericType(rType); serializer.RegisterSubtype <Message>(inh, inh.GetHashCode()); } foreach (var rType in assembly.GetTypes().Where(t => requestTypes.Contains(t.Name))) { var inh = typeof(RequestMessage <>).MakeGenericType(rType); serializer.RegisterSubtype <Message>(inh, inh.GetHashCode()); } var type = assembly.GetType(className); return((IMessageHandler)Activator.CreateInstance(type, handler, serializer, service)); }
public T Create <T>(IMessageHandler handler, ICommonSerializer serializer, string serviceName) where T : class { if (!typeof(T).IsInterface) { throw new ArgumentException("Datatype should be interface: " + typeof(T)); } var className = "ProxyFor" + typeof(T).Name; var assemblies = new HashSet <string>(); foreach (var loaded in AppDomain.CurrentDomain.GetAssemblies()) { if (!loaded.IsDynamic && loaded.FullName.StartsWith("System")) { assemblies.Add(loaded.Location); } } var requestTypes = new List <string>(); var returnTypes = new List <Type>(); var code = GenerateClassDefinition <T>(className, assemblies, requestTypes, returnTypes); var assembly = CompileAndLoadClassDefinition(code, className, assemblies); foreach (var rType in returnTypes.Distinct()) { var inh = typeof(ResponseMessage <>).MakeGenericType(rType); serializer.RegisterSubtype <Message>(inh, inh.GetHashCode()); } foreach (var rType in assembly.GetTypes().Where(t => requestTypes.Contains(t.Name))) { var inh = typeof(RequestMessage <>).MakeGenericType(rType); serializer.RegisterSubtype <Message>(inh, inh.GetHashCode()); } var type = assembly.GetType(className); return((T)Activator.CreateInstance(type, handler, serializer, serviceName)); }
public IMessageHandler Create(IMessageHandler handler, ICommonSerializer serializer, object service) { // subscribe to events on the service and forward them to the transport // generate a method that can handle incoming messages // it needs to send the results to the caller // do we need to tell the servive about the caller? no. nice but not required. we can still call a method to get current state var className = "WrapperFor" + service.GetType().Name; var assemblies = new HashSet<string>(); foreach (var loaded in AppDomain.CurrentDomain.GetAssemblies()) if (!loaded.IsDynamic && loaded.FullName.StartsWith("System")) assemblies.Add(loaded.Location); var requestTypes = new List<string>(); var returnTypes = new List<Type>(); var code = GenerateClassDefinition(className, assemblies, service, requestTypes, returnTypes); var assembly = CompileAndLoadClassDefinition(code, className, assemblies); foreach (var rType in returnTypes.Distinct()) { var inh = typeof(ResponseMessage<>).MakeGenericType(rType); serializer.RegisterSubtype<Message>(inh, inh.GetHashCode()); } foreach (var rType in assembly.GetTypes().Where(t => requestTypes.Contains(t.Name))) { var inh = typeof(RequestMessage<>).MakeGenericType(rType); serializer.RegisterSubtype<Message>(inh, inh.GetHashCode()); } var type = assembly.GetType(className); return (IMessageHandler)Activator.CreateInstance(type, handler, serializer, service); }