PHP5.5から mysql_connect()
や mysql_query()
など、mysql_***
系の関数は非推奨となりました。新方式の1つである mysqli の使い方をまとめておきます。(他にはPDO方式があります)
手続き型とオブジェクト型
mysqli の書き方には大きく2通りあります。
◎手続き型:従来とよく似た mysqli_***()
という書き方(インスタンス生成不要)
◎オブジェクト型:オブジェクト指向的な書き方(インスタンス生成必要)
例)DBへの接続
// DB接続例:mysqli_xxx関数を使う
$link = mysqli_connect("Host or IP", "User", "Pass", "DBName");
// DB接続例:mysqliクラスをオブジェクト化してから使う
$mysqli = new mysqli('Host or IP', 'User', 'Pass', 'DBName');
本ページでは、主に後者のオブジェクト型の書き方について記載します。
DBへの接続〜切断
<?php
// mysqliクラスのオブジェクトを作成
$mysqli = new mysqli('Host or IP', 'User', 'Pass', 'DBName');
if ($mysqli->connect_error) {
echo $mysqli->connect_error;
exit();
} else {
$mysqli->set_charset("utf8");
}
// ここにDB処理いろいろ書く(後述)
// DB接続を閉じる
$mysqli->close();
?>
SELECT(簡易方式)
完成しているSQLをqueryメソッドでそのまま実行する方式です。
// 完成済みのSELECT文を実行する
$sql = "SELECT user_id, name FROM user_table";
if ($result = $mysqli->query($sql)) {
// 連想配列を取得
while ($row = $result->fetch_assoc()) {
echo $row["user_id"] . $row["name"] . "<br>";
}
// 結果セットを閉じる
$result->close();
}
SELECT件数の取得:
// オブジェクト型
echo "rows=" . $result->num_rows;
// 手続き型
echo "rows=" . mysqli_num_rows($result);
SELECT(バインド方式)
SQLの一部を「?」としておき、あとから変数の値で補う(バインドする)方式です。
// SELECT文のひな型をもとにステートメントハンドルを取得する
$sql = "SELECT user_id, name FROM user_table WHERE user_id=? AND name=?";
if ($stmt = $mysqli->prepare($sql)) {
// 条件値をSQLにバインドする(補足参照)
$user_id = 123;
$name = "hanako";
$stmt->bind_param("is", $user_id, $name);
// 実行
$stmt->execute();
// 取得結果を変数にバインドする
$stmt->bind_result($user_id, $name);
while ($stmt->fetch()) {
echo "ID=$user_id, NAME=$name<br>";
}
$stmt->close();
}
SELECT件数の取得:
$stmt->store_result(); // これ忘れるとnum_rowsは0
echo "rows=" . $stmt->num_rows;
バインド式の補足:
$stmt->bind_param("is", $user_id, $name);
の第1引数 "is"
は後続のデータ型を表します。i=integer、s=string、d=double、b=blob
など。DATE型は s
で良いみたいです。
また下記のように値を引数内に直書きすることはできません。
誤)$stmt->bind_param("is", 123, "hanako");
応用例
使いやすいようにクラス化してみる。(DB接続情報は適宜変更して下さい)
<?php
/*
* MyDBクラス
*/
class MyDB
{
public $mysqli; // mysqliオブジェクト
public $mode; // 戻り値の形式:"json" or "array"(連想配列)
public $count; // SQLによって取得した行数 or 影響した行数
// コンストラクタ
function __construct($mode = "json")
{
$this->mode = $mode;
// DB接続
$this->mysqli = new mysqli('localhost', 'DB-USER', 'DB-PASS', 'DB-NAME');
if ($this->mysqli->connect_error) {
echo $this->mysqli->connect_error;
exit;
} else {
$this->mysqli->set_charset("utf8");
}
}
// デストラクタ
function __destruct()
{
// DB接続を閉じる
$this->mysqli->close();
}
// SQL実行(SELECT/INSERT/UPDATE/DELETE に対応)
function query($sql)
{
// SQL実行
$result = $this->mysqli->query($sql);
// エラー
if ($result === FALSE) {
// エラー内容
$error = $this->mysqli->errno.": ".$this->mysqli->error;
// 戻り値
$rtn = array(
'status' => FALSE,
'count' => 0,
'result' => "",
'error' => $error
);
if($this->mode == "array")
return $rtn;
else
return json_encode($rtn); // JSON形式で返す(デフォルト)
}
// SELECT文以外
if($result === TRUE) {
// 影響のあった行数を格納
$this->count = $this->mysqli->affected_rows;
// 戻り値
$rtn = array(
'status' => TRUE,
'count' => $this->count,
'result' => "",
'error' => ""
);
if($this->mode == "array")
return $rtn;
else
return json_encode($rtn); // JSON形式で返す(デフォルト)
}
// SELECT文
else {
// SELECTした行数を格納
$this->count = $result->num_rows;
// 連想配列に格納
$data = array();
while ($row = $result->fetch_assoc()) {
$data[] = $row;
}
// 結果セットを閉じる
$result->close();
// 戻り値
$rtn = array(
'status' => TRUE,
'count' => $this->count,
'result' => $data,
'error' => ""
);
if($this->mode == "array")
return $rtn;
else
return json_encode($rtn); // JSON形式で返す(デフォルト)
}
}
// 文字列をエスケープする
function escape($str)
{
return $this->mysqli->real_escape_string($str);
}
}
?>
使い方
$db = new MyDB();
echo $db->query("SELECT * FROM USERTABLE");
結果(JSON形式の文字列)
{
"status": true,
"count" : 2,
"result": [
{"UserID":"aaa", "Name":"AppleMan"},
{"UserID":"bbb", "Name":"BananaMan"}
],
"error" : ""
}
補足
JSON形式の文字列に変換する json_encode($ary)
は、通常だと日本語が \uXXXX
形式(Unicodeエスケープシーケンス)になってしまいます。PHP5.4以降では、
json_encode($ary, JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES)
とすることで、日本語のまま扱えます。
(・o・ゞ いじょー。
参考URL
mysqli_result::fetch_assoc: 結果の行を連想配列で取得する
http://www.phppro.jp/phpmanual/php/mysqli-result.fetch-assoc.html
mysqli - プリペアドステートメント
http://blog.livedoor.jp/nakamura_tech/archives/51311243.html
【PHP】mysqliとプリペアドステートメントについて|Furudateのブログ
http://furudate.hatenablog.com/entry/2013/10/04/211422
PHPでデータベースに接続するときのまとめ
http://qiita.com/mpyw/items/b00b72c5c95aac573b71
MySQL 改良版拡張モジュール|PHP: MySQLi - Manual
http://php.net/manual/ja/book.mysqli.php