RavenDB 针对索引的惰性搜索返回未初始化的统计信息

发布于 2024-12-13 16:28:17 字数 3725 浏览 4 评论 0原文

我正在尝试对 raven 数据库运行惰性查询并获取总匹配结果的计数。我发现当我查询静态索引时,惰性搜索在查询具体化时不会初始化统计信息,但否则它会正常返回。 下面是证明这种行为的测试。

[TestFixture]
public class CanSearchLazily
{
    private const int ServerPort = 8085;
    private readonly string _serverAddress = @"http://localhost:{0}".For(ServerPort);

    [Test]
    public void CanGetTotalResultsFromStatisticsOnLazySearchAgainstDynamicIndex()
    {
        CanGetTotalResultsFromStatisticsOnLazySearchAgainstAnIndex();
    }

    [Test]
    public void CanGetTotalResultsFromStatisticsOnLazySearchAgainstStaticIndex()
    {
        CanGetTotalResultsFromStatisticsOnLazySearchAgainstAnIndex("UserByFirstName");
    }

    private void CanGetTotalResultsFromStatisticsOnLazySearchAgainstAnIndex(string indexName = "")
    {
        BuilderSetup.DisablePropertyNamingFor<User, string>(x => x.Id);

        var users = Builder<User>.CreateListOfSize(2000).All()
            .With(x => x.FirstName = GetRandom.FirstName())
            .With(x => x.LastName = GetRandom.LastName())
            .Build();

        using (GetNewServer())
        using (var store = new DocumentStore { Url = _serverAddress }.Initialize())
        {
            using (var session = store.OpenSession())
            {
                users.ForEach(session.Store);
                session.SaveChanges();
                IndexCreation.CreateIndexes(typeof(UserByFirstName).Assembly, store);
                session.Query<User, UserByFirstName>().Customize(x => x.WaitForNonStaleResults()).ToList();
            }

            using (var session = store.OpenSession())
            {
                var names = session.Query<User>().Select(u => u.FirstName).Distinct().Take(15).ToList();

                RavenQueryStatistics stats;

                var query = string.IsNullOrEmpty(indexName) 
                        ? session.Query<User>().Statistics(out stats).Where(x => x.FirstName.In(names))
                        : session.Query<User>(indexName).Statistics(out stats).Where(x => x.FirstName.In(names));

                var results = query.Take(8).Lazily();

                Assert.AreEqual(8, results.Value.ToList().Count);
                Assert.AreEqual(DateTime.Now.Year, stats.IndexTimestamp.Year, "the index should have the current year on its timestamp");
                Assert.IsTrue(stats.TotalResults > 0, "The stats should return total results");
            }
        }
    }

    protected RavenDbServer GetNewServer(bool initializeDocumentsByEntitiyName = true)
    {
        var ravenConfiguration = new RavenConfiguration
        {
            Port = ServerPort,
            RunInMemory = true,
            DataDirectory = "Data",
            AnonymousUserAccessMode = AnonymousUserAccessMode.All
        };

        if (ravenConfiguration.RunInMemory == false)
            IOExtensions.DeleteDirectory(ravenConfiguration.DataDirectory);

        var ravenDbServer = new RavenDbServer(ravenConfiguration);

        if (initializeDocumentsByEntitiyName)
        {
            using (var documentStore = new DocumentStore
            {
                Url = _serverAddress
            }.Initialize())
            {
                new RavenDocumentsByEntityName().Execute(documentStore);
            }
        }

        return ravenDbServer;
    }
}

[Serializable]
public class User
{
    public string Id { get; set; }
    public string FirstName { get; set; }
    public string LastName { get; set; }
}

public class UserByFirstName : AbstractIndexCreationTask<User>
{
    public UserByFirstName()
    {
        Map = users => from user in users
                       select new {user.FirstName};
    }
}

I am trying to run lazy queries against raven db and get the counts on total matching results. I am finding when I query against a static index, a lazy search does not initialize the statistics when the query is materialized, but otherwise it comes back all right.
Below is the test to prove this behaviour.

[TestFixture]
public class CanSearchLazily
{
    private const int ServerPort = 8085;
    private readonly string _serverAddress = @"http://localhost:{0}".For(ServerPort);

    [Test]
    public void CanGetTotalResultsFromStatisticsOnLazySearchAgainstDynamicIndex()
    {
        CanGetTotalResultsFromStatisticsOnLazySearchAgainstAnIndex();
    }

    [Test]
    public void CanGetTotalResultsFromStatisticsOnLazySearchAgainstStaticIndex()
    {
        CanGetTotalResultsFromStatisticsOnLazySearchAgainstAnIndex("UserByFirstName");
    }

    private void CanGetTotalResultsFromStatisticsOnLazySearchAgainstAnIndex(string indexName = "")
    {
        BuilderSetup.DisablePropertyNamingFor<User, string>(x => x.Id);

        var users = Builder<User>.CreateListOfSize(2000).All()
            .With(x => x.FirstName = GetRandom.FirstName())
            .With(x => x.LastName = GetRandom.LastName())
            .Build();

        using (GetNewServer())
        using (var store = new DocumentStore { Url = _serverAddress }.Initialize())
        {
            using (var session = store.OpenSession())
            {
                users.ForEach(session.Store);
                session.SaveChanges();
                IndexCreation.CreateIndexes(typeof(UserByFirstName).Assembly, store);
                session.Query<User, UserByFirstName>().Customize(x => x.WaitForNonStaleResults()).ToList();
            }

            using (var session = store.OpenSession())
            {
                var names = session.Query<User>().Select(u => u.FirstName).Distinct().Take(15).ToList();

                RavenQueryStatistics stats;

                var query = string.IsNullOrEmpty(indexName) 
                        ? session.Query<User>().Statistics(out stats).Where(x => x.FirstName.In(names))
                        : session.Query<User>(indexName).Statistics(out stats).Where(x => x.FirstName.In(names));

                var results = query.Take(8).Lazily();

                Assert.AreEqual(8, results.Value.ToList().Count);
                Assert.AreEqual(DateTime.Now.Year, stats.IndexTimestamp.Year, "the index should have the current year on its timestamp");
                Assert.IsTrue(stats.TotalResults > 0, "The stats should return total results");
            }
        }
    }

    protected RavenDbServer GetNewServer(bool initializeDocumentsByEntitiyName = true)
    {
        var ravenConfiguration = new RavenConfiguration
        {
            Port = ServerPort,
            RunInMemory = true,
            DataDirectory = "Data",
            AnonymousUserAccessMode = AnonymousUserAccessMode.All
        };

        if (ravenConfiguration.RunInMemory == false)
            IOExtensions.DeleteDirectory(ravenConfiguration.DataDirectory);

        var ravenDbServer = new RavenDbServer(ravenConfiguration);

        if (initializeDocumentsByEntitiyName)
        {
            using (var documentStore = new DocumentStore
            {
                Url = _serverAddress
            }.Initialize())
            {
                new RavenDocumentsByEntityName().Execute(documentStore);
            }
        }

        return ravenDbServer;
    }
}

[Serializable]
public class User
{
    public string Id { get; set; }
    public string FirstName { get; set; }
    public string LastName { get; set; }
}

public class UserByFirstName : AbstractIndexCreationTask<User>
{
    public UserByFirstName()
    {
        Map = users => from user in users
                       select new {user.FirstName};
    }
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文