それでは最後の機能、編集機能です。
使用するSQLはUPDATEですね。
いきなり書き始める前に、流れを確認しておきましょう。
今回はこの「流れ」が超重要になります。
「流れ」をイラストで確認!
今回作る流れを一つのイラストで表すとこんな感じになります。
ポイント
・「edit.php」と「edit_done.php」の2つのファイルが出てくる
・edit.php:選択されたidを条件に、DBからデータを取得してあらかじめ内容をセットしておく
・edit_done.php:edit.phpからform送信で渡されたデータを受け取って、UPDATE処理を実行
でも、まぁ、あまりイメージできなくても今は大丈夫です!
編集画面(HTML)
それでは、まずは編集画面から作っていきましょう。
使用するファイルは「edit.php」です。
といっても、画面は基本的には、
ログイン画面や新規登録画面と同じで良いので、新規登録画面の方を再利用しましょう。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>編集画面</title>
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<div class="title-area">
<h1>編集画面</h1>
</div>
<form action="" method="POST">
<input type="text" class="input-area" name="title" placeholder="Title"> <br>
<input type="text" class="input-area" name="content" placeholder="Content"> <br>
<input type="submit" class="input-area submit" name="submit" value="更新">
</form>
</body>
</html>
画面自体はこれで完成です。
ボタンの部分を「更新」に書き換えるには、
<input type="submit" value="更新">
の「value」の値を変えると反映されます。
それから、inputタグの最後に「required」がついている場合は消しておいてください。
「required」は入力必須項目に付けるものです。(今回は特にそのような処理はいらないので)
編集画面のロジック(edit.php)
続いてロジック部分です。
まず、編集画面ということは以下のことが非常に重要です。
編集すると言うことは、
すでに登録されているタイトルと本文を書き換える
例えば、記事IDが8の投稿に対して「編集」を押したとすると、
「動作確認」と言うタイトルと
「テストで登録してみます!」と言う本文は、
編集画面にあらかじめセットされた状態になっていて欲しいですね。
こんな感じで↓
それを作っていきます!
「編集」ボタン→「編集画面」
まず「編集」ボタンをクリックして「編集画面」に遷移する流れを作ります。
編集するファイルは「main.php」です。
削除の時と同じ要領でidが末尾に付くようにしましょう。
<td><a href="edit.php?id=<?php echo $row['id'];?>">編集</a></td>
これで、
編集ボタンを押したときに「http://localhost/todo/edit.php?id=〇〇」と言うURLに飛ぶようになりました。
〇〇の部分には、自動的に選択した「id」が入るようになっています。
「編集画面」でURLからidを取得する
「編集画面」なので「edit.php」でGET通信を利用して、URLからidを取得していきます。
でも、そもそもどうしてURLからidを取得したいのでしょうか?
それは、例えば「idが8のデータ」を更新したい場合こんなSQLが作れます。
UPDATE posts SET title = '更新!', content = '更新しました!' WHERE id = 8"
UPDATE文の条件に「WHERE id = 8」とすることで、idが8のものだけ更新対象にできますよね。
この「id=8」と言う情報はどこから来ているのかというと、
メインページで「編集」ボタンをクリックした瞬間にURLの末尾についた情報ですね。
それをGET通信で取得したと言うことになります。
今回も、最初に完成形のコードを載せておきます。
<?php
require('db_connect.php');
$id = $_GET['id'];
// 更新対象の投稿内容を取得
$pdo = db_connect();
try {
$sql = "SELECT * FROM posts WHERE id = :id";
$stmt = $pdo->prepare($sql);
$stmt->bindParam(":id", $id);
$stmt->execute();
} catch (PDOException $e) {
echo $e->getMessage();
die();
}
// 取得できたタイトルと本文を変数に入れておく
$row = $stmt->fetch(PDO::FETCH_ASSOC);
$title = $row['title'];
$content = $row['content'];
?>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>編集画面</title>
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<div class="title-area">
<h1>編集画面</h1>
</div>
<form action="edit_done.php" method="POST">
<input type="text" class="input-area" name="title" placeholder="Title" value="<?php echo $title;?>"> <br>
<input type="text" class="input-area" name="content" placeholder="Content" value="<?php echo $content;?>"> <br>
<input type="submit" class="input-area submit" name="submit" value="更新">
</form>
</body>
</html>
- GET通信でidを取得
- 取得したidを条件に投稿内容をSELECT
➡︎ タイトルと本文がゲットできる! - 取得したタイトルと本文を変数に入れておく
- HTMLのvalue属性にその変数をそのままセット!
これで、編集ボタンをクリックすると「edit.php」の画面に遷移して、
自動的にタイトルと本文がセットされているはずです!
一応「戻る」ボタンをつけておいても良いかもしれませんね。
もし付けるなら、
<a href="main.php">戻る</a>
これを追加しておいてください。
もしやるなら、CSSでスタイルも整えた方が良いですね。
編集完了画面のロジック(edit_done.php)
ついに最後です。
今のところ実行してもまだ更新はできません。
「edit.php」ではUPDATEではなく「SELECT」をしただけですよね。
<今後の流れ>
- 「edit.php」で「更新」ボタンを押して「edit_done.php」にform送信する
- 「edit_done.php」でデータを受け取ってUPDATE!
- 以上!!
そうなんです、実はもうUPDATE処理をするだけで完成です。
ではやっていきましょう!
<?php
require('db_connect.php');
$title = $_POST['title'];
$content = $_POST['content'];
$submit = $_POST['submit'];
$pdo = db_connect();
try {
// UPDATE文を書く
} catch (PDOException $e) {
echo $e->getMessage();
die();
}
?>
ここで、ちょっと考えてみてください。
この後tryの中にUPDATE文を書きたいのですがどのようなSQLになると思いますか?
こんな感じですよね。
UPDATE posts SET title = :title, content = :content WHERE id = :id"
でも困ったことがあります。
ここで言う「$id」ってどこからきた$idでしょうか?
「edit.php」ではGET通信で$idを受け取りましたが、
「edit_done.php」には$idが渡されていません。
どうにかして「edit_done.php」にidを渡してあげましょう。
と言うわけで「edit.php」に手を加えます。
<form action="edit_done.php" method="POST">
<input type="text" class="input-area" name="title" placeholder="Title" value="<?php echo $title;?>"> <br>
<input type="text" class="input-area" name="content" placeholder="Content" value="<?php echo $content;?>"> <br>
<input type="hidden" name="id" value="<?php echo $id; ?>">
<input type="submit" class="input-area submit" name="submit" value="更新">
</form>
「input type=”hidden” name=”id” value=”<?php echo $id;?>”」
を追加しました。
inputのtype属性を「hidden」にすることで入力欄無しでform送信をすることができるようになります。
と言うわけで「edit_done.php」でPOST通信で受け取っておきましょう。
追記します↓
// 追加分↓
$id = $_POST['id'];
$title = $_POST['title'];
$content = $_POST['content'];
$submit = $_POST['submit'];
編集完了画面(HTML部分)
画面はものすごく簡単でOKです。
このHTMLを「edit_done.php」の下の方に追記しておきましょう!
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>編集完了画面</title>
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<div class="title-area">
<h1>編集完了画面</h1>
</div>
<div class="text-area">
<p>ID:<?php echo $id?>を編集しました。</p>
<p><a href="main.php">メイン画面に戻ります。</a></p>
</div>
</body>
</html>
CSSも軽く整えておきましょう。
.text-area {
width: 40%;
background-color: rgb(240, 233, 233);
opacity: 0.7;
margin: 100px auto 0 auto;
padding: 30px;
border-radius: 5%;
border: solid 1px white;
font-size: 28px;
}
以上!
動作確認
ついに完成しました!
それでは、動作確認といきましょうか。
「編集」ボタンを押して、編集画面に遷移します。
「タイトル」と「本文」が自動で入力されていることを確認!
ついでに、idが選択したものと一致していることを確認して、適当な値に変更してみましょう。
編集したIDが、こちらでも一致していることを確認します。
「メイン画面に戻ります。」をクリックすると、、
更新されています!!
まとめ
- 「edit.php」ではSELECTの処理
- 「edit_done.php」ではUPDATEの処理
- 「タイトル」と「本文」は自動で入力されていて欲しい
→「edit.php」のSELECTで取得したタイトルと本文を変数に入れて echoで出力
ソースコード一覧(完成版)
こちらからzip形式ダウンロードできます!
login.php
<?php
// DB接続のファイルを読み込む(db_connectメソッドを使いたいから)
require('db_connect.php');
// フォーム送信された情報を受け取る
$name = $_POST['name'];
$password = $_POST['password'];
$submit = $_POST['submit'];
// $submitが空ではない→ログインボタンが押されたと言うこと。
if (!empty($submit)) {
$pdo = db_connect();
try {
// 名前とパスワードを条件にユーザを取得
$sql = "SELECT * FROM users WHERE name = :name AND password = :password";
$stmt = $pdo->prepare($sql);
$stmt->bindParam(':name', $name);
$stmt->bindParam(':password', $password);
$stmt->execute();
} catch (PDOException $e) {
echo 'エラー:' . $e->getMessage();
die();
}
// SELECTした結果、取得できればmain.phpにリダイレクト
if ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
header("Location: main.php");
exit;
} else {
echo '<font color="red">パスワードか名前に間違いがあります。</font>';
}
}
?>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>ログインページ</title>
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<div class="title-area">
<h1>ログインページ</h1>
</div>
<form action="" method="POST">
<input type="text" class="input-area" name="name" placeholder="Your Name" required> <br>
<input type="password" class="input-area" name="password" placeholder="Your Password" required> <br>
<input type="submit" class="input-area submit" name="submit" value="Log in">
</form>
</body>
</html>
main.php
<?php
// DB接続のファイルを読み込む(db_connectメソッドを使いたいから)
require('db_connect.php');
$pdo = db_connect();
try {
// 投稿データを新しい順に並び替えて取得
$sql = "SELECT * FROM posts ORDER BY time";
$stmt = $pdo->prepare($sql);
$stmt->execute();
} catch(PDOException $e) {
echo $e->getMessage();
die();
}
?>
<!doctype html>
<html lang="en">
<head>
<!-- Required meta tags -->
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- Bootstrap CSS -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.0-beta1/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-giJF6kkoqNQ00vy+HMDP7azOuL0xtbfIcaT9wjKHr8RbDVddVHyTfAAsrekwKmP1" crossorigin="anonymous">
<title>メインページ</title>
</head>
<body>
<h1>メインページ</h1>
<a href="create.php" ><button type="button" class="btn btn-primary">新規登録</button></a>
<!-- Option 1: Bootstrap Bundle with Popper -->
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.0.0-beta1/dist/js/bootstrap.bundle.min.js" integrity="sha384-ygbV9kiqUc6oa4msXn9868pTtWMgiQaeYH7/t7LECLbyPA2x65Kgf80OJFdroafW" crossorigin="anonymous"></script>
<table class="table table-striped">
<thead>
<tr>
<th scope="col">記事ID</th>
<th scope="col">タイトル</th>
<th scope="col">本文</th>
<th scope="col">作成日</th>
<th scope="col">編集</th>
<th scope="col">削除</th>
</tr>
</thead>
<tbody>
<?php while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) : ?>
<tr>
<td><?php echo $row["id"]; ?></td>
<td><?php echo $row["title"]; ?></td>
<td><?php echo $row["content"]; ?></td>
<td><?php echo $row["time"]; ?></td>
<td><a href="edit.php?id=<?php echo $row['id'];?>">編集</a></td>
<td><a href="delete.php?id=<?php echo $row['id'];?>">削除</a></td>
</tr>
<?php endwhile; ?>
</tbody>
</table>
</body>
</html>
create.php
<?php
// DB接続のファイルを読み込む(db_connectメソッドを使いたいから)
require('db_connect.php');
// form送信された値を受け取る
$title = $_POST["title"];
$content = $_POST["content"];
$submit = $_POST["submit"];
// 送信ボタンが押されたらという条件
if (!empty($submit)) {
$pdo = db_connect();
try {
// タイトルと本文はこの時点では何が入るかわからないので「:◯◯」という形
$sql = "INSERT INTO posts (title, content) VALUES (:title, :content)";
$stmt = $pdo->prepare($sql);
$stmt->bindParam(":title", $title);
$stmt->bindParam(":content", $content);
$stmt->execute();
// 登録完了したらmain.phpへ戻る
header("Location: main.php");
} catch (PDOException $e) {
echo $e->getMessage();
die();
}
}
?>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>新規登録</title>
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<div class="title-area">
<h1>新規登録</h1>
<a href="main.php" style="color: white;">メイン画面に戻る</a>
</div>
<form action="" method="POST">
<input type="text" class="input-area" name="title" placeholder="Title" required> <br>
<input type="text" class="input-area" name="content" placeholder="Content" required> <br>
<input type="submit" class="input-area submit" name="submit" value="登録">
</form>
</body>
</html>
delete.php
<?php
// DB接続のファイルを読み込む(db_connectメソッドを使いたいから)
require('db_connect.php');
// URLの情報を見て値を取得したいので、GET通信
$id = $_GET['id'];
$pdo = db_connect();
try {
// idを条件に削除対象を決める
$sql = "DELETE FROM posts WHERE id = :id";
$stmt = $pdo->prepare($sql);
$stmt->bindParam(":id", $id);
$stmt->execute();
// main.phpにリダイレクト
header("Location: main.php");
exit;
} catch (PDOException $e) {
echo $e->getMessage();
die();
}
?>
edit.php
<?php
// DB接続のファイルを読み込む(db_connectメソッドを使いたいから)
require('db_connect.php');
// URLの情報を見て値を取得したいので、GET通信
$id = $_GET['id'];
$pdo = db_connect();
try {
// 上で取得した更新対象idを条件に投稿内容を取得
$sql = "SELECT * FROM posts WHERE id = :id";
$stmt = $pdo->prepare($sql);
$stmt->bindParam(":id", $id);
$stmt->execute();
} catch (PDOException $e) {
echo $e->getMessage();
die();
}
// 取得できたタイトルと本文を変数に入れておく
$row = $stmt->fetch(PDO::FETCH_ASSOC);
$title = $row['title'];
$content = $row['content'];
?>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>編集画面</title>
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<div class="title-area">
<h1>編集画面</h1>
</div>
<form action="edit_done.php" method="POST">
<input type="text" class="input-area" name="title" placeholder="Title" value="<?php echo $title;?>"> <br>
<input type="text" class="input-area" name="content" placeholder="Content" value="<?php echo $content;?>"> <br>
<input type="hidden" name="id" value="<?php echo $id; ?>">
<input type="submit" class="input-area submit" name="submit" value="更新">
</form>
</body>
</html>
edit_done.php
<?php
// DB接続のファイルを読み込む(db_connectメソッドを使いたいから)
require('db_connect.php');
// form送信された値を受け取る
$id = $_POST['id'];
$title = $_POST['title'];
$content = $_POST['content'];
$submit = $_POST['submit'];
$pdo = db_connect();
try {
// idを条件にタイトルと本文をUPDATE
$sql = "UPDATE posts SET title = :title, content = :content WHERE id = :id";
$stmt = $pdo->prepare($sql);
$stmt->bindParam(":id", $id);
$stmt->bindParam(":title", $title);
$stmt->bindParam(":content", $content);
$stmt->execute();
} catch (PDOException $e) {
echo $e->getMessage();
die();
}
?>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>編集完了画面</title>
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<div class="title-area">
<h1>編集完了画面</h1>
</div>
<div class="text-area">
<p>ID:<?php echo $id?>を編集しました。</p>
<p><a href="main.php">メイン画面に戻ります。</a></p>
</div>
</body>
</html>
style.css
body {
margin: 0;
padding: 0;
text-align: center;
background-image: url(../img/top1.jpg);
background-size: cover;
background-position: center;
}
/* タイトル */
.title-area {
margin-top: 100px;
color: white;
}
.title-area h1 {
font-size: 45px;
line-height: 10px;
}
.title-area p {
font-size: 25px;
}
/* フォーム */
form {
margin-top: 50px;
}
.input-area {
width: 600px;
background: transparent;
border: none;
border-bottom: 1px solid rgb(247, 241, 241);
color: #fff;
font-size: 18px;
margin-bottom: 16px;
}
input {
height: 45px;
}
input::placeholder {
color: white;
}
textarea::placeholder {
color: white;
}
/* 送信ボタン */
form .submit {
height: 50px;
background: rgb(28, 109, 249);
opacity: 0.8;
border-color: transparent;
color: white;
font-size: 20px;
font-weight: bold;
letter-spacing: 2px;
margin-top: 20px;
}
form .submit:hover {
background: rgb(73, 140, 255);
cursor: pointer;
}
/* 編集完了画面(edit_done)で使用 */
.text-area {
width: 40%;
background-color: rgb(240, 233, 233);
opacity: 0.7;
margin: 100px auto 0 auto;
padding: 30px;
border-radius: 5%;
border: solid 1px white;
font-size: 28px;
}