/// <inheritdoc /> protected override object AssignToken(IScriptToken token, ScriptContext context) { object host = hosttoken.Execute(context); if (parameters.Length == 1) { if (host is Array array) { object value = token.Execute(context); array.SetValue(value, Converter.Convert <int>(parameters[0].Execute(context))); return(value); } } PropertyInfo[] indexer = host.GetType().GetProperties().Where(p => p.GetIndexParameters().Length == parameters.Length).ToArray(); object[] parametervalues = parameters.Select(p => p.Execute(context)).Concat(new[] { token.Execute(context) }).ToArray(); Tuple <MethodInfo, int>[] evaluated = indexer.Select(i => MethodOperations.GetMethodMatchValue(i.SetMethod, parametervalues)).Where(e => e.Item2 >= 0).OrderBy(m => m.Item2).ToArray(); if (evaluated.Length == 0) { throw new ScriptRuntimeException($"No index setter found on '{host.GetType().Name}' which matched the specified parameters '{string.Join(", ", parametervalues)}'", this); } return(MethodOperations.CallMethod(this, host, evaluated[0].Item1, parametervalues, context)); }
/// <inheritdoc /> protected override object ExecuteToken(ScriptContext context) { object host = hosttoken.Execute(context); PropertyInfo[] indexer = host.GetType().GetProperties().Where(p => p.GetIndexParameters().Length == parameters.Length).ToArray(); if (indexer.Length == 0) { if (parameters.Length == 1) { if (host is Array array) { return(array.GetValue(Converter.Convert <int>(parameters[0].Execute(context)))); } if (host is IEnumerable enumerable) { return(enumerable.Cast <object>().Skip(Converter.Convert <int>(parameters[0].Execute(context))).First()); } } throw new ScriptRuntimeException($"No indexer methods found on {host}", this); } object[] parametervalues = parameters.Select(p => p.Execute(context)).ToArray(); Tuple <MethodInfo, int>[] evaluated = indexer.Select(i => MethodOperations.GetMethodMatchValue(i.GetMethod, parametervalues)).Where(e => e.Item2 >= 0).ToArray(); if (evaluated.Length == 0) { throw new ScriptRuntimeException($"No index getter found on '{host.GetType().Name}' which matched the specified parameters '{string.Join(", ", parametervalues)}'", this); } MethodInfo method = evaluated.OrderBy(m => m.Item2).Select(m => m.Item1).First(); return(MethodOperations.CallMethod(this, host, method, parametervalues, context)); }
public void Register_instance_operations() { var iop = new MethodOperations(); var config = new FlowRuntimeConfiguration() .AddInstanceOperations(iop) .AddStreamsFrom(@" / .inProcedure, Procedure .inProcedureV, ProcedureV .inProcedureC, ProcedureC ProcedureC, .outProcedureC .inProcedureVC, ProcedureVC ProcedureVC, .outProcedureVC .inProcedureVCC, ProcedureVCC ProcedureVCC.continueWith0, .outProcedureVCC0 ProcedureVCC.continueWith1, .outProcedureVCC1 .inFunction, Function Function, .outFunction .inFunctionV, FunctionV FunctionV, .outFunctionV " ); using (var fr = new FlowRuntime(config, new Schedule_for_sync_depthfirst_processing())) { var results = new List <IMessage>(); fr.Result += results.Add; fr.Process(".inProcedure"); Assert.AreEqual(99, iop.Result); fr.Process(".inProcedureV", 42); Assert.AreEqual(42, iop.Result); fr.Process(".inProcedureC"); Assert.AreEqual(99, results[0].Data); results.Clear(); fr.Process(".inProcedureVC", 99); Assert.AreEqual(100, results[0].Data); results.Clear(); fr.Process(".inProcedureVCC", 99); Assert.That(results.Select(r => r.Data).ToArray(), Is.EquivalentTo(new object[] { 100, "101" })); results.Clear(); fr.Process(".inFunction"); Assert.AreEqual(99, results[0].Data); results.Clear(); fr.Process(".inFunctionV", 99); Assert.AreEqual(100, results[0].Data); } }
/// <inheritdoc /> public object Create(IScriptToken[] parameters, ScriptContext context) { ConstructorInfo[] constructors = type.GetConstructors().Where(c => MethodOperations.MatchesParameterCount(c, parameters)).ToArray(); if (constructors.Length == 0) { throw new ScriptRuntimeException($"No matching constructors available for '{type.Name}({string.Join<IScriptToken>(",", parameters)})'", null); } object[] parametervalues = parameters.Select(p => p.Execute(context)).ToArray(); Tuple <ConstructorInfo, int>[] evaluated = constructors.Select(c => MethodOperations.GetMethodMatchValue(c, parametervalues)).Where(e => e.Item2 >= 0).ToArray(); if (evaluated.Length == 0) { throw new ScriptRuntimeException($"No matching constructor found for '{type.Name}({string.Join(", ", parametervalues)})'", null); } return(MethodOperations.CallConstructor(evaluated[0].Item1, parameters, context)); }
public void Register_instance_operations() { var iop = new MethodOperations(); var config = new FlowRuntimeConfiguration() .AddInstanceOperations(iop) .AddStreamsFrom(@" / .inProcedure, Procedure .inProcedureV, ProcedureV .inProcedureC, ProcedureC ProcedureC, .outProcedureC .inProcedureVC, ProcedureVC ProcedureVC, .outProcedureVC .inProcedureVCC, ProcedureVCC ProcedureVCC.continueWith0, .outProcedureVCC0 ProcedureVCC.continueWith1, .outProcedureVCC1 .inFunction, Function Function, .outFunction .inFunctionV, FunctionV FunctionV, .outFunctionV "); using (var fr = new FlowRuntime(config, new Schedule_for_sync_depthfirst_processing())) { var results = new List<IMessage>(); fr.Result += results.Add; fr.Process(".inProcedure"); Assert.AreEqual(99, iop.Result); fr.Process(".inProcedureV", 42); Assert.AreEqual(42, iop.Result); fr.Process(".inProcedureC"); Assert.AreEqual(99, results[0].Data); results.Clear(); fr.Process(".inProcedureVC", 99); Assert.AreEqual(100, results[0].Data); results.Clear(); fr.Process(".inProcedureVCC", 99); Assert.That(results.Select(r => r.Data).ToArray(), Is.EquivalentTo(new object[] {100, "101"})); results.Clear(); fr.Process(".inFunction"); Assert.AreEqual(99, results[0].Data); results.Clear(); fr.Process(".inFunctionV", 99); Assert.AreEqual(100, results[0].Data); } }
/// <inheritdoc /> protected override object ExecuteToken(ScriptContext context) { object host = hosttoken.Execute(context); if (host == null) { throw new ScriptRuntimeException($"'{hosttoken}' results in null", this); } if (host is IExternalMethod externmethod && MethodName.ToLower() == "invoke") { try { return(externmethod.Invoke(context.Arguments, Parameters.Select(a => a.Execute(context)).ToArray())); } catch (Exception e) { throw new ScriptRuntimeException($"Error calling external method '{externmethod}'", this, e); } } MethodInfo[] methods = host.GetType().GetMethods().Where(m => m.Name.ToLower() == methodname && MethodOperations.MatchesParameterCount(m, parameters)).ToArray(); object[] parametervalues = parameters.Select(p => p.Execute(context)).ToArray(); List <ReferenceParameter> references = new List <ReferenceParameter>(); for (int i = 0; i < parameters.Length; ++i) { if (!(parameters[i] is Reference r)) { continue; } references.Add(new ReferenceParameter(i, r)); } Tuple <MethodInfo, int>[] evaluation = methods.Select(m => MethodOperations.GetMethodMatchValue(m, parametervalues)).Where(e => e.Item2 >= 0).OrderBy(m => m.Item2).ToArray(); if (evaluation.Length > 0) { return(MethodOperations.CallMethod(this, host, evaluation[0].Item1, parametervalues, context, references)); } if (extensions != null) { Type extensionbase = host.GetType(); while (extensionbase != null) { Type lookuptype = extensionbase; if (lookuptype.IsGenericType) { lookuptype = lookuptype.GetGenericTypeDefinition(); } methods = extensions.GetExtensions(lookuptype).Where(m => m.Name.ToLower() == methodname && MethodOperations.MatchesParameterCount(m, parameters, true)).ToArray(); evaluation = methods.Select(m => MethodOperations.GetMethodMatchValue(m, parametervalues, true)).OrderBy(m => m.Item2).ToArray(); if (evaluation.Length > 0) { MethodInfo method = evaluation[0].Item1; if (method.IsGenericMethodDefinition) { method = method.MakeGenericMethod(extensionbase.GetGenericArguments()); } return(MethodOperations.CallMethod(this, host, method, parametervalues, context, references, true)); } if (extensionbase == typeof(object)) { break; } extensionbase = extensionbase.BaseType; } foreach (Type interfacetype in host.GetType().GetInterfaces().OrderBy(i => i.IsGenericType ? 0 : 1)) { Type lookuptype = interfacetype; if (lookuptype.IsGenericType) { lookuptype = lookuptype.GetGenericTypeDefinition(); } methods = extensions.GetExtensions(lookuptype).Where(m => m.Name.ToLower() == methodname && MethodOperations.MatchesParameterCount(m, parameters, true)).ToArray(); evaluation = methods.Select(m => MethodOperations.GetMethodMatchValue(m, parametervalues, true)).OrderBy(m => m.Item2).ToArray(); if (evaluation.Length > 0) { MethodInfo method = evaluation[0].Item1; if (method.IsGenericMethodDefinition) { method = method.MakeGenericMethod(interfacetype.GetGenericArguments()); } return(MethodOperations.CallMethod(this, host, method, parametervalues, context, references, true)); } } } throw new ScriptRuntimeException($"Method '{methodname}' matching the parameters '({string.Join(",", parametervalues)})' not found on type {host.GetType().Name}", this); }
public void Register_static_operations() { var iop = new MethodOperations(); var config = new FlowRuntimeConfiguration() .AddStaticOperations(typeof(MethodOperations)) .AddStreamsFrom(@" / .inProcedureVC, SProcedureVC SProcedureVC, .outProcedureVC .inFunctionV, SFunctionV SFunctionV, .outFunctionV "); using(var fr = new FlowRuntime(config, new Schedule_for_sync_depthfirst_processing())) { var results = new List<IMessage>(); fr.Result += results.Add; fr.Process(".inProcedureVC", 99); Assert.AreEqual(101, results[0].Data); results.Clear(); fr.Process(".inFunctionV", 99); Assert.AreEqual(101, results[0].Data); } }