Skip to content

ovska/FlameCsv

Repository files navigation

FlameCsv

High-performance RFC 4180-compliant CSV library for .NET 6+ with trimming/AOT support

Features

  • Designed with performance in mind, minimizing copies and allocations
  • Flexible class binding and manual record/field reading
  • Supports both RFC 4180 / Excel and Unix (escaped) styles
  • Read CSV from char or byte, e.g. TextReader, Stream, PipeReader, ReadOnlySequence, string
  • Nearly allocation free enumeration to "peek" unescaped and tokenized fields and records
  • Source generator for class bindings to completely avoid reflection and dynamic code generation

Examples

Reading records with a lambda function

var records = CsvReader.ReadRecordsAsync(
    new StringReader("1,true,Bob\r\n2,false,Alice\r\n"),
    CsvTextReaderOptions.Default,
    (int id, bool enabled, string name) => new { id, enabled, name });

await foreach (var record in records)
{
    Console.WriteLine(record);
}

Binding field indexes to classes

1,Bob
2,Alice
class User
{
    [CsvIndex(0)] public int Id { get; set; }
    [CsvIndex(1)] public string? Name { get; set; }
}
var options = CsvUtf8ReaderOptions.Default;
var file = File.OpenRead("/home/ovska/test.csv");
await foreach (var record in CsvReader.ReadAsync<User>(file, options))
{
    // ...
}

Binding to header

Id,Name
1,Bob
2,Alice
class User
{
    public int Id { get; set; }
    public string? Name { get; set; }
}
var options = new CsvUtf8ReaderOptions
{
    options.HasHeader = true;
}
var file = File.OpenRead("/home/ovska/test.csv");

await foreach (User record in CsvReader.ReadAsync<User>(file, options))
{
    // ...
}

Field index binding

[CsvIndexIgnore(2)]
record User(
    [CsvIndex(0)] int Id,
    [CsvIndex(1)] string Name,
    bool IsAdmin = false)
{
    [CsvIndex(3)]
    public DateTime Created { get; init; }
}

Reading from buffered data

var csv = @"Id,Name\n1,Bob\n2,Alice";
var options = CsvTextReaderOptions.Default;
foreach (User record in CsvReader.Read<User>(csv, options))
{
    // ...
}

Reading manually

var csv = @"1,Bob\n2,Alice";
var options = CsvTextReaderOptions.Default;
foreach (CsvRecord<char> record in CsvReader.Enumerate(csv, options))
{
    var user = new User
    {
        Id = record.GetValue<int>(0),
        Name = record.GetValue<string>(1),
    };
}

Performance

Note: CsvHelper was chosen because it is the most popular CSV library for C#. This library isn't meant to be a replacement for CsvHelper. Example CSV file used in th benchmarks is found in the TestData folder in the tests-project.


image

image


image

image

--

image

image

About

High performance RFC 4180 compliant CSV parsing library for .NET 6+

Topics

Resources

License

Stars

Watchers

Forks

Languages