2024 年度 DB 技術 : PHP + RDBMS 最低限 PHP
はじめに
PHP は Web サーバ側で動作するサーバサイドスクリプトである. 動的な Web ページの作成に良く用いられている. 文法は C 言語に似ている.
PHP のエラーの確認.
ブラウザで PHP ファイルにアクセスした時にエラーが出ることがある. エラーが出た場合はログファイルを確認することが良い.
$ sudo cat /var/log/apache2/error.log
文法
以下はホームディレクトリ以下の public_html フォルダ内で実行することを想定している.
php スクリプトは基本的に以下の構造をしており,開始タグ・終了タグが必要であることに注意されたい.
<?php //<-- 開始タグ 実行する内容; //<-- 行の末尾は ; (セミコロン) ?> //<-- 終了タグ
Hello World
基本というべき Hello World を表示するプログラムは以下のように書ける. ファイルの拡張子は .php とする.
$ vi test1.php
<?php //<-- 開始タグ
print "Hello World!"; //<-- 行の末尾は ; (セミコロン)
?> //<-- 終了タグ
このファイルをブラウザで表示させると,"Hello World!" が表示されるであろう.
変数
PHP では変数には接頭詞 $ を付けることになっている. 大文字と小文字は区別される.
PHP は C 言語と違い,変数の型を宣言する必要は無い. 代入される中身から自動的に型を決めてくれる. 以下に代表的なデータ型を挙げる.
整数 → integer 実数 →float, double 文字列 → string 論理値 → boolean 配列 → array
文字列は ' (シングルクォーテーション) もしくは, " (ダブルクォーテーション) で囲む. 以下のような変数に代入する場合には,シングルクォーテーションでもダブルクォーテーションでも, どちらを使っても問題ない.
$ vi test2.php
<?php
$a = "ようこそ"; //<-- ダブルクォーテーションで囲む
print $a;
$b = '松江へ'; //<-- シングルクォーテーションで囲む
print $a.$b; //<-- . (ドット)で文字列連結
?>
一方で,以下のような例では,シングルクォーテーションで囲むかダブルクォーテーションで 囲むかで出力が変化する. ダブルクォーテーション内の変数や改行コードは展開されるが, シングルクォーテーション内の変数や改行コードは展開されないでそのまま表示される.
$ vi test3.php
<?php
$a = "ようこそ";
print "$a";
$b = "松江へ";
print '$b'; // <-- . (ドット)で文字列連結
?>
関数
PHP には C 言語のように「関数」がある.特に有名な関数は phpinfo だと思われるが, この関数を使うと PHP の環境情報が表示される.
$ vi test4.php
<?php
phpinfo();
?>
他にも日付を表す date 関数などあり,以下のように書けば今日の日付が表示される.
$ vi test5.php
<?php
print "今日は".date("Y")."年".date("m")."月".date("j")."日 です";
?>
getenv コマンドを使うとアクセスしてきたクライアントの情報を表示することができる.
$ vi test6.php
<?php
print getenv("REMOTE_ADDR"); //<-- クライアントの IP
print getenv("HTTP_USER_AGENT"); //<-- クライアントのブラウザ情報
?>
繰り返し処理
for 文,while 文,do-while 文が使える
for 文の構造は以下の通りである.
for (初期値; 繰り返しの条件; 変化){
繰り返し実行する処理;
}
具体的には以下のように書ける
$ vi test7.php
<?php
for ($i=1; $i < 15; $i++){
print "*";
}
?>
while 文の構造は以下の通りである.
while (繰り返しの条件){
繰り返し実行する処理;
}
具体的には以下のように書ける
$ vi test8.php
<?php
$i = 1;
while ($i < 15){
print "+";
$i++;
}
?>
do-while 文の構造は以下の通りである.
do{
繰り返し実行する処理;
} while (繰り返しの条件)
具体的には以下のように書ける
$ vi test8.php
<?php
$i = 1;
do {
print "x";
$i++;
} while ($i < 15)
?>
条件分岐
条件分岐として,if 文,switch 文が使える.
if 文の構造は以下の通りである.
if (条件1){
処理1;
} elseif (条件2) {
処理2;
} else {
処理3;
}
具体的には以下のように書ける.
$ vi test9.php
<?php
// date("G") で時刻が出る
if (date("G") >= 18) {
print "こんばんは";
} elseif (date("G") >= 9) {
print "こんにちは";
} elseif (date("G") >= 6) {
print "おはよう";
} else {
print "眠くない?";
}
?>
switch 文の構造は以下の通りである.
switch (変数) {
case 変数1:
処理1;
break;
case 変数2:
処理2;
break;
default:
処理X;
}
具体的には以下のように書ける.
$ vi test10.php
<?php
// date("G") で時刻が出る
switch( date("G") ) {
case 10:
print "10 時のおやつです";
break;
case 15:
print "午後 3 時のおやつです";
break;
default:
print "おやつの時間ではないです";
}
?>
配列
PHP でも配列を使うことができる.以下のように まとめて定義することも,要素ごとに定義することもできる.
//まとめて定義 $m = array( "ネズミ", "ウシ", "トラ", "ウサギ"); //要素ごとに定義.添え字番号が入れ子になっていても構わない $m[2] = "トラ"; $m[0] = "ネズミ"; $m[1] = "ウシ"; $m[3] = "ウサギ"; //要素ごとに定義.添え字が順番通りなら以下のように省略できる. $m[] = "ネズミ"; $m[] = "ウシ"; $m[] = "トラ"; $m[] = "ウサギ";
配列を使うと,上記の test9.php は以下のように書ける.
$ vi test11.php
<?php
// date("G") で時刻が出る
$m = array("こんばんは", "こんにちは", "おはよう", "眠くない?");
if (date("G") >= 18) {
print $m[0];
} elseif (date("G") >= 9) {
print $m[1];
} elseif (date("G") >= 6) {
print $m[2];
} else {
print $m[3];
}
?>
連想配列 (ハッシュ)
配列の添え字を数字でなくユーザ定義の文字列にすることもできる.
$ vi test12.php
<?php
$score["eigo"] = 73;
$score["suugaku"] = 84;
$score["kokugo"] = 68;
print "合計点: ";
print $score["eigo"] + $score["suugaku"] + $score["kokugo"];
?>
HTML 内への埋め込み
PHP は JavaScript と同様に,HTML ファイル内に埋め込むことができる.
HTML のファイル構造は以下のようになっている.
<html>
<head>
<link href="xxx.css" rel="stylesheet" type="text/css" media="all">
<meta charset="UTF-8">
</head>
<body>
本文
</bory>
</html>
PHP で以下のようなスクリプトを hello.htm として保存して ブラウザ上で表示すると,PHP スクリプトが実行されていることが分かるだろう.
<html>
<head>
<meta charset="UTF-8">
</head>
<body>
本文
<?php
$text = "HTML内でのPHPスクリプト実行処理";
echo "<p> $text </p>";
?>
</bory>
</html>
ヒアドキュメントの利用
埋め込み Ruby で用いたようなヒアドキュメントを使うことができる. 書式は埋め込み Ruby と同様であり,
<<<終了を表す文字
文字列
終了を表す文字;
となっている.以下のような内容を hello2.htm に書いてブラウザ上で 実行してみよ.
<html>
<head>
<meta charset="UTF-8">
</head>
<body>
本文
<?php
$text =<<<eot
<h2>HTML内でのPHPスクリプト実行処理2 </h2>
<br>
ほげほげ
eot; /// 終了を表す文字の前に空白は入れない
print $text;
?>
</bory>
</html>
データベースとの連携 (1)
PHP とデータベースの連携の例を示す.ここでは db_info.php という 接続情報を書いたファイルを作り,それを読み込ませることにしている.
まず,自分のホームディレクトリにファイル db_info.php を作成する.
$ vi ~/db_info.php (
<?php
$SERV="localhost";
$USER=""; <-- 自分のユーザ名を入力
$PASS=""; <-- Unix Socket を有効にしているので空で良い
$DBNM="j4db"; <-- 既存のデータベースを選択
?>
次に,データベースから検索するためのスクリプト select.php を作成する. この例では try-catch を使ってエラー処理を書いている.通常の実行時 (try ブロック内で例外が投げられなかった場合) は, catch ブロック内は処理されなず,例外が発生した場合のみ catch ブロック内が実行される. このようにしておくと,データベースへの接続・データベース操作で何か問題が発生した場合には エラー内容を表示させることができるようになる.
$ vi ~/public_html/select.php
<?php
try{
/*************** データベースへ接続、データベース選択 ***************/
require_once("/home/hogehoge/db_info.php"); //hogehoge は自分のユーザ名に変更
$s=new PDO("mysql:host=$SERV;dbname=$DBNM",$USER,$PASS);
/*************** 検索 ***************/
$mytable = "商品" ; //テーブル名は自分のものに変更
$re=$s->query("SELECT * FROM $mytable");
/*************** クエリの結果を表示 ***************/
while($kekka=$re->fetch()){
print $kekka[0].", "; //カラム数は $dbname で選択したテーブルに合わせる
print $kekka[1].", ";
print $kekka[2];
print "<br>";
}
}catch(PDOException $e) {
//エラーメッセージ表示
print "次がエラーの内容です:".$e->getMessage();
}
?>
ヒアドキュメントを使って整形する場合は,例えば以下のように書ける.
<?php
try{
/*************** データベースへ接続、データベース選択 ***************/
require_once("/home/sugiyama/db_info.php"); //hogehoge は自分のユーザ名に変更
$s=new PDO("mysql:host=$SERV;dbname=$DBNM",$USER,$PASS);
/*************** 検索 ***************/
$dbname = "商品" ; //テーブル名は自分のものに変更
$re=$s->query("SELECT * FROM $dbname");
/*************** クエリの結果を表示 ***************/
print<<<eot
<html>
<head>
<meta charset="UTF-8">
</head>
<body>
<h1> PHP + SQL </h1>
テーブル: $dbname
<table border="1">
eot;
while($kekka=$re->fetch()){
print<<<eot
<tr><td>$kekka[0]</td><td>$kekka[1]</td><td>$kekka[2]</td></tr>
eot;
}
print<<<eot
</table>
</body>
</html>
eot;
}catch(PDOException $e) {
//エラーメッセージ表示
print "次がエラーの内容です:".$e->getMessage();
}
?>
データベースとの連携 (2) : 入力フォームの利用
データを送信する Web ページでは <FORM> タグを使う. <FORM> タグを使う場合の基本構造は以下の通りである.
<FORM METHOD="送信の方法" ACTION="データの送信先">
<INPUT TYPE="ボタンの種類" NAME="データを識別する名前"
SIZE="サイズ" VALUE="表示する文字"or"送信する値">
</FORM>
--------------------------------
METHOD: POST or GET
TYPE: submit (データ送信), button (ボタン), text (テキスト),
checkbox (チェックボックス), radio (ラジオボタン), hidden (表示なし)
例えば以下のような HTML になる.
<FORM METHOD="get" ACTION="op.php"> <INPUT TYPE="text" NAME="in" SIZE="10"> <!--10文字のテキストボックス--> <br> <INPUT TYPE="radio" NAME="r1" VALUE="bad"> r1: bad <!--r1としてbadという値を送信 --> <br> <INPUT TYPE="submit" VALUE="送信"> </FORM>
ここでは,まず,データベースの検索キーワードを入力する HTML ファイル (submit.html) を作成する.
検索キーワードの入力 <FORM METHOD="get" ACTION="op.php"> 検索キーワード:<INPUT TYPE="text" NAME="keyword" SIZE="20"> <br> <INPUT TYPE="submit" VALUE="送信"> </FORM>
次に,データベース操作の PHP ファイル (op.php) を作成する.
- GET メソッドで渡されたデータ → $GET["名前"]
- POST メソッドで渡されたデータ→ $_POST["名前"]
で参照することができる.以下では,引き渡された値を $mykey = $_GET["keyword"]; という形で変数に代入してから利用している.
<?php
try{
/*************** データベースへ接続、データベース選択 ***************/
require_once("/home/sugiyama/db_info.php"); //hogehoge は自分のユーザ名に変更
$s=new PDO("mysql:host=$SERV;dbname=$DBNM",$USER,$PASS);
/*************** 検索 ***************/
$mytable = "商品" ; //テーブル名は自分のものに変更
$mykey = $_GET["keyword"];
$re=$s->query("SELECT * FROM $mytable WHERE 商品名 LIKE \"$mykey\"");
/*************** クエリの結果を表示 ***************/
while($kekka=$re->fetch()){
print $kekka[0].", "; //カラム数は $dbname で選択したテーブルに合わせる
print $kekka[1].", ";
print $kekka[2];
print "<br>";
}
}catch(PDOException $e) {
//エラーメッセージ表示
print "次がエラーの内容です:".$e->getMessage();
}
?>
課題
既存のテーブルを表示するためのスクリプトを作成する.
- kadai_form.html
- データベース内に存在するテーブルを調べて表示する.
- フォームで表示するテーブルを指定する.
- kadai_op.php
- フォームで指定されたテーブルの全レコードを HTML の <table> タグを使って表示する.
- 表の枠線を入れる
- 表の背景に色を付ける
- 内部で,select * from テーブル名, を実行する.
- テーブルに含まれるカラム数はスクリプト内部で計算すること.
- 配列の要素数を取得して,その回数だけループを回す.
- フォームで指定されたテーブルの全レコードを HTML の <table> タグを使って表示する.
作成したスクリプトと,ブラウザ上で上記ファイルを表示したときの出力を提出すること. 後者については,アドレスバーを含むようにスクリーンショットを取得すること.