REC RPC library
rec_rpc_Client.h
Go to the documentation of this file.
1 /*
2 Copyright (c) 2011, REC Robotics Equipment Corporation GmbH, Planegg, Germany
3 All rights reserved.
4 
5 Redistribution and use in source and binary forms, with or without modification,
6 are permitted provided that the following conditions are met:
7 
8 - Redistributions of source code must retain the above copyright notice,
9  this list of conditions and the following disclaimer.
10 - Redistributions in binary form must reproduce the above copyright notice,
11  this list of conditions and the following disclaimer in the documentation and/or
12  other materials provided with the distribution.
13 - Neither the name of the REC Robotics Equipment Corporation GmbH nor the names of
14  its contributors may be used to endorse or promote products derived from this software
15  without specific prior written permission.
16 
17 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
18 OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
19 AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
20 CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
23 IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
24 OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25 */
26 
27 #ifndef _REC_RPC_CLIENT_H_
28 #define _REC_RPC_CLIENT_H_
29 
30 #include "rec/rpc/defines.h"
31 #include "rec/rpc/rec_rpc_common.h"
33 
34 namespace rec
35 {
36  namespace rpc
37  {
39  namespace client
40  {
41  class Client;
42  }
52  struct NotifierBase
53  {
60  virtual void notify( const serialization::Serializable& result, ErrorCode errorCode ) const = 0;
61  };
62 
64  typedef QSharedPointer< NotifierBase > NotifierBasePtr;
65 
66  namespace detail
67  {
68  template< typename Parent_t, typename Result_t >
69  struct Notifier : public rec::rpc::NotifierBase
70  {
71  typedef void( Parent_t::*Notify_f )( const Result_t&, rec::rpc::ErrorCode );
72 
73  Notifier( Parent_t* parent, Notify_f notifier ) : _parent( parent ), _notifier( notifier ) { }
74 
75  void notify( const serialization::Serializable& result, ErrorCode errorCode ) const
76  {
77  if ( typeid( result ) == typeid( Result_t ) )
78  {
79  ( _parent->*_notifier )( static_cast< const Result_t& >( result ), errorCode );
80  }
81  else
82  {
83  Result_t r;
84  ( _parent->*_notifier )( r, rec::rpc::WrongDataFormat );
85  }
86  }
87 
88  Parent_t* _parent;
89  Notify_f _notifier;
90  };
91  }
99  class REC_RPC_EXPORT Client : public QObject
100  {
101  Q_OBJECT
102  public:
104  static const unsigned int DefaultTimeout = 2000;
105 
111  Client( QObject* parent = 0 );
112 
114  virtual ~Client();
115 
120  QString name() const;
121 
126  bool isMultiThreadedSerializationEnabled() const;
127 
132  bool isLocalIPCEnabled() const;
133 
138  bool isConnected() const;
139 
145  QString address() const;
146 
152  QHostAddress localAddress() const;
153 
159  quint16 localPort() const;
160 
166  QHostAddress peerAddress() const;
167 
173  quint16 peerPort() const;
174 
186  QString expectedGreeting() const;
187 
198  unsigned int msTimeout() const;
199 
211  void getServerVersion( int* major, int* minor, int* patch, int* date = 0, QString* suffix = 0 );
212 
220  QString getServerVersion();
221 
222  public Q_SLOTS:
228  void setName( const QString& name );
229 
236  void setMultiThreadedSerializationEnabled( bool enabled );
237 
244  void setLocalIPCEnabled( bool enabled );
245 
253  void setAddress( const QString& address );
254 
266  void setExpectedGreeting( const QString& greeting );
267 
278  void setMsTimeout( unsigned int timeout );
279 
291  void setAutoReconnectEnabled( bool enable, unsigned int ms = 200 );
292 
303  void connectToServer( unsigned int msTimeout = DefaultTimeout );
304 
312  void disconnectFromServer();
313 
314  Q_SIGNALS:
320  void connected();
321 
329  void disconnected( rec::rpc::ErrorCode error );
330 
336  void stateChanged( QAbstractSocket::SocketState state );
337 
344  void error( QAbstractSocket::SocketError socketError, const QString& errorString );
345 
352  void log( const QString& message, int level = 1 );
353 
354  protected:
370  void invoke( const QString& name, serialization::SerializablePtrConst param, serialization::SerializablePtr result, bool blocking );
371 
385  void publishTopic( const QString& name, serialization::SerializablePtrConst data );
386 
399  void registerNotifier( const QString& name, NotifierBasePtr notifier );
400 
411  void unregisterNotifier( const QString& name );
412 
422  bool isNotifierRegistered( const QString& name ) const;
423 
437  void registerTopicListener( const QString& name, TopicListenerBasePtr listener );
438 
449  void unregisterTopicListener( const QString& name );
450 
460  bool isTopicListenerRegistered( const QString& name ) const;
461 
462  private:
463  client::Client* _client;
464  };
465  }
466 }
467 
476 #define DECLARE_NOTIFIER( FUNCTIONNAME ) \
477  private: \
478  rec::rpc::NotifierBasePtr create##FUNCTIONNAME##Notifier(); \
479  void FUNCTIONNAME##Finished( const FUNCTIONNAME##Result& result, rec::rpc::ErrorCode errorCode );
480 
491 #define BEGIN_NOTIFIER( CLASSNAME, FUNCTIONNAME ) \
492  inline rec::rpc::NotifierBasePtr CLASSNAME::create##FUNCTIONNAME##Notifier() \
493  { \
494  return rec::rpc::NotifierBasePtr( new rec::rpc::detail::Notifier< CLASSNAME, FUNCTIONNAME##Result >( this, &CLASSNAME::FUNCTIONNAME##Finished ) ); \
495  } \
496  void CLASSNAME::FUNCTIONNAME##Finished( const FUNCTIONNAME##Result& result, rec::rpc::ErrorCode errorCode ) \
497  {
498 
502 #define END_NOTIFIER }
503 
514 #define REGISTER_NOTIFIER( FUNCTIONNAME ) registerNotifier( #FUNCTIONNAME, create##FUNCTIONNAME##Notifier() );
515 
525 #define UNREGISTER_NOTIFIER( FUNCTIONNAME ) unregisterNotifier( #FUNCTIONNAME );
526 
534 #define IS_NOTIFIER_REGISTERED( FUNCTIONNAME ) isNotifierRegistered( #FUNCTIONNAME );
535 
545 #define PREPARE( FUNCTIONNAME ) \
546  const char* funcName = #FUNCTIONNAME; \
547  FUNCTIONNAME##ParamPtr paramPtr = rec::rpc::detail::createSerializable< FUNCTIONNAME##Param >(); \
548  FUNCTIONNAME##Param& param = *paramPtr; \
549  FUNCTIONNAME##ResultPtr resultPtr = rec::rpc::detail::createSerializable< FUNCTIONNAME##Result >(); \
550  FUNCTIONNAME##Result& result = *resultPtr;
551 
563 #define INVOKE( BLOCKING ) invoke( funcName, paramPtr, resultPtr, BLOCKING );
564 
579 #define INVOKE_SIMPLE( FUNCTIONNAME, PARAM, BLOCKING ) \
580  FUNCTIONNAME##ResultPtr resultPtr = rec::rpc::detail::createSerializable< FUNCTIONNAME##Result >(); \
581  FUNCTIONNAME##Result& result = *resultPtr; \
582  invoke( #FUNCTIONNAME, rec::rpc::detail::createSerializable< FUNCTIONNAME##Param >( PARAM ), resultPtr, BLOCKING );
583 
597 #define INVOKE_SIMPLE_EMPTY( FUNCTIONNAME, BLOCKING ) \
598  FUNCTIONNAME##ResultPtr resultPtr = rec::rpc::detail::createSerializable< FUNCTIONNAME##Result >(); \
599  FUNCTIONNAME##Result& result = *resultPtr; \
600  invoke( #FUNCTIONNAME, rec::rpc::detail::createSerializable< rec::rpc::serialization::Serializable >(), resultPtr, BLOCKING );
601 
602 #endif //_REC_RPC_CLIENT_H_
ErrorCode
Pre-defined error codes.
RPC response notifier wrapper interface.
#define REC_RPC_EXPORT
Definition: defines.h:49
RPC client base class.