當前位置: 妍妍網 > 碼農

.net中透過Bogus庫生成 100 萬個虛擬產品數據並將其插入到 SQL Server 資料庫中,測試必備

2024-05-18碼農


概述: 我們需要在 SQL Server 資料庫中建立 100 萬個虛擬產品數據,這些數據可用於開發或效能測試。計畫該計畫是使用 .NET 6.0 作為框架的控制台應用程式。計畫名稱為 InsertMillionRecords我們將使用Bogus軟體包來生成隨機產品數據。我們使用 Entity Framework Core 作為數據存取層。產品型號為了對資料庫中的 Products 表進行建模,我們需要建立 Product 類:public class Product { public int Id { get; set; } public string Code { get;

我們需要在 SQL Server 資料庫中建立 100 萬個虛擬產品數據,這些數據可用於開發或效能測試。

計畫

該計畫是使用 .NET 6.0 作為框架的控制台應用程式。

計畫名稱為 InsertMillionRecords

我們將使用Bogus軟體包來生成隨機產品數據。

我們使用 Entity Framework Core 作為數據存取層。

產品型號

為了對資料庫中的 Products 表進行建模,我們需要建立 Product 類:

public classProduct
{
publicint Id { get; set; }
publicstring Code { get; set; }
publicstring Description { get; set; }
publicstring Category { get; set; }
publicdecimal Price { get; set; }
}

實體框架數據上下文

接下來,我們建立 Entity Framework 數據上下文類:

usingMicrosoft.EntityFrameworkCore;
namespaceInsertMillionRecords;
public classDataContext : DbContext
{
publicDataContext(DbContextOptions<DataContext> options) : base(options)
{
}
publicDbSet<Product> Products { get; set; }
}

Program.cs檔

初始化數據上下文

首先,我們需要初始化數據上下文:

var connectionString = "Data Source=localhost; Initial Catalog=Product; Integrated Security=True";
var contextOptionsBuilder = newDbContextOptionsBuilder<DataContext>();
contextOptionsBuilder.UseSqlServer(connectionString);
var context = newDataContext(contextOptionsBuilder.Options);

我們透過對連線字串進行寫死,使事情變得更簡單。不用擔心!

建立資料庫

每次執行指令碼時,我們都需要確保重新建立資料庫。

await context.Database.EnsureDeletedAsync();
await context.Database.EnsureCreatedAsync();

設定 Bogus Faker 類

首先,我們初始化 Faker<Product> 物件。

接下來,我們使用該方法來設定 Product 類的每個內容。RuleFor()

自我解釋的程式碼:

var faker = newFaker<Product>();
faker.RuleFor(p => p.Code, f => f.Commerce.Ean13());
faker.RuleFor(p => p.Description, f => f.Commerce.ProductName());
faker.RuleFor(p => p.Category, f => f.Commerce.Categories(1)[0]);
faker.RuleFor(p => p.Price, f => f.Random.Decimal(1, 1000));

生成 100 萬個虛擬產品數據

var products = faker.Generate(1000000);

該變量現在包含 100 萬個產品數據!products

建立 10 批插入

如果我們一次插入 100 萬條記錄,則可能會發生超時。

因此,我們將該過程分為 10 批。每批一次插入 100K 條記錄。

var batches = products
.Select((p, i) => (Product: p, Index: i))
.GroupBy(x => x.Index / 100_000)
.Select(g => g.Select(x => x.Product).ToList())
.ToList();

將每個批次插入資料庫

var count = 0;
foreach (var batch in batches)
{
batchCount++;
Console.WriteLine($"Inserting batch {count} of {batches.Count}...");
await context.Products.AddRangeAsync(batch);
await context.SaveChangesAsync();
}

Program.cs檔的完整程式碼:

usingBogus;
usingInsertMillionRecords;
usingMicrosoft.EntityFrameworkCore;
usingSystem.Diagnostics;
// initialize data context
var connectionString = "Data Source=localhost; Initial Catalog=Product; Integrated Security=True";
var contextOptionsBuilder = newDbContextOptionsBuilder<DataContext>();
contextOptionsBuilder.UseSqlServer(connectionString);
var context = newDataContext(contextOptionsBuilder.Options);
// create database
await context.Database.EnsureDeletedAsync();
await context.Database.EnsureCreatedAsync();
// setup bogus faker
var faker = newFaker<Product>();
faker.RuleFor(p => p.Code, f => f.Commerce.Ean13());
faker.RuleFor(p => p.Description, f => f.Commerce.ProductName());
faker.RuleFor(p => p.Category, f => f.Commerce.Categories(1)[0]);
faker.RuleFor(p => p.Price, f => f.Random.Decimal(1, 1000));
// generate 1 million products
var products = faker.Generate(1000000);
var batches = products
.Select((p, i) => (Product: p, Index: i))
.GroupBy(x => x.Index / 100000)
.Select(g => g.Select(x => x.Product).ToList())
.ToList();
// insert batches
var stopwatch = newStopwatch();
stopwatch.Start();
var count = 0;
foreach (var batch in batches)
{
count++;
Console.WriteLine($"Inserting batch {count} of {batches.Count}...");
await context.Products.AddRangeAsync(batch);
await context.SaveChangesAsync();
}
stopwatch.Stop();
Console.WriteLine($"Elapsed time: {stopwatch.Elapsed}");
Console.WriteLine("Press any key to exit...");








執行應用程式

現在,讓我們執行應用程式。我們可以使用_釋放_模式來加快該過程。

在我的機器上花了 1 分 9 秒:

現在,我們在 Products 表中有 100 萬條記錄:

我計劃使用這些虛擬數據來測試 SQL Server 中的全文搜尋功能。