andrewb andrewb - 4 years ago 113
C# Question

Entity is not saved to database via WebApi call

I am trying to insert an item using Entity Framework via a WebApi action. The context seems to show that the item has been saved, but when I check in the underlying database the item was not saved.

The HelpRequest parameter in PostHelpRequest is resolved correctly (it matches what I include in the PostMan body data)

Here is the action:

public class HelpRequestController : ApiController
{

public HttpResponseMessage PostHelpRequest(HelpRequest item)
{
var context = new MyDbContext();
try
{
using (var newcontext = new MyDbContext())
{
newcontext.HelpRequests.Add(item);
newcontext.SaveChanges();
}
}
catch (Exception ex)
{
throw new Exception(ex.Message);
}

var response = Request.CreateResponse<HelpRequest>(HttpStatusCode.Created, item);
string uri = Url.Link("DefaultApi", new { id = 0 });
response.Headers.Location = new Uri(uri);
return response;
}


My context:

public class MyDbContext : DbContext
{

public DbSet<HelpRequest> HelpRequests { get; set; }

}


My generated model:

public partial class HelpRequest
{
public int Id { get; set; }
public string Title { get; set; }
public string Message { get; set; }
public System.DateTime CreateDate { get; set; }
public Nullable<bool> Responded { get; set; }
}


I am testing this via PostMan and my body data is set to raw, json

{"Title":"Title1","Message":"Message1","CreateDate":"2017-02-05T10:03:35.258"}


The Id column in the database is set as primary and identity.

Edit:

I have found the issue, but not sure how to solve it.

When I step through the code and look at newcontext.Database.ConnectionString it is referencing a SQLExpress database - it seems it made one for the project.

However, when I open up the model and look at the connection string, it is referencing the correct server and database.

Why is the context being assigned the wrong connection string?

Edit: connection string and context constructor

<connectionStrings>
<add name="connname1" connectionString="metadata=res://*/Model1.csdl|res://*/Model1.ssdl|res://*/Model1.msl;provider=System.Data.SqlClient;provider connection string=&quot;data source=servername;initial catalog=mydatabase1;user id=andrewb;password=hahayeahright;MultipleActiveResultSets=True;App=EntityFramework&quot;" providerName="System.Data.EntityClient" />
</connectionStrings>


Constructor:

public MyDbContext()
{
Database.Log = sql => System.Diagnostics.Debug.Write(sql);
}


Final edit: The solution was that I need to set the constructor in my context with the name of the connection string I want to use. See Igor's answer.

Answer Source

Check your web.config section connectionStrings. Ideally you create a unique name for your connection string and use that name in the constructor of your DbContext. Even easier is to pass that name through in the default constructor to the parameterized constructor of DbContext.

MyDbContext.cs

public class MyDbContext : DbContext
{
    public MyDbContext() : base("Name=bcard_portal")

    public DbSet<HelpRequest> HelpRequests { get; set; }
}

web.config

<connectionStrings>
  <add name="bcard_portal" connectionString="data source=servername;initial catalog=mydatabase1;user id=andrewb;password=hahayeahright;MultipleActiveResultSets=True" providerName="System.Data.SqlClient" />
</connectionStrings>

Side note: If you are using EF6 and code first with DbContext then use a standard ADO.NET db connection string in your web.config, not the convoluted version that the (older) edmx designer makes use of.

Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download