CGIとは 


ざっくりいうと…

JavaScriptから「Pythonなどのプログラム」を実行できるしくみです.

JavaScriptとプログラム間で,値の受け渡しもできます.

(研究室のサーバで動かすときは,ちょっと手こずるので,
注意してください.)

やりかた 


HTMLで2つの値を入力してもらい,JavaScriptでそれらをプログラムに送り, プログラム内でそれらの積を求めて,それを返す
HTMLとJavaScript,Pythonの例です.

aaa.jpg


最低限必要なものは,青太字で書いています.

/index.html


<!DOCTYPE html>
<html lang = 'ja'>

<head>
<meta charset = 'UTF-8'>
</head>

<body>
<input id = "input1" type = "text">x<input id = "input2" type = "text">=
<span id = "result"></span>
<br>
<input type = 'button' value = 'EXECUTE' onClick = 'execute()'>
<script type = 'text/javascript' src = 'main.js'></script>
</body>

</html>



/main.js


async function execute() {

const url = "./cgi-bin/program.py";
// プログラムの相対パス
//(プログラムは「/cgi-bin」下にいれるのが定石です)

const left = document.getElementById("input1").value;
const right = document.getElementById("input2").value;
// 入力された値を読みとります

const sendData = {
"left": left,
"right": right,
};
// プログラムに送りたい値を,連想配列で書きます

const request = {
"method": "POST",
"headers": {"Content-Type": "application/json", "charset":"utf-8"},
"body": JSON.stringify(sendData),
};

const responce = await fetch(url, request);
// ここでプログラムを実行させます
//「responce」には,プログラムからやってきたデータなどが入ります

const receivedData = await responce.json();
// プログラムからやってきたデータを,使いやすいように連想配列に変換します

const html = receivedData["result"];
// あとはふつうの連想配列とおんなじように使えます

document.getElementById("result").innerHTML = html
// HTMLに反映します

};



/cgi-bin/program.py


#!C:\Users\...\AppData\Local\Programs\Python\Python38\python.exe
# coding: utf-8

# 1行目で,「#!」に続けて,Pythonのインタプリタを絶対パスで指定します

import sys
import io
import json

sys.stdin = io.TextIOWrapper(sys.stdin.buffer, encoding = "utf-8")
sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding = "utf-8")
# 日本語(2バイト文字)をふくむデータを送受信するときに
# 文字化けしないようにするためのおまじない

received_data = json.loads(sys.stdin.readline())
# 「received_data」に,JavaScriptからやってきたデータが,辞書形式で入ります

f = open("./cgi-bin/log.txt", "w", encoding = "utf-8")
# デバッグしたいときに,よく「print」文を使いたくなりますが
# ここでは「print」文は使えないので
# テキストファイルに出力します

f.write(received_data)
# たとえば変数の中身を見たいときは,こんな感じで…

left = received_data["left"]
right = received_data["right"]
# あとはふつうの辞書形式とおなじように使えます

result = int(left) * int(right)

send_data = {
"result": result
}
# JavaScriptに送りたいデータを,辞書形式で書きます

print("Content-type: text/html; charset=utf-8\r\n")
print(json.dumps(send_data))
# JavaScriptにデータを送ります

f.close()
exit()



研究室のサーバでやるときの注意点! 


それぞれのファイルの置くところ 


HTML,CSS,JavaScriptなど
/var/www/html/

プログラム
/var/www/cgi-bin/

(プログラムを「/var/www/html/」下(「/var/www/html/.../cgi-bin/」など)においても
動かないので注意!)


プログラムのアクセス権限はゆるゆるに 


どのアクセス権限が最小限必要なのかは未調査ですが,
7777にしておくと確実です(あたりまえですが).


Pythonのインタプリタ 


/usr/local/pyenv/versions/3.8.5/bin/python3.8


404 Not Foundが出るときは… 


JavaScriptで指定しているプログラムのパスが
間違っていないか確認してください.


500 Internal Server Errorが出るときは… 


JavaScriptで指定しているプログラムのパスは合っていますが,
そのプログラムを実行している(実行しようとした)ときに,
なにかしらのエラーが発生しています.

・プログラムの権限がゆるゆるになっているか確認してください

・プログラムがちゃんと正しく実行できるか(コンパイル上のエラーがないか)確認してください
特に,インタプリタのパスが正しいか,ライブラリが(もちろんサーバ側に)
インストールされているか確認してください.

エラーログは/var/log/下に残されますが,
見るためには管理者権限が必要です…


トップ   新規 一覧 検索 最終更新   ヘルプ   最終更新のRSS