E-MailRelay

grequestclient.cpp
Go to the documentation of this file.
1//
2// Copyright (C) 2001-2024 Graeme Walker <graeme_walker@users.sourceforge.net>
3//
4// This program is free software: you can redistribute it and/or modify
5// it under the terms of the GNU General Public License as published by
6// the Free Software Foundation, either version 3 of the License, or
7// (at your option) any later version.
8//
9// This program is distributed in the hope that it will be useful,
10// but WITHOUT ANY WARRANTY; without even the implied warranty of
11// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12// GNU General Public License for more details.
13//
14// You should have received a copy of the GNU General Public License
15// along with this program. If not, see <http://www.gnu.org/licenses/>.
16// ===
17///
18/// \file grequestclient.cpp
19///
20
21#include "gdef.h"
22#include "gstr.h"
23#include "grequestclient.h"
24#include "glog.h"
25
26 GSmtp::RequestClient::RequestClient( GNet::EventState es , const std::string & key , const std::string & ok ,
27 const GNet::Location & location , unsigned int connection_timeout , unsigned int response_timeout ,
28 unsigned int idle_timeout ) :
29 GNet::Client(es,location,
30 GNet::Client::Config()
31 .set_line_buffer_config(GNet::LineBuffer::Config::newline())
32 .set_connection_timeout(connection_timeout)
33 .set_response_timeout(response_timeout)
34 .set_idle_timeout(idle_timeout)) ,
35 m_eol(1U,'\n') ,
36 m_key(key) ,
37 m_ok(ok) ,
38 m_timer(*this,&RequestClient::onTimeout,es)
39{
40 G_DEBUG( "GSmtp::RequestClient::ctor: " << location.displayString() << ": "
41 << connection_timeout << " " << response_timeout ) ;
42}
43
44 void GSmtp::RequestClient::onConnect()
45{
46 G_DEBUG( "GSmtp::RequestClient::onConnect" ) ;
47 if( busy() )
48 send( requestLine(m_request) ) ; // GNet::Client::send()
49}
50
51 void GSmtp::RequestClient::request( const std::string & request_payload )
52{
53 G_DEBUG( "GSmtp::RequestClient::request: \"" << request_payload << "\"" ) ;
54 if( busy() )
55 throw ProtocolError() ;
56
57 m_request = request_payload ;
58 m_timer.startTimer( 0U ) ;
59
60 // clear the base-class line buffer of any incomplete line
61 // data from a previous request -- this is racey for servers
62 // that incorrectly reply with more than one line
63 clearInput() ;
64}
65
66 void GSmtp::RequestClient::onTimeout()
67{
68 if( connected() )
69 send( requestLine(m_request) ) ; // GNet::Client::send()
70}
71
72 bool GSmtp::RequestClient::busy() const
73{
74 return !m_request.empty() ;
75}
76
77 void GSmtp::RequestClient::onDelete( const std::string & reason )
78{
79 if( !reason.empty() )
80 G_WARNING( "GSmtp::RequestClient::onDelete: error: " << reason ) ;
81}
82
83 void GSmtp::RequestClient::onSecure( const std::string & , const std::string & , const std::string & )
84{
85}
86
87 bool GSmtp::RequestClient::onReceive( const char * line_data , std::size_t line_size , std::size_t ,
88 std::size_t , char )
89{
90 std::string line( line_data , line_size ) ;
91 G_DEBUG( "GSmtp::RequestClient::onReceive: [" << G::Str::printable(line) << "]" ) ;
92 if( busy() )
93 {
94 m_request.erase() ;
95 eventSignal().emit( std::string(m_key) , result(line) , std::string() ) ; // empty string if matching m_ok
96 return false ;
97 }
98 else
99 {
100 return true ;
101 }
102}
103
104 void GSmtp::RequestClient::onSendComplete()
105{
106}
107
108std::string GSmtp::RequestClient::requestLine( const std::string & request_payload ) const
109{
110 return request_payload + m_eol ;
111}
112
113std::string GSmtp::RequestClient::result( std::string line ) const
114{
115 G::Str::trimRight( line , "\r" ) ;
116 return !m_ok.empty() && line.find(m_ok) == 0U ? std::string() : line ;
117}
118
GNet::EventState
A lightweight object containing an ExceptionHandler pointer, optional ExceptionSource pointer and opt...
Definition: geventstate.h:131
GNet::Location
A class that represents the remote target for out-going client connections.
Definition: glocation.h:70
GNet::Location::displayString
std::string displayString() const
Returns a string representation for logging and debug.
Definition: glocation.cpp:182
GSmtp::Client
A class which acts as an SMTP client, sending messages to a remote SMTP server.
Definition: gsmtpclient.h:64
GSmtp::RequestClient
A network client class that interacts with a remote server using a stateless line-based request/respo...
Definition: grequestclient.h:47
GSmtp::RequestClient::busy
bool busy() const
Returns true after request() and before the subsequent event signal.
Definition: grequestclient.cpp:72
GSmtp::RequestClient::RequestClient
RequestClient(GNet::EventState, const std::string &key, const std::string &ok, const GNet::Location &host_and_service, unsigned int connection_timeout, unsigned int response_timeout, unsigned int idle_timeout)
Constructor.
Definition: grequestclient.cpp:26
GSmtp::RequestClient::request
void request(const std::string &)
Issues a request.
Definition: grequestclient.cpp:51
G::Str::trimRight
static std::string & trimRight(std::string &s, std::string_view ws, std::size_t limit=0U)
Trims the rhs of s, taking off up to 'limit' of the 'ws' characters.
Definition: gstr.cpp:313
G::Str::printable
static std::string printable(const std::string &in, char escape='\\')
Returns a printable representation of the given input string, using chacter code ranges 0x20 to 0x7e ...
Definition: gstr.cpp:913
glog.h
grequestclient.h
gstr.h
GNet
Network classes.
Definition: gdef.h:1243
GNet::Client::Config
A structure containing GNet::Client configuration parameters.
Definition: gclient.h:87