public static ActionInfo GetActionInfo(Type actionType) { if (actionType == null) { throw new ArgumentNullException(nameof(actionType)); } lock (_cachedActionInfosLock) { if (_cachedActionInfos.TryGetValue(actionType, out var actionInfo)) { return(actionInfo); } if (!typeof(IAction <T>).IsAssignableFrom(actionType) || actionType.IsAbstract) { throw new InvalidOperationException($"Type \"{actionType.FullName}\" does not inherit from \"{typeof(IAction<T>).FullName}\"."); } if (!TryGetActionConstructor(actionType, out var constructorInfo)) { throw new InvalidOperationException($"No constructor for type \"{actionType.FullName}\" was found."); } var metadataAttr = actionType.GetCustomAttribute <ActionAttribute>(false); var imports = GetTypesToImport(constructorInfo); actionInfo = new ActionInfo( actionType, metadataAttr?.FriendlyName, metadataAttr?.Description, imports); _cachedActionInfos.Add(actionType, actionInfo); return(actionInfo); } }
public DefaultActionContext(IExportProvider globalExportProvider, ActionInfo actionInfo) { _globalExportProvider = globalExportProvider ?? throw new ArgumentNullException(nameof(globalExportProvider)); _actionInfo = actionInfo ?? throw new ArgumentNullException(nameof(actionInfo)); }
/// <summary> /// Creates an instance of the action related to the given <see cref="ActionInfo"/>. /// Required services and imports will be taken from the given <see cref="IServiceProvider"/> and <see cref="IExportProvider"/>. /// </summary> /// <param name="actionInfo">The related action-info of the action to create.</param> /// <param name="serviceProvider">The service-provider used for dependency-injection.</param> /// <param name="exportProvider">The export-provider used for dependency-injection.</param> /// <exception cref="ArgumentNullException"></exception> /// <exception cref="InvalidOperationException"></exception> public static object CreateInstance(ActionInfo actionInfo, IServiceProvider serviceProvider, IExportProvider exportProvider) { if (actionInfo == null) { throw new ArgumentNullException(nameof(actionInfo)); } if (serviceProvider == null) { throw new ArgumentNullException(nameof(serviceProvider)); } if (exportProvider == null) { throw new ArgumentNullException(nameof(exportProvider)); } var parameters = actionInfo.Constructor.GetParameters(); var parameterValues = new object[parameters.Length]; var parameterValuesSet = new bool[parameters.Length]; foreach (var curImport in actionInfo.Imports) { var importValue = exportProvider.GetExport(curImport.Type, curImport.Name); if (importValue == null) { throw new InvalidOperationException( string.Format( "Unable to resolve import for type \"{0}\"{1} while attempting to activate \"{2}\".", curImport.Type.FullName, curImport.Name == null ? string.Empty : $" and name \"{curImport.Name}\"", actionInfo.ActionType.FullName)); } parameterValues[curImport.ConstructorIndex] = importValue; parameterValuesSet[curImport.ConstructorIndex] = true; } for (int i = 0; i < parameters.Length; i++) { if (!parameterValuesSet[i]) { var value = serviceProvider.GetService(parameters[i].ParameterType); if (value == null) { if (!TryGetParameterDefaultValue(parameters[i], out var defaultValue)) { throw new InvalidOperationException($"Unable to resolve service for type \"{parameters[i].ParameterType}\" while attempting to activate \"{actionInfo.ActionType.FullName}\"."); } parameterValues[i] = defaultValue; } else { parameterValues[i] = value; } } } try { return(actionInfo.Constructor.Invoke(parameterValues)); } catch (TargetInvocationException ex) { ExceptionDispatchInfo.Capture(ex.InnerException).Throw(); // The above line will always throw, but the compiler requires we throw explicitly. throw; } }
public ActionException(string message, Exception innerException, ActionInfo actionInfo) : base(message, innerException) { ActionInfo = actionInfo; }
public ActionException(string message, ActionInfo actionInfo) : this(message, null, actionInfo) { }
public ActionCollectionEntry(ActionInfo actionInfo, int priority) { ActionInfo = actionInfo ?? throw new ArgumentNullException(nameof(actionInfo)); Priority = priority; }