🏠 ホーム
nginx
apache
ネットワーク
Linux
根本の仕組み
クラウド

🔐 外部画像を安全にプロキシ経由で表示し、改ざんも検出する方法【Go言語+Base64活用】

  インフラ >     クラウド >  

Webサービスでユーザーが外部の画像URLを登録できるようにしている場合、意図しない改ざんやマルウェアの混入リスクが常に存在します。

この記事では以下を解説します:

Go言語を用いた実装例と共に、画像保存なしでセキュリティを担保するアプローチをご紹介します。


🔥 なぜ画像のプロキシ表示が必要か?

ユーザーが登録する画像URLが自分の管理外のドメイン(例: https://sample.com/image.jpg)だった場合、以下のようなセキュリティリスクがあります。

リスク 内容
☠️ マルウェアの埋め込み EXIFやファイル構造を悪用した攻撃
🕵️ トラッキング目的の画像 Cookie送信やIP取得のリスク
🎭 登録後に画像を差し替える 表面上は同じURLでも別画像にすり替えられる

✅ ステップ1:安全なプロキシ構成

最初のステップとして、自前のサーバーを介して外部画像を表示する構成を取ります。

ユーザー → 自サーバー(画像プロキシ)→ 外部画像URL

🎯 なぜプロキシを通すのか?


🧼 ステップ2:Goで画像検証+再エンコード

以下のような処理で安全化します:

  1. Content-Type(MIME)確認

  2. image.Decode()でファイルの形式・構造検証

  3. 再エンコード(JPEGやPNGとして)してEXIF含むメタデータを除去

  4. その結果の画像を返却(または保存)

// 画像の読み込み・再エンコード(安全化)
img, _, err := image.Decode(bytes.NewReader(data))
var buf bytes.Buffer
err = jpeg.Encode(&buf, img, nil) // 再エンコードでEXIF等除去

この処理を行うことで、悪意あるEXIF情報や不可視のペイロードを除去し、安全に配信可能になります。


🔍 ステップ3:改ざんチェック(保存しない構成で)

💡 アイデア:Base64文字列にして先頭・末尾を保存

画像本体は保存せず、Base64化した文字列の一部のみ(先頭・末尾)を保存します。

base64Str := base64.StdEncoding.EncodeToString(buf.Bytes())
pre := base64Str[:500]
tail := base64Str[len(base64Str)-500:]

これをDBに保存:

ad.PathBannerPre = pre
ad.PathBannerTail = tail

🔁 次回以降の比較:

  1. 同じ画像URLから再取得

  2. 再エンコード後のBase64文字列のpre/tailとDBに保存された値を比較

  3. 一致しなければ画像が変更されたと判断


🧠 拡張アイデア:画像の四隅部分だけでチェック

全体の先頭・末尾以外に、画像の左上・右上・左下・右下などの特定ピクセルエリアだけをBase64化して比較するという高度な実装も可能です。


💾 サーバー保存 vs プロキシ型:どちらがコスト高?

方法 特徴 ディスクコスト CPUコスト 安全性
🔁 プロキシ+毎回再エンコード 保存しない 高(都度処理)
💾 サーバー保存+初回検査 ローカル配信

🎯 実運用構成イメージ

  1. 登録時に画像をプロキシ取得

  2. MIME / EXIF チェック & 再エンコード

  3. Base64 変換 → pre / tail をDB保存

  4. 表示時にはプロキシ経由で再取得 or キャッシュ活用

  5. 一定期間ごとに再チェック可能


📝 まとめ

項目 内容
セキュリティ EXIF除去・トラッキング防止・差し替え検出
保存構成 少人数ならローカル保存が現実的
非保存構成 Base64比較で改ざん検出できる
Go実装 image.Decode, jpeg.Encode, base64.EncodeToString を使用

📢 最後に

この手法は、広告画像やユーザーアップロード画像を扱う全てのサービスに活用できます。
特に「画像は保存したくないけど、安全性は担保したい」サービスには理想的な構成です。


ご希望があれば、この仕組みをOSS化したサンプルリポジトリやAPIモックも公開可能です。
Zenn、Qiita、GitHubでの共有も検討中ですので、ご要望があればお知らせください!


必要に応じて、記事タイトルや構成をZenn・Qiita向けに調整した構成にもできますので、お気軽にご相談ください。

登録日:

更新日:

by

コメント         tweetでコメント