1

I am refactoring an MVC 3 application, and moved a set of similar items into a partial view so I can keep that template DRY. Since the pieces don't all have the exact same properties, I am creating anonymous types like this:

var model1 = new { Description = "description 1", Message = "message 1" }

and passing them to the partial view like so:

@Html.Partial("_Partial", model1)

The partial view is then attempting to render certain blocks based on existence of a specific property, i.e.

@if (Model.Description != null) { @Model.Description }

My issue is that even though I can see and navigate the Model object in the watch window during execution, I get a RuntimeBinderException in the if test that states 'object' does not contain a definition for 'ShowApplied'. I can obtain the values through reflection by calling (Model.GetType().GetProperty("ShowApplied").GetValue(Model)), but would much rather use the format shown in my code sample. I have been unable to find a clean solution...

  1. How can I pass an anonymously-typed object to a partial view and access its properties directly? I feel like there is something simple I'm missing...
  2. Why am I able to see the Model properties while debugging, but not access them from code?

EDIT

  • I am specifying @model dynamic.
  • Using an interface requires creating non-anonymous types because, as this answer explains,

An anonymous type cannot be cast to any interface or type except for object.

Community
  • 1
  • 1
brichins
  • 3,825
  • 2
  • 39
  • 60
  • Do you specify your model within the partialview as: `@model dynamic` – David Tansey Jun 01 '15 at 21:41
  • @DavidTansey I did specify `dynamic`, but it made no difference – brichins Jun 01 '15 at 21:43
  • You could bind your partial views to interfaces instead. Then have your various classes implement the appropriate interface you need. – Jasen Jun 01 '15 at 21:46
  • @Jasen That may be a good solution; having Intellisense back would be an added bonus. – brichins Jun 01 '15 at 21:51
  • possible duplicate of [send object through ViewData.Model in asp.net mvc](http://stackoverflow.com/questions/29409811/send-object-through-viewdata-model-in-asp-net-mvc) –  Jun 01 '15 at 22:03
  • @StephenMuecke Close enough - I was unable to find that before posting, but it addresses my issue and is close enough to close my question as a duplicate. Thanks for finding that. – brichins Jun 01 '15 at 22:11

1 Answers1

0

Insights from the comments (thank you) imply I have 2 options, since (as the answer to the linked question points out),

Anonymous types are internal, so their properties can't be seen outside their defining assembly.

and therefore are inaccessible to the Razor binding engine.

  1. Use @Html.DisplayFor("amount") and deal with not having IntelliSense, reference lookups, etc.

  2. Create classes that implement a common interface and bind my partial view to that interface.

brichins
  • 3,825
  • 2
  • 39
  • 60
  • [This article](http://www.gregshackles.com/anonymous-view-models-in-asp-net-mvc-using-dynamics/), linked from the accepted answer to the linked question, points out a 3rd option - `ExpandoObject`. I haven't tried this myself yet, but will likely proceed with creating classes rather than teach my team about ExpandoObject, which won't be available to all of our projects. – brichins Jun 01 '15 at 22:20
  • Tried out `ExpandoObject` just for kicks - the article outlines an extension for reflection on a dynamic. Otherwise the `View/Partial` call throws a compliation error: `System.Web.Mvc.HtmlHelper' has no applicable method named 'Partial' but appears to have an extension method by that name. Extension methods cannot be dynamically dispatched. Consider casting the dynamic arguments or calling the extension method without the extension method syntax.` – brichins Jun 01 '15 at 22:31