Search code examples
csvhelper

write a space delimited file with csvhelper


I did not see this option in CsvHelper, but does this library support space delimiters such that there is a predetermined number of characters like spaces or periods for each field?

example: firstname -len:10 lastname - len:15 would translate to this with periods

john......doe............
sam.......simpson........

Solution

  • CsvHelper doesn't currently support fixed width files. There is an open feature request to add fixed width support, but I don't think there are any plans to implement it anytime soon. https://github.com/CsvHelperContrib/CsvHelperContrib/issues/2

    If you are writing a fixed width file, this should work. I don't have a way to read a fixed width file.

    public class Program
    {
        public static void Main(string[] args)
        {     
            var records = new List<Foo>
            {
                new Foo { FirstName = "john", LastName = "doe" },
                new Foo { FirstName = "sam", LastName = "simpson"}
            };
    
            using (CsvWriter csv = new CsvWriter(Console.Out))
            {
                csv.Configuration.RegisterClassMap<FooMap>();
                csv.Configuration.HasHeaderRecord = false;
                csv.Configuration.Delimiter = "";
                csv.Configuration.ShouldQuote = (field, context) => false;
                csv.WriteRecords(records);
            }
    
            Console.ReadLine();
        }
    }
    
    public class Foo
    {
        public string FirstName { get; set; }
        public string LastName { get; set; }
    }
    
    public sealed class FooMap : ClassMap<Foo>
    {
        public FooMap()
        {
            Map(m => m.FirstName).TypeConverter(new FixedWidthOutput(10, '.'));
            Map(m => m.LastName).TypeConverter(new FixedWidthOutput(15, '.'));
        }
    }
    
    public class FixedWidthOutput : DefaultTypeConverter
    {
        private readonly int _fieldLength;
        private readonly char _paddingCharacter;
    
        public FixedWidthOutput(int fieldLength, char paddingCharacter = ' ')
        {
            _fieldLength = fieldLength;
            _paddingCharacter = paddingCharacter;
        }
    
        public override string ConvertToString(object value, IWriterRow row, MemberMapData memberMapData)
        {
            return value.ToString().PadRight(_fieldLength, _paddingCharacter);
        }
    }