简体   繁体   中英

How to work with InteractiveViews (Entity Framework 6.2)?

I try to use InteractiveViews nuget package to improve first query execution at my code first app.

namespace POC.UnitTests
    {
        [TestFixture]
        public class EntityFrameworkViewCachingTests
        {
        private Stopwatch _watch;
        private FileViewCacheFactory _veiwFactory;
        private static string _path;

        [OneTimeSetUp]
        public void Setup()
        {
            _watch = new Stopwatch();
            _connectionDictionary = new Dictionary<int, SqlConnectionStringBuilder>()
            {
                { 1, new SqlConnectionStringBuilder()
                    {
                        UserID = "UserId",
                        Password = "Password",
                        InitialCatalog = "MyDatabase",
                        DataSource = @"MyDb",
                        ConnectTimeout = 30,
                        MinPoolSize = 0,
                        MaxPoolSize = 100,
                        MultipleActiveResultSets = true,
                    }
            };

            _path = Path.GetFullPath(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, @"..\..\..\", "EFCache.xml"));
            _veiwFactory = new FileViewCacheFactory(_path);

            _watch.Start();

            Start(() =>
            {
                using (var ctx = new ThickDbContext(_connectionDictionary[1].ToString()))
                {
                    InteractiveViews.SetViewCacheFactory(
                        ctx,
                        _veiwFactory
                    );
                }

                Debug.WriteLine($"Work with cache consumed: {_watch.ElapsedMilliseconds} ms.");
            });

            _watch.Stop();
        }

        [Test]
        [TestCase(1)]
        public void QueryExecutionPerfomanceTest(int id)
        {
            // Arrange.
            var sqlConnection = _connectionDictionary[id].ToString();

            // Act.
            _watch.Reset();
            _watch.Start();

            //Create dbContext, work with them and dispose it.
            using (var dbContext = new ThickDbContext(sqlConnection))
            {
                var result = dbContext.RESOURCES.SingleOrDefault(r => r.RESOURCEID == id);

                _watch.Stop();

                //Fill dynamic DTO.
                _info = new QueryDataDTO
                {
                    Id = id,
                    DurationTime = _watch.ElapsedMilliseconds,
                    Source = typeof(RESOURCE).Name,
                };

                // Assert.
                Debug.WriteLine($"id: {_info.id}. Duration: {_info.DurationTime} ms.");
            }
        }

        private void Start(Action a)
        {
            // Sync.
            a.Invoke();
        }
    }
}

I've been expected that pre-generation views will greatly impove perfomance at first query execution, but I get in general the equal results before and after generating EFCache.xml.

Also i read one post ( https://github.com/moozzyk/EFInteractiveViews/issues/7 ), but actually did not understand: Actually InteractiveViews works with EF 6.2 or not )

Both results (after and before view generation) show:

Work with cache consumed: 7518 ms.
id: 1. Duration: 3007 ms.

Thus, total time: 10.525

Work with cache consumed: 7363 ms.
id: 1. Duration: 1968 ms."

Thus, total time: 9.331

Q: Тhe difference is negligible ( ~ 13%) Where am I wrong with my implementation?

PS I work with very big dbContext to get the more obvious result (482 Entities).

So, i've looked at InteractiveViews nuget package source code and have concluded that it was effective on old Entity Framework version, but didn't such now. (EF 6.2) The WorkFlow is build so that it invokes SetViewCacheFactory method in the beginning to register itself.

In that method ((IObjectContextAdapter)context).ObjectContext initialization is extremely slow if you have "thick" model ( 482 entities in my case -takes 8 sec.).
The worst of this that this method is done at each first execution , wheather cache file is already done or it isn't ). Ps I think it necessary for check current database state. (

var storageMappingItemCollection = 
                (StorageMappingItemCollection)context.MetadataWorkspace.GetItemCollection(DataSpace.CSSpace);)

Second part ( It's about loading/ writing view cache xml file ) works with subsequent queries and actually no better build-in caching mechanism). Because subsequent queries very fast in both cases. When I noticed InteractiveViews package, I thought It help me improve my first query execution after I create cache file,

I think I will be skip slow default initialization processes and instead of that will be read all appropriate information from cache file, but it work in other way ( as I describe above)

Ps if I'm wrong please correct me

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM