SQLを直で触る私とmd5
今日の学びを書きます ひっそりPHP書いてるびきニキです。
今日はログイン機能を作っていたのですが、あまりに間抜けすぎるミスをしたので備忘録です
作ったログイン機能の動きを確認するべく実行してみたのですが、正しいパスワードとIDを入れても失敗判定が続きます。ユーザーをかなり昔に作ったこともあり、記憶違いかなと思った私は新規ユーザーを作りました。
phpMyAdminを直で触って…。
新規ユーザーを作って、正しいユーザー情報を入力してもダメ。なんでだろうと思っていたのですが「md5関数を使用していた」のが問題でした。
ついでに解説、htmlspecialchars
XSS攻撃への対策は、<や>といったHTMLタグを構成しうる危険な文字を別の文字に置き換えることです。
PHPには
htmlspecialchars()
という関数が用意されており、この関数を通すことで無害な文字へと変換することができます。
具体的には次のように使用していました。
$staff_code = $_POST['code'];
$staff_pass = $_POST['pass'];
$staff_code = htmlspecialchars($staff_code);
$staff_pass = htmlspecialchars($staff_pass);
$staff_pass = md5($staff_pass); // こいつは後から触れます
これをすることで<や>が<や>といった実体参照に置き換わり、見かけ上同じ内容を表示しているが、タグとして認識されない無害な文字列へと置き換わります。
このようにhtmlspecialchars()を使用することで、無害な文字へとエスケープして表示させることができるようになります。
md5とかいう魔法
特殊文字を無害化した後に書いてあるこいつこそがmd5です。
$staff_pass = md5($staff_pass);
この行では、md5 関数を使用してパスワードをMD5ハッシュに変換しています。
MD5はハッシュ関数の一つで、任意の長さのデータを固定長のハッシュ値に変換します。これは、平文のパスワードをデータベースに保存する代わりに、ハッシュ値を保存するためよく使用されます(聞くところによると)。
ただし、MD5は現在ではセキュリティ上の理由から推奨されていないので、今はより安全なハッシュ関数(例:password_hash)の使用が望ましいんだって。
自分でこうコードを書いていたのをすっかり忘れていました。つまり、コード上ではハッシュ値に変換して保存していたのに、直でSQLデータを追加したことで変換前の文字列が入っていて弾かれていたわけです。そりゃあそう。
ちゃんとデバッグっぽいこともしました。echo残しっぱなしだとそれはそれで怒られました。