2023-07-23
前回はまず何もいじらないでそのままテンプレートモジュールを動かしたが、当然ながら実践ではmod_mytest.cのなかで、様々な外部ライブラリと連携した処理を書くことになる。
今回、そのなかでRedisのC言語ライブラリhiredis、PostgreSQLのC言語ライブラリlibpqを組み込んで接続、切断をしてみる。これができれば似た他のすべての処理を自作モジュールのなかで行えるはずである。
hiredisをソースコードからインストールすると、ヘッダファイルは/usr/local/include/hiredisに、ライブラリファイルは/usr/local/lib/libhiredis.soとなる。何もせずに自作Apacheモジュールでこれを使おうとすると、Apache再起動時のモジュール読み込み時にUndefined Symbolとなってしまう。
これはapxs2コマンドでビルドするとき、パスを指定してあげれば解決する。
ひとまず、以下のように、redis,postgresql両方に接続して、そのまま切断するmod_mytest.cに改造した。
C/C++ | mod_mytest.c | GitHub Source |
/* ** mod_mytest.c -- Apache sample mytest module ** [Autogenerated via ``apxs -n mytest -g''] ** ** To play with this sample module first compile it into a ** DSO file and install it into Apache's modules directory ** by running: ** ** $ apxs -c -i mod_mytest.c ** ** Then activate it in Apache's apache2.conf file for instance ** for the URL /mytest in as follows: ** ** # apache2.conf ** LoadModule mytest_module modules/mod_mytest.so ** <Location /mytest> ** SetHandler mytest ** </Location> ** ** Then after restarting Apache via ** ** $ apachectl restart ** ** you immediately can request the URL /mytest and watch for the ** output of this module. This can be achieved for instance via: ** ** $ lynx -mime_header http://localhost/mytest ** ** The output should be similar to the following one: ** ** HTTP/1.1 200 OK ** Date: Tue, 31 Mar 1998 14:42:22 GMT ** Server: Apache/1.3.4 (Unix) ** Connection: close ** Content-Type: text/html ** ** The sample page from mod_mytest.c */ #include <stdio.h> #include <string.h> #include <stdlib.h> #include <unistd.h> #include <sys/time.h> #include <hiredis/hiredis.h> #include <postgresql/libpq-fe.h> #include "httpd.h" #include "http_config.h" #include "http_protocol.h" #include "ap_config.h" #include "http_log.h" /* The sample content handler */ static int mytest_handler(request_rec *r) { redisContext *rdconn; PGconn *pgconn; if (strcmp(r->handler, "mytest")) { return DECLINED; } r->content_type = "text/html"; if (!r->header_only){ ap_rputs("The sample page from mod_mytest.c\n", r); rdconn = redisConnect("127.0.0.1", 6379); if (!rdconn) { ap_rputs("redisConnect error\n", r); return OK; } if (rdconn->err) { ap_log_rerror(APLOG_MARK, APLOG_CRIT, 0, r,"%s", rdconn->errstr); ap_rputs("redisConnect error\n", r); redisFree(rdconn); return OK; } pgconn = PQconnectdb( "host=127.0.0.1 port=5432 dbname=ekidb" ); if(!pgconn || PQstatus( pgconn ) == CONNECTION_BAD ){ ap_rputs("PQconnectdb error\n", r); if(pgconn){ PQfinish(pgconn); } redisFree(rdconn); return OK; } ap_rputs("redisConnect/PQconnectdb SUCCESS\n", r); PQfinish(pgconn); redisFree(rdconn); } return OK; } static void mytest_register_hooks(apr_pool_t *p) { ap_hook_handler(mytest_handler, NULL, NULL, APR_HOOK_MIDDLE); } /* Dispatch list for API hooks */ module AP_MODULE_DECLARE_DATA mytest_module = { STANDARD20_MODULE_STUFF, NULL, /* create per-dir config structures */ NULL, /* merge per-dir config structures */ NULL, /* create per-server config structures */ NULL, /* merge per-server config structures */ NULL, /* table of config file commands */ mytest_register_hooks /* register hooks */ };
redisConnectの詳細エラーログがある場合Apacheのログに出すようにしている。
それ以外はブラウザへ返す文字列にエラーまたは成功を追記して終了。
以下のようにコンパイルするのがポイント。
apxs2 -I/usr/local/include -L/usr/local/lib -lhiredis -lpq -c mod_mytest.c
/usr/local/libにライブラリパスを通して使用ライブラリを宣言してコンパイルする。
インストール、Apache再起動に変更はなし。
sudo apxs2 -i -a -n 'mytest' mod_mytest.la sudo /etc/init.d/apache2 restart
エラーが出なければ、ちゃんと/usr/local/lib/libhiredis.soが組み込まれている。
あとは前回と変更なく下記URI設定になっているとして、
<virtualhost> (中略) <location> SetHandler mytest </location> </virtualhost>
http://192.168.1.55/mytest
などと打って
The sample page from mod_mytest.c redisConnect/PQconnectdb SUCCESS
と表示されれば、自作モジュールでredisConnect、PQconnectdbができており、あらゆる処理ができることとなる。
※本記事内容の無断転載を禁じます。
ご連絡は以下アドレスまでお願いします★
さくらインターネットでPython MecabをCGIから使う
さくらインターネットのPHPでAnalytics-G4 APIを使う
インクルードパスの調べ方
【Git】特定ファイルを除外する.gitignore
【Ubuntu/Debian】NVIDIA関係のドライバを自動アップデートさせない
【Python】Spacyを使用して文章から出発地と目的地を抜き出す
HomeBrewでApache2を入れて自動起動つきで動かしPHPモジュールと連携する
macOSに標準付属のApacheを自動起動つきで動かす
HomeBrewでPostgreSQLを入れて自動起動つきで動かす
Windows版Google Driveが使用中と言われアンインストールできない場合
【C/C++】小数点以下の切り捨て・切り上げ・四捨五入
進研ゼミチャレンジタッチをAndroid端末化する
Windows11+WSL2でUbuntuを使う【2】ブリッジ接続+固定IPの設定
Googleスプレッドシートで図形をコピーして使いまわすには
【Linux】iconv/libiconvをソースコードからインストール
【Apache】サーバーに同時接続可能なクライアント数を調整する
Pythonで処理にかかった時間を計測するには
Windows11のコマンドプロンプトでテキストをコピーする