自分だけのスペイン語検索ログを作る ログ編

構想編スマホ編の続きです。

スマホから自分の知らない単語(スペイン語)をサーバーに送り付けて保存するだけの簡単なシステムを目指します。

プログラムリンク(https://github.com/samsumario/blog_public/tree/main/blog_3164)

今回のやりたいことの大枠はサーバーに送られてきた単語が既にDBに登録されていたら検索回数を+1。そうで無ければ単語を新規登録するだけです。

サーバーアプリらしくphpで作成しますが、先ずはDB操作処理をすっ飛ばしてindex.phpにはやりたいことの大枠だけ記述しました。

if ($_GET["word"] != null) {
    $cnt = accessDB("SEARCH", $_GET["word"]);

    if($cnt > 0){
        accessDB("ADD", $_GET["word"], $cnt+1);
    }
    else{
        accessDB("NEW", $_GET["word"]);
    }
}

phpではgetで送られてきた変数は&_GETで取れます。今回は変数名をwordとしているので&_GET[“word”]。

DB操作はaccessDBという関数に丸投げしています。

 

残り課題は

1.DBへの接続

2.DBにスマホから送られてきた単語が登録されているのか検索する

3.検索結果により検索回数を増やすor新規単語登録

4.エラーがあればエラー内容を保存

の4つです。

今回はあくまで簡素なプログラムを目指しているのでindex.phpとは別ファイルを作ってクラスも作らずべたべたfunctionで書いていきます。(logging.php全文)

ちなみに想定しているデータベースは下記の通りでフィールドはid,word,countの3つだけの単純なテーブルです。

idwordcount
1hacer10
2tener6
3estar2

 

DBへの接続

3~9行目:DBのパスワードなどを書いたファイルを用意して参照させる

11~37行目:DBを操作。毎回try catchでpdoオブジェクトを作るのが面倒なので検索・回数修正・新規登録の3つの処理は今回は文字列で判断して他の関数で書くことにします。(もう少しマシなやり方を知りたい…)

38行目:単語検索時に検索回数をreturnする。検索回数が無いorエラーの時は-1を返す。

function accessDB($cmd, $word, $count = 0) {
    
    $filePath = "./~.txt";
    $key = explode(",", file_get_contents($filePath));
    $host = $key[0];
    $user = $key[1];
    $pass = $key[2];
    $dbName = $key[3];
    $dbTable = $key[4];

    try {
        $sql = new PDO(
                    "mysql:dbname=".$dbName.";host=".$host.";charset=utf8;",
                    $user, $pass);
        
        if($cmd == "SEARCH"){
            $result = search($dbTable, $sql, $word);
        }
        elseif($cmd == "NEW"){
            insert($dbTable, $sql, $word);
            $result = -1;
        }
        elseif($cmd == "ADD"){
            update($dbTable, $sql, $word, $count);
            $result = -1;
        }
        else{
            print("cmd error");
            $result = -1;
        }

        $sql = null;
    }
    catch(Exception $e) {
            my_error_log($word, $e->getMessage());
			die();
    }

    return $result;
}

 

単語の検索

SQLインジェクション対策があるということでbindValueで書いてみました。

エラーがあればmy_error_logでエラー内容を保存。無ければ検索回数をreturnします。

function search($table, $sql, $word) {
    $stmti = $sql->prepare('SELECT * FROM '.$table.' WHERE word = :word LIMIT 0, 1;');
    $stmti->bindValue(':word', $word, PDO::PARAM_STR);
    $res = $stmti->execute();
    $err = $stmti->errorInfo();
    $retval = 0;

    if($res and ($err[0] == 00000)){
        $result = $stmti->fetch(PDO::FETCH_ASSOC);
        $retval = $result["cnt"];
    }
    else{
        my_error_log($word, $err[2]);
    }

    $stmti = null;
    return $retval;
}

 

新規単語登録

単語の検索とほぼ同じですが、戻り値不要なのでfetch()関数を使っていません。

データベースのidはAUTO_INCREMENTに設定してwordとcountだけ登録することを想定しています。

function insert($table, $sql, $word) {
    $stmti = $sql->prepare('INSERT INTO '.$table.' (word,cnt) VALUES (:word,:count)');
    $stmti->bindValue(':word', $word, PDO::PARAM_STR);
    $stmti->bindValue(':count', 1, PDO::PARAM_INT);
    $stmti->execute();

    $err = $stmti->errorInfo();
    if($err[0]!=00000){
        my_error_log($word, $err[2]);
    }

    $stmti = null;
}

 

検索回数アップデート

引数のcountをそのまま更新しています。

function update($table, $sql, $word, $count) {
    $stmti = $sql->prepare('UPDATE '.$table.' SET cnt = :count WHERE word = :word;');
    $stmti->bindValue(':count', $count, PDO::PARAM_INT);
    $stmti->bindValue(':word', $word, PDO::PARAM_STR);
    $stmti->execute();

    $err = $stmti->errorInfo();
    if($err[0]!=00000){
        my_error_log($word, $err[2]);
    }

    $stmti = null;
}

 

エラー時処理

DBに接続した時、単語検索した時、新規単語登録した時、検索回数を修正した時の4パターンそれぞれでエラー時に検索単語とエラー内容をセットでテキストファイル保存します。

ファイル名は時刻にしておきます。

function my_error_log($word, $errorInfo){
    date_default_timezone_set('Asia/Tokyo');
    
    $file_name = "./error/".date("Y_m_d H_i_s");

    $line = $word . " | " . $errorInfo;

    if (!file_exists($file_name)) {
        file_put_contents($file_name.".txt", $line, LOCK_EX);
    }else{
        file_put_contents($file_name."2.txt", $line, FILE_APPEND);
    }
}

以上でスマホから送られてきた単語をDBに保存して検索回数をカウントするシステムが取り合えず完成です。

次回は検索単語の意味をスマホに返す部分を作っていこうと思います。

コメントを残す

メールアドレスが公開されることはありません。