Python・HTML・PHPを使った動的ページを作るまで

ソフト開発

Pythonのライブラリを使って
株のチャートを生成し、比較する動的ページを作成ました。

このページを作るにあたって、出来た事や躓いた事を復習も兼ねてまとめます。

やりたかったこと。

Pythonの機能をブログから使えるようにする。

具体的には

  • ブログのページから証券コードや日付を入力する。
  • Pythonで株のチャート画像を作成。
  • 二つの画像を比較して、似ているか確認。

画像にすれば、異なる日付・金額でも比較出来るって事が狙い。

実装した機能

プログラミング言語を複数使用しています。
コード内で赤文字にしている所は、他言語とのやり取り箇所なので、要注目です。

1.HTMLのformからPHPにpostし、PHP内で変数として使用。

まず、HTML

<form action="https://osotodegohan.com/python/candle.php" method="POST" id="AjaxForm">
   <div>基準銘柄コード:<input id="base_company" type="number" name="base"></div>
   <div>基準始め日:<input id="base_sdate" type="date" name="base_sdate"></div>
   <div>基準終り日:<input id="base_edate" type="date" name="base_edate"></div>

   <div>比較銘柄コード:<input id="hikaku_company" type="number" name="hikaku"></div>
   <div>比較始め日:<input id="hikaku_sdate" type="date" name="hikaku_sdate"></div>
   <div>比較終り日:<input id="hikaku_edate" type="date" name="hikaku_edate"></div>

   <input id="serach" type="submit" value="送信">
</form>

<div id="result">「送信」ボタンを押すとここに実行結果が表示されます。</div>

2~7行目のtypeを変える事で、数字だったり、文字だったりと変える事が出来ます。

number:数字。date:日付。などなど。入力したい項目に合わせていく必要があります。

自学の為に、送信ボタンのIDをsearchと替えていますが
このIDをJavaScriptの1行目と揃える必要があります。

次に、PHP

<?php
    //echo "base。";
    $base = $_POST['base'];
    $base_sdate = $_POST['base_sdate'];//文字形式2022-06-03
    $base_edate = $_POST['base_edate'];
    //echo $base;

    //echo "hikaku。";
    $hikaku = $_POST['hikaku'];
    $hikaku_sdate = $_POST['hikaku_sdate'];
    $hikaku_edate = $_POST['hikaku_edate'];
?>

HTMLのname部分が送られてきます。

つまり、HTMLのinputタグのnameの名称と
PHPの$_POST[***];の***が一致させる必要があります。

今回、初めてPHPに触れたので

  • 「$」は変数
  • 行の最後は「;」
  • コメントアウトは「//」
  • 「echo」が表示

まずはこれを抑えておかないと
開発が進まないです。

JavaScriptの使用

また、ここではJavaScriptを使用していて、(Ajaxの部分)
そのコードはこのページから拝借しました。

WPでボタンクリックでPHP実行しページ遷移無しでpost送信してJavascriptで結果を表示する方法

下記のJavaScriptコードは、上のサイトのそのままコピーとなります。


$('#AjaxForm').submit(function(event) {
    // HTMLでの送信をキャンセル
    event.preventDefault();
    var $form = $(this);
    var $button = $form.find('.submit');
    $.ajax({
        url: $form.attr('action'),
        type: $form.attr('method'),
        data: $form.serialize(),
        timeout: 10000,  // 単位はミリ秒
        // 送信前
        beforeSend: function(xhr, settings) {
            // ボタンを無効化し、二重送信を防止
            $button.attr('disabled', true);
$("#result").text("")
        },
        // 応答後
        complete: function(xhr, textStatus) {
            // ボタンを有効化し、再送信を許可
            $button.attr('disabled', false);
        },
        // 通信成功時の処理
        success: function(result, textStatus, xhr) {
            // 入力値を初期化
            $form[0].reset();
            $("#result").append(result);
        },
        // 通信失敗時の処理
        error: function(xhr, textStatus, error) {
            alert('エラー暫くたってからお試しください。');
        }
    });
    // …
});

詳細はリンク先を見て頂きたいです。

wordpressのテーマがcocoonであれば、カスタムJavaScriptに書けば使えます。
確かに機能しましたので、大変ありがたい事です。

2.PHPから引数付きでPythonを実行。

これもPHPコード。
PHPによる外部実行です。execの部分がそれです。

  • 第一引数は実行コマンド
  • 第二引数は外部実行ファイルの結果
  • 第三引数は成功・失敗とか数字で入ります。

所々ある「.」は文字結合です。

  $value = $param1.' '.$param2.' '.$param3.' '.$param4.' '.$param5.' '.$param6;
  $pythonScript = "~/public_html/osotodegohan.com/python/******.cgi";
    $cmd = "export LANG=ja_JP.UTF-8;~/.pyenv/versions/anaconda3-2020.02/bin/python"." ".$pythonScript." ".$value ;

    exec($cmd,$output,$result);

$cmdで実行コマンドを作っています。

$cmd=「おまじない」;「Pythonのパス」〇「****.py」〇「1」〇「2」〇「3」となるように
〇の部分は半角スペースです。

おまじない部

