0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

PowerShellスクリプトによるCSVの文字コード変換

Last updated at Posted at 2023-07-06

はじめに

本記事は以下のイベントに参加しております。

筆者の環境は以下のとおりです。
 ・Windows10 Home(22H2)
 ・PSVersion 5.1.19041.3031(バージョンは各自$PSVersionTableで確認してください)

また、OS実行ポリシーの確認及び変更が必要な場合があります。

背景

・(表面上は見えないけれど)ANSI前提で取込処理されている箇所に
 UTF8のファイルを入れたら文字化けしたので対応できないでしょうか。
 といった問い合わせが来ました。

・現状のシステム構築している環境単体ではできないが
 (汎用的なDBの文字コードを後から変更もしたくないですし...)
 取込前に変換することで対応できるかもしれない。

前提

 ・BOM付UTF8しか判定できない。
 ・nkf等を利用したくない
  (色々なリスクを考慮して素のPowershellで処理したい)。
   
(+αメンテナンスの期間を見ても放置気味なので利用したくない)

記述したスクリプト

・コメントや内容から判断してもらえれば助かります

■パターン1(フォルダを指定して配下のCSVを全変換する)

<# 
  ・特定のフォルダ内のCSVを全てUTF-8からShift-JISに変換するスクリプト
#>

# 引数でフォルダのパスを受け取る
Param ($arg0)

# フォルダからファイルの一覧(CSVのみ)を取得する
$folderFileList = Get-ChildItem -File $arg0\*.csv

# 取得したファイル数分ループする
foreach ($item in $folderFileList)
{
    # ここから文字コードがUTF-8かの判定処理
    Byte[] $data = Get-Content $item -Encoding Byte
    # bom付きかどうかを判定する
    $tmp = ""
    if ($data.Length -ge 3) {
    # 取得したByte文字列の長さが3以上だったら
        foreach($element in $data[0..2])
        {
            # 1バイトを2桁の16進数に変換する
            $tmp = $tmp + $element.ToString("X2")
            # 先頭3バイトが"EFBBBF"かどうかで、utf8かどうかを判断する
        }
    }
    if ($tmp -eq "EFBBBF") {
        # Out-FileでEncoding defaultを指定しShift-JISに変換
        # 同じファイル名で直接上書きできない為、「元ファイル => 変換後ファイル => 元ファイル」と書込んでから変換後ファイルを削除する
        Get-Content -Encoding UTF8 $item | Out-File -Encoding default $arg0\SJIS_From_UTF8.csv
        Get-Content -Encoding default $arg0\SJIS_From_UTF8.csv | Out-File -Encoding default $item
        Remove-item $arg0\SJIS_From_UTF8.csv
    }
}

■パターン2(フォルダとファイルを指定して変換する)

<# 
  ・CSVをUTF-8からShift-JISに変換するスクリプト
#>

# 引数でフォルダパスとファイルパスを受け取る
Param(
    $folder_path,
    $file_path
)

# ここから文字コードがUTF-8かの判定処理
Byte[] $data = Get-Content $file_path -Encoding Byte
# bom付きかどうかを判定する
$tmp = ""
if ($data.Length -ge 3) {
# 取得したByte文字列の長さが3以上だったら
    foreach($element in $data[0..2])
    {
        # 1バイトを2桁の16進数に変換する
        $tmp = $tmp + $element.ToString("X2")
        # 先頭3バイトが"EFBBBF"かどうかで、UTF-8かどうかを判断する
    }
}
if ($tmp -eq "EFBBBF") {
    # Out-FileでEncoding defaultを指定しShift-JISに変換
    # 同じファイル名で直接上書きできない為、「元ファイル => 変換後ファイル => 元ファイル」と書込んでから変換後ファイルを削除する
    Get-Content -Encoding UTF8 $file_path | Out-File -Encoding default $folder_path\SJIS_From_UTF8.csv
    Get-Content -Encoding default $folder_path\SJIS_From_UTF8.csv | Out-File -Encoding default $file_path
    Remove-item $folder_path\SJIS_From_UTF8.csv
}

文字コード判定参考

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?