I'm trying to use a Lambda expression and reflection to get a member hierarchical name (rather than using a text constant), to enforce compile-time errors if my control binding information is invalid.
This is in an ASP.NET MVC project, but it's not an MVC-specific question AFAIK. EDIT: Specifically, I want the following to evaluate to true:
string fullname = GetExpressionText(model => model.Locations.PreferredAreas);
"Locations.PreferredAreas" == fullname;
Instead I get a compile error:
Error 4: Cannot convert lambda expression to type 'System.Linq.Expressions.LambdaExpression' because it is not a delegate type.
Why does the parameter work in the second case below, but not the first?
// This doesn't compile:
string tb1 = System.Web.Mvc.ExpressionHelper.
GetExpressionText(model => model.Locations.PreferredAreas);
// But this does:
MvcHtmlString tb2 =
Html.TextBoxFor(model => model.Locations.PreferredAreas);
Here's the relevant code from the ASP.NET MVC Codeplex project. It looks to me like it passes the same parameter through to the same method:
// MVC extension method
public static MvcHtmlString TextBoxFor<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TProperty>> expression, IDictionary<string, object> htmlAttributes) {
ModelMetadata metadata = ModelMetadata.FromLambdaExpression(expression, htmlHelper.ViewData);
return TextBoxHelper(
htmlHelper,
metadata,
metadata.Model,
ExpressionHelper.GetExpressionText(expression),
htmlAttributes);
}
// MVC utility method
public static string GetExpressionText(LambdaExpression expression) {
// Split apart the expression string for property/field accessors to create its name
// etc...
The error message is correct. A lambda can be converted to a compatible delegate type, D, or to an expression-of-compatible-delegate-type Expression<D>
. Expression<Func<TM, TP>>
is one of those. "LambdaExpression" is neither of those. Therefore you get an error trying to convert the lambda to LambdaExpression, but not to an actual expression tree type. There has to be a delegate in there somewhere.