⇧ 是非とも成功して欲しいプロジェクトですな、御武運長久。
シェルスクリプトで名前空間っぽいことしたい
シェルスクリプトで、関数などの名前が被るのはNGということで、「名前空間」っぽいことを実現したいと思っていたところ、
⇧ 同じようなことを考えておられる先人の方がおりました。
試してみました。
⇧ 上記サイト様を参考にディレクトリ構造とかを表示します。
以下のような、構成。
インプットは、
⇧ 前回の記事の時と全く同じです。CSVファイルの中身は省略してます。
ID,都道府県市区町村コード,市区町村名,基準メッシュ・コード T00001,13101,千代田区,53394509 T00002,13101,千代田区,53394518 T00003,13101,千代田区,53394519 T00004,13101,千代田区,53394528 ...省略 T03426,13999,境界未定地域,45405294 T03427,13999,境界未定地域,47396763 T03428,13999,境界未定地域,47401024 T03429,13999,境界未定地域,47401034
で、シェルスクリプトの中身は、以下のような感じです。
■/home/ts0818/work/test_validate/validation_csv/func/constants/validate/csv_header.sh
#!/bin/bash # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【定数】 # ■ バリデーション対象のCSVファイルのヘッダーの一覧 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ csv_header() { CSV_HEADER_13() { echo ID,都道府県市区町村コード,市区町村名,基準メッシュ・コード } }
■/home/ts0818/work/test_validate/validation_csv/func/validate_common.sh
#!/bin/bash validate_common() { # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数定義】 # ■ 共通的なバリデーション処理に関する関数 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】空文字かどうかバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_empty() { echo "【start】validate_empty()" if [[ -z "$1" ]]; then echo "空文字です" else echo "空文字ではありません" fi echo "【finish】validate_empty()" } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】NULLかどうかバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_null() { echo "【start】validate_null()" if [[ "$1" == "NULL" ]]; then echo "NULLです" else echo "NULLではありません" fi echo "【finish】validate_null()" } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】全角文字のみかどうかバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_full_width() { echo "【start】validate_full_width()" if [[ "$1" =~ ^[^\x01-\x7E\xA1-\xDF]+$ ]]; then echo "全角文字です" else echo "全角文字ではありません" fi echo "【finish】validate_full_width()" } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】半角文字のみかどうかバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_half_width() { echo "【start】validate_half_width()" if [[ "$1" =~ ^[[:ascii:]]+$ ]]; then echo "半角文字です" else echo "半角文字ではありません" fi echo "【finish】validate_half_width()" } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】半角数字のみかどうかバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_digits() { echo "【start】validate_digits()" if [[ "$1" =~ ^[0-9]+$ ]]; then echo "半角数字です" else echo "半角数字ではありません" fi echo "【finish】validate_digits()" } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】半角英字のみかどうかバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_alphabets() { echo "【start】validate_alphabets()" if [[ "$1" =~ ^[a-zA-Z]+$ ]]; then echo "半角英字です" else echo "半角英字ではありません" fi echo "【finish】validate_alphabets()" } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】配列が空かどうかバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_array_empty() { echo "【start】validate_array_empty()" local -a arr=("${!1}") if [ ${#arr[@]} -eq 0 ]; then echo "配列は空です"; else echo "配列は空ではありません"; fi; echo "【finish】validate_array_empty()" } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】配列の要素が半角数字で、且つ、9桁の固定長であるかどうかバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_array_element_legth_all_9() { echo "【start】validate_array_element_legth_all_9()" local -a arr=("${!1}") local valid=true for i in "${arr[@]}"; do if ! [[ "$i" =~ ^[0-9]{9}$ ]]; then valid=false; break; fi; done; if $valid; then echo "配列は9桁の半角数字です"; else echo "配列は9桁の半角数字ではありません"; fi; echo "【finish】validate_array_element_legth_all_9()" } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】配列の要素が半角数字で、且つ、10桁の固定長であるかどうかバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_array_element_legth_all_10() { echo "【start】validate_array_element_legth_all_10()" local -a arr=("${!1}") local valid=true for i in "${arr[@]}"; do if ! [[ "$i" =~ ^[0-9]{10}$ ]]; then valid=false; break; fi; done; if $valid; then echo "配列は10桁の半角数字です"; else echo "配列は10桁の半角数字ではありません"; fi; echo "【finish】validate_array_element_legth_all_10()" } }
■/home/ts0818/work/test_validate/validation_csv/validate_csv_13.sh
#!/bin/bash # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【外部ファイル読み込み】 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # 共通的な関数を定義したファイルを読み込み source /home/ts0818/work/test_validate/validation_csv/func/validate_common.sh # CSVファイルのヘッダーの一覧を定義したファイルを読み込み source /home/ts0818/work/test_validate/validation_csv/func/constants/validate/csv_header.sh validate_csv_13() { HEADER=$(csv_header;CSV_HEADER_13) # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数定義】 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】CSVファイルのヘッダー行以外のバリデーション # ■ @param $1 CSVファイルの1行分 # ■ @param $2 ログファイル # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function execute_validate() { validate_column_01 $1[0] $2 >> $2 validate_column_02 $1[1] $2 >> $2 validate_column_03 $1[2] $2 >> $2 validate_column_04 $1[3] $2 >> $2 } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】CSVファイルのヘッダー行に対するバリデーション # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_header() { echo -e "【start】validate_header()\n" 1>&2 echo -e "HEADER:"${HEADER}"\n" 1>&2 echo -e '$1:'"$1"'\n' 1>&2 inputHeader=`echo "$1" | sed -e "s/[\r\n]\+//g"` isCorrectHeader=1 if [[ "${inputHeader}" = "${HEADER}" ]]; then echo -e "正しいヘッダーです。\n" 1>&2; isCorrectHeader=0 else echo -e "ヘッダーが不正です。\n" 1>&2; isCorrectHeader=1 fi echo -e "${isCorrectHeader}\n" 1>&2 echo -e "【finish】validate_header()\n" 1>&2 echo ${isCorrectHeader} } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】CSVファイルの1列目に対するバリデーション # ■ @param $1 CSVファイルの1列目 # ■ @param $2 ログファイル # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_column_01() { echo -e "【start】validate_column_01()\n" >> $2 # 必須チェック validate_common;validate_empty "$1" echo -e "【finish】validate_column_01()\n" >> $2 } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】CSVファイルの2列目に対するバリデーション # ■ @param $1 CSVファイルの2列目 # ■ @param $2 ログファイル # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_column_02() { echo -e "【start】validate_column_02()\n" >> $2 # 必須チェック validate_common;validate_empty "$1" # 数値のみかチェック validate_common;validate_digits "$1" echo -e "【finish】validate_column_02()\n" >> $2 } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】CSVファイルの3列目に対するバリデーション # ■ @param $1 CSVファイルの3列目 # ■ @param $2 ログファイル # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_column_03() { echo -e "【start】validate_column_03()\n" >> $2 # 必須チェック validate_common;validate_empty "$1" # 全角文字のみかチェック validate_common;validate_full_width "$1" echo -e "【finish】validate_column_03()\n" >> $2 } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】CSVファイルの4列目に対するバリデーション # ■ @param $1 CSVファイルの4列目 # ■ @param $2 ログファイル # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ function validate_column_04() { echo -e "【start】validate_column_04()\n" >> $2 # 必須チェック validate_common;validate_empty "$1" # 数値のみかチェック validate_common;validate_digits "$1" echo -e "【finish】validate_column_04()\n" >> $2 } }
■/home/ts0818/work/test_validate/validation_csv/validate_csv_main.sh
#!/bin/bash #export LANG=ja_JP.sjis # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【外部ファイル読み込み】 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # 各CSVファイルのバリデーション関数を定義したファイルを読み込み source /home/ts0818/work/test_validate/validation_csv/validate_csv_13.sh # CSVファイルのヘッダーの一覧を定義したファイルを読み込み source /home/ts0818/work/test_validate/validation_csv/func/constants/validate/csv_header.sh # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【変数定義】 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ log=/home/ts0818/work/test_validate/validation_csv/log/debug.log # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数定義】 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ validate_csv_main() { # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】CSVファイルのバリデーションを実行 # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # function main() { main() { echo "【start】main()" echo '$1'$1 >> ${log} # バリデーションを選択 selectValidate=$(select_validate $1) echo 'selectValidate:'${selectValidate} >> ${log} # 選択されたバリデーションの処理を実施する if [ 13 -eq ${selectValidate} ]; then rowCount=1 while IFS=, read -r -a row; do echo -e "■${rowCount}行目のバリデーションを開始します。■" >> ${log} validate_csv_13;execute_validate ${row} ${log} echo -e "■${rowCount}行目のバリデーションを終了します。■" >> ${log} # 行数をインクリメント rowCount=$((rowCount+1)) done < $1 else echo "バリデーションの処理が行われませんでした。" fi echo "【finish】main()" } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【関数】CSVファイルのバリデーションを選択 # ■ @param $1 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # function select_validate() { select_validate() { echo -e "【start】select_validate()\n" 1>&2 echo "【start】select_validate()" >> ${log} while read -r -a row; do echo 'row:'${row} >> ${log} validateHeader=`validate_csv_13;validate_header ${row}` echo -e 'validateHeader:'${validateHeader}"\n" 1>&2 if [ 0 -eq ${validateHeader} ]; then echo 13; break; else echo 255; break; fi done < $1 } } # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ # ■ 【処理】 # ■■■■■■■■■■■■■■■■■■■■■■■■■■■ targetDir=/home/ts0818/work/test_validate/data/file/csv for file in `\find ${targetDir} -name '*.csv'`; do # validate_csv_main;main $file done
⇧ で実行すると、
⇧ バリデーションの内容は兎も角として、処理自体は行われているようです。
バリデーション処理は、Microsoft Bingの提案をそのまま使ったから、勿論動いて無さそうね...AIさん平気で嘘付くからなぁ…
う~む、シェルスクリプトだと、Pythonより更にバリデーションの実装に辛みがあるような...
毎度モヤモヤ感が半端ない...
今回はこのへんで。