はじめまして。ルーターのMatsunagaです。 今回はCSVのファイルフォーマット仕様について、推奨されている形式と、仕様を定義する際の注意点について書いていきます。

CSVとは

CSVとはComma-Separated Valuesの略で、カンマ区切りで並べた値という意味です。
例えば以下のような形になります。

"名前","生年月日","郵便番号","住所","電話番号"
"ルー太郎","2009/1/1","000-0000","東京都hoge区hoge1-1","00-0000-0001"
"ルー子","2009/1/2","000-0001","神奈川県hoge市hoge1-2","00-0000-0002"

弊社では、クローラーで収集したデータをCSV形式でサーバーにアップロードする形で提供することが多いのですが、取り込みを行う際にトラブルにならないよう、システム側の仕様とすり合わせながら、適切な形式でCSVを定義していくことが大切になります。

CSV仕様について

では、そもそも正しいCSVの仕様って何なのか?実はCSVの仕様は公式には定義されておらず、細部の実装はソフトによって異なっています。
それらを追認する形で、2005年10月、RFC 4180 で Informational(IESGの外部で決定された有用な情報の提供)として仕様が成文化されました。
公式な定義が存在しない以上、言ってしまえばなんでもありなのですが、
せっかくIETFが定義してくれた仕様があるわけなので、今回はこちらの仕様を詳しく紹介していきます。

CSVの書式の定義(Definition of the CSV Format)

RFC4180の日本語訳( http://www.kasai.fm/wiki/rfc4180jp )によれば、CSV書式の定義は以下の通りです。以下、サンプルのCSV上では改行コードを見えるように表すため、便宜的に「(CRLF)」という文字列で改行を表現します。

  1. 各レコードは、改行(CRLF)を区切りとする、分割された行に配置される。
    aaa,bbb,ccc(CRLF)
    zzz,yyy,xxx(CRLF)
    
  2. ファイル末尾のレコードの終端には、改行はあってもなくてもよい。
    aaa,bbb,ccc(CRLF)
    zzz,yyy,xxx
    
  3. ファイルの先頭には、オプションとして、通常行と同一の書式を持つ、ヘッダ行が存在してもよい。
    このヘッダは、ファイル中の各フィールドの名称を保持し、ファイルの残りの部分にある各レコードが持っているのと同じ数のフィールドを持つべきである。
    ヘッダ行の有無は、このMIMEタイプのオプションパラメータ"header"で明示するべきである。
    field_name,field_name,field_name(CRLF)
    aaa,bbb,ccc(CRLF)
    zzz,yyy,xxx(CRLF)
    
  4. ヘッダと各レコードは、コンマで区切られた、一つ以上のフィールドを含む。
    各行が保持するフィールドの数は、ファイル全体を通じ、同一であるべきである。
    スペースは、フィールドの一部とみなす。無視すべきではない。最後のフィールドは、コンマで終わってはならない。例えば
    aaa,bbb,ccc
    
  5. (レコード中の) 各フィールドは、それぞれダブルクォーテーションで囲んでも囲わなくてもよい 。
    フィールドがダブルクォーテーションで囲まれていない場合、そのフィールドの値には、ダブルクォーテーションが含まれてはいけない。例えば、
    "aaa","bbb","ccc" (CRLF)
    zzz,yyy,xxx
    
  6. 改行(CRLF)、ダブルクォーテーション、カンマを含むフィールドは、ダブルクォーテーションで囲むべきである。例えば、
    "aaa","b(CRLF)
    bb","c,cc"(CRLF)
    zzz,yyy,xxx
    
  7. フィールドがダブルクォーテーションで囲まれている場合、フィールドの値に含まれるダブルクォーテーションは、その直前にひとつダブルクォーテーションを付加して、エスケープしなければならない。例えば、
    "aaa","b""bb","ccc"
    

改行コードについて

上記の通り、RFCではCRLFを推奨していますが、
プラットフォームごとの改行コードの違い(一般的にWindowsはCRLF、UNIXはLF。)を考慮すると、
CSVを解釈するプログラム側では両方に対応することをお勧めします。

ダブルクォート囲いについて

フィールドをダブルクォーテーションで囲む方法と、ダブルクォーテーションで囲まない方法の2種類がありますが、フィールド内に改行コード、ダブルクォーテーション(")、カンマ(,)のいずれかを含む場合、ダブルクォーテーション囲いが必須のため、基本的にはダブルクォーテーションで囲む方法をお勧めします。

なお、フィールド内のダブルクォーテーションは("")の形でエスケープする必要があります。

正しくない形式: t"est,test,test
正しくない形式: t""est,test,test
正しい形式: "t""est","test","test"

取り決めするべき項目

ここまで、RFCに基づく推奨の形式を紹介してきましたが、実際にはプロジェクトや状況に応じてCSV仕様を定義することになるかと思います。CSV仕様を定義する際は、以下の項目について相互に取り決めを行いましょう。
ここが食い違ってしまうと思わぬトラブルに繋がります! 

  1. 文字コード
  2. 改行コード
  3. ヘッダ行の有無
  4. 区切り文字
  5. ダブルクォートで囲むか否か
  6. ダブルクォートで囲まない場合、制御文字(ダブルクォート、カンマ、タブ、改行)の処理方法

まとめ

以上、CSVの仕様について書いてきました。
CSVは幅広く扱われている形式であるにも関わらず、様々な仕様が存在しており、情報も少ないため、苦労されている方も多いのではないかと思います。CSVを扱う際は、本記事を参考していただければと思います!