как можно инструктировать структуру сущностей не обновлять свойство модели - PullRequest
3 голосов
/ 13 октября 2011

Я использую Asp.net MVC и Entity Framework (код ниже только для демонстрации)

У меня есть модель, как показано ниже

  public class Person
    {
        [Key]
        public int Id { get; set; }

        [Required]
        public string FirstName { get; set; }

        /*Time at which person was created*/
        public DateTime CreatedOn { get; set; }  /*should not change once created*/
    }

Во время создания + вставки нового человека я вручную устанавливаю свойство CreatedOn datetime.

При обновлении

My View имеет только одно текстовое поле

 @using (Html.BeginForm())
        {
            @Html.LabelFor(a => a.FirstName) 
            @Html.EditorFor(a => a.FirstName) 
            @Html.ValidationMessageFor(a => a.FirstName)            
            <br />
            <input type="submit" name="name" value="submit" />
}

Контроллер

    [HttpPost]
    public ActionResult EditPerson(Person person)
    {
        if (ModelState.IsValid)
        {
            db.Entry(person).State = EntityState.Modified;
            db.SaveChanges();

            /* ----------------
              Error here
              ----------------- 
             */

            return RedirectToAction("ListPerson");
        }
        return View(person);            
    }

Я получаю сообщение об ошибке в указанном месте в моем коде, ошибка: The conversion of a datetime2 data type to a datetime data type resulted in an out-of-range value. Ошибка кажется очевидной, поскольку person объект, полученный внутри контроллера, имеет значение времени по умолчанию, и структура сущностей пытается обновить это поле.

Мой вопрос заключается в том, как я могу указать платформе сущностей не обновлять свойство . Предположим в приведенном выше случае, если для CreatedOn свойства, которое я говорю, чтобы сущность не обновляла его, я не получу ошибку.

Я пробовал атрибут [Editable(false)] на CreatedOn, но он не работал.

Есть несколько вариантов, например, перед обновлением я сначала загружаю существующую сущность из базы данных и копирую свойство selectedOn .....

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

Редактировать 1

Сначала я использую код.

1 Ответ

2 голосов
/ 13 октября 2011

Конкретная ошибка, которую вы получаете, заключается в том, что для CreatedOn установлено значение по умолчанию. Когда вы выполняете обратную передачу, вам нужно будет загрузить объект из базы данных, обновить его и затем сохранить. Этим вы остановите эту конкретную ошибку, с которой вы столкнулись.

Похоже, что вы используете свою модель сущности в качестве модели в вашем контроллере. Я бы не рекомендовал это. Создавая модель специально для публикации, вы можете удалить любые не редактируемые поля из вашей модели. Затем вы должны скопировать значения модели из ViewModel в вашу модель Entity. Это не позволяет пользователям редактировать свойства, которые вы, возможно, не хотите, чтобы они редактировали.

public class PersonViewModel
{
    [Key]
    public int Id { get; set; }

    [Required]
    public string FirstName { get; set; }
}

Основная причина, по которой это хорошая идея, заключается в том, что кто-то может попытаться угадать, какие значения также могут работать. Например, если у вас есть свойство в вашем Person объекте с именем IsAdministrator, и я должен был перехватить сообщение и добавить &IsAdministrator=on&Adminstrator=on&Admin=on (для покрытия нескольких баз), то ModelBinder примет это значение и применит его к модели. , Теперь я только что стал администратором в вашей системе. Я понимаю, что это много работы, если у вас много моделей, но никогда не стоит использовать ваши модели сущностей для сообщений.

Вы также можете использовать атрибут Bind, чтобы ограничить элементы, связанные картографом.

public ActionResult EditPerson([Bind(Exclude = "CreatedOn")] Person person)

Это должно помешать связующему привязывать это конкретное свойство. Однако это не решит вашу проблему, поскольку при создании объекта person всегда устанавливается значение по умолчанию. Единственный способ исправить это - загрузить ваш объект из базы данных, а затем обновить / сохранить его.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...