Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

SaveChangesAsync not updating value in database table

This is my Table:Statistics

Id,Depth,RefreshCounter

Sample Records:

Id    Depth      RefreshCounter
 1     1           1
 2     1           0
 3     1           0
 4     1           0

Now what i need to do is whenever i am refreshing the page i need to increment this refreshcounter value by 1 in Database table with Depth 1.

I am calling this method like this on load of my view page:

@Html.Action("IncrementRefreshcounter", "Statistics", new { id = 1})  //for eg:1,2,3,4

Here is my code which does this:

    [ChildActionOnly]
    public ActionResult IncrementRefreshcounter(int id)
       {
         using ( var context = new MyDBContext())
         {
//at each page refresh i would be passing different id to my controller from view.for eg 1,2,3,4
         var data=context.Statistics.where(x=>x.Depth==1 && r.Id==id).FirstorDefualt();
             context.RefreshCounter++;//Increment here RefreshCounter.
             context.SaveChangesAsync();
             return PartialView("xxx")
            }
        }

I am calling this method when my View Loads.Problem is when i run my Application first time and calling this method it successfully updated RefreshCounter by 1 but after that whenever i refresh my page and calling this method it never updated RefreshCounter for any records with Depth=1.

In my sample Records you can see that Id 1 with Depth 1 have refresh counter with value 1 because it was the first time when i have run my application and it has successfully updated that value but after that it is never updating any value for eg:Id 2 Depth 1

It is incrementing only 1 time RefreshCounter but after that it never increments that variable.

Can anybody tell me what the problem is SaveChangesAsync ??

like image 304
Learning-Overthinker-Confused Avatar asked May 22 '15 05:05

Learning-Overthinker-Confused


People also ask

When should I call SaveChangesAsync?

The idea here is that if there is other work you can do (on the server) while the Save operation is in progress, then you should use SaveChangesAsync . Do not use "await". Just call SaveChangesAsync , and then continue to do other stuff in parallel.

How to update data in DbContext?

This can be achieved in several ways: setting the EntityState for the entity explicitly; using the DbContext. Update method (which is new in EF Core); using the DbContext. Attach method and then "walking the object graph" to set the state of individual properties within the graph explicitly.

What does SaveChangesAsync return?

SaveChangesAsync() returns the number of lines changed. It is possible (at least theoretically) that two user will simultenously work to delete the same id in the database.


2 Answers

You have to await the save otherwise the method will continue and your context would go out of scope before saving changes. You have to make the method asynchronous, too.

public **async** Task<ActionResult> IncrementRefreshcounter(int id)
       {
         using ( var context = new MyDBContext())
         {
//at each page refresh i would be passing different id to my controller from view.for eg 1,2,3,4
         var data=context.Statistics.where(x=>x.Depth==1 && r.Id==id).FirstorDefualt();
             context.RefreshCounter++;//Increment here RefreshCounter.
             await context.SaveChangesAsync();
            }
        }
like image 87
Eddie Paz Avatar answered Oct 30 '22 14:10

Eddie Paz


Try this:

   public async Task<ActionResult> IncrementRefreshcounter(int id)
   {
     using ( var context = new MyDBContext())
     {
//at each page refresh i would be passing different id to my controller from view.for eg 1,2,3,4
     var data=context.Statistics.where(x=>x.Depth==1 && r.Id==id).FirstorDefualt();
         context.RefreshCounter++;//Increment here RefreshCounter.
         await context.SaveChangesAsync();
        }
    }

SaveChanges will execute on the current thread and block the thread while waiting for the query to complete, preventing the thread from doing other work, even though the thread is just sitting there waiting for IO.

SaveChangesAsync will kick off the IO command and then free up the request thread to do other work while the IO is in progress. Once the IO completes, the rest of the method is executed on the captured synchronization context.

So for a web server using asyncrhonous APIs for IO bound work enables you to serve more requests with fewer threads and thus makes your application more scalable and it will use much less memory as well as each thread has 1MB of stack space by default.

Synchronous work is like the SaveChanges method. The method call does not return until the changes are saved.

Asynchronous work is like SaveChangesAsync, the method call initiates the operation and returns a Task so you can keep track of it. The changes are then saved in the background some time later and in the mean time you can use the returned Task to keep track of the operation.

like image 21
NeddySpaghetti Avatar answered Oct 30 '22 14:10

NeddySpaghetti