Come posso ottenere una stringa come
Namespace.IMyService.Do("1")
dall'espressione come dimostrata in questo snip:
IMyService myService = ...;
int param1 = 1;
myExpressionService.Get(c => myService.Do(param1));
In realtà non desidero chiamare Do
meno che non venga soddisfatta una condizione utilizzando la stringa generata.
Dovrai attraversare gli Expression trees
. Ecco alcuni esempi di codice:
internal static class myExpressionService
{
public static string Get(Expression<Action> expression)
{
MethodCallExpression methodCallExpression = (MethodCallExpression)expression.Body;
var method = methodCallExpression.Method;
var argument = (ConstantExpression) methodCallExpression.Arguments.First();
return string.Format("{0}.{1}({2})", method.DeclaringType.FullName, method.Name, argument.Value);
}
}
Funziona se chiamato in questo modo: string result = myExpressionService.Get(() => myService.Do(1));
L'output è: Namespace.IMyService.Do(1)
Puoi estenderlo / aggiornarlo per gestire il tuo scenario.
Funzionerebbe anche (anche se non è particolarmente elegante):
public static string MethodCallExpressionRepresentation(this LambdaExpression expr)
{
var expression = (MethodCallExpression)expr.Body;
var arguments = string.Join(", ", expression.Arguments.OfType<MemberExpression>().Select(x => {
var tempInstance = ((ConstantExpression)x.Expression).Value;
var fieldInfo = (FieldInfo)x.Member;
return "\"" + fieldInfo.GetValue(tempInstance).ToString() + "\"";
}).ToArray());
return expression.Object.Type.FullName + "." + expression.Method.Name + "(" + arguments + ")";
}
Puoi chiamarlo così:
Expression<Action> expr = c => myService.Do(param1));
var repr = expr.MethodCallExpressionRepresentation(); // Namespace.IMyService.Do("1")