using System;
using System.Collections.Generic;
using System.Text;
using System.Reflection;
using System.IO;
using System.Linq;
using System.Globalization;
#if !SILVERLIGHT
using System.Runtime.Serialization.Formatters.Binary;
#endif
namespace SuperSocket.Common
{
///
/// Assembly Util Class
///
public static class AssemblyUtil
{
///
/// Creates the instance from type name.
///
///
/// The type.
///
public static T CreateInstance(string type)
{
return CreateInstance(type, new object[0]);
}
///
/// Creates the instance from type name and parameters.
///
///
/// The type.
/// The parameters.
///
public static T CreateInstance(string type, object[] parameters)
{
Type instanceType = null;
var result = default(T);
instanceType = Type.GetType(type, true);
if (instanceType == null)
throw new Exception(string.Format("The type '{0}' was not found!", type));
object instance = Activator.CreateInstance(instanceType, parameters);
result = (T)instance;
return result;
}
///
/// Gets the type by the full name, also return matched generic type without checking generic type parameters in the name.
///
/// Full name of the type.
/// if set to true [throw on error].
/// if set to true [ignore case].
///
#if !NET35
public static Type GetType(string fullTypeName, bool throwOnError, bool ignoreCase)
{
var targetType = Type.GetType(fullTypeName, false, ignoreCase);
if (targetType != null)
return targetType;
var names = fullTypeName.Split(',');
var assemblyName = names[1].Trim();
try
{
var assembly = Assembly.Load(assemblyName);
var typeNamePrefix = names[0].Trim() + "`";
var matchedTypes = assembly.GetExportedTypes().Where(t => t.IsGenericType
&& t.FullName.StartsWith(typeNamePrefix, ignoreCase, CultureInfo.InvariantCulture)).ToArray();
if (matchedTypes.Length != 1)
return null;
return matchedTypes[0];
}
catch (Exception e)
{
if (throwOnError)
throw e;
return null;
}
}
#else
public static Type GetType(string fullTypeName, bool throwOnError, bool ignoreCase)
{
return Type.GetType(fullTypeName, null, (a, n, ign) =>
{
var targetType = a.GetType(n, false, ign);
if (targetType != null)
return targetType;
var typeNamePrefix = n + "`";
var matchedTypes = a.GetExportedTypes().Where(t => t.IsGenericType
&& t.FullName.StartsWith(typeNamePrefix, ign, CultureInfo.InvariantCulture)).ToArray();
if (matchedTypes.Length != 1)
return null;
return matchedTypes[0];
}, throwOnError, ignoreCase);
}
#endif
///
/// Gets the implement types from assembly.
///
/// The type of the base type.
/// The assembly.
///
public static IEnumerable GetImplementTypes(this Assembly assembly)
{
return assembly.GetExportedTypes().Where(t =>
t.IsSubclassOf(typeof(TBaseType)) && t.IsClass && !t.IsAbstract);
}
///
/// Gets the implemented objects by interface.
///
/// The type of the base interface.
/// The assembly.
///
public static IEnumerable GetImplementedObjectsByInterface(this Assembly assembly)
where TBaseInterface : class
{
return GetImplementedObjectsByInterface(assembly, typeof(TBaseInterface));
}
///
/// Gets the implemented objects by interface.
///
/// The type of the base interface.
/// The assembly.
/// Type of the target.
///
public static IEnumerable GetImplementedObjectsByInterface(this Assembly assembly, Type targetType)
where TBaseInterface : class
{
Type[] arrType = assembly.GetExportedTypes();
var result = new List();
for (int i = 0; i < arrType.Length; i++)
{
var currentImplementType = arrType[i];
if (currentImplementType.IsAbstract)
continue;
if (!targetType.IsAssignableFrom(currentImplementType))
continue;
result.Add((TBaseInterface)Activator.CreateInstance(currentImplementType));
}
return result;
}
#if SILVERLIGHT
#else
///
/// Clone object in binary format.
///
///
/// The target.
///
public static T BinaryClone(this T target)
{
BinaryFormatter formatter = new BinaryFormatter();
using (MemoryStream ms = new MemoryStream())
{
formatter.Serialize(ms, target);
ms.Position = 0;
return (T)formatter.Deserialize(ms);
}
}
#endif
///
/// Copies the properties of one object to another object.
///
///
/// The source.
/// The target.
///
public static T CopyPropertiesTo(this T source, T target)
{
return source.CopyPropertiesTo(p => true, target);
}
///
/// Copies the properties of one object to another object.
///
///
/// The source.
/// The properties predict.
/// The target.
///
public static T CopyPropertiesTo(this T source, Predicate predict, T target)
{
PropertyInfo[] properties = source.GetType()
.GetProperties(BindingFlags.Instance | BindingFlags.Public | BindingFlags.GetProperty);
Dictionary sourcePropertiesDict = properties.ToDictionary(p => p.Name);
PropertyInfo[] targetProperties = target.GetType()
.GetProperties(BindingFlags.Instance | BindingFlags.Public | BindingFlags.SetProperty)
.Where(p => predict(p)).ToArray();
for (int i = 0; i < targetProperties.Length; i++)
{
var p = targetProperties[i];
PropertyInfo sourceProperty;
if (sourcePropertiesDict.TryGetValue(p.Name, out sourceProperty))
{
if (sourceProperty.PropertyType != p.PropertyType)
continue;
if (!sourceProperty.PropertyType.IsSerializable)
continue;
p.SetValue(target, sourceProperty.GetValue(source, null), null);
}
}
return target;
}
///
/// Gets the assemblies from string.
///
/// The assembly def.
///
public static IEnumerable GetAssembliesFromString(string assemblyDef)
{
return GetAssembliesFromStrings(assemblyDef.Split(new char[] { ',', ';' }, StringSplitOptions.RemoveEmptyEntries));
}
///
/// Gets the assemblies from strings.
///
/// The assemblies.
///
public static IEnumerable GetAssembliesFromStrings(string[] assemblies)
{
List result = new List(assemblies.Length);
foreach (var a in assemblies)
{
result.Add(Assembly.Load(a));
}
return result;
}
}
}