gitで1行になっているjsonファイルをどうするか?【解決編】

前回、git管理を行うために自動更新される1行JSONについての問題を整理しました。

  • JSONファイルが1行で保存されている
  • プロジェクトのファイルはエディタ側で監視されている
  • プロジェクトファイルを外部ツールから直接書き換えるのは得策ではない

それに対する1つの対応策として、

編集のリポジトリとコミット用のリポジトリを分ける、というのを考えました。

今回は、それをやってみようと思います。

対応策のざっくりとしたイメージです。

編集用のリポジトリ配下に対するファイル操作を検知して、そのファイルがJSONであった場合は整形ツールを使い、コミット用のリポジトリにコピーする、という流れになります。

ここでファイル操作の検知と整形ツールが必要になってきます。

  • fswatch: ファイルに対する操作を検知するコマンド
  • jq: javascriptの整形ツール

これらは事前にインストールして準備しておきます。自分の環境では、どちらもhomebrewコマンドでインストールすることができました。

まずは編集用のリポジトリですが、これは前回作成したプロジェクトを使います。
このプロジェクトはツクールGUIで直接開くプロジェクトです。

コミット用のリポジトリは、この編集用のリポジトリをコピーしたものになります。
.gitも含めてまるごとコピーして、準備は完了です。

次にfswatchというコマンドを利用します。このコマンドはファイルに対する操作を検知することができる便利なコマンドです。

今回はこんな風に使います。

$ fswatch -r 編集用リポジトリのディレクトリ | xargs -I{} ./cosmetic-mirror.sh {}

(xargsの処理については、書く気力が尽きたのでいつか追記します(笑))

fswatchから変更を検知したファイルパスが渡ってくるので、それにxargsコマンドで引数として受け取り、整形してコピーするスクリプト(cosmetic-mirror.sh)に渡します。

このスクリプトでJSONファイルのファイル操作が検知された時点で、jqコマンドで整形を行ってからコピーを行います。

cosmetic-mirror.shはこんな感じになります。(cosmetci-mirror.shには実行権限をつけておきます)

編集用のリポジトリ名はSimpleQuest、コミット用のリポジトリ名はMirrorSimpleQuestとしています。

#!/usr/bin/env bash

# fswatchで通知された情報が入ってくる、空白区切りの形式
# 空白区切りの1番目にファイルパスが入っているので、それを取り出す
path=(${1})

# 変更されたファイルパスを表示する(確認用)
echo path

# コピー元ファイルの存在チェック 存在しない場合は削除なのでコピー先を削除する
if [ ! -e $path ]; then
  echo 'コピー元のファイルが存在しないので、削除します。'
  rm $newpath
  exit
fi

# 差分確認用のリポジトリディレクトリパスに書き換え
newpath=${path/SimpleQuest/MirrorSimpleQuest}

if [[ $(echo $path | grep -e 'json') ]]; then
  echo 'jsonファイルを読みやすい形式に加工処理します。'
  cat $path | jq . > $newpath
else
  echo 'JSON以外はそのままコピーして保存します。'
  cp $path $newpath
fi

準備ができたので、fswatchのコマンドを実行します。

$ fswatch -r SimpleQuest | xargs -I{} ./cosmetic-mirror.sh {}

ターミナルで実行すると実行中になります。解除する時は、Ctrl+Cで解除できます。

この状態でツクールのプロジェクト保存を押してみましょう。

そうすると実行中のターミナルに変更を検知したファイルがズラズラっと表示されます。
自分の環境では以下のファイルが表示されました。

  • data/*.json
  • index.html
  • js/plugin.js
  • package.json

何も編集していない状態での上書き保存では、data/System.jsonのversionIdのみが変更差分となります。

初回のみは整形された情報も入ってくるので、これらのファイル全てにdiffがあるはずです。

整形された内容を確認しコミットしておけば、次回以降は変更箇所のみが表示されるでしょう。

試しに整形された内容をコミット後にもう一度プロジェクトを上書き保存すると、data/System.jsonのversionIdのみが変更差分として表示されることを確認できました。

-  "versionId": 61991541,
+  "versionId": 97635348,

これであの1行JSONを回避して、編集内容のdiffを楽に確認できるようになりました。

もっといい方法があると思いますので、あったらぜひ教えて下さい。

それでは、今回はこのへんで。

(殴り書きの内容なので説明が雑です、、、ご了承ください)

追記

現行では、ファイルの削除に対応していないですね、、、(汗)
暇を見つけて修正します、、、

=> ファイルの存在チェックと削除処理を入れました。

タイトルとURLをコピーしました