PHPとデータベースを使って星占いページを作成しましょう。
完成イメージ


フォルダ構成とファイル名
- 作成フォルダ:
php-practice-zodiac作成ファイル:z_list.php - 使用CSSファイル(任意):
style.cssは任意で作成
データベーステーブルの作成
下記の仕様書を元にtestdbにzodiacテーブルを作成しましょう。
CREATE TABLE zodiac ( id INT AUTO_INCREMENT PRIMARY KEY, score INT(4) NOT NULL, sign VARCHAR(30) NOT NULL, fortune TEXT NOT NULL, lucky_color CHAR(7) NOT NULL, color_name VARCHAR(10) NOT NULL, image VARCHAR(255) NOT NULL );
下記のCSVファイルをインポートします。エクセルで作成し、CSVに書き出すことで毎月の更新が楽になります。
1,100,おひつじ座,エネルギッシュな月です。新しいことに挑戦することで運気がさらにアップ。積極的な行動が吉です。人との出会いにも恵まれそう。少し背伸びする挑戦が開運のカギ。,#dd2727,赤,ohitsuji.png 2,67,おうし座,落ち着いて過ごせる月です。生活リズムを整えることで心身ともに充実。計画的に物事を進めると良い成果が得られます。自宅の整理整頓も運気アップ。,#228b22,緑,oushiza.png 3,61,ふたご座,コミュニケーション運が絶好調。情報交換やSNSで新しいアイデアが生まれます。外に出て人と関わると運が開けます。意見交換がラッキーアクション。,#ffd700,金色,futagoza.png 4,77,かに座,家族や身近な人との時間を大切にすると心が満たされる月。家の中の模様替えや整理整頓も吉。気分がスッキリして新しい一歩が踏み出せます。,#ffffff,白,kaniza.png 5,75,しし座,注目が集まる月。自信を持って行動すると周囲からの評価が高まります。リーダーシップを発揮してみましょう。積極的に発言するとさらに吉。,#ffa500,オレンジ,shishiza.png 6,74,おとめ座,細かい作業や整理整頓がはかどる月。勉強や資格取得に集中するのもおすすめ。健康管理にも気を配ると良い結果に。早寝早起きが開運ポイント。,#87ceeb,空色,otomeza.png 7,68,てんびん座,人間関係が活発になる月。新しい出会いやコラボが生まれそう。バランス感覚を活かして調整役になると運気アップ。感謝の言葉を伝えると良い流れに。,#ff69b4,ピンク,tenbinza.png 8,66,さそり座,深い対話や研究が吉。じっくり物事に向き合うと良い成果が出ます。感情の整理も進めて心のデトックスを。夜の散歩がひらめきを呼びます。,#000000,黒,sasoriza.png 9,94,いて座,行動力が試される月。旅行や新しい挑戦にツキがあります。やりたいことに素直に飛び込むと成長につながります。アウトドア活動が吉。,#1e90ff,青,iteza.png 10,65,やぎ座,努力が実を結ぶ月。コツコツと取り組んできたことが形になります。責任感を持って最後までやり抜きましょう。計画表を見直すと効果的。,#8b4513,茶色,yagiza.png 11,97,みずがめ座,独創的なアイデアが浮かぶ月。新しいプロジェクトや提案に挑戦すると良い結果に。自由な発想がカギです。ノートにアイデアを書き留めて吉。,#800080,紫,mizugameza.png 12,87,うお座,感受性が豊かになる月。芸術や音楽に触れると心が満たされます。人の優しさに触れて癒される瞬間も多そうです。映画鑑賞がおすすめ。,#191970,紺,uoza.png
星占い最初の画面
z-list.phpの作成手順
- データベースに接続(
common.phpを作成) SELECT id, sign,image FROM zodiac ORDER BY idで取得したデータを配列に入れ表示- 一覧ページからのリンク(GETパラメータを使った遷移します)

