public ContentTypeWriter GetTypeWriter(string name, Type contentType, Dictionary <string, object> writerData) { if (typeWriterMap.Count == 0) { ProcessAssemblies(); } Type writerType = typeWriterMap.FirstOrDefault(t => t.Value.Name == name).Value; if (writerType == null) { return(null); } var args = writerType.BaseType.GetGenericArguments(); if (args.Length == 0 || !contentType.Equals(args[0])) { return(null); } ContentTypeWriter result = (ContentTypeWriter)Activator.CreateInstance(writerType); if (result != null) { foreach (var param in writerData) { var propInfo = writerType.GetProperty(param.Key, BindingFlags.FlattenHierarchy | BindingFlags.Public | BindingFlags.Instance); if (propInfo == null || propInfo.GetSetMethod(false) == null) { continue; } if (propInfo.PropertyType.IsInstanceOfType(param.Value)) { propInfo.SetValue(result, param.Value, null); } else { // find a type converter for this property var typeConverter = TypeDescriptor.GetConverter(propInfo.PropertyType); if (typeConverter.CanConvertFrom(param.Value.GetType())) { var propValue = typeConverter.ConvertFrom(null, CultureInfo.InvariantCulture, param.Value); propInfo.SetValue(result, propValue, null); } } } MethodInfo dynMethod = result.GetType().GetMethod("Initialize", BindingFlags.Public | BindingFlags.Instance); dynMethod.Invoke(result, new object[] { _typeWriterManager }); } return(result); }
/// <summary> /// Retrieves the worker writer for the specified type. /// </summary> /// <param name="type">The type.</param> /// <returns>The worker writer.</returns> /// <remarks>This should be called from the ContentTypeWriter.Initialize method.</remarks> public ContentTypeWriter GetTypeWriter(Type type, Dictionary <string, object> writerData) { if (typeWriterMap.Count == 0) { ProcessAssemblies(); } ContentTypeWriter result = null; var contentTypeWriterType = typeof(ContentTypeWriter <>).MakeGenericType(type); Type typeWriterType; if (!typeWriterMap.TryGetValue(contentTypeWriterType, out typeWriterType)) { var inputTypeDef = type.GetGenericTypeDefinition(); Type chosen = null; foreach (var kvp in typeWriterMap) { var args = kvp.Key.GetGenericArguments(); if (args.Length == 0) { continue; } if (!args[0].IsGenericType) { continue; } // Compare generic type definition var keyTypeDef = args[0].GetGenericTypeDefinition(); if (inputTypeDef.Equals(keyTypeDef)) { chosen = kvp.Value; break; } } try { var concreteType = type.GetGenericArguments(); result = (ContentTypeWriter)Activator.CreateInstance(chosen.MakeGenericType(concreteType)); // save it for next time. typeWriterMap.Add(contentTypeWriterType, result.GetType()); } catch (Exception) { throw new ArgumentException(String.Format("Could not find ContentTypeWriter for type '{0}'", type.Name)); } } else { result = (ContentTypeWriter)Activator.CreateInstance(typeWriterType); } if (result != null) { foreach (var param in writerData) { var propInfo = typeWriterType.GetProperty(param.Key, BindingFlags.FlattenHierarchy | BindingFlags.Public | BindingFlags.Instance); if (propInfo == null || propInfo.GetSetMethod(false) == null) { continue; } if (propInfo.PropertyType.IsInstanceOfType(param.Value)) { propInfo.SetValue(result, param.Value, null); } else { // find a type converter for this property var typeConverter = TypeDescriptor.GetConverter(propInfo.PropertyType); if (typeConverter.CanConvertFrom(param.Value.GetType())) { var propValue = typeConverter.ConvertFrom(null, CultureInfo.InvariantCulture, param.Value); propInfo.SetValue(result, propValue, null); } } } MethodInfo dynMethod = result.GetType().GetMethod("Initialize", BindingFlags.Public | BindingFlags.Instance); dynMethod.Invoke(result, new object[] { _typeWriterManager }); } return(result); }