piapia123
ja

JavaScript の圧縮・難読化

整形

処理はすべてブラウザ内で完結します。データは送信されません

入力
ファイルをここにドロップすると読み込めます
出力

JavaScript を小さく、読みにくくします:コメントと空白の削除、文字列のエスケープ、数値の16進数化、ローカル変数の短縮。 ⚠️ まず最も大事なこと:難読化はコードを保護しません。 ブラウザで動く JavaScript は、受け取った側が必ず読めます。改名やエスケープが変えるのは「読むのがどれだけ面倒か」だけで、コードの構造(関数がいくつあるか、どれがどれを呼ぶか、分岐がどうなっているか)は一切変わっていません —— そして情報量があるのは構造のほうです。難読化解除ツールは整形と名前の推測だけで読める形に戻せます。難読化にかかった手間より、ずっと少ない手間で。本当に守りたいもの —— 鍵、中核アルゴリズム、認可の判定 —— はサーバー側にしか置けません。フロントエンドに置けば公開です。 では何の役に立つのか。実用的な場面は二つです:ファイルを小さくする(コメント・空白・長いローカル名は実際にバイト数へ効きます)ことと、「ソースを表示」を軽く見たときの敷居を上げることです。「少し難読化された圧縮ツール」だと思って使えば、期待は外れません。 改名はきわめて保守的です。一つも変えないほうが、間違って変えるよりましだという方針で作っています。トップレベルは一切触りません(エクスポートかもしれず、ページ内の別の `<script>` と共有するグローバルかもしれません)。`eval`、`with`、動的な `import()` があれば改名自体を諦めます(これらは実行時に文字列から変数名を組み立てられるため、静的解析が追いつきません)。新しい名前はコード中に現れるどんな名前とも衝突させません。それでも間違えた場合の代償は、エラーではなく結果が静かに変わること —— だからこそ構文の境界ごとに「難読化の前後で実行して結果を比べる」テストを用意しています。

機能

  • コメントと余分な空白をすべて削除
  • 文字列を16進数または Unicode エスケープに(非ラテン文字は \u を使い、バイトを壊しません)
  • 数値リテラルを16進数に
  • ローカル変数を `a` `b` `c` … に改名(トップレベルはそのまま)
  • 任意:`console.*` 呼び出しを削除
  • サイズの変化と改名した個数を表示
  • ⚠️ コードを保護しません —— 理由は下の Q&A に記載

使い方

  1. 左側に JavaScript を貼り付けます
  2. 改名・文字列の符号化・数値・console の扱いを必要に応じて調整します
  3. Ctrl/⌘ + Enter か「実行」を押します
  4. 先頭行の右のボタンで難読化後のコードをコピーします

よくある質問

難読化すればコードは安全ですか?
いいえ。 この種のツールについて最も明確にしておくべき点です。 JavaScript がユーザーのブラウザで動くには、ソースをそのブラウザへ渡す必要があります。そしてブラウザに渡したものは、ユーザーが必ず取得できます。難読化はソースを読みにくくするだけで、読めなくはしません —— この二つは頻繁に混同されます。 本ツールの内容で言えば:改名は呼び名を変えただけで、呼び出し関係もループも分岐もそのままです。文字列エスケープは実行時にブラウザが元に戻すので、コンソールに貼れば元の文字列が出ます。より強力な難読化(制御フローの平坦化、文字列配列の暗号化、アンチデバッグ)は読み手に数時間の手間を強いますが、解除ツールも並行して進化しています —— しかも代償として、本番のスタックトレースが `a` `b` `c` の羅列になり、障害調査が著しく難しくなります。 結論:秘密である必要のあるものはフロントエンドに置かないこと。 鍵、署名ロジック、業務ルールはサーバー側で実行し、クライアントは API を呼ぶだけにしてください。
なぜ改名されない変数があるのですか?
いずれも意図的なものです。トップレベルの宣言は一切触りません —— モジュールのエクスポートかもしれず(外部がその名前で参照します)、ページ内の別スクリプトと共有するグローバルかもしれません。どちらもコード自体からは判別できません。import した名前も触りません(別モジュールのエクスポートを指すため)。プロパティ名も触りません(`obj.userName` の `userName`)—— 改名すると存在しないプロパティを読むことになり、しかも `obj.userName` だけ変えて `obj["userName"]` を変えなければ両者の結果が食い違います。 また、`eval`・`with`・動的な `import()` が含まれる場合、ファイル全体で改名を諦めます。これらは実行時に文字列から変数名を組み立てられ、静的解析では追えないためです。どれが原因かは結果欄に明示されます。
難読化したコードはそのまま動きますか?
動きます。意味は変わりません —— 改名もエスケープも意味を保つ変換で、出力は入力と振る舞いが等価です。 ただし、これを「理論上正しいはず」で済ませてはいません。改名が誤る唯一の形は「触るべきでない場所に触る」ことで、その失敗は例外を投げません —— 結果が静かに変わるだけです。そこでテストは、各スニペットを難読化の前後で実行し結果が一致することを要求する形で組み、クロージャ、分割代入(省略記法 `{x}` や既定値 `{x = 1}` を含む)、`for (let)` の反復ごとの束縛、ラベル付きジャンプ、`class` の getter、オプショナルチェーン、テンプレート文字列、正規表現、BigInt といった壊れやすい箇所を網羅しています。 それでも、公開前に難読化後のコードで自分のテストを流してください。あなたのテストが踏んでいない経路が露呈するかもしれません。

関連ツール