2024-10-25


Amazon Linux2でC/C++バイナリのFastCGIを作成しnginx経由でアクセスの続きです。
このときのCサンプルではCGIパラメータの収受に対応してませんでしたが、FCGI_APIを通じて、GET/POSTいずれのフォームデータにもアクセスできるよう改造しました。
libfcgiのC言語APIであるFCGI_を使ってフォームデータを取得するやりかたがWebで全く見つからなかったため、
https://github.com/toshic/libfcgi/blob/master/include/fcgi_stdio.h
を直接見てみたところ、POSTフォームを受け取る標準入力はstdinに代えてFCGI_stdinとすればよく、freadはFCGI_freadとすればよい。大きなデータを出力して返すならFCGI_printfに代えてFCGI_fwriteにFCGI_stdoutを指定すればよい。
それらをすべて使ってフォームデータ受け取り・内容出力をしてみたサンプルソースが以下。
| C/C++ | fcgi_form.cpp | GitHub Source |
#include <string.h>
#include <stdint.h>
#include <stdlib.h>
#include <sys/types.h>
#include <unistd.h>
#include "fcgi_config.h"
#include "fcgi_stdio.h"
int main (void) {
uint32_t access_counter = 0;
while (FCGI_Accept() >= 0) {
FCGI_printf("Content-type: text/plain\r\n"
"\r\n"
"Hello World! Access Counter : %ld\n",
++access_counter);
char *ptr,*mem = NULL; size_t len = 0,frn;
if( (ptr = getenv( "QUERY_STRING" )) != NULL && (len = strlen( ptr )) > 0 ){
FCGI_printf("GET Parameter String :\n");
mem = strdup( ptr );
}
else if( (ptr = getenv( "CONTENT_LENGTH" )) != NULL && (len = atoi( ptr )) > 0 ){
FCGI_printf("POST Parameter String :\n");
if( (mem = (char*)malloc( len + 1 )) != NULL ){
frn = FCGI_fread( mem,len,1,FCGI_stdin );
mem[len] = '\0';
}
}
if (mem) {
FCGI_fwrite( mem,len,1,FCGI_stdout );
FCGI_printf("\n");
free(mem);
}
}
return 0;
}
前回のアクセスカウンタ出力に加え、環境変数QUERY_STRINGに中身があればGETリクエストなのでそのまま出力、CONTENT_LENGTHが1以上ならPOSTリクエストなので、疑似標準入力FCGI_stdinからFCGI_freadで取得。出力はFCGI_stdoutにFCGI_fwriteしている。
コンパイル・リンク
g++ -o form.fcgi fcgi_form.cpp -lfcgi
実行バイナリファイルform.fcgiが出来上がる。場所は/home/ec2-user以下にできたものとする。
FastCGIデーモンプロセスとして起動
前回と同様UNIXドメインソケット接続で待ち受ける。
ps aux | grep fcgi # すでに立ち上がっていないか確認,あったらkillしておく cgi-fcgi -connect /home/ec2-user/form.sock /home/ec2-user/form.fcgi Content-type: text/plain Hello World! Access Counter : 1
フォームパラメータつき実行テスト
curlを使う。POSTフォームのテスト
curl -XPOST --data 'param1=value1¶m2=value2' http://localhost:80/form.cgi Hello World! Access Counter : 2 POST Parameter String : param1=value1¶m2=value2
無事パラメータを取得し出力できている。GETもやってみる。
curl 'http://localhost:80/form.cgi?param1=value1¶m2=value2' Hello World! Access Counter : 3 GET Parameter String : param1=value1¶m2=value2
Cサンプルのソースを改造したのみなので、その他nginxの設定などは前回を参照してください。
※本記事内容の無断転載を禁じます。
ご連絡は以下アドレスまでお願いします★
Wav2Lipのオープンソース版を改造して外部から呼べるAPI化する
Wav2Lipのオープンソース版で静止画の口元のみを動かして喋らせる
【iOS】アプリアイコン・ロゴ画像の作成・設定方法
オープンソースリップシンクエンジンSadTalkerをAPI化してアプリから呼ぶ【2】
オープンソースリップシンクエンジンSadTalkerをAPI化してアプリから呼ぶ【1】
【Xcode】iPhone is not available because it is unpairedの対処法
【Let's Encrypt】Failed authorization procedure 503の対処法
【Debian】古いバージョンでapt updateしたら404 not foundでエラーになる場合
ファイアウォール内部のWindows11 PCにmacOS Sequoiaからリモートデスクトップする
進研ゼミチャレンジタッチをAndroid端末化する
Windows11+WSL2でUbuntuを使う【2】ブリッジ接続+固定IPの設定
Windows11のコマンドプロンプトでテキストをコピーする
Androidホームで左にスワイプすると出てくるニュース共を一切表示させない方法
【Apache】サーバーに同時接続可能なクライアント数を調整する
Googleスプレッドシートを編集したら自動で更新日時を入れる
VirtualBoxの仮想マシンをWindows起動時に自動起動し終了時に自動サスペンドする
Node.jsからPostgreSQLサーバに接続・操作する
【Makefile】依存関係ファイル/静的/動的ライブラリ/実行ファイルをまとめてメイク