Почему viewmodel modelstate проверяет свойство навигации объекта?

У меня проблема с простой проверкой во время контроллера Создать действие для объекта ARTICLE. Я использую базу данных EF 4 в первую очередь. Объект ARTICLE используется в качестве внешнего ключа в объекте ACTION(ACTION.ARTICLE_id). Вот почему инструмент генерации кода добавляет свойство навигации к объекту ARTICLE, даже если оно не имеет особого смысла. Каждый раз, когда я обновляю сущности, выражение появляется в форме ниже (СТАТЬЯ). Я проверял весь внешний ключ много раз снова. Я действительно не знаю, что делать с этой ошибкой, чтобы сделать чистый солутон, а не просто очистить ошибку в действии контроллера. Все - даже вид - леса.

Действие:

    [HttpPost]
    [Authorize(Roles = "ARTICLE_ADMIN")]
    public ActionResult Edit(ARTICLE article)
    {
        if (ModelState.IsValid)
        {
            article.date_modified = DateTime.Now;

            string newimage = this.Request.Form["preview_image_filename"];
            string oldimage = this.Request.Form["original_image_filename"];

            if (newimage.NotNullOrEmpty())
            {
                article.preview_image = newimage;
            }
            else
            {
                article.preview_image = oldimage;
            }

            db.Entry(article).State = EntityState.Modified;
            db.SaveChanges();
            return RedirectToAction("Index");
        }

        article.date_modified = DateTime.Now;

        ViewBag.ARTICLE_CATEGORY_id = new SelectList(db.ARTICLE_CATEGORY, "ARTICLE_CATEGORY_id", "description", article.ARTICLE_CATEGORY_id);
        ViewBag.ARTICLE_STATUS_id = new SelectList(db.ARTICLE_STATUS, "ARTICLE_STATUS_id", "description", article.ARTICLE_STATUS_id);
        ViewBag.WEB_USER_id = new SelectList(db.WEB_USER, "WEB_USER_id", "login", article.WEB_USER_id);
        return View(article);
    }

Я использую эту модель сущности, созданную с помощью инструмента генерации кода с добавленными аннотациями в классе метаданных, это не может быть проще

public partial class ARTICLE
{
    public ARTICLE()
    {
        this.PROGRAM_WEEK_DAY_ITEM = new HashSet<PROGRAM_WEEK_DAY_ITEM>();
        this.STORAGE = new HashSet<STORAGE>();
        this.SHOW = new HashSet<SHOW>();
        this.ACTION = new HashSet<ACTION>();
    }

    public int ARTICLE_id { get; set; }
    public System.DateTime date_created { get; set; }
    public Nullable<System.DateTime> date_modified { get; set; }
    public string title { get; set; }
    public string html { get; set; }
    public int WEB_USER_id { get; set; }
    public int ARTICLE_STATUS_id { get; set; }
    public int ARTICLE_CATEGORY_id { get; set; }
    public Nullable<System.DateTime> date_published { get; set; }
    public string preview_image { get; set; }

    //code generation tool added those navigation props
    public virtual ARTICLE_CATEGORY ARTICLE_CATEGORY { get; set; }
    public virtual ARTICLE_STATUS ARTICLE_STATUS { get; set; }
    public virtual WEB_USER WEB_USER { get; set; }
    public virtual ICollection<PROGRAM_WEEK_DAY_ITEM> PROGRAM_WEEK_DAY_ITEM { get; set; }
    public virtual ICollection<STORAGE> STORAGE { get; set; }
    public virtual ICollection<SHOW> SHOW { get; set; }

    //this one causes trouble I think, but no clue why
    public virtual ICollection<ACTION> ACTION { get; set; }
}

класс метаданных - просто отображать имена и форматы:

public class ARTICLE_Metadata
{
    [Key]
    public int ARTICLE_id { get; set; }

    [Display(Name="Vytvořeno")]
    public System.DateTime date_created { get; set; }

    [Display(Name = "Změněno")]
    public Nullable<System.DateTime> date_modified { get; set; }

    [Display(Name = "Publikováno")]
    [DisplayFormat(DataFormatString = "{0:MM/dd/yyyy}", ApplyFormatInEditMode = true)]
    public Nullable<System.DateTime> date_published { get; set; }

    [Display(Name = "Titulek článku")]
    public string title { get; set; }

    [Display(Name = "Obsah článku")]
    [UIHint("tinymce_full"), AllowHtml]
    public string html { get; set; }

    [Display(Name = "Vytvořil")]
    public int WEB_USER_id { get; set; }

    [Display(Name = "Status")]
    public int ARTICLE_STATUS_id { get; set; }

    [Display(Name = "Kategorie")]
    public int ARTICLE_CATEGORY_id { get; set; }

    [Display(Name = "Náhledový obrázek")]
    public string preview_image { get; set; }
}

и, наконец, в виде бритвы:

@using (Html.BeginForm("Create", "Articles", FormMethod.Post, new { @class = "base-form" }))
{
@Html.ValidationSummary(true)

<fieldset>
    <legend>Nový článek</legend>

    @Html.DatePickerFor(model => model.date_published, false)
    @Html.HiddenFor(model => model.WEB_USER_id)

    <p class="editor-label">
        @Html.LabelFor(model => model.ARTICLE_STATUS_id)
        @Html.DropDownList("ARTICLE_STATUS_id")
        @Html.ValidationMessageFor(model => model.ARTICLE_STATUS_id)
    </p>

    <p class="editor-label">
        @Html.LabelFor(model => model.ARTICLE_CATEGORY_id)
        @Html.DropDownList("ARTICLE_CATEGORY_id")
        @Html.ValidationMessageFor(model => model.ARTICLE_CATEGORY_id)
    </p>

    <p class="editor-label">
        @Html.LabelFor(model => model.title)
        @Html.EditorFor(model => model.title)
        @Html.ValidationMessageFor(model => model.title)
    </p>

    <div class="html-editor">
        @Html.EditorFor(model => model.html)
    </div>

    <p>
        <input type="submit" value="Vytvořit" class="submit" />
    </p>
</fieldset>
}

Когда модель проверяет и приходит к действию контроллера, ModelState.IsValid == false, ModelState сообщает об ошибке в свойстве ACTION, которого даже нет в таблице и не должно быть там, это свойство навигации.

Исключением является ошибка: преобразование параметра из типа "System.String" в тип "namespace.ACTION" не выполнено, поскольку преобразователь типов не может преобразовать эти типы.

Я пытался прикрепить изображение в режиме отладки, но эта сеть не позволила мне это сделать. У меня есть другие объекты, управляемые через контроллеры, и я смотрю так же - около 30, где этого не происходит.

Как избавиться от этой проблемы, не создавая дополнительную модель с теми же свойствами, но без навигационных? Или просто запретите включение этого свойства навигации в проверку. Или это новая ерунда от Microsoft?

1 ответ

Решение

Иногда эти странные ошибки в db-first происходят из-за того, что имя свойства навигации в объекте совпадает с именем другого объекта. Я сам иногда сталкивался с этими проблемами, и я не знаю точно, в чем причина.

В любом случае, переименование этого свойства навигации должно избавить вас от этой странной ошибки...

Другие вопросы по тегам