【发布时间】:2012-06-25 15:40:35
【问题描述】:
我想将文本文件中的 1 亿个条目(每一行是一个类似 csv 的条目)导入 RavenDB 数据库。最快的方法是什么?
补充说明:
我还没有任何索引(我将在插入数据后创建它们)。 RavenDB 在本地机器上以服务模式运行,没有增强安全性(但是;因为我仍在测试 RavenDB)。该测试将在 2 台不同的机器上运行,1) 2 核 4GB 内存 2) 8 核 12 GB 内存。
我已经将部分数据(200 万个条目)插入到 RavenDB 中,但它并没有我想要的那么快。通过使用 OpenAsyncSession 并为每 1024 条记录调用 SaveChangesAsync 并通过调用 OpenAsyncSession 再次创建一个新会话,而不是在 500`000 个条目后等待返回任务(由 SaveChangesAsync 返回),我得到一个“索引超出范围”异常,我不能根除。但是如果我等待任务结束(通过创建与核心数量相同的任务),进程会成功但不够快。
这段代码运行成功:
using (var reader = new StreamReader(@"D:\*\DATA.TXT", Encoding.UTF8))
{
string line = null;
IAsyncDocumentSession session = null;
var tasks = new List<Task>();
var locCount = 0;
while ((line = reader.ReadLine()) != null)
{
if (string.IsNullOrWhiteSpace(line)) continue;
var loc = Parse(line);
if (session == null) session = documentStore.OpenAsyncSession();
session.Store(loc);
locCount++;
if (locCount % 1024 == 0 && session != null)
{
try
{
var t = session.SaveChangesAsync();
tasks.Add(t);
session = null;
}
catch (Exception x)
{
// ... something ...
}
}
if (tasks.Count >= NUMBER_OF_CORES)
{
Task.WaitAll(tasks.ToArray());
tasks.Clear();
}
}
if (session != null)
{
if (tasks.Count > 0)
{
Task.WaitAll(tasks.ToArray());
tasks.Clear();
}
session.SaveChangesAsync().Wait();
session = null;
}
}
谢谢
【问题讨论】:
-
如果你不等待完成,它当然看起来很快。因为处理还没有完成。这不是一个有效的基准。
-
文档数据库与“记录”无关。您可能希望了解如何对这些数据进行建模以适合文档数据库。有关类似场景的示例,请参阅 ayende.com/blog/154401/… 和 ayende.com/blog/156386/…
-
@synhershko 我知道 - 在某种程度上 - 这是关于文件的,我在这里使用了“记录”这个词,因为当时我没有更好的词; “进入”也许? “目的”? “信息”?我不知道...谢谢!
-
我的观点 - 你可能需要做的插入比你想象的要少得多。最快的方法是使用一个简单的控制台应用程序批量执行此操作 - 如果您对每一组调用 SaveChanges,会话 API 将为您执行此操作。大多数情况下,您会发现从您的来源读取数据将花费大部分时间。
-
@usr 处理已完成,RavenDB 为 ACID。索引可能没有赶上,但所有信息都已经可用。
标签: c# asynchronous insert nosql ravendb