-1

I'm very new in MVC 5 and EF6 and need help please.

I have two classes and one single View, I can get the values of class Person but class Address is always null.

I tried use constructor and Bind in PersonController/Create

My classes:

public partial class Person
{
    [Key]
    public int PersonID { get; set; }
    [Required]
    [StringLength(40)]
    public string Name { get; set; }
    [StringLength(40)]
    public string Email { get; set; }
    public virtual Address AddressDI { get; set; }
}

public class Address
{
    [Key]
    public int AddressID { get; set; }
    [Required]
    public string City { get; set; }
    [Required]
    public string Street { get; set; }
    [Required]
    public virtual Person PersonDI { get; set; }
}

Controller

public class ContatoController : Controller
{
    private readonly Address _address;

    public PersonController()
    {
         _address = new Address();
    }

    HttpPost]
    ValidateAntiForgeryToken]
    public ActionResult Create([Bind(Include = @"Name,Email,AddressID,City,")] Person person, Address address)
    {
        if (ModelState.IsValid)
        {   
            db.Person.Add(person);
            db.SaveChanges();
            return RedirectToAction("Index");
        }
        return View(person);
    }

    /* Other Actions and stuffs */
}

This is my 3 days pain :(

user3062
  • 3
  • 4
  • Show your view (which is clearly wrong if its not binding) –  Nov 20 '17 at 21:53
  • I will try this: https://stackoverflow.com/questions/5550627/two-models-in-one-view-in-asp-mvc-3 – user3062 Nov 20 '17 at 23:13
  • That would be crazy in your case - your `Person` model already contains a property for `Address` so if you have generated you view correctly (which you have not bothered to show) then it will be correctly bound to the `Address` of `Person` (and you do not need you `Address address` parameter in the POST method which would not be bound anyway) –  Nov 21 '17 at 00:01
  • The problem was that I changed the View after scafolding. But now is working because I created a Partial View for Person and Address. – user3062 Nov 21 '17 at 00:18
  • So you changed it incorrectly but are expecting us to guess what it is. And in any case your editing data so always use a view model. –  Nov 21 '17 at 00:19

1 Answers1

0

I don't know what exactly you're trying to achieve here. If you want to post a person class then just post the person:

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create(Person person)
{ 
    if (ModelState.IsValid)
    {   
        db.Person.Add(person);
        db.SaveChanges();
        return RedirectToAction("Index");
    }
    return View(person);
}

and in the view, something like:

@model Partner
@Html.BeginForm("Create","Contato", FormMethod.Post){
  @Html.TextboxFor(p => Model.AddressDI.City)
}

Also it is a common practice to send data across controller actions in wrapper classes referred to as viewModels. ViewModels usually contain everything that needs to be posted or displayed at a given moment in the view, as well as potential parameters for the view.

something like:

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create(ContatoViewModel viewModel)
{
    var person = new Person();
    person.Name = viewModel.Name;
    person.Email = viewModel.Email;
    person.AddressDI = viewModel.AddressDI

    if (ModelState.IsValid)
    {   
        db.Person.Add(person);
        db.SaveChanges();
        return RedirectToAction("Index");
    }
    return View(viewModel);
}

Being honest I can't say more without seeing what you're doing in the view.

More on MVVM pattern: https://msdn.microsoft.com/en-us/library/hh848246.aspx

There are tools available such as Jimmy Bogard's AutoMapper which help with copying the values between the view models and the classes.

qubits
  • 1,227
  • 3
  • 20
  • 50