読者です 読者をやめる 読者になる 読者になる

one's way blog

ワクワクを生み出せるWebエンジニアを目指して。

【40:ユーザ管理画面 】PHPからDB基本操作

f:id:seintoseiya:20151009204216p:plain
プロジェクトNo.40:ユーザ管理画面 - DEMO

前回の超簡素なログインシステムに引き続き、ユーザ管理画面を作りました。
SELECT, INSERT, DELETE, UPDATEと基本的な機能のみを考えて、なるべくセキュリティにも気を使いました。

一覧表示(SELECT)

まずはDBの内容を表示するためにSELECT文を発行します。
DB接続部分は前回と同じなので省略します。
ユーザ入力を使用しないので、query()を使ってforeach()で繰り返して出力しています。

PHP
<?php
$sql = "SELECT * FROM login";
print "<table border='1'><tr><th>user</th><th>password</th></tr>";
foreach ($pdo->query($sql) as $row) {
	print "<tr><td>" . $row['user'] . "</td><td>" . $row['pass'] . "</td></tr>";
}
print "</table>";
?>

ユーザ追加(INSERT)

ユーザからの入力値を扱う場合は注意が必要です。
入力値をフィルタ関数でチェックして、プリペアードステートメントを使いSQLインジェクション対策をします。
また、今回はuserをPRIMARYに設定しているので、既に存在しているuserを追加しようとするとSQLエラーが発生します。
INSERT IGNORE INTOはPRIMARYエラーを発生させずに実行でき、もちろんデータ追加は行なわれません。
$stmt->rowCount()で追加レコード数が取得できるので、これを使ってメッセージの分岐を行います。

PHP
<?php
$i_user = (string)filter_input(INPUT_POST, 'user');
$i_pass = (string)filter_input(INPUT_POST, 'pass');

// 中略

$stmt = $pdo->prepare("INSERT IGNORE INTO login (user, pass) VALUES (?, ?)");
$stmt->bindValue(1, $i_user);
$stmt->bindValue(2, $i_pass);
$stmt->execute();
if ($stmt->rowCount()===0) {
    print "既に存在するユーザです。";
}else{
    print "新しいレコードを追加しました。";
}
?>

ユーザ削除(DELETE)

INSERTとほぼ同じです。

余談ですが、HTMLの方でuserの値を入力させるのではなく、
削除ボタンを用意して、あらかじめ指定したuser値をそこから取得して削除する様にした場合は、
プリペアードステートメントを使わなくても、exec()でも良いかと思います。
exec()は返り値に実行結果のカウントを返すのでシンプルなソースになるかと思います。

PHP
<?php
$i_user = (string)filter_input(INPUT_POST, 'user');

// 中略

$stmt = $pdo->prepare("DELETE FROM login WHERE user = ?");
$stmt->bindValue(1, $i_user);
$stmt->execute();
if ($stmt->rowCount()===0) {
    print "指定したユーザは存在しません";
}else{
    print "1件削除しました。";
}
?>

パスワード変更(UPDATE)

UPDATEの際は、最初にパスワードを変更する対象のuserが存在するかをチェックする必要があります。
SELECT文を事前に発行してチェックするでも良いですが、
INSERT、DELETEの時と同じ様に、存在しないユーザを指定された場合でもUPDATE文を発行して、
実行件数を取得した後にメッセージ分岐すれば、SQL文の発行が一回で済みます。

PHP
<?php
$i_user = (string)filter_input(INPUT_POST, 'user');
$i_newpass = (string)filter_input(INPUT_POST, 'newpass');

// 中略

$stmt = $pdo->prepare("UPDATE login SET pass = ? WHERE user = ?");
$stmt->bindValue(1, $i_newpass);
$stmt->bindValue(2, $i_user);
$stmt->execute();
if ($stmt->rowCount()===0) {
    print "指定したユーザは存在しません";
}else{
    print "パスワードを変更しました。";
}
?>

HTMLフォームで気をつける事

HTML
<form method="post" action="insert.php">
	user:<br>
	<input type="text" name="user" maxlength="50" pattern="^[0-9A-Za-z]+$" title="必須項目:半角英数字で入力してください。" required>
	<br>
	password:<br>
	<input type="password" name="pass" maxlength="100" pattern="^[0-9A-Za-z]+$" title="必須項目:半角英数字で入力してください。" required><br>
	<input type="submit" value="Create">
</form>

最大文字数の指定

DBのフィールド設定に合わせた最大文字数(maxlength)を指定します。

半角英数字のみ入力に制限する

HTML5のpattern属性を使えば楽に実装できます。

JavaScriptでも書けますが、HTML5に対応しているブラウザを想定しているなら上記がシンプルだと思います。
他にもimeなんちゃらという対応も出てきたが、IEFirefoxのみ対応ということで論外でした。

必須項目設定をする

これもHTML5の機能ですが、inputエレメントにrequiredを付けるだけで必須項目チェックをしてくれます。

パスワードの伏字

パスワードを伏字にしたい場合は、とするとできます。
マルチバイト文字の直接入力は不可能ですが、コピペすると可能になるので、上記のpattern属性を使用すると良いかと思います。

全ソースはこちら

github.com

関連アプリ・書籍

いきなりはじめるPHP~ワクワク・ドキドキの入門教室~

いきなりはじめるPHP~ワクワク・ドキドキの入門教室~

パーフェクトPHP

パーフェクトPHP

独習PHP 第2版

独習PHP 第2版