WEB担当者は知っておきたい!SQLインジェクションとその対策!PHP例あり

現在、多くの企業でホームページが作られるようになりました。 昔は名刺代わりに利用されていたホームページですが、近年は 「マーケティングの中心」 として自動的に24時間365日集客を行ってくれるツールとして、有効活用化が求められています。 そんなホームページのセキュリティとして知っておきたいのが 「SQLインジェクション」 です。 今回は、このSQLインジェクションについてお話していきます。

SQLインジェクションとは

SQLインジェクションとは

SQLインジェクションとは[/caption] SQLインジェクションとは、ホームページなどで利用される「顧客情報」などがデータベース化されている場合、そのデータベースを扱うSQLという言語を使った攻撃の事を言います。 例えば、 ・商品情報 ・マイページで個人情報 ・イベント情報 ・従業員情報 などがホームページ上に記載されているケースは多いです。 これらの情報はデータベース管理されるのが一般的で、この情報を改ざんするなどの攻撃になります。 似たような攻撃手法としてクロスサイトスクリプティングという方法があります。 クロスサイトスクリプティングはフォーム事態を改変させるなど、攻撃対象がフォームそのものである事が多いのに対し、SQLインジェクションは、名前の通り「SQL」を使った攻撃に特化しています。

SQLインジェクションの例 PHP

SQLインジェクションの例 PHP

SQLインジェクションの例 PHP[/caption] では、ここからは実際のSQLインジェクションの手法について見ていきます。 現在多くのホームページは、PHPというプログラミング言語を使用していますので、例としてPHPを用いて説明していきます。

脆弱なフォームとは

攻撃の対象になるのは、主にフォームです。 例えば、氏名やTELなどの入力欄になります。

フォーム

今回は簡単に作りますが、このようなフォームで入力されたデータは、サーバー側のPHPで処理されます。

amela.co.jp news image 4

この様に、フォームから送られてきたデータを活用して処理を行います。 次に、このフォームから入力された値を、データベースに入れるとします。 その際、変数をSQL文に変換する必要があります。

amela.co.jp news image 5

最終的に、

SELECT * FROM users WHERE name='画面から登録された氏名'

このような形でSQLを作りたかったという仮定です。 (氏名を元にユーザーテーブルからデータを取得する) この時、仮にユーザーが氏名の部分に 「’ OR name LIKE ‘%」 という文字を打った場合、どうなるでしょう。 完成するSQL文は

SELECT * FROM users WHERE name='' OR name LIKE '%'

となります。 これは、usersテーブルから、全てのユーザー情報を取得する事を意味しています。 つまり、製作者側が意図していないSQLが実行されてしまった事になります。 本来こういったフォームでは、シングルコーテーションをSQL文に入れる際にはエスケープするなど、対処するのですが、対処できていないフォームを 「脆弱性のあるフォーム」 と呼ぶのです。

もしもSQLインジェクションされるとどのような被害があるのか

では、先程のような形でSQLを不適切な形に改ざんされる事には、どのようなリスクが有るのでしょうか。

データベースに蓄積された非公開情報の閲覧

データベースに蓄積された非公開情報を閲覧できるようになります。 例えば、通常多くのSQLでは「;」をつけることで、SQL文の終わりを指定できます。 そのため、「;」の後ろの文字は、次のSQL文と判断されます。 先程の例の氏名の入力に 「’;SELECT * FROM orders WHERE id LIKE ‘%」 と入力したとします。 するとSQL文としては

SELECT * FROM users WHERE name='';SELECT * FROM orders WHERE id LIKE '%'

となります。 これは、usersテーブルの検索とは別に、ordersテーブルを全検索しています。 そのため、理論上全てのテーブルの情報を取得する事自体は可能になるのです。

データベースに蓄積された情報の改ざん、消去

次に、データの改ざんや削除が考えられます。 例えば、ユーザー情報を更新する際に、

UPDATE users SET name='test' WHERE id='1'

このような形でUPDATE文を実行しますが、このWHERE文を無効にするような形でSQLインジェクションを仕掛ければ、 (先程のSELECT文でやった事と同様の内容) 全てのユーザーの名前を「test」で上書きすることが可能になります。 これにより改ざんや削除が可能になるのです。

不正ログイン

SQLを改ざんする事によって、メールアドレスやパスワードをリセットし、自分のメールアドレスに初期化したパスワードを送らせるような攻撃が考えられます。 そうすると、不正にログインが可能になり、その他の個人情報を見られたり、不正にクレジットカードを使って買い物をされる・・・といった危険性もあるでしょう。

ストアドプロシージャ等を利用したOSコマンドの実行

