diff --git a/extra/csv/csv.factor b/extra/csv/csv.factor index d774c2d6a4..fbb3677491 100644 --- a/extra/csv/csv.factor +++ b/extra/csv/csv.factor @@ -10,34 +10,35 @@ IN: csv DEFER: quoted-field +! trims whitespace from either end of string +: trim-whitespace ( str -- str ) + [ blank? ] trim ; inline + +: skip-to-field-end ( -- endchar ) + ",\n" read-until nip ; inline + : not-quoted-field ( -- endchar ) ",\"\n" read-until ! " dup { { CHAR: " [ drop drop quoted-field ] } ! " - { CHAR: , [ swap % ] } - { CHAR: \n [ swap % ] } - { f [ swap % ] } ! eof + { CHAR: , [ swap trim-whitespace % ] } + { CHAR: \n [ swap trim-whitespace % ] } + { f [ swap trim-whitespace % ] } ! eof } case ; : maybe-escaped-quote ( -- endchar ) - read1 - dup - { { CHAR: " [ , quoted-field ] } ! " is an escaped quote - { CHAR: \s [ drop not-quoted-field ] } - { CHAR: \t [ drop not-quoted-field ] } - [ drop ] + read1 dup + { { CHAR: " [ , quoted-field ] } ! " is an escaped quote + { CHAR: , [ ] } ! end of quoted field + [ 2drop skip-to-field-end ] ! end of quoted field + padding } case ; - -! trims whitespace from either end of string -: trim-whitespace ( str -- str ) - [ blank? ] trim ; inline : quoted-field ( -- endchar ) "\"" read-until ! " drop % maybe-escaped-quote ; : field ( -- sep string ) - [ not-quoted-field ] "" make trim-whitespace ; + [ not-quoted-field ] "" make ; ! trim-whitespace : (row) ( -- sep ) field ,