Skip to content

Performance issue #82

@xeo545x39

Description

@xeo545x39

Using this library 1.0.2 version with EF Core 9.0.3

Inserting 1000 records takes about 16 seconds. I've saved some time with manually passing DbConnection, because without it EF opened connection for each record, but even now it's also very slow.

Seems it executes a command for each row. Is there any way to speed it up?

builder.Services.AddSingleton(x =>
{
    var connection = new ClickHouseConnection(x.GetRequiredService<ClickHouseOptions>()
        .ConnectionString);
    
    connection.Open();

    return connection;
});

builder.Services.AddDbContextFactory<HistoricalDbContext>((services, optionsBuilder) => optionsBuilder
    .EnableThreadSafetyChecks(false)
    .UseClickHouse(services.GetRequiredService<ClickHouseConnection>(),
        x => x.MaxBatchSize(1000)
            .MinBatchSize(100)
            .UseQuerySplittingBehavior(QuerySplittingBehavior.SplitQuery)));

 await using var db = await _dbFactory.CreateDbContextAsync(ct);

        db.Klines.AddRange(klines.Select(x => new KlineDto
        {
            Exchange = exchange.Value,
            MarketType = Enum.Parse<Storage.Dto.MarketType>(marketType.ToString()),
            Close = x.Close,
            Confirmed = x.Confirmed,
            High = x.High,
            Interval = x.Interval.Value,
            Low = x.Low,
            Open = x.Open,
            Volume = x.Volume,
            Symbol = x.Symbol,
            QuoteVolume = x.QuoteVolume,
            StartTime = x.StartTime,
        }));

        await db.SaveChangesAsync(ct);

        _logger.LogTrace("Added {N} klines", klines.Count());
Microsoft.EntityFrameworkCore.Database.Command: Debug: Creating DbCommand for 'ExecuteReader'.
Microsoft.EntityFrameworkCore.Database.Command: Debug: Created DbCommand for 'ExecuteReader' (0ms).
Microsoft.EntityFrameworkCore.Database.Command: Debug: Initialized DbCommand for 'ExecuteReader' (1ms).
Microsoft.EntityFrameworkCore.Database.Command: Debug: Executing DbCommand [Parameters=[p0='?' (DbType = Int32), p1='?' (DbType = DateTime), p2='?', p3='?' (DbType = Decimal), p4='?' (DbType = Boolean), p5='?', p6='?' (DbType = Decimal), p7='?', p8='?' (DbType = Decimal), p9='?' (DbType = Decimal), p10='?' (DbType = Decimal), p11='?' (DbType = Decimal)], CommandType='0', CommandTimeout='0']
INSERT INTO "Klines" ("MarketType", "StartTime", "Symbol", "Close", "Confirmed", "Exchange", "High", "Interval", "Low", "Open", "QuoteVolume", "Volume")
VALUES ({p0:Int32}, {p1:DateTime}, {p2:String}, {p3:Decimal(24, 10)}, {p4:Bool}, {p5:String}, {p6:Decimal(24, 10)}, {p7:String}, {p8:Decimal(24, 10)}, {p9:Decimal(24, 10)}, {p10:Decimal(24, 10)}, {p11:Decimal(24, 10)});
Microsoft.EntityFrameworkCore.Database.Command: Information: Executed DbCommand (16ms) [Parameters=[p0='?' (DbType = Int32), p1='?' (DbType = DateTime), p2='?', p3='?' (DbType = Decimal), p4='?' (DbType = Boolean), p5='?', p6='?' (DbType = Decimal), p7='?', p8='?' (DbType = Decimal), p9='?' (DbType = Decimal), p10='?' (DbType = Decimal), p11='?' (DbType = Decimal)], CommandType='0', CommandTimeout='0']
INSERT INTO "Klines" ("MarketType", "StartTime", "Symbol", "Close", "Confirmed", "Exchange", "High", "Interval", "Low", "Open", "QuoteVolume", "Volume")
VALUES ({p0:Int32}, {p1:DateTime}, {p2:String}, {p3:Decimal(24, 10)}, {p4:Bool}, {p5:String}, {p6:Decimal(24, 10)}, {p7:String}, {p8:Decimal(24, 10)}, {p9:Decimal(24, 10)}, {p10:Decimal(24, 10)}, {p11:Decimal(24, 10)});
Microsoft.EntityFrameworkCore.Database.Command: Debug: Closing data reader to 'historical' on server '(null)'.
Microsoft.EntityFrameworkCore.Database.Command: Debug: A data reader for 'historical' on server '(null)' is being disposed after spending 0ms reading results.

Image

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions