Line data Source code
1 : /**
2 : * @file
3 : *
4 : * @brief Source for zeromqsend plugin
5 : *
6 : * @copyright BSD License (see LICENSE.md or https://www.libelektra.org)
7 : *
8 : */
9 :
10 : #ifndef HAVE_KDBCONFIG
11 : #include "kdbconfig.h"
12 : #endif
13 :
14 : #include <kdberrors.h>
15 :
16 : #include "zeromqsend.h"
17 :
18 : #include <kdbhelper.h>
19 : #include <kdblogger.h>
20 :
21 : #include <errno.h> // errno
22 : #include <stdlib.h> // strtol()
23 :
24 0 : static long convertUnsignedLong (const char * string, long defaultValue)
25 : {
26 : char * end;
27 0 : errno = 0;
28 0 : long value = strtol (string, &end, 10);
29 0 : if (*end == 0 && errno == 0)
30 : {
31 : return value;
32 : }
33 : else
34 : {
35 0 : return defaultValue;
36 : }
37 : }
38 :
39 20 : int elektraZeroMqSendOpen (Plugin * handle, Key * errorKey ELEKTRA_UNUSED)
40 : {
41 : // read endpoint from configuration
42 20 : Key * endpointKey = ksLookupByName (elektraPluginGetConfig (handle), "/endpoint", 0);
43 20 : const char * endpoint = ELEKTRA_ZEROMQ_DEFAULT_PUB_ENDPOINT;
44 20 : if (endpointKey)
45 : {
46 0 : endpoint = keyString (endpointKey);
47 : }
48 :
49 : // read timeout for connections from plugin configuration
50 20 : Key * connectTimeoutKey = ksLookupByName (elektraPluginGetConfig (handle), "/connectTimeout", 0);
51 20 : long connectTimeout = ELEKTRA_ZEROMQ_DEFAULT_CONNECT_TIMEOUT;
52 20 : if (connectTimeoutKey)
53 : {
54 0 : connectTimeout = convertUnsignedLong (keyString (connectTimeoutKey), ELEKTRA_ZEROMQ_DEFAULT_CONNECT_TIMEOUT);
55 : }
56 :
57 : // read timeout for subscriptions from plugin configuration
58 20 : Key * subscribeTimeoutKey = ksLookupByName (elektraPluginGetConfig (handle), "/subscribeTimeout", 0);
59 20 : long subscribeTimeout = ELEKTRA_ZEROMQ_DEFAULT_SUBSCRIBE_TIMEOUT;
60 20 : if (subscribeTimeoutKey)
61 : {
62 0 : subscribeTimeout = convertUnsignedLong (keyString (subscribeTimeoutKey), ELEKTRA_ZEROMQ_DEFAULT_SUBSCRIBE_TIMEOUT);
63 : }
64 :
65 20 : ElektraZeroMqSendPluginData * data = elektraPluginGetData (handle);
66 20 : if (!data)
67 : {
68 20 : data = elektraMalloc (sizeof (*data));
69 20 : data->zmqContext = NULL;
70 20 : data->zmqPublisher = NULL;
71 20 : data->endpoint = endpoint;
72 20 : data->connectTimeout = connectTimeout;
73 20 : data->subscribeTimeout = subscribeTimeout;
74 20 : data->hasSubscriber = 0;
75 : }
76 20 : elektraPluginSetData (handle, data);
77 :
78 20 : return 1; /* success */
79 : }
80 :
81 20 : int elektraZeroMqSendGet (Plugin * handle ELEKTRA_UNUSED, KeySet * returned, Key * parentKey)
82 : {
83 20 : if (!strcmp (keyName (parentKey), "system/elektra/modules/zeromqsend"))
84 : {
85 20 : KeySet * contract = ksNew (
86 : 30, keyNew ("system/elektra/modules/zeromqsend", KEY_VALUE, "zeromqsend plugin waits for your orders", KEY_END),
87 : keyNew ("system/elektra/modules/zeromqsend/exports", KEY_END),
88 : keyNew ("system/elektra/modules/zeromqsend/exports/open", KEY_FUNC, elektraZeroMqSendOpen, KEY_END),
89 : keyNew ("system/elektra/modules/zeromqsend/exports/get", KEY_FUNC, elektraZeroMqSendGet, KEY_END),
90 : keyNew ("system/elektra/modules/zeromqsend/exports/set", KEY_FUNC, elektraZeroMqSendSet, KEY_END),
91 : keyNew ("system/elektra/modules/zeromqsend/exports/close", KEY_FUNC, elektraZeroMqSendClose, KEY_END),
92 : #include ELEKTRA_README
93 : keyNew ("system/elektra/modules/zeromqsend/infos/version", KEY_VALUE, PLUGINVERSION, KEY_END), KS_END);
94 20 : ksAppend (returned, contract);
95 20 : ksDel (contract);
96 :
97 20 : return 1; /* success */
98 : }
99 :
100 : return 1; /* success */
101 : }
102 :
103 0 : int elektraZeroMqSendSet (Plugin * handle, KeySet * returned ELEKTRA_UNUSED, Key * parentKey ELEKTRA_UNUSED)
104 : {
105 0 : ElektraZeroMqSendPluginData * pluginData = elektraPluginGetData (handle);
106 0 : ELEKTRA_NOT_NULL (pluginData);
107 :
108 0 : int result = elektraZeroMqSendPublish ("Commit", keyName (parentKey), pluginData);
109 0 : switch (result)
110 : {
111 : case 1:
112 : // success!
113 : break;
114 : case -1:
115 : // connection timeout - hub not running
116 0 : ELEKTRA_ADD_INSTALLATION_WARNING (parentKey, "Could not connect to hub. Please start hub using `kdb run-hub-zeromq`");
117 0 : break;
118 : case -2:
119 : // subscription timeout - no applications are listening for notifications, can be ignored
120 : break;
121 : default:
122 0 : ELEKTRA_ADD_PLUGIN_MISBEHAVIOR_WARNING (parentKey, "Could not send notifications");
123 0 : break;
124 : }
125 :
126 0 : return 1; /* success */
127 : }
128 :
129 20 : int elektraZeroMqSendClose (Plugin * handle, Key * parentKey ELEKTRA_UNUSED)
130 : {
131 20 : ElektraZeroMqSendPluginData * pluginData = elektraPluginGetData (handle);
132 20 : if (pluginData == NULL)
133 : {
134 : return 1;
135 : }
136 :
137 20 : if (pluginData->zmqPublisher)
138 : {
139 0 : zmq_close (pluginData->zmqPublisher);
140 0 : pluginData->zmqPublisher = NULL;
141 : }
142 :
143 20 : if (pluginData->zmqContext)
144 : {
145 0 : zmq_ctx_destroy (pluginData->zmqContext);
146 0 : pluginData->zmqContext = NULL;
147 : }
148 :
149 20 : elektraFree (pluginData);
150 20 : elektraPluginSetData (handle, NULL);
151 :
152 20 : return 1; /* success */
153 : }
154 :
155 20 : Plugin * ELEKTRA_PLUGIN_EXPORT
156 : {
157 : // clang-format off
158 20 : return elektraPluginExport("zeromqsend",
159 : ELEKTRA_PLUGIN_OPEN, &elektraZeroMqSendOpen,
160 : ELEKTRA_PLUGIN_GET, &elektraZeroMqSendGet,
161 : ELEKTRA_PLUGIN_SET, &elektraZeroMqSendSet,
162 : ELEKTRA_PLUGIN_CLOSE, &elektraZeroMqSendClose,
163 : ELEKTRA_PLUGIN_END);
164 : }
|