Ccmmutty logo
Commutty IT
3 min read

React-adminでUnicode以外の文字コードでCSVダウンロード

https://cdn.magicode.io/media/notebox/b41d201c-52f4-43f6-a311-e07b789e3784.jpeg

概要

管理画面系のフロントを作る時に欲しい機能が一通りそろっている便利なライブラリReact-adminに関してダウンロードの文字コードを変える方法についてのメモ

React-adminとは

A frontend Framework for building data-driven applications running in the browser, on top of REST/GraphQL APIs, using React and Material Design. Open sourced and maintained by marmelab. 引用:公式ドキュメント
簡単に説明すると「ReactとMaterial UIを使ってCRUD+管理画面系のフロントにありがちな機能を備えているフレームワーク」という感じです。
デモページに飛ぶと 「良い感じの管理画面」が少ないコードで実現されてるのが分かると思います。

やりたいこと

このライブラリには任意でCSVダウンロード処理を呼べるdownloadCSVという関数があるのですが、依存ライブライリとしてjsonexportが既にサポートされており、これを使ってコンバートするとCSV文字列がUnicode文字になってしまう(というよりJavaScriptの文字列がUTF-16 コードユニットとして符号化されているのでどうしようもない)ところをなんとかShift-JISのCSVファイルにしたい。

解決法

コンバートされた後のCSV文字列の文字コードを変えてからdownloadCSVを呼ぶ。 そのためにencoding.jsというライブラリを使用しました。

Step1 install

npm install --save-dev encoding-japanese
または
yarn add --dev encoding-japanese
TypeScriptを使用している場合
npm install --save-dev @types/encoding-japanese
または
yarn add --dev @types/encoding-japanese
も忘れずにインストールしておきましょう。

Step2 Use

React-adminの公式ドキュメントのdownloadCSVの使用例を改造してみます(リンク先の実装と同じ箇所を一部省略してます)。
import { convert, stringToCode } from 'encoding-japanese';
import { downloadCSV } from 'react-admin';
import jsonExport from 'jsonexport/dist';

const exporter = posts => {

    // 省略

    jsonExport(postsForExport, {
        headers: ['id', 'title', 'author_name', 'body']
    }, (err, csv) => {

       // ライブラリを使って文字コードを変換
        const unicodeArray = stringToCode(csv);
        const shiftJisArray = convert(unicodeArray, {
            to: 'SJIS',
            from: 'UNICODE',
        });
        const csvOfShiftJis = new Uint8Array(shiftJisArray);

        // 変換したcsv文字列でダウンロードを呼び出す
        downloadCSV(csvOfShiftJis, 'posts');
    });
};
これで(UnicodeとShift-JISに両方含まれている文字なら)同じ文字でコードだけが変わった
例えば「𠮟」のようなUnicodeにあってShift-JISに無い文字はencode.jsの仕様により「?」になる

Discussion

コメントにはログインが必要です。