ストアドプロシージャとは、SQL内で利用されるプログラミングで、OSコマンドの実行が可能です。 そのため、公開しているシステム以外の部分でも情報の漏洩や改ざんの危険性が出てきてしまうのです。

SQLインジェクションはどのように対策する?

SQLインジェクションはどのように対策する?

SQLインジェクションはどのように対策する?[/caption] では、このSQLインジェクションに対してどのような対策が可能なのでしょうか。

入力値をエスケープする

少し触れましたが、入力された値をエスケープすることで、不正な文字を入力出来なくすることが可能です。

$name = mysqli_real_escape_string(SQLへの接続情報,$_POST["name"]);

今回、SQLへの接続情報は例として作っていませんが、mysqlを利用する場合には、このような形でエスケープ処理が可能になります。

エラーメッセージを表示しない

攻撃者は、わざとおかしな入力値を入力し、エラーを出力させます。 このエラー内容によって ・システムの構成 ・システムの穴 ・データベースのカラム構成 などを読み解こうとします。 開発する時点では、エラーメッセージが出る事は、非常にありがたいものです。 しかし、実際にリリースしたシステムにこのようなエラーメッセージを表示してしまうと、攻撃者に対して「脆弱性のヒント」を与えてしまう事と同じなのです。 だからこそ、本番環境ではエラーメッセージを表示しないというのは、シンプルですが非常に効果的です。

データベースの権限設定をしっかりと行う

データベースを利用する際、例えば ・管理者が利用できる画面 ・会員が利用できる画面 ・一般ユーザーが利用できる画面 というように、利用者の属性によってPHP側での処理が分かれている事が多いです。 そして、PHPの処理を始める際にデータベースへの接続を行いますが、この時に ・接続先のMySQLサーバ ・ユーザー名 ・パスワード を指定します。 このユーザーを複数作ることが可能で、またユーザーごとに権限を付与することが可能です。 ・操作可能なテーブル ・SELECTは可能だがDELETEやUPDATEは不可 などの設定を行うことが可能です。 それにより、不必要なテーブルへのアクセスを禁止することも、セキュリティの観点から重要になります。

SQLの作成にはプレースホルダを利用する

プレースホルダとは、実際の内容を後から挿入するために、最初の段階では場所の指定だけを行うような作り方になります。 例えば、これまでの説明でSQL文を作成する際に、

amela.co.jp news image 7

この様に、直接文字列の結合を行いました。 これを、直接文字列を結合するのではなく、

amela.co.jp news image 8

この様に、「:変数名」を付けて作成します。 その後、「バインド」と呼ばれる形で先程の変数の値を置き換えてSQLを実行することが出来ます。 このプレースホルダを利用することで、SQLインジェクションを回避することが出来ます。

WAFを導入する

WAF(Web Application Firewall)は、WEBアプリケーションの脆弱性対策として利用されるサービスです。 WAFは、WEBアプリケーション自体に実装するのではなく、ネットワークに配置するなどして対策をします。 これにより、SQLインジェクションだけではなく ・バッファオーバーフロー ・クロスサイトスクリプティング ・OSコマンドインジェクション など、他の攻撃にも対処することが出来ます。

環境を最新にしておく

OSやプログラミング言語、その他導入しているソフトなどに関して、全てを最新の状況にしておくことも1つの対策です。 例えば、昔は使われていたけど、脆弱性が見つかったため、最新バージョンでは使用できなくなった機能が存在するものは多いです。 PHPでも、 ・古い関数の廃止 ・新しい関数の登場 は常にあります。 そのため、古い環境のまま放置しておくこと自体が、非常に危険なのです。

セキュリティの相談ならAMELAに

今回は、WEBの担当者に知っておいて欲しい「SQLインジェクション」についてお話してきました。 プログラムの話も少し出てきたので、難しく感じたかもしれませんが、結論からすると 「知識や経験の無いプログラマーが安易に作ったプログラム」 というのは危険性が伴う事があるということです。 特に昨今は、誰でも簡単にフリーランスとして独立できる環境が整ってきています。 オンラインスクールでも、フリーランスとして活躍できることを謳う業者も多いです。 そのため、自分に自信のある人ほど 「オンラインスクールで学んですぐに独立する」 と考えている可能性があります。 そういったフリーランスでも、実力があれば良いのですが、費用だけで選んでしまうとこういったトラブルに発展する可能性もあるのです。 そのため、もしもこれからWEBを活用したビジネスを行っていく予定であれば、是非AMELAにご相談下さい。 専門的な知識を持った人材を派遣することも出来れば、オフショア開発で安価なシステム開発を行うことも可能です。