🍫

Webページの見た目の差分を比較・抽出するツールを作った

2023/03/14に公開3

Webページの開発環境と本番環境の見た目を比較するツールを作りました。

GitHubのリポジトリはこちら
https://github.com/chinen-octtn/webPageDiff

はじめに

なぜこのツールを作ったか

数百ページに及ぶリファクタリングを行った際に、各ページのレイアウトに影響が出ていないか目視で検証するのが大変だったことから、このツールを作りました。

当時は、開発環境と本番環境のWebページをブラウザで並べて表示し、タブを切り替えて差異がないか目視で確認していました。コンテンツ量が多く何度もスクロールしながら確認しなければならないページでは見落としが起きないように集中力を保つ必要があり、100ページ以上の確認には3時間近くもかかっている状況でした。

全ページの確認が完了するまでに時間がかかりすぎることや、見落としのリスクもある方法を改善したいとツールを探したのですが希望に合うものが見つからず、自作することにしました。

  • レイアウトを比較して差がある場合は可視化したい
  • できるだけグローバルにインストールしたくない
  • アプリも増やしたくない(使いたいときだけ使う)
  • ローカルでさくっと確認したい(毎回Gitプッシュ → CIは待てない)

このツールでできること

比較したい2ページのURLを入力して、それらの差分を抽出します。
差分がある場合はスクリーンショットにハイライトして視覚的に確認できます。(差分確認用の画像を生成する)


仕組み

CLIで比較したいページのURLを入力すると、差分を抽出して画像化する構成にしました。

Webページをキャプチャする方法

playwrightを使ってスクリーンショットを撮影し、画像を生成します。

処理の実行にはNode.jsを採用しました。

コードを一部抜粋します。

CLIからURLを渡すために環境変数を使っています。

import playwright from "playwright";

const ENV = process.env;

const webPath = [
  {
    id: "original",
    url: ENV.ORIGINAL,
  },
  {
    id: "compare",
    url: ENV.COMPARE,
  },
];

(async () => {
  webPath.forEach(async (webPage) => {
    const browser = await playwright["chromium"].launch();
    const context = await browser.newContext();
    const page = await context.newPage();
    await page.goto(webPage["url"]);
    await page.screenshot({
      path: `images/${webPage["id"]}.png`,
      fullPage: true,
    });
    await browser.close();
  });
})();

キャプチャした画像を比較する方法

画像の比較のためにimageMagicを採用しました。

compareコマンドで画像パスを渡すと差分を抽出してくれます。

compare 比較元の画像パス 比較用の画像パス 差分画像を出力するパス

CLIで実行できるようにする

シェルスクリプトを作成しました。

#!/bin/zsh

#元ページのURLを入力するプロンプトを表示
echo -n original: 
read str 

#比較ページのURLを入力するプロンプトを表示
echo -n compareWith: 
read str2 

#環境変数にURLを渡してnodeタスク実行、スクリーンショットを生成する
ORIGINAL="${str}" COMPARE="${str2}" node ./tasks/diff.mjs

#画像比較を実行
compare $(cd $(dirname $0);pwd)/images/original.png $(cd $(dirname $0);pwd)/images/compare.png $(cd $(dirname $0);pwd)/images/diff_pc.png

ツールの使い方

初回のみインストール環境を準備します。次回からはコマンド1行で実行できます。

詳しくは、GitHubのREADMEに記載しており、この記事では抜粋して紹介します。

インストール方法(初回のみ)

GitHubのリポジトリをcloneします。

git clone https://github.com/chinen-octtn/webPageDiff.git

imageMagicが入っていない場合はインストールします。

brew install imagemagick

playwright をインストールします。

cd /PATH/TO/webPageDiff
npm install

ファイルの実行権限を付与します。

cd /PATH/TO/webPageDiff
chmod u+x diff

CLIでの実行

cloneしたリポジトリへの移動し、コマンド実行します。

cd /PATH/TO/webPageDiff
./diff

処理が始まると、下記のようにCLIが入力を受け付けます。

% ./diff
original:

比較元ページ(original)のURLを入力してEnter、次は比較ページ(compareWith)のURLを入力してEnterします。

% ./diff
original:https://example.com/
compareWith:https://example.net/

自動的に処理が動いて、ディレクトリ内に画像が生成されます。

diff_pc.pngはPCレイアウトでの差分で、diff_sp.pngはスマートフォンレイアウトでの差分となります。
違いがある部分は赤色で表示されます。

まとめ

ツール制作に割くことができる時間は限られていたので、即席で簡易的に作りましたが、それでも導入前と比較するとリファクタリングの検証に要する時間は大幅に短縮されました。
(1ページあたり1〜2分かかった作業が20秒くらいで終わる)

ツールの特徴やメリット

このツールの特徴は、ローカルで動作することです。Gitにプッシュする前にすぐに確認したいときに便利です。また、localhostで開発中のページやIP制限されたページも差分比較の対象とすることができます。(Webツールだと難しいはず)

エラー通知やしっかり検証する環境を求めるのであれば、CIを導入した方が良いでしょう。

このツールはリファクタリング後の「レイアウトの変化がないこと」を確認する目的で作成したため、ピクセルパーフェクトなデザインのチェックには適していません。(1pxのズレでも差分として検出されるため現実的ではない)

ツールの改善点や今後の展望

「なぜこのツールを作ったか」の項目では、「できるだけグローバルにインストールしたくない」と述べていますが、imageMagicはインストールが必要です。これは改善したい点です。

筆者はフロントエンド開発が主な業務なので、Node.jsの環境は用意していますが、PythonやPHPなど、その他の言語の動作環境はローカルにないため、できればnpmパッケージをローカルにインストールするだけで済むような構成にしたいと考えています。
もっと良い方法があれば教えてください。

  • npmパッケージのみで実現したい
  • インストール不要のWeb版も作りたい
  • CLIだけでなくGUIがあると良さそう
  • 複数ページをまとめて処理できるようにしたい

知見のある方、似たような解決方法をご存知の方はぜひ連絡・コメントください。一緒に開発してみたいという方も歓迎です。

Discussion

まぁしまぁし

記事を見た方から、imageMagicを使わなくてもplaywrightだけで差分比較できそうというコメントをもらったので、さっそく調べて改修してみます。情報ありがとうございます!