Search code examples
c#csvhelper

How can I have an optional header row when reading a CSV file?


I need to import a CSV file that may or may not have a header record.

If I read a file that doesn't have a header row it assumes the first data row is the header and doesn't return it. If I specify HasHeaderRecord = false it will throw an exception when there is a header record.

Is there a way to use the CsvHelper library and have an optional header record?

I can get this to work using this approach, but it seems like there could be a better way:

csvReader.Configuration.HasHeaderRecord = false;

while (csvReader.Read())
{
    try
    {
        var record = csvReader.GetRecord<MyModel>();
        myRecordList.Add(record);
    }
    catch (ReaderException rex)
    {
        // Check if this is an error with no header record and ignore
        if (rex.ReadingContext.CurrentIndex == 1 &&
            rex.ReadingContext.RawRecord.ToLower().Contains("myHeaderColumnName"))
        {
            continue;
        }
    }
}

Solution

  • I'm not sure if this is the best way, but it does bypass throwing an exception.

    public static void Main(string[] args)
    {
        using (var reader = new StreamReader("path\\to\\file.csv"))
        using (CsvReader csv = new CsvReader(reader))
        {
            csv.Read();
            csv.ReadHeader();
    
            if (!csv.Context.HeaderRecord.Contains("myHeaderColumnName"))
            {
                csv.Configuration.HasHeaderRecord = false;
                reader.BaseStream.Position = 0;
            }
    
            var records = csv.GetRecords<MyModel>().ToList();                        
        }
    }