最初のexportからUTF-8までは日本語でUTF-8形式で といったおまじない的なもの。
私自身は分かっていませんが、
あった方が良いと見かけたのと、動いているのでそのまま残しています。

Pythonのパス部

~(チルダ)がホームパスが入ります。

私はレンタルサーバーのconohawingを使っています。

ssh接続してpipを使うためにanacondaを入れました。

今までは外付けSSDにubuntuを入れて開発していましたので、anacondaが何を担っているのか、正直理解していません。

が、実行コマンドを作るために、実行ファイルのpythonが必要なため入れました。

ファイルのパス部

$pythonScriptがpythonファイルまでのパス

.cgiとなっているのは、参考したページがそうなっていたから。

今となっては拡張子「****.py」のファイルでも実行できることが分かったのですが、
ちゃんと動いているので、そのまま。笑

まぁ、ファイル名をcgiとしても、pythonで実行しているんですがね。

引数部

Pythonに送るデータは半角スペースを入れてつなげていきます。

python側は
import sys
sys.argv[]配列で受け取ります。

sys.argv[1]からが引数受け取り部になります。

result部について

これがくせ者で、成功が0。
私が引っ掛かったのは失敗で2。

参考文献を忘れましたが、2は命令エラー。

つまり、上の$cmdが悪いということです。

レンタルサーバーを使用するので、パスの指定の仕方が分からず
非常に苦労しました。

~(チルダ)を使ったり、正しいと考えられるパスを直打ちして
何度も実行したのを思い出します。

PHPの要所にechoを入れて、どこまで動いているか確認するといった
デバッグ方法で地道にエラー2を解決しました。

python側ではpathlibといった
****.pyまでのpathを見つけるライブラリもあるので
そういったのを駆使するのもバグ消しに大切です。

3.Pythonが画像を作成し、画像を比較。

pythonに関してはこちら

OpenCVとNumPyで2つの画像を比較(完全一致、部分一致の比率)

このサイトをまんま使わせて頂きました。

4.所定のサーバーに保存。

これはほぼパスの指定の仕方が問題です。

大体「no such file or dictionary」で詰まって飽きます。笑
そんなファイルやフォルダはないですよ。と言われるのです。

パスを見直しましょう。

確認の仕方は

パスを変数に代入して、表示させる。
文字表現を見直す。(ダブルコーテーションとシングルコーテーションが混ざっていないか。など)

ひたすら画面とにらめっこです。

5.PHPで演算結果や画像をブログに表示する。

PHPは1アクションで1Postだそうです。

今回実装したのは、演算結果と画像を画面に返す。のが目的になります。

当初、画像処理はこのサイトを見ました。

PHPで画像を表示する3つの方法を現役エンジニアが解説【初心者向け】

ですが!!

PHPのHTMLへの応答ヘッダーもtype:textになります。
なので、画像が必ず文字化けするんです。

ということで、PHPにHTML形式で画像までのパスを表記して
HTMLにtext形式として応答させることになりました。

これに気付くのにも時間がかかり、正直、飽きます。笑

そして、壊れた画像がマークが出てくるので、F12でパスを確認

これです。幾度となくお世話になった。
F12の一番左の矢印のアイコンから、壊れた画像マークをクリックすると
PHPの返したHTML形式の画像パスが探せます。

おまけ レンタルサーバーにPython環境構築編

下のサイトで
ConohawingにPython環境を入れる方法と
実行パス・ファイルパスの書き方を参考にしました。

Conoha WingでPythonを使う方法

ただ、2点気になったのが、

『fatal: remote error:
 The unauthenticated git protocol on port 9418 is no longer supported.』

なのが出たら、

『git clone git://github.com/yyuu/pyenv.git ~/.pyenv』ではなく
『git clone https://github.com/yyuu/pyenv.git ~/.pyenv』

ということ。

コマンドがありません。と出たら

.bash_profile編集後にコマンドラインから
$ source ~/.bash_profile

として、更新をする必要があります。

うまくいかなかったら、とにかく更新してみるのも大事かと思います。

追記 javascriptからPHPを実行して、サーバサイドのファイルを削除する。

作成したWebアプリを実行すると、サーバにpngファイルが生成されるのですが、
このままでは画像データが増える一方なので、削除する機能を実装しました。

方法は

1.HTMLのformからPHPにpostし、PHP内で変数として使用。

で作ったJavascriptの通信成功時の処理に
サーバの画像データを削除するPHPを入れるだけ。

詳しくは下記記事に書きました。

参考にしたページはこちら。

グラビカ学習帳 様
JavaScriptから引数つきでPHPを実行

最後に

長々と書いた上に、画像少なめと視認性・可読性の悪い記事になりましたが
最後まで見られた方には感謝です。

主に初学者ですが、何か躓き、このページに辿り着き、問題解決になれば嬉しい限りです。

今回の試みで色んな事が学べました。

言語を組み合わせる事でフロントエンド⇔バックエンドのやり取りも学べました。
「F12」の開発ツールもある程度、見れるようになったりもしました。

また、if文など、基本文法も言語によって、多少書き方が異なるので
そういった経験も出来ました。

色々書いたけど、一番躓いたのはパス。
パスの書き方に苦しんだ記憶しかない・・・。

コメント

タイトルとURLをコピーしました