I'm trying to learn Go. I'm working to unmarshal CSV records into structs so that I can then create inserts and import this data into my DB.
I am looking for a way to automate marshaling, in a similar manner as encoding
When I run main, I am receiving an error
panic: strconv.ParseInt: parsing "id": invalid syntax
I've written some code which is supposed to unmarshal my .csv records to struct
func Unmarshal(reader *csv.Reader, v interface{}) error {
record, err := reader.Read()
if err != nil {
return err
}
s := reflect.ValueOf(v).Elem()
if s.NumField() != len(record) {
return &FieldMismatch{s.NumField(), len(record)}
}
for i := 0; i < s.NumField(); i++ {
f := s.Field(i)
switch f.Type().String() {
case "string":
f.SetString(record[i])
case "int":
ival, err := strconv.ParseInt(record[i], 10, 0)
if err != nil {
return err
}
f.SetInt(ival)
default:
return &UnsupportedType{f.Type().String()}
}
}
return nil
}
I created this struct in another file:
type InsertToDatabase struct {
ID int `csv:"id"`
groupId int `csv:"group_id"`
Name string `csv:"name"`
Status int `csv:"status"`
}
When main is run, it should run this bit of code and then parse through my .csv file to create inserts, which are then ran on my local DB.
var InsertTest InsertToDatabase
reader := csv.NewReader(file)
for {
err := Unmarshal(reader, &InsertTest)
if err == io.EOF {
break
}
if err != nil {
panic(err)
}
channel <- InsertTest
}
}
Is there a way to improve readability of this code? Also, should I loop and call .Read
to process one line at a time?