ArnLib  4.0.x
Active Registry Network
ArnRpc.hpp
Go to the documentation of this file.
1 // Copyright (C) 2010-2022 Michael Wiklund.
2 // All rights reserved.
3 // Contact: arnlib@wiklunden.se
4 //
5 // This file is part of the ArnLib - Active Registry Network.
6 // Parts of ArnLib depend on Qt and/or other libraries that have their own
7 // licenses. Usage of these other libraries is subject to their respective
8 // license agreements.
9 //
10 // GNU Lesser General Public License Usage
11 // This file may be used under the terms of the GNU Lesser General Public
12 // License version 2.1 as published by the Free Software Foundation and
13 // appearing in the file LICENSE_LGPL.txt included in the packaging of this
14 // file. In addition, as a special exception, you may use the rights described
15 // in the Nokia Qt LGPL Exception version 1.1, included in the file
16 // LGPL_EXCEPTION.txt in this package.
17 //
18 // GNU General Public License Usage
19 // Alternatively, this file may be used under the terms of the GNU General Public
20 // License version 3.0 as published by the Free Software Foundation and appearing
21 // in the file LICENSE_GPL.txt included in the packaging of this file.
22 //
23 // Other Usage
24 // Alternatively, this file may be used in accordance with the terms and conditions
25 // contained in a signed written agreement between you and Michael Wiklund.
26 //
27 // This program is distributed in the hope that it will be useful, but WITHOUT ANY
28 // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
29 // PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
30 //
31 
32 #ifndef ARNRPC_HPP
33 #define ARNRPC_HPP
34 
35 #define no_queue // MetaObject tag to give Invoke::NoQueue
36 
37 #include "ArnLib_global.hpp"
38 #include "Arn.hpp"
39 #include "ArnError.hpp"
40 #include "MQFlags.hpp"
41 #include "ArnCompat.hpp"
42 #include <QGenericArgument>
43 #include <QString>
44 #include <QByteArray>
45 #include <QObject>
46 #include <QMetaType>
47 
49 #define MQ_ARG(type, label, data) MQArgument<type >(#type, #label, data)
50 
51 class ArnRpcPrivate;
52 class ArnRpcReceiverStorage;
53 class ArnDynamicSignals;
54 class ArnPipe;
55 class QMetaMethod;
56 class QTimer;
57 
59 class ARNLIBSHARED_EXPORT MQGenericArgument : public QGenericArgument
60 {
61 public:
62  inline MQGenericArgument( const char* aName = arnNullptr, const char* aLabel = arnNullptr,
63  const void* aData = arnNullptr)
64  : QGenericArgument( aName, aData), _label(aLabel) {}
65  inline MQGenericArgument( const QGenericArgument& qgenArg)
66  : QGenericArgument( qgenArg), _label("") {}
67  inline const char* label() const {return _label;}
68 
69 private:
70  const char* _label;
71 };
72 
73 
75 template <class T>
77 {
78 public:
79  inline MQArgument( const char* aName, const char* aLabel, const T &aData)
80  : MQGenericArgument( aName, aLabel, static_cast<const void*>(&aData))
81  {}
82 };
83 
84 
85 class ArnRpcMode {
86  Q_GADGET
87  Q_ENUMS(E)
88 public:
89  enum E {
91  Provider = 0x0001,
93  AutoDestroy = 0x0002,
95  UuidPipe = 0x0004,
97  NoDefaultArgs = 0x0008,
99  SendSequence = 0x0010,
101  CheckSequence = 0x0020,
103  OnlyPosArgIn = 0x0040,
105  NamedArg = 0x0080,
107  NamedTypedArg = 0x0100,
109  UseDefaultCall = 0x0200,
111  Debug = 0x8000,
116  };
118 };
119 
120 
122 
156 class ARNLIBSHARED_EXPORT ArnRpc : public QObject
157 {
158  Q_OBJECT
159  Q_DECLARE_PRIVATE(ArnRpc)
160 
161 public:
162  typedef ArnRpcMode Mode;
163 
164  struct Invoke {
165  enum E {
167  NoQueue = 0x01
168  };
170  };
171 
172  explicit ArnRpc( QObject* parent = arnNullptr);
173  ~ArnRpc();
174 
176 
178  QString pipePath() const;
179 
180  bool open( const QString& pipePath);
181 
183 
188  void setPipe( ArnPipe* pipe);
189 
191 
194  ArnPipe* pipe() const;
195 
196  bool setReceiver( QObject* receiver, bool useTrackRpcSender = true);
197  QObject* receiver() const;
198 
199  void setMethodPrefix( const QString& prefix);
200  QString methodPrefix() const;
201 
203 
205  void setIncludeSender( bool v);
206 
207  void setMode( Mode mode);
208 
210 
212  Mode mode() const;
213 
215 
219  void setHeartBeatSend( int time);
220 
222 
226  int getHeartBeatSend() const;
227 
229 
233  void setHeartBeatCheck( int time);
234 
236 
240  int getHeartBeatCheck() const;
241 
243 
246  bool isHeartBeatOk() const;
247 
248  void addSenderSignals( QObject* sender, const QString& prefix);
249 
251 
270  bool invoke( const QString& funcName,
279 
281 
301  bool invoke( const QString& funcName,
302  Invoke invokeFlags,
311 
312  ArnRpc* rpcSender();
313  static ArnRpc* rpcSender( QObject* receiver);
314 
316 
329  static void batchConnect( const QObject* sender, const ARN_RegExp& rgx,
330  const QObject* receiver, const QString& replace,
331  Mode mode = Mode());
332 
334 
348  void batchConnect( const ARN_RegExp& rgx,
349  const QObject* receiver, const QString& replace,
350  Mode mode = Mode()) {
351  batchConnect( this, rgx, receiver, replace, mode);
352  }
353 
355 
369  void batchConnect( const QObject* sender, const ARN_RegExp& rgx,
370  const QString& replace,
371  Mode mode = Mode()) {
372  batchConnect( sender, rgx, this, replace, mode);
373  }
374 
376  bool isConvVariantPar() const;
377  void setConvVariantPar( bool convVariantPar);
379 
380 signals:
382 
385  void pipeClosed();
386 
388 
392  void textReceived( const QString& text);
393 
395 
399  void defaultCall( const QByteArray& data);
400 
402  void outOfSequence();
403 
405 
409  void heartBeatChanged( bool isOk);
410 
412  void heartBeatReceived();
413 
414 public slots:
416 
420  void sendText( const QString& txt);
421 
422 private slots:
423  void pipeInput( const QByteArray& data);
424  void destroyPipe();
425  void timeoutHeartBeatSend();
426  void timeoutHeartBeatCheck();
427 
429 protected:
430  void errorLog( const QString& errText, ArnError err = ArnError::Undef, void* reference = arnNullptr);
431 
432  ArnRpc( ArnRpcPrivate& dd, QObject* parent);
433  ArnRpcPrivate* const d_ptr;
435 
436 private:
437  struct RpcTypeInfo {
438  const char* rpcTypeName;
439  const char* qtTypeName;
440  int typeId;
441  };
442  struct ArgInfo {
443  QGenericArgument arg;
444  QByteArray name;
445  QByteArray qtType;
446  int typeId;
447  const void* data;
448  bool hasName;
449  bool hasType;
450  bool dataAsArg;
451  bool isPositional;
452  bool isBinary;
453  bool isDataAlloc;
454  bool isArgAlloc;
455  ArgInfo() {
456  typeId = 0;
457  data = arnNullptr;
458  hasName = false;
459  hasType = false;
460  dataAsArg = false;
461  isPositional = false;
462  isBinary = false;
463  isDataAlloc = false;
464  isArgAlloc = false;
465  }
466  };
467  struct MethodsParam {
468  QList<QByteArray> methodNames;
469  struct Params {
470  QList<QByteArray> paramNames;
471  QList< QList<int> > methodIdsTab;
472  QList<int> allMethodIds;
473  };
474  QList<Params> paramTab;
475  };
476 
477  void init();
478  bool xsmAddArg( Arn::XStringMap& xsm, const MQGenericArgument& arg, uint index, int& nArg);
479  bool xsmLoadArg( const Arn::XStringMap& xsm, ArgInfo& argInfo, int& index, const QByteArray& methodName);
480  bool argLogic( ArgInfo* argInfo, char* argOrder, int& argc, const QByteArray& methodName);
481  int argLogicFindMethod( const ArgInfo* argInfo, int argc, const QByteArray& methodName);
482  bool checkConvVarPar( const QByteArray& methodName, int argc);
483  bool importArgData( ArgInfo& argInfo, const QByteArray& methodName, bool useVarPar);
484  void funcHeartBeat( const Arn::XStringMap& xsm);
485  void funcHelp( const Arn::XStringMap& xsm);
486  void funcHelpMethod( const QMetaMethod& method, const QByteArray& name, int parNumMin, int flags);
487  void funcArg( const Arn::XStringMap& xsm);
488 
489  void setupReceiverMethodsParam();
490  void deleteReceiverMethodsParam();
491  static bool hasSameParamNames( const QMetaMethod& method1, const QMetaMethod& method2);
492  static QByteArray methodSignature( const QMetaMethod& method);
493  static const RpcTypeInfo& typeInfoFromRpc( const QByteArray& rpcTypeName);
494  static const RpcTypeInfo& typeInfoFromQt( const QByteArray& qtTypeName);
495  static const RpcTypeInfo& typeInfoFromId( int typeId);
496  static const RpcTypeInfo& typeInfoNull();
497 
498  static RpcTypeInfo _rpcTypeInfoTab[];
499 };
500 
503 Q_DECLARE_METATYPE(ArnRpc*)
504 
505 #endif // ARNRPC_HPP
Convenience, combined UuidPipe and AutoDestroy
Definition: ArnRpc.hpp:113
When calling out, uses named argument e.g "myFunc count=123".
Definition: ArnRpc.hpp:105
void batchConnect(const QObject *sender, const ARN_RegExp &rgx, const QString &replace, Mode mode=Mode())
Make batch connection from one senders signals to this ArnRpc:s slots/signals.
Definition: ArnRpc.hpp:369
void batchConnect(const ARN_RegExp &rgx, const QObject *receiver, const QString &replace, Mode mode=Mode())
Make batch connection from this ArnRpc:s signals to another receivers slots/signals.
Definition: ArnRpc.hpp:348
Container class with string representation for serialized data.
Definition: XStringMap.hpp:107
Only allow calling in with positional argument (typed)
Definition: ArnRpc.hpp:103
#define MQ_DECLARE_FLAGSTXT(FEStruct)
Flags text.
Definition: MQFlags.hpp:57
#define MQ_DECLARE_FLAGS(FEStruct)
Flags.
Definition: MQFlagsBase.hpp:49
Similar to QArgument but with added argument label (parameter name)
Definition: ArnRpc.hpp:76
QList< QList< int > > methodIdsTab
Definition: ArnRpc.hpp:471
#define ARN_RegExp
Definition: ArnCompat.hpp:70
When receiver method missing, send defaultCall() signal instead of error.
Definition: ArnRpc.hpp:109
QList< QByteArray > paramNames
Definition: ArnRpc.hpp:470
Remote Procedure Call.
Definition: ArnRpc.hpp:156
Check sequence order information from pipe. Can generate signal outOfSequence().
Definition: ArnRpc.hpp:101
MQGenericArgument(const QGenericArgument &qgenArg)
Definition: ArnRpc.hpp:65
Provider side (opposed to requester)
Definition: ArnRpc.hpp:91
#define MQ_DECLARE_OPERATORS_FOR_FLAGS(FEStruct)
Definition: MQFlagsBase.hpp:65
When calling out, uses named argument with type e.g "myFunc count:int=123".
Definition: ArnRpc.hpp:107
const char * label() const
Definition: ArnRpc.hpp:67
Send sequence order information to pipe.
Definition: ArnRpc.hpp:99
MQGenericArgument(const char *aName=arnNullptr, const char *aLabel=arnNullptr, const void *aData=arnNullptr)
Definition: ArnRpc.hpp:62
Use AutoDestroy for the pipe, i.e. it is closed when tcp/ip is broken.
Definition: ArnRpc.hpp:93
Use an unique uuid in the pipe name.
Definition: ArnRpc.hpp:95
ArnItem specialized as a pipe.
Definition: ArnPipe.hpp:64
If guarantied no default arguments, full member name overload is ok.
Definition: ArnRpc.hpp:97
ArnRpcMode Mode
Definition: ArnRpc.hpp:162
#define ARNLIBSHARED_EXPORT
Similar to QGenericArgument but with added argument label (parameter name)
Definition: ArnRpc.hpp:59
Convenience, combined NamedArg and NamedTypedArg
Definition: ArnRpc.hpp:115
Debug mode, dumping info for the batch connections.
Definition: ArnRpc.hpp:111
MQArgument(const char *aName, const char *aLabel, const T &aData)
Definition: ArnRpc.hpp:79