In one of the columns, regarding price, the data is in a weird format when the price starts with 0. Example : instead of 0,60 the format would be ,60. I tried to use the CsvHelper library from .NET nuget packages, and i would receive, of course an exception when reaching a line with this kind of values, because it could not convert this to double.
This library has a documentation regarding mapping, but i could not find anything documente on how to custom config my situation :
https://joshclose.github.io/CsvHelper/examples/configuration/class-maps/type-conversion/
Can someone give me a hint/tip for this situation ?
Here is my class setup:
public class Article
{
public int Id { get; set; }
public int ItemID { get; set; }
public string? Barcode { get; set; }
public double Price{ get; set; }
}
public class ArticleClassMap : ClassMap<Article>
{
public ArticleClassMap()
{
Map(m => m.ItemID).Name("itemID");
Map(m => m.Barcode).Name("barcode");
Map(m => m.Price).Name("price");
}
}
Here is how my file row with issues would look like : 1234|9999| ,60
Where 1234 would be the ItemId, 9999 EAN, and ,60 would represent a price of 0,60.
Here is how the CsvReader is setup :
using (var reader = new StreamReader(stream, Encoding.UTF8))
{
using (var csv = new CsvReader(reader, config))
{
csv.Context.RegisterClassMap<ArticleClassMap>();
var records = csv.GetRecords<Article>().ToList();
return records;
}
}
CodePudding user response:
I think you problem comes form ',' in your price normaly it should be '.' One solution is custom convert commas to periods and then parse to double like this:
Map(m => m.ItemID).Name("itemID");
Map(m => m.Barcode).Name("barcode");
Map(m => m.Price).Convert(row =>
{
return Double.Parse(row.Row.GetField<string>("price").Replace(',', '.'));
});
CodePudding user response:
After hours of trying, I found a working solution in my case :
I've created a customer converter:
public class PriceConverter : DefaultTypeConverter
{
public override object ConvertFromString(string text, IReaderRow row, MemberMapData memberMapData)
{
double result;
//replace space with 0 in position 5 of string text, if position 5 is an empty character
if (text.Length > 5 && text[5] == ' ')
{
text = text.Remove(5, 1).Insert(5, "0");
}
result = double.Parse(text);
return result;
}
public override string ConvertToString(object value, IWriterRow row, MemberMapData memberMapData)
{
return value?.ToString();
}
}
This works in the case, because in the .csv file the positions are fixed! So, before the comma, we always have the whole value.
Then I applied it to the mapping like this :
public ArticleClassMap()
{
Map(m => m.Price).Name("price").TypeConverter<PriceConverter>();
}