anoncom blog
  • ホーム
  • About
KEEP IN TOUCH

PreparedなINSERT文を簡単に作る方法

11月07
2009
Leave a Comment Written by anon
このエントリーをはてなブックマークに追加
はてなブックマーク - PreparedなINSERT文を簡単に作る方法
Share on LinkedIn

PHPでWebアプリケーションなどを開発していて、SQL文を発行する際に、セキュア面や利便性などから、ADODBやPDOなどを用いて、Prepared Statementを使うSQLを書くこともあると思います。

その際、特にINSERT文などはカラムの数だけVALUESの中に ? が並ぶことになるかと思います。

-- 例:
INSERT INTO 
`persons` (`id`, `name`, 'age`, `birthday`, `mailaddress`, `phone`, `zipcode`, `address`) 
VALUES (?, ?, ?, ?, ?, ?, ?, ?);

このとき、 ? がひたすら並んでいるだけとなると非常に見づらく、INSERTする情報が多くなってくると、指定したカラム数と VALUESの ? の数が一致せず、

Number of variables doesn’t match number of parameters in prepared statement

といったエラーに遭遇したことが一度はあるかと思います。
特に、プログラムの改修をする際などは、カラム名だけ追加して、うっかり VALUESの ? だけ追加のし忘れなどをしてしまうことなんかも。。。

そこで、Prepared Statementを作る際のINSERT文のSQLを簡単で分かりやすくしたいと思います。

< ?php
$dsn = 'mysql:dbname=testdb;host=127.0.0.1';
$user = 'dbuser';
$password = 'dbpass';

try {
    $db = new PDO($dsn, $user, $password);
	
	// INSET対象となるカラム名を指定
	$columns = array(
		'id',
		'name',
		'age',
		'birthday',
		'mailaddress',
		'phone',
		'zipcode',
		'address',
	);
	
	$binds = array(
		1	=> 'anon',
		2	=> 'anon',
		3	=> '25',
		4	=> '1984-05-02',
		5	=> '[email protected]',
		6	=> '03-xxxx-xxxx',
		7	=> 'xxxxxx',
		8	=> 'Tokyo',
	);
	
	$sql = 'INSERT INTO persons '
		 . implode(', ', $columns)
		 . ') VALUES ('
		 . implode(', ', array_fill(0, count($columns), '?'))
		 . ')'
		 ;
	
	/*
	// またはテーブル名やカラム名を明示的にクオートする場合はこちら
	$sql = 'INSERT INTO `persons` '
		 . '`' . implode('`, `', $columns) . '`'
		 . ') VALUES ('
		 . implode(', ', array_fill(0, count($columns), '?'))
		 ;
	*/
	
	$stmt = $db->prepare($sql);
	
	foreach($binds as $key => $value){
		$stmt->bindValue($key, $value);
	}
	
	return $stmt->execute();
	
} catch (Exception $e) {
	error_log('[' . get_class($e) . '] ' . $e->getMessage() . ' in ' . $e->getFile() . ' on line ' . $e->getLine());
}

要点は、 $columnsという配列にカラム名を配列で持たせ、Prepared INSERT文を発行する際に、implode()関数でそのカラム名をカンマ区切りで連結、VALUESの ? は array_fill()関数で、カラム名の配列の値の数だけ ? で埋めた配列を作成し、さらにそれをimplode()関数で連結していく。

というだけです。

バインドの個所は今回手抜きにしてしまいました。
本当はバインドも同じようにもう少し見直せばもっと分かりやすく、簡潔にできると思うのですが、
いい書き方が浮かびませんでした。。。

Related posts:

  1. 接続先のサーバが応答するか判別する
Posted in PHP, 開発 - Tagged PHP, TIPS
SHARE THIS Twitter Facebook Delicious StumbleUpon E-mail
« Windows 7 をアンインストールしてみた
» PHPで相対パスから絶対URL(URI)を作成する

No Comments Yet

コメントを残す コメントをキャンセル

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

*

*

次のHTML タグと属性が使えます: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

中の人

名前: あのん (anon) anon
詳細

 

2009年11月
日 月 火 水 木 金 土
« 10月   1月 »
1234567
891011121314
15161718192021
22232425262728
2930  

カテゴリー

  • Android
  • iPhone
  • Java
  • Linux
  • Mac
  • PC
  • PHP
  • Twitter
  • VOCALOID
  • イベント
  • サーバ
  • ソフトウェア
  • ネタ
  • ネット
  • モバイル
  • 無分類
  • 話題
  • 開発

アーカイブ

  • 2011年12月
  • 2011年9月
  • 2011年4月
  • 2011年3月
  • 2011年2月
  • 2011年1月
  • 2010年10月
  • 2010年8月
  • 2010年7月
  • 2010年6月
  • 2010年5月
  • 2010年3月
  • 2010年1月
  • 2009年11月
  • 2009年10月
  • 2009年8月
  • 2009年6月
  • 2009年4月
  • 2009年3月
  • 2009年2月
  • 2009年1月
  • 2008年12月
  • 2008年11月
  • 2008年7月
  • 2008年4月

最近の投稿

  • Galaxy Nexusを購入しました
  • さくらのVPSを使いながら行ったウェブサイトの3つの負荷対策
  • PSNの障害と個人情報漏洩について
  • ミクパ♪(初音ミク ライブパーティ 2011)に行ってきたよ
  • FirefoxからChromeに乗り換えてみた

最近のコメント

  • Twitterアカウント名が商標権侵害で訴えられそうになった話 に 2011年2月のこれだけ読めば分かる Web 制作者向け情報まとめ | ウェブル より
  • Twitterアカウント名が商標権侵害で訴えられそうになった話 に 2/1 (火) 前田敦子 豊胸疑惑でネット炎上(画像) | マスコミの気になるニュースをまとめ読み! より
  • Twitterアカウント名が商標権侵害で訴えられそうになった話 に クロネコ より
  • Twitterアカウント名が商標権侵害で訴えられそうになった話 に eamcet*[SEO対策調査自動更新ブログ] | とあるTwitterユーザー、商標権侵害を理由にTwitterアカウント名の変更を求められる より
  • Twitterアカウント名が商標権侵害で訴えられそうになった話 に 心は萌え より

Tweet on Twitter

EvoLve theme by Theme4Press  •  Powered by WordPress anoncom blog