MySQLのSELECT文からPHPを使って覧表示してみよう

フォルダとファイル名

php-db フォルダに db03.php ファイルを作成します。
ここでは、データベースに保存したデータを SELECT 文で取得し、HTMLテーブルに一覧表示する方法を学びます。

チェックポイント

  • SELECT 文でデータを取得できたか?
  • fetchAll(PDO::FETCH_ASSOC) で配列として取り出せたか?
  • ループで1件ずつHTMLに出力できたか?

基本コード(db03.php)

<?php
$dsn = 'mysql:host=localhost;dbname=testdb;charset=utf8mb4';
$user = 'root';
$password = '';

function h($str)
{
    return htmlspecialchars($str, ENT_QUOTES, 'UTF-8');
}

try {
    $pdo = new PDO($dsn, $user, $password);
    $pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

    echo "接続成功!<br>";

    // 1) データを SELECT
    $stmt = $pdo->query("SELECT * FROM users ORDER BY id ASC");
    $rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
} catch (PDOException $e) {
    echo "エラー:" . $e->getMessage();
    exit;
}
?>
<!DOCTYPE html>
<html lang="ja">

<head>
    <meta charset="UTF-8">
    <title>ユーザー一覧</title>
    <style>
        table {
            border-collapse: collapse;
            margin-top: 1em;
        }

        th,
        td {
            border: 1px solid #666;
            padding: .5em 1em;
        }
    </style>
</head>

<body>
    <h1>ユーザー一覧</h1>
    <table>
        <tr>
            <th>ID</th>
            <th>名前</th>
            <th>メール</th>
            <th>登録日時</th>
        </tr>
        <?php foreach ($rows as $row): ?>
            <tr>
                <td><?= h($row['id']) ?></td>
                <td><?= h($row['name']) ?></td>
                <td><?= h($row['email']) ?></td>
                <td><?= h($row['created_at']) ?></td>
            </tr>
        <?php endforeach; ?>
    </table>
</body>

</html>

SELECT文でデータを取得

$stmt = $pdo->query("SELECT * FROM users ORDER BY id ASC");
  • query() … シンプルなSQLを1回実行
  • SELECT * … 全ての列を取得
  • ORDER BY id ASC … idの昇順で並び替え

fetchAll(PDO::FETCH_ASSOC)

$rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
  • fetchAll() … 結果をまとめて配列として取得
  • PDO::FETCH_ASSOC … カラム名をキーにした「連想配列」として取り出す
  • $rows は「レコード(行)の配列」になる
[
  ['id'=>1, 'name'=>'山田太郎', 'email'=>'taro@example.com', 'created_at'=>'2025-08-27 12:00:00'],
  ['id'=>2, 'name'=>'山田花子', 'email'=>'hanako@example.com', 'created_at'=>'2025-08-27 12:01:00'],
  ...
]

foreachで出力

<?php foreach ($rows as $row): ?>
  <tr>
                <td><?= h($row['id']) ?></td>
                <td><?= h($row['name']) ?></td>
                <td><?= h($row['email']) ?></td>
                <td><?= h($row['created_at']) ?></td>
  </tr>
<?php endforeach; ?>
  • $rows を1行ずつ取り出し、HTMLに埋め込む
  • 出力時は必ず 関数にしておいたhtmlspecialchars() でエスケープしてXSS対策
  • SELECT でデータを取得
  • fetchAll(PDO::FETCH_ASSOC) で「連想配列」として扱う
  • foreach でループしながら HTML に表示
  • 出力は htmlspecialchars() で安全に

検索機能を追加

上記の基本コードに検索機能を追加してみましょう。(php-db0303.php)

<?php
$dsn = 'mysql:host=localhost;dbname=testdb;charset=utf8mb4';
$user = 'root';
$password = '';

function h($str)
{
    return htmlspecialchars($str, ENT_QUOTES, 'UTF-8');
}

$keyword = $_GET['keyword'] ?? ''; // フォームからのキーワード(GET)

try {
    $pdo = new PDO($dsn, $user, $password);
    $pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

    // SQL文と実行
    if ($keyword !== '') {
        $stmt = $pdo->prepare("SELECT * FROM users WHERE name LIKE ? ORDER BY id ASC");
        $stmt->execute(['%' . $keyword . '%']);
    } else {
        $stmt = $pdo->query("SELECT * FROM users ORDER BY id ASC");
    }

    $rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
} catch (PDOException $e) {
    echo "エラー:" . $e->getMessage();
    exit;
}
?>

<!DOCTYPE html>
<html lang="ja">

<head>
    <meta charset="UTF-8">
    <title>ユーザー一覧(検索機能付き)</title>
    <style>
        table {
            border-collapse: collapse;
            margin-top: 1em;
        }

        th,
        td {
            border: 1px solid #666;
            padding: .5em 1em;
        }

        form {
            margin-bottom: 1em;
        }
    </style>
</head>

<body>
    <h1>ユーザー一覧</h1>

    <form method="get">
        <input type="text" name="keyword" placeholder="名前で検索" value="<?= h($keyword) ?>">
        <button type="submit">検索</button>
        <a href="php-db03-search.php">リセット</a>
    </form>

    <?php if (count($rows) > 0): ?>
        <table>
            <tr>
                <th>ID</th>
                <th>名前</th>
                <th>メール</th>
                <th>登録日時</th>
            </tr>
            <?php foreach ($rows as $row): ?>
                <tr>
                    <td><?= h($row['id']) ?></td>
                    <td><?= h($row['name']) ?></td>
                    <td><?= h($row['email']) ?></td>
                    <td><?= h($row['created_at']) ?></td>
                </tr>
            <?php endforeach; ?>
        </table>
    <?php else: ?>
        <p>該当するユーザーは見つかりませんでした。</p>
    <?php endif; ?>
</body>

</html>

解説

区分解説内容
$_GET['keyword'] ?? ''フォームから受け取った値。空なら空文字を代入。
LIKE演算子%キーワード%で名前に部分一致検索を実現。
prepare + executeSQLインジェクション対策として安全な書き方。
htmlspecialchars()表示時のXSS対策。
count($rows)結果があるかどうかの条件分岐に使用。
<form method="get">検索フォームをGETで送信(URLにキーワードが残る)。