SHINYA TECH

公務員(行政職)から34歳でエンジニア転職した人

#11 ここまでの復習(PHP-MySQL接続・データ追加・取得、バリデーション処理)

f:id:kshinya-tech:20220220052107p:plain

ここまでに学んだ内容を基に、タスク管理ツールをバージョンアップしていきます。

タスク管理ツールについて、これまでに行ったこと

  1. 要件定義(課題要件、業務要件、機能要件)を行った。
  2. 配列、while、if、foreach、関数を用いてターミナル上で動作するようにした。

shinya-tech.com

今回バージョンアップする内容

  1. PHPからMySQLに接続し、データの追加・取得を行えるようにする。
  2. バリデーション処理を追加する。

shinya-tech.com

shinya-tech.com

shinya-tech.com

shinya-tech.com

追加で学んだこと

日付の入力チェック(バリデーション)は入力形式が正しいかのみ判定できるようにしました。

$date = '20220220';
$format_date = '%Y%m%d';
if (strptime($date, $format_date)) {
    echo 'OK';
} else {
    echo '入力形式が異なります';
}

参考にしたサイト:PHPで正しい日付チェック

ただし、公式ドキュメントではstrptimeを使用することについて、非推奨していることから、今後、違う方法に変更しないといけない。

以下のサイトを参考にコードを後日変更予定。

xiyuan.jp

書いたコード

<?php

// バリデーション処理を定義
function validate($task)
{
    $errors = [];

    // タスク名が正しく入力されているかチェック
    if (!strlen($task['name'])) {
        $errors['name'] = 'タスク名を入力してください';
    } elseif (mb_strlen($task['name']) > 255) {
        $errors['name'] = 'タスク名は255文字以内で入力してください';
    }

    $date = $task['limit_date'];
    $format_date = '%Y%m%d';

    // 期限が正しく入力されているかチェック
    if (!strlen($task['limit_date'])) {
        $errors['limit_date'] = '期限を入力してください';
    } elseif (!strptime($date, $format_date)) {
        $errors['limit_date'] = '期限は「YYYYmmdd」の形式で入力してください(例:20150219)';
    }

    // 進捗状況が正しく入力されているかチェック
    if (!strlen($task['status'])) {
        $errors['status'] = '進捗状況を登録してください';
    } elseif (!in_array($task['status'], ['未', '着手', '済'])) {
        $errors['status'] = '進捗状況は「未、着手、済」のいずれかを入力してください';
    }

    // 備考が正しく入力されているかチェック
    if (mb_strlen($task['remarks']) > 255) {
        $errors['remarks'] = '備考は255文字以内で入力してください';
    }

    return $errors;
}


// MySQLに接続する関数を定義
function dbConnect()
{
    $link = mysqli_connect('db', 'book_log', 'pass', 'book_log');

    if (!$link) {
        echo 'Error: データベースに接続できませんでした' . PHP_EOL;
        echo 'Debugging error:' . mysqli_connect_error() . PHP_EOL;
        exit;
    }

    return $link;
}


// タスクを登録する関数を定義
function createTask($link)
{
    $task = [];

    echo 'タスクを登録してください' . PHP_EOL;
    echo 'タスク名:';
    $task['name'] = trim(fgets(STDIN));

    echo '期限(YYYYmmddで入力):';
    $task['limit_date'] = trim(fgets(STDIN));

    echo '進捗状況(未、着手、済):';
    $task['status'] = trim(fgets(STDIN));

    echo '備考:';
    $task['remarks'] = trim(fgets(STDIN));

    $validated = validate($task);
    if (count($validated) > 0) {
        foreach ($validated as $error) {
            echo $error . PHP_EOL;
        }
        return;
    }

    $sql = <<<EOT
INSERT INTO tasks (
    name,
    limit_date,
    status,
    remarks
) VALUES (
    "{$task['name']}",
    "{$task['limit_date']}",
    "{$task['status']}",
    "{$task['remarks']}"
);
EOT;

    $result = mysqli_query($link, $sql);
    if ($result) {
        echo 'データを追加しました' . PHP_EOL;
    } else {
        echo 'Error: データの追加に失敗しました' . PHP_EOL;
        echo 'Debugging error:' . mysqli_error($link) . PHP_EOL;
    }
}


// タスクを表示する関数を定義
function showTask($link)
{
    $sql = 'SELECT name,limit_date,status,remarks FROM tasks';
    $results = mysqli_query($link, $sql);

    // 連想配列で結果を取得する
    while ($tasks = mysqli_fetch_assoc($results)) {
        echo 'タスク名:' . $tasks['name'] . PHP_EOL;
        echo '期限:' . $tasks['limit_date'] . PHP_EOL;
        echo '進捗状況:' . $tasks['status'] . PHP_EOL;
        echo '備考:' . $tasks['remarks'] . PHP_EOL;
        echo '------------------' . PHP_EOL;
    }
}


$link = dbConnect();


while (true) {
    echo '1:タスクを登録する' . PHP_EOL;
    echo '2:タスク一覧を表示する' . PHP_EOL;
    echo '9:終了する' . PHP_EOL;
    echo '上記メニュー番号を入力してください(1,2,9) : ';
    $i = trim(fgets(STDIN));
    if ($i === '1') {
        createTask($link);
    } elseif ($i === '2') {
        showTask($link);
    } elseif ($i === '9') {
        // データベースとの接続を切断
        mysqli_close($link);
        break;
    }
}

備忘録(詰まった点)

データベースのカラム名に予約語を使っており、エラーが出た。

limit → NG (limitは予約語)

limit_date → OK

www.dbonline.jp