BOOST ASIO - How to write console server

前端 未结 2 413
臣服心动
臣服心动 2020-12-01 20:21

I have to write asynchronous TCP Sever. TCP Server have to be managed by console (for eg: remove client, show list of all connected client, etcc..)

The problem is: H

相关标签:
2条回答
  • 2020-12-01 20:55

    If I understand the OP correctly, he/she wants to run an async TCP server that is controlled via a console i.e console is used as user interface. In that case you don't need a separate client application to query the server for connected clients, etc.:

    • You need to spawn a thread that somehow calls the io_service::run method. Currently you are calling this from main. Since your server will probably be scoped in main, you need do something like pass a ref to the server to the new thread. The io_service could e.g be a member of the server class (unless your application has other requirements in which case pass both the server and the io_service to the new thread).
    • add the corresponding methods such as showClients, closeServer, etc. to your server class
    • make sure that these calls which are triggered via the console are thread-safe
    • in your closeServer method you could for instance call io_service::stop which would result in the server ending.
    0 讨论(0)
  • 2020-12-01 21:00

    The problem is: How can I attach (or write) console, which can calls above functionalities. This console have to be a client? Should I run this console client as a sepearate thread?

    You don't need a separate thread, use a posix::stream_descriptor and assign STDIN_FILENO to it. Use async_read and handle the requests in the read handlers.

    #include <boost/asio.hpp>
    
    #include <boost/bind.hpp>
    #include <boost/enable_shared_from_this.hpp>
    #include <boost/shared_ptr.hpp>
    
    #include <iostream>
    
    using namespace boost::asio;
    
    class Input : public boost::enable_shared_from_this<Input>
    {
    public:
        typedef boost::shared_ptr<Input> Ptr;
    
    public:
        static void create(
                io_service& io_service
                )
        {
            Ptr input(
                    new Input( io_service )
                    );
            input->read();
        }
    
    private:
        explicit Input(
                io_service& io_service
             ) :
            _input( io_service )
        {
            _input.assign( STDIN_FILENO );
        }
    
        void read()
        {
            async_read(
                    _input,
                    boost::asio::buffer( &_command, sizeof(_command) ),
                    boost::bind(
                        &Input::read_handler,
                        shared_from_this(),
                        placeholders::error,
                        placeholders::bytes_transferred
                        )
                    );
        }
    
        void read_handler(
                const boost::system::error_code& error,
                size_t bytes_transferred
                )
        {
            if ( error ) {
                std::cerr << "read error: " << boost::system::system_error(error).what() << std::endl;
                return;
            }
    
            if ( _command != '\n' ) {
                std::cout << "command: " << _command << std::endl;
            }
    
            this->read();
        }
    
    private:
        posix::stream_descriptor _input;
        char _command;
    };
    
    int
    main()
    {
        io_service io_service;
        Input::create( io_service );
        io_service.run();
    }
    
    0 讨论(0)
提交回复
热议问题