SHOEISHA iD

※旧SEメンバーシップ会員の方は、同じ登録情報(メールアドレス&パスワード)でログインいただけます

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

オープンソースC++用クラスライブラリPOCO活用講座

POCO::Netライブラリによる組み込みWebサーバの実装

オープンソースC++用クラスライブラリPOCO活用講座(1)


  • X ポスト
  • このエントリーをはてなブックマークに追加

カンタンWebサーバを作る

 アプリケーション組み込み型Webサーバの用途として、独自のGUI画面の代わりに、ブラウザを使用するアプリケーションをイメージしています。例えば、「Googleデスクトップ」のような感じです。Googleデスクトップは、設定メニューを呼び出すと、ブラウザが立ち上がります。URL入力欄をよく見てください。

URL入力欄
URL入力欄

 どこかのWebサーバと通信しているわけではなく、ローカルのWebサーバと通信して設定画面をブラウザに表示しているのです。この形であれば、ローカルの環境にあまり左右されずに、柔軟なGUI画面を構成できるのではないでしょうか。

Googleデスクトップ設定画面
Googleデスクトップ設定画面

プロジェクトを作る

 では、まず新規のプロジェクトを作ります。[新規作成]メニューで、プロジェクトを選択します。新しいプロジェクトのダイアログが表示されるので、Win32コンソールアプリケーションのテンプレートを選び、プロジェクト名は任意の名前、例えば「MiniWebServer」にします。[OK]をクリックすると、アプリケーションウィザードの設定になりますので、アプリケーションの種類を「コンソールアプリケーション」にします。

プロジェクト画面
プロジェクト画面

「MiniWebServer.cpp」の中身

 サンプルと同様、「MiniWebServer.cpp」の1ファイルにクラスの定義と実装を記述することにします。

「MiniWebServer.cpp」全ソース
#include "stdafx.h"

#include "Poco/Net/HTTPServer.h"
#include "Poco/Net/HTTPRequestHandler.h"
#include "Poco/Net/HTTPRequestHandlerFactory.h"
#include "Poco/Net/HTTPServerParams.h"
#include "Poco/Net/HTTPServerRequest.h"
#include "Poco/Net/HTTPServerResponse.h"
#include "Poco/Net/HTTPServerParams.h"
#include "Poco/Net/ServerSocket.h"
#include "Poco/Util/ServerApplication.h"

#include "Poco/File.h"

class NotFileHandler: public Poco::Net::HTTPRequestHandler
{
public:
    
    void handleRequest(Poco::Net::HTTPServerRequest& request,
                        Poco::Net::HTTPServerResponse& response)
    {
        response.setStatusAndReason(Poco::Net::HTTPResponse::HTTP_NOT_FOUND);
        response.setContentType("text/html");

        std::ostream& ostr = response.send();
        ostr << "<html><head>";
        ostr << "<title>MiniWebServer powered by POCO</title>";
        ostr << "</head><body>ファイルがありません<br />";
        ostr << "</body></html>";
    }
};

class FileRequestHandler: public Poco::Net::HTTPRequestHandler
{
public:
    
    void handleRequest(Poco::Net::HTTPServerRequest& request,
                            Poco::Net::HTTPServerResponse& response)
    {
        try{
            std::string fpass = ".";
            fpass += request.getURI();

            response.sendFile(fpass, "text/html");
        }
        catch(Poco::Exception& )
        {
        }
    }
};

class MiniRequestHandlerFactory: public Poco::Net::HTTPRequestHandlerFactory
{
public:

    Poco::Net::HTTPRequestHandler*
        createRequestHandler(const Poco::Net::HTTPServerRequest& request)
    {
        std::string fpass = ".";
        fpass += request.getURI();

        Poco::File f(fpass);
        if ( !f.exists() || !f.isFile() ) return new NotFileHandler();

        return new FileRequestHandler();
    }
};

class MiniWebServer: public Poco::Util::ServerApplication
{
protected:
    
    int main(const std::vector<std::string>& args)
    {
        int maxThreads = 1;                            // クライアント最大同時接続数

        // 接続スレッド数設定
        Poco::ThreadPool::defaultPool().addCapacity(maxThreads);

        // 設定値クラス
        Poco::Net::HTTPServerParams* pParams = new Poco::Net::HTTPServerParams;
        
        pParams->setMaxQueued(100);                    // 接続要求ソケット最大数
        pParams->setMaxThreads(maxThreads);
        Poco::Net::ServerSocket svs(9980);            // 9980ポート使用

        // HTTPサーバクラスのインスタンス
        Poco::Net::HTTPServer    srv(new MiniRequestHandlerFactory(), svs, pParams); 

        srv.start();                    // サーバ動作開始
        waitForTerminationRequest();    // CTRL-C が押されるまで、
                                        // またはプロセスが強制終了されるまで待機

        srv.stop();                     // サーバ動作ストップ

        return Application::EXIT_OK;
    }
};


int _tmain(int argc, _TCHAR* argv[])
{
    MiniWebServer app;
    return app.run(argc, argv);
}

 サンプルソースではusing宣言を用いて、各クラスの名前空間の記述を省略していました。それでは、どれがPOCOのクラスが分かりにくいので、MiniWebServer.cppでは、名前空間も省略せずに記述しています。例えば、ServerApplicationを、Poco::Util::ServerApplicationとしています。

次のページ
ソース解説

この記事は参考になりましたか?

  • X ポスト
  • このエントリーをはてなブックマークに追加
オープンソースC++用クラスライブラリPOCO活用講座連載記事一覧

もっと読む

この記事の著者

山田 祥寛(ヤマダ ヨシヒロ)

静岡県榛原町生まれ。一橋大学経済学部卒業後、NECにてシステム企画業務に携わるが、2003年4月に念願かなってフリーライターに転身。Microsoft MVP for Visual Studio and Development Technologies。執筆コミュニティ「WINGSプロジェクト」代表。主な著書に「独習シリーズ(Java・C#・Python・PHP・Ruby・JSP&サーブレットなど)」「速習シリーズ(ASP.NET Core・Vue.js・React・TypeScript・ECMAScript、Laravelなど)」「改訂3版JavaScript本格入門」「これからはじめるReact実践入門」「はじめてのAndroidアプリ開発 Kotlin編 」他、著書多数

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

WINGSプロジェクト 高江 賢(タカエ ケン)

WINGSプロジェクトについて>有限会社 WINGSプロジェクトが運営する、テクニカル執筆コミュニティ(代表 山田祥寛)。主にWeb開発分野の書籍/記事執筆、翻訳、講演等を幅広く手がける。2018年11月時点での登録メンバは55名で、現在も執筆メンバを募集中。興味のある方は、どしどし応募頂きたい。著書記事多数。 RSS X: @WingsPro_info(公式)、@WingsPro_info/wings(メンバーリスト) Facebook

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

この記事は参考になりましたか?

この記事をシェア

  • X ポスト
  • このエントリーをはてなブックマークに追加
CodeZine(コードジン)
https://codezine.jp/article/detail/1792 2007/11/20 13:20

おすすめ

アクセスランキング

アクセスランキング

イベント

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

新規会員登録無料のご案内

  • ・全ての過去記事が閲覧できます
  • ・会員限定メルマガを受信できます

メールバックナンバー

アクセスランキング

アクセスランキング