MVC Razor dinamik modeli, 'nesne', 'ÖzellikAdı' için tanım içermiyor


106

Razor görünüm altyapısıyla MVC 3 kullanma. Bu Görünüme sahibim:

@model dynamic
@{
    var products = (List<ListItemBaseModel>)Model.Products;
    var threshold = (int)(Model.Threshold ?? 1);
    var id = Guid.NewGuid().ToString();
}

Bu kod kullanılarak başka bir görünümden çağrılır:

@Html.Partial("PartialViewName", new { Products = Model, Threshold = 5 })

Her iki Görünümde de hata ayıkladığımda ve Modeli izlediğimde, doğru nesneyi içeriyor gibi görünüyor. Kodu çalıştırdığımda "var products =" satırında şunu söyleyen bir hata alıyorum:

"nesne", "Ürünler" için bir tanım içermiyor

Biri bana neden bu hatayı aldığımı açıklayabilir mi? Yine, Model nesnesini hata ayıklama modunda izlediğimde iyi görünüyor (2 özelliğe sahip: Ürünler ve Eşik)


Yanıtlar:


150

Anonim bir sınıfın bir örneğini görünüm modeli olarak mı geçiriyorsunuz? Bunu az önce denedim (CSHTML'de dinamik görünüm modeli) ve anonim bir sınıf kullanırken sizinle aynı hatayı aldım, ancak adlandırılmış bir sınıf oluşturursam iyi çalıştı. Aradım ama bunu hiçbir yerde görmedim.

// error
return View(new { Foo = 1, Bar = "test" });

// worked
return View(new TestClass { Foo = 1, Bar = "test" });

DÜZENLEME # 1:

David Ebbo'ya göre anonim bir türü dinamik olarak yazılmış bir görünüme geçiremezsiniz çünkü anonim türler olarak derlenir internal. CSHTML görünümü ayrı bir derlemede derlendiğinden, anonim türün özelliklerine erişemez.

DÜZENLEME # 2:

David Ebbo, yazısını şu açıklamayla düzenledi:

Not (12/22/2011): MVC 3 dinamik için doğrudan desteğe sahip olduğundan, aşağıdaki teknik artık gerekli değildir. Bu gönderi aslında özelliğin MVC'ye entegre edilmesine yol açan şeydi!


1
Düzenlemeyi bilmek güzel. Ben de aynı sorunu yaşadım ve oradaki WTF'yi anlamadım. Açıklama için teşekkürler.
Yanick Rochon

18
DÜZENLEME # 2, şimdi (MVC> 3) "hata" ile işaretlenmiş satıra yapmanın mümkün olduğunu gösteriyor? return View(new { Foo = 1, Bar = "test" });? Çünkü MVC 4 kullanıyorum ve hala "nesne Foo için bir tanım içermiyor"
spor

@ beni de spor yapıyor ... bir çözüm buldunuz mu? (yanında ToExpando)
Alex

2
Şimdi 2018'de ASP.NET Core 2.1 ve Razor görünümlerini kullanarak, orijinal sorudaki hatanın beni hala ısırdığını görüyorum. Bu yüzden, MVC 3'ün tüm bunları düzeltmesiyle ilgili bu konuşmanın neyle ilgili olduğunu bilmiyorum, çünkü hala bozuk görünüyor.
Andrew Arnott

41

.NET 4.0'da Anonim türler kolayca ExpandoObjects'e dönüştürülebilir ve bu nedenle tüm sorunlar, dönüşümün ek yüküyle giderilir. Buraya göz atın


Rica ederim. Belki bu, anonim türleri daha kullanışlı hale getirmek için M $ 'ı
başlatır

Bu Kısmi Ürünler için de geçerli mi?
Partial'lerin

1
Ne parçaları? Bir örnek verebilir misiniz?
Adaptabi

27

Bunun dahili özelliklere sahip anonim türlerle ilgisi yoktur.

Öyle mükemmel mümkün kısmi görünümüne bir görünümden anonim türlerini geçmek

Bugün aynı sorunla karşılaştım ve anonim türleri ve bunların içsel internalözelliklerini iletme sorunuyla (doğrudan) ilgisi yoktu .

Bu nedenle, OP'lerin sorusuyla ilgili olarak, @ Lucas'ın cevabı önemsizdir - geçici çözüm işe yarayacak olsa bile .

OPs sorusunda, anonim bir tür, montaj X'teki bir görünümden, montaj X'teki bir parçaya aktarılıyor , bu nedenle David Ebbo'nun özelliklerin anonim türler için dahili olmasıyla ilgili ana hatlarını çizdiği sorunun hiçbir önemi yok; görünüm, kısmi ve anonim tür için derlenmiş tipleri aynı montaj içerdiği .

Öyleyse, anonim bir tipin bir bakış açısıyla kısmi bir görüşe geçmemesine neden olan şey nedir?

En azından benim durumumda , AYNI KLASÖR'de çözülemeyen bir model türü belirten başka bir görünüme sahip olmanın neden olduğunu keşfettim . Görünümler çalışma zamanında derlenir ve bu nedenle, çalışma zamanında görünümleri derleme başarısızlığı da dinamik türleri derlemede başarısızlık anlamına gelir ve kısmi yalnızca bir object. Neler olduğu hemen belli değil, ancak OP'lerin özel örneğinde (ve benimkinde) sorunun nedeni muhtemelen budur.

İlginçtir ki, model türü doğruysa, ancak görünümün başka bir bölümü derlenmezse, anonim türlerin aynı şekilde etkilenmemesi ilginçtir. Bu, Razor'un görünümün bileşen parçalarının dinamik derlemesini nasıl böldüğüne bağlı olmalıdır.

Sorun yaratan görünümü düzelttikten sonra, tüm çözümü yeniden oluşturun veya düzeltilip düzeltilmediğini kontrol etmeden önce projeyi temizleyin ve yeniden oluşturun.

Bununla tekrar yakalanmamanızı sağlamak için, Razor görünümlerinizin derleme zamanı derlemesini csprojdosyanıza ekleyerek etkinleştirebilirsiniz :

<PropertyGroup>
    <MvcBuildViews>true</MvcBuildViews>
</PropertyGroup>

2
Bu sorunumu çözdü - "@model dynamic" kullanmak başlangıçta doğru çözüm gibi görünüyordu, ama aslında beni yanlış yola götürüyordu.
crimbo

Çözümü temizledim, yeniden oluşturdum ve hata gitti .. 121 artı oy yanlış.
maxbeaudoin

Cevabımı,
Lucas

Zaman zaman görünüm derlemesini etkinleştirmek, büyük kod tabanı için her zaman yararlıdır. T4MVC ile ilgili her türlü sorunu, yazım hatalarını, ortaya koyduğu güçlü yazım sayesinde vb. Hataları ortaya çıkarır.
Denis The Menace

Oh, doğru: Burada bir bakış açısından kısmi bir geçişten bahsettiğimizi fark ettim. Bir denetleyiciden bir görünüme değil, benim sorunum bu.
mwardm

9

Aşağıdaki sınıfı çözümünüzün herhangi bir yerine ekleyin (Sistem ad alanını kullanın, böylece herhangi bir referans eklemek zorunda kalmadan kullanıma hazır olur) -

    namespace System
    {
        public static class ExpandoHelper
        {
            public static ExpandoObject ToExpando(this object anonymousObject)
            {
                IDictionary<string, object> anonymousDictionary = HtmlHelper.AnonymousObjectToHtmlAttributes(anonymousObject);
                IDictionary<string, object> expando = new ExpandoObject();
                foreach (var item in anonymousDictionary)
                    expando.Add(item);
                return (ExpandoObject)expando;
            }

        }
    }

Modeli görünüme gönderdiğinizde Expando'ya dönüştürün:

    return View(new {x=4, y=6}.ToExpando());

1
Önce dinamik bir nesne oluşturmak ve sonra bir ExpandoObject oluşturmak benim için gereksiz bir ek yük gibi görünüyor ... Bunun yerine ExpandoObject'i oluşturun ..
Baz1nga

@ Baz1nga Yapamazsınız ... new Expando () {prop = value, ...}, bu da onu sorunlu hale getiriyor. Benzer kullanım için Json.Net'in JObject'ini kullanıyorum.
Tracker1

3
İçinde HtmlHelper olması yanlış geliyor ... public static ExpandoObject ToExpando (bu nesne o) {IDictionary <string, object> expando = new ExpandoObject (); foreach (o.GetType (). GetProperties ()) {expando.Add (yeni KeyValuePair <string, nesne> (propertyInfo.Name, propertyInfo.GetValue (o, index: null))); } return (ExpandoObject) expando; }
erlando

6

dynamicKısmi görünümde Model türünü kullanmak yerine .

Sen kullanarak anonim nesne özelliklerini çağırabilir @ViewData.Eval("foo")yerine @Model.foo.

Ardından @Model dynamicgörünümden kaldırabilirsiniz .

Son zamanlarda Facebook Sosyal Yorumlar Entegrasyonu için görünümler arasında bazı özellikleri aktarırken bu sorunla karşılaştım. Örnek kod:

Html.RenderPartial(@"Layouts/Partials/_Comments", new {currentUrl = Model.CurrentPage.GetAbsoluteUrl(), commentCount = 5 });

Sonra benim görüşüme göre bu div var:

<div class="fb-comments" data-href="@ViewData.Eval("currentUrl")" data-numposts="@ViewData.Eval("commentCount")" data-width="100%"></div>

0

Bu hatayı aldığınızdan emin değilim çünkü geçici çözümü uygulamıyorsunuz. Kısmi görünümde aynı hatayı aldım. çözüm sadece yapıyı temizlemek ve yeniden inşa etmekti. sözdizimi doğruysa, kodun çalışması gerekir, ancak ustura motoru kod değişikliklerini doğru şekilde güncellemiyor olabilir.


0

Sözlük kullanarak bu sorunu çözdüm.

 @Html.Partial("_Partial", new Dictionary<string, string> { { "Key1", "Val1" }, { "Key2", "Val2" }, { "Key3", "Val3" } });

-6

dynamicTipi kullanmak için Microsoft.CSharpmontaja başvurmanız gerekir

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.