QueryTrackingBehavior has no Effect on DbContext
Asked Answered
L

1

6

Perhaps my expectation requires resetting.

I was doing a proof of concept for a "non-tracking" context. In the constructor of the context, I added the following lines:

ChangeTracker.QueryTrackingBehavior = QueryTrackingBehavior.NoTracking;
ChangeTracker.Tracked += ChangeTracker_Tracked;

and the following handler:

private void ChangeTracker_Tracked(object sender, Microsoft.EntityFrameworkCore.ChangeTracking.EntityTrackedEventArgs e)
{
    Debug.WriteLine("Tracking has commenced");
}

My expectation was that if I added an entity to the context, the Tracked handler would not fire because of the NoTracking tracking behavior configuration. But when I add an entity, sure enough, the event fires!

var pub = new Publishers
{
    Name = "Blabla"
};
var ctx = serviceProvider.GetService<LibraryNoTrackingContext>();
ctx.Publishers.Add(pub);

By my observation, the QueryTrackingBehavior configuration does not seem to be working, as change tracking is happening.

Have I got that wrong? If so, how is the No Change Tracking meant to work?

Note: I also tried the following code:

serviceCollection.AddDbContext<LibraryNoTrackingContext>(
        o =>
        {
            o.UseSqlServer(configuration.GetConnectionString("Default"));
            o.UseQueryTrackingBehavior(QueryTrackingBehavior.NoTracking);
        });
Langbehn answered 21/7, 2020 at 4:2 Comment(0)
L
12

Ok, I figured this out with a bit of experimentation. I'll leave this answer here for people looking into this.

The QueryTrackingBehavior of QueryTrackingBehavior.NoTracking is doing what it should be doing.
My comprehension was the problem.

If you retrieve data, using a "no tracking" context, those entities will not be added to the ChangeTracker.

However, if you add entities to the context, even if it is a "no tracking" context, those entities will be tracked i.e. they will be added to the ChangeTracker.

So, a "no tracking" context is still of value, if you want to use it for requests that will do not more than retrieve data. Every entity retrieved will not be tracked.

If you find yourself adding an entity to such a context, you may want to ask yourself why you need to be doing that.

Langbehn answered 23/7, 2020 at 23:32 Comment(1)
Thanks for this - I was looking for confirmation that QueryTrackingBehavior.NoTracking in the constructor was obeyed. Personally, I use that option by default to speed up queries, and explicitly call the appropriate methods when modifying/inserting/deleting data. 95% of my queries are reads - so in terms of your last sentence, I do that all the time!!Pulse

© 2022 - 2024 — McMap. All rights reserved.