如何在发布帖子请求时避免重复输入?

时间:2015-03-10 03:08:20

标签: c# json entity-framework asp.net-web-api

在ASP.NET中使用嵌套对象发布对象时遇到问题。我有一个Status类,它有一个User对象(发布状态的用户)。以JSON格式发布状态时,它也具有用户对象。问题是,它不是添加状态与该用户,而是添加状态和新用户,这显然不是我想要的。

这是JSON的样子。具有id 2的用户已存在于数据库中,但是当发布此用户时,将创建另一个用户。

{
    "User": {
        "Id": 2,
        "First": "Tobin",
        "Last": "Brown",
        "Email": null,
        "Profile": null,
        "Height": 75,
        "Weight": 165,
        "BirthDate": "1991-04-24T00:00:00"
    },
    "Id": 2,
    "Type": 0,
    "Time": "2015-03-08T11:01:48"
}

用户类:

public class User
{
    [Key]
    public int Id { get; set; }
    public string First { get; set; }
    public string Last { get; set; }
    [DataType(DataType.EmailAddress)]
    public string Email { get; set; }
    public Profile Profile { get; set; }
    public double Height { get; set; }
    public double Weight { get; set; }
    public DateTime BirthDate { get; set; }
    public virtual List<TeamUser> Teams { get; set; }
    [JsonIgnore]
    public virtual List<Status> Statuses { get; set; }
}

状态类:

public class Status
{
    [Key]
    public int Id { get; set; }
    public StatusType Type { get; set; }
    public DateTime Time { get; set; }
    public virtual User User { get; set; }
    public virtual Activity Activity { get; set; }
}

最后,这是我的控制器方法,它使用实体框架处理向数据库添加状态:

[ResponseType(typeof(Status))]
public IHttpActionResult PostStatus(Status status)
{
    if (!ModelState.IsValid)
    {
        return BadRequest(ModelState);
    }
    db.Statuses.Add(Status);
    db.SaveChanges();
    return Ok(status);
}

如果我在JSON中传递用户ID,为什么会创建新用户?

3 个答案:

答案 0 :(得分:1)

由于状态输入是新的,因此实体框架将其所有关联对象视为新对象。您上面的示例可以修改如下

1)将UserId属性添加到Status类 2)使用JSON中相应的用户对象ID设置UserId属性。它现在看起来像这样

{
    "Id": 2,
    "Type": 0,
    "UserId": 2,
    "Time": "2015-03-08T11:01:48"
}

3)在您的控制器中,设置status.User = null

数据库中的Status表应将UserId外键映射到User的ID列。

答案 1 :(得分:0)

我认为您需要在致电EntityState之前将Unchanged设为db.SaveChanges()

如下所示:

db.Entry<User>(status.User).State = EntityState.Unchanged; 

有关详细信息,请访问此MSDN article

答案 2 :(得分:0)

您可能需要将现有用户重新附加到db上下文(如果设置status.User = null不起作用)

if (status.User!=null)
{
    db.Users.Attach(status.User)
    db.Entry<User>(status.User).State = EntityState.Unchanged;
}