CSV Dock / 開発者向けドキュメント
MITライセンス・無料v0.1.0パッケージ公開準備中

API リファレンス

文字列を検査するlint、検査して変換するconvert、分割して入力するcreateLinterの仕様です。入力はデコード済みのJavaScript文字列です。

lint(text, options?)

LintResultを同期的に返します。入力中の文字を集計し、CP932への変換と往復変換、辞書に登録された注意点を確認します。入力文字列は変更しません。

import { lint } from '@csvdock/cp932-lint';

const report = lint('氏名,備考\n𠮷田,①番', {
  format: 'csv',
  delimiter: ',',
  header: true,
  maxPositionsPerChar: 5,
});

// report.errors[0].char === '𠮷'
// report.errors[0].positions[0]:
// { index: 6, line: 2, column: 1, columnName: '氏名' }

共通の検査オプション

項目初期値説明
context'general''jinmei'で全件の置換提案を抑制。convertで置換を指定すると例外になります。
format'text''csv'で論理レコードとフィールドの位置を付けます。
delimiter','ASCIIの1文字。NUL・引用符・改行は指定不可。区切りの自動検出は行いません。
headertrueCSVの先頭レコードを列名に使用。先頭レコードも検査対象です。
maxPositionsPerChar5文字ごとに保存する位置の数。0〜100。上限を超えてもcountは全件を数えます。
maxUniqueChars20000文字種数の上限。1〜100000。超過すると検査を停止します。
maxHeaderChars65536CSVの列名を保持するための上限。1〜1000000。
maxColumns10000CSVのフィールド数の上限。1〜100000。

位置の数え方

  • indexは元の入力全体における0始まりのUnicodeコードポイント位置です。JavaScriptのUTF-16コードユニット位置ではありません。𠮷は1文字として数えます。
  • lineは1始まりのCSV論理レコード番号です。見出しを1レコード目として数えます。引用符内の改行では番号が増えません。
  • columnは1始まりのフィールド番号です。画面上の桁位置ではありません。
  • columnNameheader: trueのときの列名です。header: falseでは列名を付けません。
  • format: 'text'ではindexだけを返します。文字は引用符や区切りを含む元の入力で集計します。

返り値

type Severity = 'error' | 'warning' | 'info';

interface Position {
  index: number;
  line?: number;
  column?: number;
  columnName?: string;
}

interface CharIssue {
  char: string;
  codePoint: string;
  count: number;
  severity: Severity;
  category: 'unmappable' | 'risky' | 'jinmei' | 'gaiji';
  suggestion: string | null;
  reason: string;
  reasonEn: string;
  docs: string;
  positions: Position[];
}

interface LintResult {
  safe: boolean;
  errors: CharIssue[];
  warnings: CharIssue[];
  stats: {
    totalChars: number;
    uniqueChars: number;
    convertibleRate: number;
  };
}

safeerrors.length === 0です。警告を許容してよいかは受入先の仕様によって判断してください。convertibleRateは入力文字の出現数を基準にした、エンコーダーで表現できる文字の割合です。往復変換の一致や、外字の受入可否を保証する値ではありません。空文字列では1です。totalCharsには区切り文字や改行も含まれます。

docsにはCSV Dock上の説明URLを返します。reasonは日本語、reasonEnは英語です。人名異体字・外字とcontext: 'jinmei'ではsuggestionnullです。

convert(text, options?)

入力を検査し、明示的に指定した置換を適用してから再検査します。bytesapplied、置換後のresultを返します。停止条件に該当する場合はConversionErrorを投げ、バイト列を返しません。

import { convert, ConversionError } from '@csvdock/cp932-lint';

try {
  const output = convert('連絡先,山田①', {
    to: 'CP932',
    replace: 'none',
    failOn: 'warning',
  });
  // output.bytes: Uint8Array
  // output.applied: Array<{ from: string; to: string; count: number }>
  // output.result: 置換後のLintResult
} catch (error) {
  if (error instanceof ConversionError) {
    // この例では①の警告により、出力を停止します。
    console.log(error.result.warnings);
  } else {
    throw error;
  }
}
項目初期値説明
to'CP932''SJIS'も同じCP932出力の別名。厳密なJIS X 0208限定出力には対応しません。
replace'none''none'は置換なし。'safe'は辞書で許可した候補。'custom'はcustomMapを使用します。
customMapなし1つのUnicodeスカラー値から空でない文字列への対応表。replace: 'custom'と合わせて指定します。
failOn'error''warning'ではエラーに加えて警告も停止対象です。エラーを無視するモードはありません。

用途を確認したうえで、置換を指定する

const output = convert('分類,①', {
  replace: 'custom',
  customMap: { '①': '(1)' },
});
// output.applied: [{ from: '①', to: '(1)', count: 1 }]

safeは「用途に関係なく意味が同じ」という保証ではありません。例えば記号をASCIIに変えると、表記は変わります。変更を許容できる項目だけに使い、appliedを確認してください。

format: 'csv'では、区切り文字・引用符・改行を追加、削除、変更する置換は例外で停止します。CSVの構造を変える処理は、フィールドを解析したうえで別途行ってください。

人名異体字と外字は置換対象にできません。

customMapで別の文字への変更を指定すると例外になります。context: 'jinmei'ではreplace: 'safe''custom'自体が例外になります。変換できない氏名はUTF-8で保持し、受入先との運用を確認してください。

createLinter(options?)

feed(chunk: string)で文字列を順番に渡し、最後にfinish()LintResultを受け取ります。CSVの途中やサロゲートペアの途中でチャンクが分かれても、境界をまたいで検査します。

import { createLinter } from '@csvdock/cp932-lint';

const linter = createLinter({ format: 'csv', header: true });
linter.feed('氏名,備考\n"𠮷');
linter.feed('田","改行を含む\n備考"');
const report = linter.finish();

ファイルのバイト列は事前にデコードしてください。バイト単位のチャンクでは、デコーダー側でも文字の途中の状態を維持する必要があります。createLinter自体は文字コードの自動検出やデコードを行いません。

入力全体の走査は必要です。文字の判定結果は再利用しますが、処理時間は入力長にも依存します。メモリは文字種数、保持する位置、CSVヘッダーなどに依存し、上限超過時は例外で停止します。変換用のストリーミングAPIではありません。

例外と入力の制限

例外意味
ConversionError変換の停止条件に該当。resultから検査結果を取得できます。
CsvSyntaxErrorCSVの引用符などの構文が不正。未完の引用符はfinish時にも検出します。
ResourceLimitError文字種数、CSVヘッダー、列数などの上限を超過。
LintError上記の共通の基底型。codeでエラーを識別できます。

検査を完了できなかった例外を、問題のないLintResultとして扱わないでください。不正な型や値にはTypeError、数値オプションの範囲外にはRangeErrorを返します。

文字データを利用する

import {
  UNMAPPABLE, RISKY, JINMEI, GAIJI_RANGES,
} from '@csvdock/cp932-lint/data';

変換不可文字、互換性に注意する文字、人名異体字、Unicode私用領域の定義を公開します。データの理由は日本語と英語を含みます。文字一覧も同じデータから作成しています。