<?php
require 'common.php';
$sql = $pdo->query('SELECT id, sign, image FROM zodiac ORDER BY id');
$signs = $sql->fetchAll(PDO::FETCH_ASSOC);
?>
z-list.phpの例
<?php
require 'common.php';
$sql = $pdo->query('SELECT id, sign,image FROM zodiac ORDER BY id');
$signs = $sql->fetchAll(PDO::FETCH_ASSOC);
?>
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>星占い一覧</title>
<link rel="stylesheet" href="style.css">
</head>
<body>
<div class="content">
<h1>星座を選んでください</h1>
<ul class="list">
<?php foreach ($signs as $s): ?>
<li>
<a href="z_show.php?id=<?= h($s['id']) ?>">
<div>
<img src="img/<?= h($s['image']) ?>" alt="<?= h($s['sign']) ?>">
</div>
<div>
<?= h($s['sign']) ?>
</div>
</a>
</li>
<?php endforeach; ?>
</ul>
</div>
</body>
</html>
各星座名をクリックし、星占いを表示
各星座名をクリックすると、その星座の運勢を表示するページを作成します。
表示させたい画像は、あらかじめ img/ フォルダに用意し、
データベーステーブルの image カラムに登録したファイル名と合わせておきましょう。
完成イメージ


z-show.php の作成手順
- common.php を読み込み、データベース接続
- URLパラメータ
idを取得$_GET['id'] ?? 0で取得、無ければ 0 にしておく - データベースから該当の星座を1件取得
- HTMLに埋め込んで表示
- 画像 (
imageカラム) - 星座名 (
signカラム) - 運勢 (
fortuneカラム) - ラッキーカラー名 (
color_nameカラム) - 背景色を
lucky_colorのカラーコードにする
- 画像 (
解答例 z-show.php
<?php
require 'common.php';
$sign_id = $_GET['id'] ?? 0;
// 選択された星座を取得
$sql = $pdo->prepare('SELECT * FROM zodiac WHERE id=?');
$sql->execute([$sign_id]);
$row = $sql->fetch(PDO::FETCH_ASSOC);
?>
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title><?= $row ? h($row['sign']) . ' の運勢' : '星占い結果'; ?></title>
<style>
body {
background-color: <?= $row ? h($row['lucky_color']) : '#fff'; ?>;
}
.lucky_color {
color: <?= $row ? h($row['lucky_color']) : '#000'; ?>;
}
</style>
<link rel="stylesheet" href="style.css">
</head>
<body>
<?php if ($row): ?>
<div class="card">
<!-- 画像 -->
<img src="img/<?= h($row['image']) ?>" alt="<?= h($row['sign']) ?>">
<!-- 星座名 -->
<h2><?= h($row['sign']) ?> の運勢</h2>
<!-- 運勢とラッキーカラー -->
<p><?= nl2br(h($row['fortune'])) ?></p>
<p>ラッキーカラー:<span class="lucky_color"><?= h($row['color_name']) ?></span></p>
<p><a href="z-list.php">← 一覧に戻る</a></p>
</div>
<?php else: ?>
<div class="card">
<p>選択された星座が見つかりません。</p>
<p><a href="z-list.php">一覧に戻る</a></p>
</div>
<?php endif; ?>
</body>
</html>
スコアを元にランキングも表示しよう!
ランキング(順位)を計算
z-list.phpファイルに下記のコードを追加してみましょう
<?php
require 'common.php';
$sign_id = $_GET['id'] ?? 0;
// まず選択された星座を取得
$sql = $pdo->prepare('SELECT * FROM zodiac WHERE id=?');
$sql->execute([$sign_id]);
$row = $sql->fetch(PDO::FETCH_ASSOC);
// 順位計算(scoreでソートして、何位かを求める)
$rank = null;
if ($row) {
//zodiac_score テーブルから id カラムだけを、score の降順で取得。
//スコアの高い順に並べた星座IDの一覧の取得。
$sql_all = $pdo->query('SELECT id FROM zodiac ORDER BY score DESC');
//連想配列の配列
// $all = [
// 0 => ['id' => 3], // スコア1位の星座(id=3)
// 1 => ['id' => 7], // スコア2位の星座(id=7)
// 2 => ['id' => 1], // スコア3位の星座(id=1)
// ...
// ];
$all = $sql_all->fetchAll(PDO::FETCH_ASSOC);
//foreach で1行ずつ見ていき、「選ばれた星座のidと一致する行」を探す
foreach ($all as $index => $r) {
//$r['id'] は「今ループで取り出した行のid」
//$sign_id は「URLパラメータで指定されたid(選ばれた星座のid)」
if ($r['id'] === $sign_id) {
$rank = $index + 1; // 配列は0始まりなので+1
}
}
}
?>
解答例 z-ranking.php
<?php
require 'common.php';
$sign_id = $_GET['id'] ?? 0;
// まず選択された星座を取得
$sql = $pdo->prepare('SELECT * FROM zodiac WHERE id=?');
$sql->execute([$sign_id]);
$row = $sql->fetch(PDO::FETCH_ASSOC);
// 順位計算(scoreでソートして、何位かを求める)
$rank = null;
if ($row) {
//zodiac_score テーブルから id カラムだけを、score の降順で取得。
//スコアの高い順に並べた星座IDの一覧の取得。
$sql_all = $pdo->query('SELECT id FROM zodiac ORDER BY score DESC');
//連想配列の配列
// $all = [
// 0 => ['id' => 3], // スコア1位の星座(id=3)
// 1 => ['id' => 7], // スコア2位の星座(id=7)
// 2 => ['id' => 1], // スコア3位の星座(id=1)
// ...
// ];
$all = $sql_all->fetchAll(PDO::FETCH_ASSOC);
//foreach で1行ずつ見ていき、「選ばれた星座のidと一致する行」を探す
foreach ($all as $index => $r) {
//$r['id'] は「今ループで取り出した行のid」
//$sign_id は「URLパラメータで指定されたid(選ばれた星座のid)」
if ($r['id'] == $sign_id) {
$rank = $index + 1; // 配列は0始まりなので+1
}
}
}
?>
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title><?= $row ? h($row['sign']) . ' の運勢' : '星占い結果'; ?></title>
<style>
body {
background-color: <?= $row ? h($row['lucky_color']) : '#fff'; ?>;
}
.lucky_color {
color: <?= $row ? h($row['lucky_color']) : '#000'; ?>;
}
</style>
<link rel="stylesheet" href="style.css">
</head>
<body>
<?php if ($row): ?>
<div class="card">
<!-- 画像 -->
<img src="img/<?= h($row['image']) ?>" alt="<?= h($row['sign']) ?>">
<!-- 星座名と順位 -->
<h2><?= h($row['sign']) ?> の運勢</h2>
<?php if ($rank): ?>
<p><strong>今月の順位:<?= h($rank) ?>位</strong></p>
<?php endif; ?>
<!-- 運勢とラッキーカラー -->
<p><?= nl2br(h($row['fortune'])) ?></p>
<p>
ラッキーカラー:<span class="lucky_color"><?= h($row['color_name']) ?></span>
</p>
<p><a href="z-list.php">← 一覧に戻る</a></p>
</div>
<?php else: ?>
<div class="card">
<p>選択された星座が見つかりません。</p>
<p><a href="z-list.php">一覧に戻る</a></p>
</div>
<?php endif; ?>
</body>
</html>
ステップアップ:z-list.php をランキング順に並べる
一覧ページを id順(12星座の固定順) ではなく、score(スコアの降順) で並べ替えてランキング表示にしてみましょう。
- SQLの並び順を変更する
- これまで
ORDER BY idだった部分を
→ORDER BY score DESCに変更します。 DESCは「降順」という意味で、大きい数字から順に並べます。
- これまで
- スコアも取得して表示する
SELECT id, sign, image, score FROM zodiacとして、scoreカラムも取り出します。- HTML部分で
<?= $s['score'] ?>点を追加すると、点数付きで表示できます。
- ランキング形式で表示する
<ul>ではなく<ol>(順序付きリスト)を使うとマークアップになります。- 各行には「スコア」「星座名」「詳細リンク」を表示します。
- 1位だけclassをつけて目立つように表示
解答例 z-list-ranking.php
<?php
require 'common.php';
// スコアの高い順に並べ替え
$sql = $pdo->query('SELECT id, sign, image, score FROM zodiac ORDER BY score DESC');
$signs = $sql->fetchAll(PDO::FETCH_ASSOC);
?>
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>星座ランキング</title>
<style>
.first {
font-size: 1.5em;
font-weight: bold;
color: red;
background: #ffe600;
padding: 5px 10px;
border-radius: 5px;
}
</style>
</head>
<body>
<h1>星座ランキング</h1>
<ol>
<?php foreach ($signs as $index => $s): ?>
<li class="<?= ($index === 0) ? 'first' : '' ?>">
<?= ($index + 1) ?>位
<?= $s['score'] ?>点
<a href="z-show.php?id=<?= $s['id'] ?>">
<?= htmlspecialchars($s['sign']) ?>
</a>
</li>
<?php endforeach; ?>
</ol>
</body>
</html>
