protected override object ResolveParameterValue(ParameterInfo parameterInfo, IRepositoryMethodParameters parameters, out Exception exception) { if (parameterInfo.ParameterType.IsAssignableFrom(typeof(IRepositoryMethodParameters)) || //legacy repository method definition parameterInfo.ParameterType.IsAssignableFrom(typeof(IDictionary <string, string>)) && parameterInfo.Name.StartsWith(LegacyParameterNameStartWith, StringComparison.Ordinal)) { exception = null; return(parameters); } return(base.ResolveParameterValue(parameterInfo, parameters, out exception)); }
protected virtual RepositoryMethodResolveInfo ResolveRepositoryMethod( string methodName, IRepositoryMethodParameters parameters) { RepositoryMethodResolveInfo res = null; foreach (var strategy in RepositoryMethodResolveStrategies) { res = strategy.Resolve(methodName, parameters); if (res != null) { return(res); } } throw new Exception($"'{methodName}' repository method hasn't been found for the specified set of parameters."); }
public CallMethodResult Execute(string methodName, IRepositoryMethodParameters parameters = null) { object methodResult; var resolveInfo = ResolveRepositoryMethod(methodName, parameters); try { methodResult = resolveInfo.Method.Invoke(resolveInfo.Instance, resolveInfo.Parameters); if (methodResult is Task task) { methodResult = TaskReflectionHelper.WaitForTask(task); } } catch (TargetInvocationException ex) when(ex.InnerException != null) { try { throw ex.InnerException; } catch (AggregateException e) { throw e.Flatten(); } } if (typeof(CallMethodResult).IsAssignableFrom(resolveInfo.Method.ReturnType)) { return(methodResult as CallMethodResult); } return(new CallMethodResult { Result = methodResult, ResultType = resolveInfo.Method.ReturnType, ResultIsHandled = false }); }
protected virtual object ResolveParameterValue(ParameterInfo parameterInfo, IRepositoryMethodParameters parameters, out Exception exception) { exception = null; try { if (!parameters.ContainsKey(parameterInfo.Name)) { if (parameterInfo.HasDefaultValue) { return(parameterInfo.DefaultValue); } throw new Exception($"'{parameterInfo.Name}' parameter has not been defined."); } return(parameters[parameterInfo.Name].SpecflowConvert(parameterInfo.ParameterType)); } catch (Exception ex) { exception = ex; } return(null); }
public RepositoryMethodResolveInfo Resolve(string methodName, IRepositoryMethodParameters parameters) { if (parameters == null) { parameters = new RepositoryMethodParameters(); } var methods = TypeOfInstance.GetMethods(MethodSearchBindingFlags); if (TypeOfInstance.IsInterface) { methods = methods .Union(TypeOfInstance.GetInterfaces().SelectMany(x => x.GetMethods(MethodSearchBindingFlags))) .ToArray(); } methods = FilterByParameters(FilterByMethodName(methods, methodName), parameters).ToArray(); if (!methods.Any()) { return(null); } if (methods.Distinct(new MethodParameterNamesEqualityComparer()).Count() != methods.Length) { throw new Exception( $"'{TypeOfInstance.Name}' type has ambiguous definitions of '{methodName}' method with the same names of parameters."); } var exceptions = new List <Exception>(); foreach (var method in methods) { var methodParams = method.GetParameters(); var paramValues = new List <object>(); var paramsPopulated = true; foreach (var methodParam in methodParams) { var value = ResolveParameterValue(methodParam, parameters, out var ex); if (ex != null) { exceptions.Add(new Exception( $"Resolving of '{method.Name}' method with {methodParams.Length} parameters has been failed.", ex)); paramsPopulated = false; break; } paramValues.Add(value); } if (paramsPopulated) { return(new RepositoryMethodResolveInfo { Method = method, Instance = Instance, Parameters = paramValues.ToArray() }); } } if (exceptions.Any()) { throw new AggregateException( $"Resolving of '{methodName}' method of '{typeof(TInstance).Name}' type has thrown errors. See inner exceptions for more details.", exceptions); } return(null); }
protected virtual IEnumerable <MethodInfo> FilterByParameters(IEnumerable <MethodInfo> methods, IRepositoryMethodParameters parameters) { return(methods.Where(m => { var p = m.GetParameters(); return !p.Any() && !parameters.Any() || p.Any() && !p.Select(x => x.Name).Except(parameters.Select(x => x.Key)).Any(); })); }
protected override IEnumerable <MethodInfo> FilterByParameters(IEnumerable <MethodInfo> methods, IRepositoryMethodParameters parameters) { var callResultMethods = methods.Where(m => typeof(CallMethodResult).IsAssignableFrom(m.ReturnType)).ToArray(); var genericMethods = callResultMethods.Where(m => { var p = m.GetParameters(); return(p.Length == 1 && (typeof(IRepositoryMethodParameters).IsAssignableFrom(p[0].ParameterType) || //legacy repository method definition typeof(IDictionary <string, string>).IsAssignableFrom(p[0].ParameterType) && p[0].Name.StartsWith(LegacyParameterNameStartWith, StringComparison.Ordinal))); }).ToArray(); return(genericMethods.Union(base.FilterByParameters(callResultMethods.Except(genericMethods), parameters))); }