n8n-nodes-qlik-cloud 1.0.0 → 1.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,7 @@
1
+ import type { ICredentialType, INodeProperties } from 'n8n-workflow';
2
+ export declare class QlikCloudApi implements ICredentialType {
3
+ name: string;
4
+ displayName: string;
5
+ documentationUrl: string;
6
+ properties: INodeProperties[];
7
+ }
@@ -0,0 +1,33 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.QlikCloudApi = void 0;
4
+ class QlikCloudApi {
5
+ constructor() {
6
+ this.name = 'qlikCloudApi';
7
+ this.displayName = 'Qlik Cloud API';
8
+ this.documentationUrl = 'https://qlik.dev/apis/rest/';
9
+ this.properties = [
10
+ {
11
+ displayName: 'Tenant URL',
12
+ name: 'baseUrl',
13
+ type: 'string',
14
+ default: '',
15
+ required: true,
16
+ placeholder: 'https://{tenant}.{region}.qlikcloud.com',
17
+ description: 'The base URL of your Qlik Cloud tenant',
18
+ },
19
+ {
20
+ displayName: 'API Key (Access Token)',
21
+ name: 'accessToken',
22
+ type: 'string',
23
+ typeOptions: {
24
+ password: true,
25
+ },
26
+ default: '',
27
+ required: true,
28
+ description: 'Bearer token for API authentication. Generate from Qlik Cloud console',
29
+ },
30
+ ];
31
+ }
32
+ }
33
+ exports.QlikCloudApi = QlikCloudApi;
@@ -0,0 +1,9 @@
1
+ import type { ICredentialType, INodeProperties } from 'n8n-workflow';
2
+ export declare class QlikCloudOAuth2Api implements ICredentialType {
3
+ name: string;
4
+ displayName: string;
5
+ documentationUrl: string;
6
+ extends: string[];
7
+ properties: INodeProperties[];
8
+ preAuthentication(this: any, credentials: any): Promise<any>;
9
+ }
@@ -0,0 +1,72 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.QlikCloudOAuth2Api = void 0;
4
+ const scopes = [
5
+ 'https://analysis.windows.net/powerbi/api/.default',
6
+ ];
7
+ class QlikCloudOAuth2Api {
8
+ constructor() {
9
+ this.name = 'qlikCloudOAuth2Api';
10
+ this.displayName = 'Qlik Cloud OAuth2 API';
11
+ this.documentationUrl = 'https://qlik.dev/authenticate/';
12
+ this.extends = ['oAuth2Api'];
13
+ this.properties = [
14
+ {
15
+ displayName: 'Tenant URL',
16
+ name: 'baseUrl',
17
+ type: 'string',
18
+ default: '',
19
+ required: true,
20
+ placeholder: 'https://{tenant}.{region}.qlikcloud.com',
21
+ description: 'The base URL of your Qlik Cloud tenant',
22
+ },
23
+ {
24
+ displayName: 'Authorization URL',
25
+ name: 'authUrl',
26
+ type: 'hidden',
27
+ default: '',
28
+ required: true,
29
+ },
30
+ {
31
+ displayName: 'Access Token URL',
32
+ name: 'accessTokenUrl',
33
+ type: 'hidden',
34
+ default: '',
35
+ required: true,
36
+ },
37
+ {
38
+ displayName: 'Scope',
39
+ name: 'scope',
40
+ type: 'hidden',
41
+ default: scopes.join(' '),
42
+ description: 'OAuth2 scopes required for Qlik Cloud API access',
43
+ },
44
+ {
45
+ displayName: 'Authentication',
46
+ name: 'authentication',
47
+ type: 'hidden',
48
+ default: 'body',
49
+ },
50
+ ];
51
+ }
52
+ async preAuthentication(credentials) {
53
+ const baseUrl = credentials.baseUrl;
54
+ // Extract tenant and region from base URL
55
+ // Expected format: https://tenant.region.qlikcloud.com
56
+ const urlParts = new URL(baseUrl);
57
+ const hostname = urlParts.hostname;
58
+ const parts = hostname.split('.');
59
+ if (parts.length < 3) {
60
+ throw new Error('Invalid Qlik Cloud tenant URL format');
61
+ }
62
+ const tenant = parts[0];
63
+ const region = parts[1];
64
+ // Construct OAuth endpoints
65
+ const authEndpoint = `https://auth.${region}.qlikcloud.com/oauth/authorize`;
66
+ const tokenEndpoint = `https://auth.${region}.qlikcloud.com/oauth/token`;
67
+ credentials.authUrl = authEndpoint;
68
+ credentials.accessTokenUrl = tokenEndpoint;
69
+ return credentials;
70
+ }
71
+ }
72
+ exports.QlikCloudOAuth2Api = QlikCloudOAuth2Api;
@@ -0,0 +1 @@
1
+ export { QlikCloud } from './nodes/QlikCloud/QlikCloud.node';
package/dist/index.js ADDED
@@ -0,0 +1,5 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.QlikCloud = void 0;
4
+ var QlikCloud_node_1 = require("./nodes/QlikCloud/QlikCloud.node");
5
+ Object.defineProperty(exports, "QlikCloud", { enumerable: true, get: function () { return QlikCloud_node_1.QlikCloud; } });
@@ -0,0 +1,5 @@
1
+ import type { IExecuteFunctions, INodeExecutionData, INodeType, INodeTypeDescription } from 'n8n-workflow';
2
+ export declare class QlikCloud implements INodeType {
3
+ description: INodeTypeDescription;
4
+ execute(this: IExecuteFunctions): Promise<INodeExecutionData[][]>;
5
+ }
@@ -0,0 +1,346 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.QlikCloud = void 0;
4
+ const n8n_workflow_1 = require("n8n-workflow");
5
+ const transport_1 = require("./shared/transport");
6
+ const index_1 = require("./resources/apps/index");
7
+ const index_2 = require("./resources/assistants/index");
8
+ const index_3 = require("./resources/audits/index");
9
+ const index_4 = require("./resources/items/index");
10
+ async function handleAppsResource(operation, context) {
11
+ if (operation === 'getAll') {
12
+ const returnAll = context.getNodeParameter('returnAll', 0);
13
+ const limit = returnAll ? undefined : context.getNodeParameter('limit', 0);
14
+ const options = context.getNodeParameter('options', 0);
15
+ const qs = {};
16
+ if (limit) {
17
+ qs.limit = limit;
18
+ }
19
+ if (options.name) {
20
+ qs.name = options.name;
21
+ }
22
+ if (options.spaceId) {
23
+ qs.spaceId = options.spaceId;
24
+ }
25
+ const response = await transport_1.qlikApiRequest.call(context, 'GET', '/api/v1/apps', undefined, qs);
26
+ return response.data || response;
27
+ }
28
+ if (operation === 'get') {
29
+ const appId = context.getNodeParameter('appId', 0);
30
+ return await transport_1.qlikApiRequest.call(context, 'GET', `/api/v1/apps/${appId}`);
31
+ }
32
+ if (operation === 'create') {
33
+ const name = context.getNodeParameter('name', 0);
34
+ const options = context.getNodeParameter('options', 0);
35
+ const body = { attributes: { name } };
36
+ if (options.description) {
37
+ body.attributes.description = options.description;
38
+ }
39
+ if (options.locale) {
40
+ body.attributes.locale = options.locale;
41
+ }
42
+ if (options.spaceId) {
43
+ body.attributes.spaceId = options.spaceId;
44
+ }
45
+ return await transport_1.qlikApiRequest.call(context, 'POST', '/api/v1/apps', body);
46
+ }
47
+ if (operation === 'update') {
48
+ const appId = context.getNodeParameter('appId', 0);
49
+ const body = context.getNodeParameter('body', 0);
50
+ return await transport_1.qlikApiRequest.call(context, 'PUT', `/api/v1/apps/${appId}`, body);
51
+ }
52
+ if (operation === 'delete') {
53
+ const appId = context.getNodeParameter('appId', 0);
54
+ await transport_1.qlikApiRequest.call(context, 'DELETE', `/api/v1/apps/${appId}`);
55
+ return { success: true };
56
+ }
57
+ if (operation === 'copy') {
58
+ const appId = context.getNodeParameter('appId', 0);
59
+ const name = context.getNodeParameter('name', 0);
60
+ const options = context.getNodeParameter('options', 0);
61
+ const body = { attributes: { name } };
62
+ if (options.description) {
63
+ body.attributes.description = options.description;
64
+ }
65
+ if (options.spaceId) {
66
+ body.attributes.spaceId = options.spaceId;
67
+ }
68
+ return await transport_1.qlikApiRequest.call(context, 'POST', `/api/v1/apps/${appId}/copy`, body);
69
+ }
70
+ if (operation === 'export') {
71
+ const appId = context.getNodeParameter('appId', 0);
72
+ return await transport_1.qlikApiRequest.call(context, 'POST', `/api/v1/apps/${appId}/export`, {});
73
+ }
74
+ if (operation === 'publish') {
75
+ const appId = context.getNodeParameter('appId', 0);
76
+ const options = context.getNodeParameter('publishOptions', 0);
77
+ const body = {};
78
+ if (options.spaceId) {
79
+ body.spaceId = options.spaceId;
80
+ }
81
+ return await transport_1.qlikApiRequest.call(context, 'POST', `/api/v1/apps/${appId}/publish`, body);
82
+ }
83
+ if (operation === 'privileges') {
84
+ return await transport_1.qlikApiRequest.call(context, 'GET', '/api/v1/apps/privileges');
85
+ }
86
+ throw new n8n_workflow_1.NodeOperationError(context.getNode(), `Unknown operation: ${operation}`);
87
+ }
88
+ async function handleAssistantsResource(operation, context) {
89
+ if (operation === 'getAll') {
90
+ const options = context.getNodeParameter('options', 0);
91
+ const qs = {};
92
+ if (options.limit) {
93
+ qs.limit = options.limit;
94
+ }
95
+ return await transport_1.qlikApiRequest.call(context, 'GET', '/api/v1/assistants', undefined, qs);
96
+ }
97
+ if (operation === 'get') {
98
+ const assistantId = context.getNodeParameter('assistantId', 0);
99
+ return await transport_1.qlikApiRequest.call(context, 'GET', `/api/v1/assistants/${assistantId}`);
100
+ }
101
+ if (operation === 'create') {
102
+ const name = context.getNodeParameter('name', 0);
103
+ const options = context.getNodeParameter('options', 0);
104
+ const body = { name };
105
+ if (options.description) {
106
+ body.description = options.description;
107
+ }
108
+ return await transport_1.qlikApiRequest.call(context, 'POST', '/api/v1/assistants', body);
109
+ }
110
+ if (operation === 'search') {
111
+ const assistantId = context.getNodeParameter('assistantId', 0);
112
+ const query = context.getNodeParameter('query', 0);
113
+ const options = context.getNodeParameter('options', 0);
114
+ const body = { text: query };
115
+ if (options.topN) {
116
+ body.topN = options.topN;
117
+ }
118
+ if (options.mode) {
119
+ body.mode = options.mode;
120
+ }
121
+ return await transport_1.qlikApiRequest.call(context, 'POST', `/api/v1/assistants/${assistantId}/actions/search`, body);
122
+ }
123
+ if (operation === 'delete') {
124
+ const assistantId = context.getNodeParameter('assistantId', 0);
125
+ await transport_1.qlikApiRequest.call(context, 'DELETE', `/api/v1/assistants/${assistantId}`);
126
+ return { success: true };
127
+ }
128
+ throw new n8n_workflow_1.NodeOperationError(context.getNode(), `Unknown operation: ${operation}`);
129
+ }
130
+ async function handleAuditsResource(operation, context) {
131
+ if (operation === 'getAll') {
132
+ const returnAll = context.getNodeParameter('returnAll', 0);
133
+ const limit = returnAll ? undefined : context.getNodeParameter('limit', 0);
134
+ const options = context.getNodeParameter('options', 0);
135
+ const qs = {};
136
+ if (limit) {
137
+ qs.limit = limit;
138
+ }
139
+ if (options.eventType) {
140
+ qs.eventType = options.eventType;
141
+ }
142
+ if (options.userId) {
143
+ qs.userId = options.userId;
144
+ }
145
+ if (options.source) {
146
+ qs.source = options.source;
147
+ }
148
+ if (options.eventTime) {
149
+ qs.eventTime = options.eventTime;
150
+ }
151
+ if (options.sort) {
152
+ qs.sort = options.sort;
153
+ }
154
+ const response = await transport_1.qlikApiRequest.call(context, 'GET', '/api/v1/audits', undefined, qs);
155
+ return response.data || response;
156
+ }
157
+ if (operation === 'get') {
158
+ const auditId = context.getNodeParameter('auditId', 0);
159
+ return await transport_1.qlikApiRequest.call(context, 'GET', `/api/v1/audits/${auditId}`);
160
+ }
161
+ if (operation === 'getSources') {
162
+ const response = await transport_1.qlikApiRequest.call(context, 'GET', '/api/v1/audits/sources');
163
+ return response.data || response;
164
+ }
165
+ if (operation === 'getTypes') {
166
+ const response = await transport_1.qlikApiRequest.call(context, 'GET', '/api/v1/audits/types');
167
+ return response.data || response;
168
+ }
169
+ if (operation === 'getSettings') {
170
+ const response = await transport_1.qlikApiRequest.call(context, 'GET', '/api/v1/audits/settings');
171
+ return response.data || response;
172
+ }
173
+ throw new n8n_workflow_1.NodeOperationError(context.getNode(), `Unknown operation: ${operation}`);
174
+ }
175
+ async function handleItemsResource(operation, context) {
176
+ if (operation === 'getAll') {
177
+ const returnAll = context.getNodeParameter('returnAll', 0);
178
+ const limit = returnAll ? undefined : context.getNodeParameter('limit', 0);
179
+ const options = context.getNodeParameter('options', 0);
180
+ const qs = {};
181
+ if (limit) {
182
+ qs.limit = limit;
183
+ }
184
+ if (options.name) {
185
+ qs.name = options.name;
186
+ }
187
+ if (options.resourceType) {
188
+ qs.resourceType = options.resourceType;
189
+ }
190
+ if (options.spaceId) {
191
+ qs.spaceId = options.spaceId;
192
+ }
193
+ if (options.ownerId) {
194
+ qs.ownerId = options.ownerId;
195
+ }
196
+ if (options.sort) {
197
+ qs.sort = options.sort;
198
+ }
199
+ const response = await transport_1.qlikApiRequest.call(context, 'GET', '/api/v1/items', undefined, qs);
200
+ return response.data || response;
201
+ }
202
+ if (operation === 'get') {
203
+ const itemId = context.getNodeParameter('itemId', 0);
204
+ return await transport_1.qlikApiRequest.call(context, 'GET', `/api/v1/items/${itemId}`);
205
+ }
206
+ if (operation === 'update') {
207
+ const itemId = context.getNodeParameter('itemId', 0);
208
+ const body = context.getNodeParameter('body', 0);
209
+ return await transport_1.qlikApiRequest.call(context, 'PUT', `/api/v1/items/${itemId}`, body);
210
+ }
211
+ if (operation === 'delete') {
212
+ const itemId = context.getNodeParameter('itemId', 0);
213
+ await transport_1.qlikApiRequest.call(context, 'DELETE', `/api/v1/items/${itemId}`);
214
+ return { success: true };
215
+ }
216
+ if (operation === 'collections') {
217
+ const itemId = context.getNodeParameter('itemId', 0);
218
+ const options = context.getNodeParameter('options', 0);
219
+ const qs = {};
220
+ if (options.limit) {
221
+ qs.limit = options.limit;
222
+ }
223
+ const response = await transport_1.qlikApiRequest.call(context, 'GET', `/api/v1/items/${itemId}/collections`, undefined, qs);
224
+ return response.data || response;
225
+ }
226
+ if (operation === 'publishedItems') {
227
+ const itemId = context.getNodeParameter('itemId', 0);
228
+ const options = context.getNodeParameter('options', 0);
229
+ const qs = {};
230
+ if (options.limit) {
231
+ qs.limit = options.limit;
232
+ }
233
+ const response = await transport_1.qlikApiRequest.call(context, 'GET', `/api/v1/items/${itemId}/publisheditems`, undefined, qs);
234
+ return response.data || response;
235
+ }
236
+ if (operation === 'settings') {
237
+ const settingsOperation = context.getNodeParameter('settingsOperation', 0);
238
+ if (settingsOperation === 'get') {
239
+ const response = await transport_1.qlikApiRequest.call(context, 'GET', '/api/v1/items/settings');
240
+ return response.data || response;
241
+ }
242
+ if (settingsOperation === 'patch') {
243
+ const body = context.getNodeParameter('body', 0);
244
+ const response = await transport_1.qlikApiRequest.call(context, 'PATCH', '/api/v1/items/settings', body);
245
+ return response.data || response;
246
+ }
247
+ }
248
+ throw new n8n_workflow_1.NodeOperationError(context.getNode(), `Unknown operation: ${operation}`);
249
+ }
250
+ class QlikCloud {
251
+ constructor() {
252
+ this.description = {
253
+ displayName: 'Qlik Cloud',
254
+ name: 'qlikCloud',
255
+ icon: 'file:qlik.svg',
256
+ group: ['transform'],
257
+ version: 1,
258
+ subtitle: '={{$parameter["resource"] + ": " + $parameter["operation"]}}',
259
+ description: 'Interact with Qlik Cloud APIs (Apps, Items, Audits, Assistants)',
260
+ defaults: {
261
+ name: 'Qlik Cloud',
262
+ },
263
+ inputs: ['main'],
264
+ outputs: ['main'],
265
+ credentials: [
266
+ {
267
+ name: 'qlikCloudApi',
268
+ required: true,
269
+ },
270
+ ],
271
+ properties: [
272
+ {
273
+ displayName: 'Resource',
274
+ name: 'resource',
275
+ type: 'options',
276
+ noDataExpression: true,
277
+ options: [
278
+ {
279
+ name: 'Apps',
280
+ value: 'apps',
281
+ description: 'Manage Qlik Cloud applications',
282
+ },
283
+ {
284
+ name: 'Assistants',
285
+ value: 'assistants',
286
+ description: 'Interact with AI assistants',
287
+ },
288
+ {
289
+ name: 'Audits',
290
+ value: 'audits',
291
+ description: 'Access audit logs and events',
292
+ },
293
+ {
294
+ name: 'Items',
295
+ value: 'items',
296
+ description: 'Manage items in Qlik Cloud',
297
+ },
298
+ ],
299
+ default: 'apps',
300
+ },
301
+ ...index_1.appDescription,
302
+ ...index_2.assistantDescription,
303
+ ...index_3.auditDescription,
304
+ ...index_4.itemDescription,
305
+ ],
306
+ };
307
+ }
308
+ async execute() {
309
+ const items = this.getInputData();
310
+ let responseData;
311
+ const returnData = [];
312
+ const resource = this.getNodeParameter('resource', 0);
313
+ const operation = this.getNodeParameter('operation', 0);
314
+ for (let i = 0; i < items.length; i++) {
315
+ try {
316
+ if (resource === 'apps') {
317
+ responseData = await handleAppsResource(operation, this);
318
+ }
319
+ else if (resource === 'assistants') {
320
+ responseData = await handleAssistantsResource(operation, this);
321
+ }
322
+ else if (resource === 'audits') {
323
+ responseData = await handleAuditsResource(operation, this);
324
+ }
325
+ else if (resource === 'items') {
326
+ responseData = await handleItemsResource(operation, this);
327
+ }
328
+ const executionData = this.helpers.constructExecutionMetaData(this.helpers.returnJsonArray(Array.isArray(responseData) ? responseData : [responseData]), { itemData: { item: i } });
329
+ returnData.push(...executionData);
330
+ }
331
+ catch (error) {
332
+ if (this.continueOnFail()) {
333
+ returnData.push({
334
+ json: { error: error.message },
335
+ pairedItem: i,
336
+ });
337
+ }
338
+ else {
339
+ throw error;
340
+ }
341
+ }
342
+ }
343
+ return [returnData];
344
+ }
345
+ }
346
+ exports.QlikCloud = QlikCloud;
@@ -0,0 +1,11 @@
1
+ import type { INodeProperties } from 'n8n-workflow';
2
+ export declare const appsGetAllDescription: INodeProperties[];
3
+ export declare const appsGetDescription: INodeProperties[];
4
+ export declare const appsCreateDescription: INodeProperties[];
5
+ export declare const appsUpdateDescription: INodeProperties[];
6
+ export declare const appsDeleteDescription: INodeProperties[];
7
+ export declare const appsCopyDescription: INodeProperties[];
8
+ export declare const appsExportDescription: INodeProperties[];
9
+ export declare const appsPublishDescription: INodeProperties[];
10
+ export declare const appsPrivilegesDescription: INodeProperties[];
11
+ export declare const appDescription: INodeProperties[];