~ari-tczew/ubuntu/natty/clementine/lp-747113

« back to all changes in this revision

Viewing changes to 3rdparty/gloox/adhoc.h

  • Committer: Artur Rona
  • Date: 2011-04-04 20:05:33 UTC
  • Revision ID: ari-tczew@ubuntu.com-20110404200533-6aclzasj5pp8t1hq
* New upstream release. (LP: #747113)
* Drop all patches, have been applied upstream.
* Update debian/copyright.
* Refresh description in debian/control in order to avoid lintian error.
* Bump debhelper to 8.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
  Copyright (c) 2004-2009 by Jakob Schroeter <js@camaya.net>
 
3
  This file is part of the gloox library. http://camaya.net/gloox
 
4
 
 
5
  This software is distributed under a license. The full license
 
6
  agreement can be found in the file LICENSE in this distribution.
 
7
  This software may not be copied, modified, sold or distributed
 
8
  other than expressed in the named license agreement.
 
9
 
 
10
  This software is distributed without any warranty.
 
11
*/
 
12
 
 
13
 
 
14
 
 
15
#ifndef ADHOC_H__
 
16
#define ADHOC_H__
 
17
 
 
18
#include "dataform.h"
 
19
#include "disco.h"
 
20
#include "disconodehandler.h"
 
21
#include "discohandler.h"
 
22
#include "iqhandler.h"
 
23
#include "stanzaextension.h"
 
24
 
 
25
#include <string>
 
26
#include <list>
 
27
#include <map>
 
28
 
 
29
namespace gloox
 
30
{
 
31
 
 
32
  class ClientBase;
 
33
  class Stanza;
 
34
  class AdhocHandler;
 
35
  class AdhocCommandProvider;
 
36
 
 
37
  /**
 
38
   * @brief This class implements a provider for XEP-0050 (Ad-hoc Commands).
 
39
   *
 
40
   * The current, not complete, implementation is probably best suited for fire-and-forget
 
41
   * type of commands. Any additional feature, like multiple stages, etc., would have to be
 
42
   * added separately.
 
43
   *
 
44
   * To offer commands to remote entities, use this class as follows:<br>
 
45
   * Create a class that will handle command execution requests and derive it from
 
46
   * AdhocCommandProvider. Instantiate an Adhoc object and register your
 
47
   * AdhocCommandProvider-derived object with the Adhoc object using
 
48
   * registerAdhocCommandProvider(). The additional parameters to that method are the internal
 
49
   * name of the command as used in the code, and the public name of the command as it
 
50
   * will be shown to an end user:
 
51
   * @code
 
52
   * MyClass::someFunc()
 
53
   * {
 
54
   *   Adhoc* m_adhoc = new Adhoc( m_client );
 
55
   *
 
56
   *   // this might be a bot monitoring a weather station, for example
 
57
   *   m_adhoc->registerAdhocCommandProvider( this, "getTemp", "Retrieve current temperature" );
 
58
   *   m_adhoc->registerAdhocCommandProvider( this, "getPressure", "Retrieve current air pressure" );
 
59
   *   [...]
 
60
   * }
 
61
   * @endcode
 
62
   * In this example, MyClass is AdhocCommandProvider-derived so it is obviously the command handler, too.
 
63
   *
 
64
   * And that's about it you can do with the Adhoc class. Of course you can have a AdhocCommandProvider
 
65
   * handle more than one command, just register it with the Adhoc object for every desired command,
 
66
   * like shown above.
 
67
   *
 
68
   * What the Adhoc object does when you install a new command is tell the supplied Disco object
 
69
   * to advertise these commands to clients using the 'Service Discovery' protocol to learn about
 
70
   * this implementation's features. These clients can then call and execute the command. Of course you
 
71
   * are free to implement access restrictions to not let anyone mess with your bot, for example.
 
72
   * However, the commands offered using Service Discovery are publically visible in any case.
 
73
   *
 
74
   * To execute commands offered by a remote entity:<br>
 
75
   * ...TBC...
 
76
   *
 
77
   * XEP version: 1.2
 
78
   * @author Jakob Schroeter <js@camaya.net>
 
79
   */
 
80
  class GLOOX_API Adhoc : public DiscoNodeHandler, public DiscoHandler, public IqHandler
 
81
  {
 
82
    public:
 
83
      /**
 
84
       * @brief An abstraction of an Adhoc Command element (from Adhoc Commands, XEP-0050)
 
85
       * as a StanzaExtension.
 
86
       *
 
87
       * @author Jakob Schroeter <js@camaya.net>
 
88
       * @since 1.0
 
89
       */
 
90
      class GLOOX_API Command : public StanzaExtension
 
91
      {
 
92
        friend class Adhoc;
 
93
 
 
94
        public:
 
95
 
 
96
          /**
 
97
           * Specifies the action to undertake with the given command.
 
98
           */
 
99
          enum Action
 
100
          {
 
101
            Execute       =  1,     /**< The command should be executed or continue to be executed.
 
102
                                     * This is the default value. */
 
103
            Cancel        =  2,     /**< The command should be canceled. */
 
104
            Previous      =  4,     /**< The command should be digress to the previous stage of
 
105
                                     * execution. */
 
106
            Next          =  8,     /**< The command should progress to the next stage of
 
107
                                     * execution. */
 
108
            Complete      = 16,     /**< The command should be completed (if possible). */
 
109
            InvalidAction = 32      /**< The action is unknown or invalid. */
 
110
          };
 
111
 
 
112
          /**
 
113
           * Describes the current status of a command.
 
114
           */
 
115
          enum Status
 
116
          {
 
117
            Executing,              /**< The command is being executed. */
 
118
            Completed,              /**< The command has completed. The command session has ended. */
 
119
            Canceled,               /**< The command has been canceled. The command session has ended. */
 
120
            InvalidStatus           /**< The status is unknown or invalid. */
 
121
          };
 
122
 
 
123
          /**
 
124
           * An abstraction of a command note.
 
125
           *
 
126
           * @author Jakob Schroeter <js@camaya.net>
 
127
           * @since 1.0
 
128
           */
 
129
          class GLOOX_API Note
 
130
          {
 
131
 
 
132
            friend class Command;
 
133
 
 
134
            public:
 
135
              /**
 
136
               * Specifies the severity of a note.
 
137
               */
 
138
              enum Severity
 
139
              {
 
140
                Info,               /**< The note is informational only. This is not really an
 
141
                                     * exceptional condition. */
 
142
                Warning,            /**< The note indicates a warning. Possibly due to illogical
 
143
                                     * (yet valid) data. */
 
144
                Error,              /**< The note indicates an error. The text should indicate the
 
145
                                     * reason for the error. */
 
146
                InvalidSeverity     /**< The note type is unknown or invalid. */
 
147
              };
 
148
 
 
149
              /**
 
150
               * A convenience constructor.
 
151
               * @param sev The note's severity.
 
152
               * @param note The note's content.
 
153
               */
 
154
              Note( Severity sev, const std::string& note )
 
155
                : m_severity( sev ), m_note( note ) {}
 
156
 
 
157
              /**
 
158
               * Destructor.
 
159
               */
 
160
              ~Note() {}
 
161
 
 
162
              /**
 
163
               * Returns the note's severity.
 
164
               * @return The note's severity.
 
165
               */
 
166
              Severity severity() const { return m_severity; }
 
167
 
 
168
              /**
 
169
               * Returns the note's content.
 
170
               * @return The note's content.
 
171
               */
 
172
              const std::string& content() const { return m_note; }
 
173
 
 
174
              /**
 
175
               * Returns a Tag representation of the Note.
 
176
               * @return A Tag representation.
 
177
               */
 
178
              Tag* tag() const;
 
179
 
 
180
            private:
 
181
#ifdef ADHOC_COMMANDS_TEST
 
182
            public:
 
183
#endif
 
184
              /**
 
185
               * Constructs a new Note from the given Tag.
 
186
               * @param tag The Tag to parse.
 
187
               */
 
188
              Note( const Tag* tag );
 
189
 
 
190
              Severity m_severity;      /**< The note's severity. */
 
191
              std::string m_note;       /**< The note's content. */
 
192
          };
 
193
 
 
194
          /**
 
195
           * A list of command notes.
 
196
           */
 
197
          typedef std::list<const Note*> NoteList;
 
198
 
 
199
          /**
 
200
           * Creates a Command object that can be used to perform the provided Action.
 
201
           * This constructor is used best to continue execution of a multi stage command
 
202
           * (for which the session ID must be known).
 
203
           * @param node The node (command) to perform the action on.
 
204
           * @param sessionid The session ID of an already running adhoc command session.
 
205
           * @param action The action to perform.
 
206
           * @param form An optional DataForm to include in the request. Will be deleted in Command's
 
207
           * destructor.
 
208
           */
 
209
          Command( const std::string& node, const std::string& sessionid, Action action,
 
210
                   DataForm* form = 0 );
 
211
 
 
212
          /**
 
213
           * Creates a Command object that can be used to perform the provided Action.
 
214
           * This constructor is used best to reply to an execute request.
 
215
           * @param node The node (command) to perform the action on.
 
216
           * @param sessionid The (possibly newly created) session ID of the adhoc command session.
 
217
           * @param status The execution status.
 
218
           * @param form An optional DataForm to include in the reply. Will be deleted in Command's
 
219
           * destructor.
 
220
           */
 
221
          Command( const std::string& node, const std::string& sessionid, Status status,
 
222
                   DataForm* form = 0 );
 
223
 
 
224
          /**
 
225
           * Creates a Command object that can be used to perform the provided Action.
 
226
           * This constructor is used best to reply to a multi stage command that is not yet completed
 
227
           * (for which the session ID must be known).
 
228
           * @param node The node (command) to perform the action on.
 
229
           * @param sessionid The (possibly newly created) session ID of the adhoc command session.
 
230
           * @param status The execution status.
 
231
           * @param executeAction The action to execute.
 
232
           * @param allowedActions Allowed reply actions.
 
233
           * @param form An optional DataForm to include in the reply. Will be deleted in Command's
 
234
           * destructor.
 
235
           */
 
236
          Command( const std::string& node, const std::string& sessionid, Status status,
 
237
                   Action executeAction, int allowedActions = Complete,
 
238
                   DataForm* form = 0 );
 
239
 
 
240
          /**
 
241
           * Creates a Command object that can be used to perform the provided Action.
 
242
           * This constructor is used best to execute the initial step of a command
 
243
           * (single or multi stage).
 
244
           * @param node The node (command) to perform the action on.
 
245
           * @param action The action to perform.
 
246
           * @param form An optional DataForm to include in the request. Will be deleted in Command's
 
247
           * destructor.
 
248
           */
 
249
          Command( const std::string& node, Action action,
 
250
                   DataForm* form = 0 );
 
251
 
 
252
          /**
 
253
           * Creates a Command object from the given Tag.
 
254
           * @param tag A &lt;command&gt; tag in the adhoc commands' namespace.
 
255
           */
 
256
          Command( const Tag* tag = 0 );
 
257
 
 
258
          /**
 
259
           * Virtual destructor.
 
260
           */
 
261
          virtual ~Command();
 
262
 
 
263
          /**
 
264
           * Returns the node identifier (the command).
 
265
           * @return The node identifier.
 
266
           */
 
267
          const std::string& node() const { return m_node; }
 
268
 
 
269
          /**
 
270
           * Returns the command's session ID, if any.
 
271
           * @return The command's session ID.
 
272
           */
 
273
          const std::string& sessionID() const { return m_sessionid; }
 
274
 
 
275
          /**
 
276
           * Returns the execution status for a command. Only valid for execution
 
277
           * results.
 
278
           * @return The execution status for a command.
 
279
           */
 
280
          Status status() const { return m_status; }
 
281
 
 
282
          /**
 
283
           * Returns the command's action.
 
284
           * @return The command's action.
 
285
           */
 
286
          Action action() const { return m_action; }
 
287
 
 
288
          /**
 
289
           * Returns the ORed actions that are allowed to be executed on the
 
290
           * current stage.
 
291
           * @return An int containing the ORed actions.
 
292
           */
 
293
          int actions() const { return m_actions; }
 
294
 
 
295
          /**
 
296
           * Returns the list of notes associated with the command.
 
297
           * @return The list of notes.
 
298
           */
 
299
          const NoteList& notes() const { return m_notes; }
 
300
 
 
301
          /**
 
302
           * Use this function to add a note to the command.
 
303
           * @param note A pointer to a Note object. The Command will own
 
304
           * the Note.
 
305
           */
 
306
          void addNote( const Note* note ) { m_notes.push_back( note ); }
 
307
 
 
308
          /**
 
309
           * Returns the command's embedded DataForm.
 
310
           * @return The command's embedded DataForm. May be 0.
 
311
           */
 
312
          const DataForm* form() const { return m_form; }
 
313
 
 
314
          // reimplemented from StanzaExtension
 
315
          virtual const std::string& filterString() const;
 
316
 
 
317
          // reimplemented from StanzaExtension
 
318
          virtual StanzaExtension* newInstance( const Tag* tag ) const
 
319
          {
 
320
            return new Command( tag );
 
321
          }
 
322
 
 
323
          // reimplemented from StanzaExtension
 
324
          virtual Tag* tag() const;
 
325
 
 
326
          // reimplemented from StanzaExtension
 
327
          virtual StanzaExtension* clone() const
 
328
          {
 
329
            Command* c = new Command();
 
330
 
 
331
            NoteList::const_iterator it = m_notes.begin();
 
332
            for( ; it != m_notes.end(); ++it )
 
333
              c->m_notes.push_back( new Note( *(*it) ) );
 
334
 
 
335
            c->m_node = m_node;
 
336
            c->m_sessionid = m_sessionid;
 
337
            c->m_form = m_form ? static_cast<DataForm*>( m_form->clone() ) : 0;
 
338
            c->m_action = m_action;
 
339
            c->m_status = m_status;
 
340
            c->m_actions = m_actions;
 
341
 
 
342
            return c;
 
343
          }
 
344
 
 
345
        private:
 
346
#ifdef ADHOC_COMMANDS_TEST
 
347
        public:
 
348
#endif
 
349
          NoteList m_notes;
 
350
 
 
351
          std::string m_node;
 
352
          std::string m_sessionid;
 
353
          DataForm* m_form;
 
354
          Action m_action;
 
355
          Status m_status;
 
356
          int m_actions;
 
357
      };
 
358
 
 
359
      /**
 
360
       * Constructor.
 
361
       * Creates a new Adhoc client that registers as IqHandler with a ClientBase.
 
362
       * @param parent The ClientBase used for XMPP communication.
 
363
       */
 
364
      Adhoc( ClientBase* parent );
 
365
 
 
366
      /**
 
367
       * Virtual destructor.
 
368
       */
 
369
      virtual ~Adhoc();
 
370
 
 
371
      /**
 
372
       * This function queries the given remote entity for Adhoc Commands support.
 
373
       * @param remote The remote entity's JID.
 
374
       * @param ah The object handling the result of this request.
 
375
       */
 
376
      void checkSupport( const JID& remote, AdhocHandler* ah );
 
377
 
 
378
      /**
 
379
       * Retrieves a list of commands from the remote entity. You should check whether the remote
 
380
       * entity actually supports Adhoc Commands by means of checkSupport().
 
381
       * @param remote The remote entity's JID.
 
382
       * @param ah The object handling the result of this request.
 
383
       */
 
384
      void getCommands( const JID& remote, AdhocHandler* ah );
 
385
 
 
386
      /**
 
387
       * Executes or continues the given command on the given remote entity.
 
388
       * To construct the @c command object, it is recommended to use either
 
389
       * Command( const std::string&, Action ) to begin execution of a command, or
 
390
       * Command( const std::string&, const std::string&, Action ) to continue execution
 
391
       * of a command.
 
392
       * @param remote The remote entity's JID.
 
393
       * @param command The command to execute.
 
394
       * @param ah The object handling the result of this request.
 
395
       */
 
396
      void execute( const JID& remote, const Adhoc::Command* command, AdhocHandler* ah );
 
397
 
 
398
      /**
 
399
       * Use this function to respond to an execution request submitted by means
 
400
       * of AdhocCommandProvider::handleAdhocCommand().
 
401
       * It is recommended to use
 
402
       * Command( const std::string&, const std::string&, Status, DataForm* )
 
403
       * to construct the @c command object.
 
404
       * Optionally, an Error object can be included. In that case the IQ sent is of type @c error.
 
405
       * @param remote The requester's JID.
 
406
       * @param command The response. The Adhoc object will own and delete the
 
407
       * command object pointed to.
 
408
       * @param error An optional Error obejct to include.
 
409
       */
 
410
      void respond( const JID& remote, const Adhoc::Command* command, const Error* error = 0 );
 
411
 
 
412
      /**
 
413
       * Using this function, you can register a AdhocCommandProvider -derived object as
 
414
       * handler for a specific Ad-hoc Command as defined in XEP-0050.
 
415
       * @param acp The obejct to register as handler for the specified command.
 
416
       * @param command The node name of the command. Will be announced in disco#items.
 
417
       * @param name The natural-language name of the command. Will be announced in disco#items.
 
418
       */
 
419
      void registerAdhocCommandProvider( AdhocCommandProvider* acp, const std::string& command,
 
420
                                         const std::string& name );
 
421
 
 
422
      /**
 
423
       * Use this function to unregister an adhoc command previously registered using
 
424
       * registerAdhocCommandProvider().
 
425
       * @param command The command to unregister.
 
426
       */
 
427
      void removeAdhocCommandProvider( const std::string& command );
 
428
 
 
429
      // reimplemented from DiscoNodeHandler
 
430
      virtual StringList handleDiscoNodeFeatures( const JID& from, const std::string& node );
 
431
 
 
432
      // reimplemented from DiscoNodeHandler
 
433
      virtual Disco::IdentityList handleDiscoNodeIdentities( const JID& from,
 
434
          const std::string& node );
 
435
 
 
436
      // reimplemented from DiscoNodeHandler
 
437
      virtual Disco::ItemList handleDiscoNodeItems( const JID& from, const JID& to, const std::string& node );
 
438
 
 
439
      // reimplemented from IqHandler
 
440
      virtual bool handleIq( const IQ& iq );
 
441
 
 
442
      // reimplemented from IqHandler
 
443
      virtual void handleIqID( const IQ& iq, int context );
 
444
 
 
445
      // reimplemented from DiscoHandler
 
446
      virtual void handleDiscoInfo( const JID& from, const Disco::Info& info, int context );
 
447
 
 
448
      // reimplemented from DiscoHandler
 
449
      virtual void handleDiscoItems( const JID& from, const Disco::Items& items, int context );
 
450
 
 
451
      // reimplemented from DiscoHandler
 
452
      virtual void handleDiscoError( const JID& from, const Error* error, int context );
 
453
 
 
454
    private:
 
455
#ifdef ADHOC_TEST
 
456
    public:
 
457
#endif
 
458
      typedef std::map<const std::string, AdhocCommandProvider*> AdhocCommandProviderMap;
 
459
      AdhocCommandProviderMap m_adhocCommandProviders;
 
460
 
 
461
      enum AdhocContext
 
462
      {
 
463
        CheckAdhocSupport,
 
464
        FetchAdhocCommands,
 
465
        ExecuteAdhocCommand
 
466
      };
 
467
 
 
468
      struct TrackStruct
 
469
      {
 
470
        JID remote;
 
471
        AdhocContext context;
 
472
        std::string session;
 
473
        AdhocHandler* ah;
 
474
      };
 
475
      typedef std::map<std::string, TrackStruct> AdhocTrackMap;
 
476
      AdhocTrackMap m_adhocTrackMap;
 
477
 
 
478
      ClientBase* m_parent;
 
479
 
 
480
      StringMap m_items;
 
481
      StringMap m_activeSessions;
 
482
 
 
483
  };
 
484
 
 
485
}
 
486
 
 
487
#endif // ADHOC_H__