@pipedream/zendesk 0.3.5 → 0.4.0

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.
package/README.md CHANGED
@@ -1,8 +1,11 @@
1
1
  # Overview
2
2
 
3
- Using the Zendesk API, you can build custom apps and integrations to automate processes and help your teams build better customer relationships.
3
+ Using the Zendesk API, you can build custom apps and integrations to automate
4
+ processes and help your teams build better customer relationships.
4
5
 
5
- The API provides a range of methods to interact with your customer help desk, customer data, and customer communication tools. This enables you to create custom customer experiences that are tailored to your business needs.
6
+ The API provides a range of methods to interact with your customer help desk,
7
+ customer data, and customer communication tools. This enables you to create
8
+ custom customer experiences that are tailored to your business needs.
6
9
 
7
10
  Some examples of what you can build using the Zendesk API include:
8
11
 
@@ -0,0 +1,70 @@
1
+ import app from "../../zendesk.app.mjs";
2
+
3
+ export default {
4
+ key: "zendesk-create-ticket",
5
+ name: "Create Ticket",
6
+ description: "Creates a ticket. [See the docs](https://developer.zendesk.com/api-reference/ticketing/tickets/tickets/#create-ticket).",
7
+ type: "action",
8
+ version: "0.0.1",
9
+ props: {
10
+ app,
11
+ ticketCommentBody: {
12
+ propDefinition: [
13
+ app,
14
+ "ticketCommentBody",
15
+ ],
16
+ },
17
+ ticketPriority: {
18
+ propDefinition: [
19
+ app,
20
+ "ticketPriority",
21
+ ],
22
+ },
23
+ ticketSubject: {
24
+ propDefinition: [
25
+ app,
26
+ "ticketSubject",
27
+ ],
28
+ },
29
+ ticketStatus: {
30
+ propDefinition: [
31
+ app,
32
+ "ticketStatus",
33
+ ],
34
+ },
35
+ },
36
+ methods: {
37
+ createTicket(args = {}) {
38
+ return this.app.create({
39
+ path: "/tickets",
40
+ ...args,
41
+ });
42
+ },
43
+ },
44
+ async run({ $: step }) {
45
+ const {
46
+ ticketCommentBody,
47
+ ticketPriority,
48
+ ticketSubject,
49
+ ticketStatus,
50
+ } = this;
51
+
52
+ const response = await this.createTicket({
53
+ step,
54
+ data: {
55
+ ticket: {
56
+ comment: {
57
+ body: ticketCommentBody,
58
+ },
59
+ priority: ticketPriority,
60
+ subject: ticketSubject,
61
+ status: ticketStatus,
62
+ },
63
+ },
64
+ });
65
+
66
+ step.export("$summary", `Successfully created ticket with ID ${response.ticket.id}`);
67
+
68
+ return response;
69
+ },
70
+ };
@@ -0,0 +1,38 @@
1
+ import app from "../../zendesk.app.mjs";
2
+
3
+ export default {
4
+ key: "zendesk-delete-ticket",
5
+ name: "Delete Ticket",
6
+ description: "Deletes a ticket. [See the docs](https://developer.zendesk.com/api-reference/ticketing/tickets/tickets/#delete-ticket).",
7
+ type: "action",
8
+ version: "0.0.1",
9
+ props: {
10
+ app,
11
+ ticketId: {
12
+ propDefinition: [
13
+ app,
14
+ "ticketId",
15
+ ],
16
+ },
17
+ },
18
+ methods: {
19
+ deleteTicket({
20
+ ticketId, ...args
21
+ } = {}) {
22
+ return this.app.delete({
23
+ path: `/tickets/${ticketId}`,
24
+ ...args,
25
+ });
26
+ },
27
+ },
28
+ async run({ $: step }) {
29
+ await this.deleteTicket({
30
+ step,
31
+ ticketId: this.ticketId,
32
+ });
33
+
34
+ step.export("$summary", "Successfully deleted ticket");
35
+
36
+ return true;
37
+ },
38
+ };
@@ -0,0 +1,80 @@
1
+ import app from "../../zendesk.app.mjs";
2
+
3
+ export default {
4
+ key: "zendesk-update-ticket",
5
+ name: "Update Ticket",
6
+ description: "Updates a ticket. [See the docs](https://developer.zendesk.com/api-reference/ticketing/tickets/tickets/#update-ticket).",
7
+ type: "action",
8
+ version: "0.0.1",
9
+ props: {
10
+ app,
11
+ ticketId: {
12
+ propDefinition: [
13
+ app,
14
+ "ticketId",
15
+ ],
16
+ },
17
+ ticketCommentBody: {
18
+ propDefinition: [
19
+ app,
20
+ "ticketCommentBody",
21
+ ],
22
+ },
23
+ ticketPriority: {
24
+ propDefinition: [
25
+ app,
26
+ "ticketPriority",
27
+ ],
28
+ },
29
+ ticketSubject: {
30
+ propDefinition: [
31
+ app,
32
+ "ticketSubject",
33
+ ],
34
+ },
35
+ ticketStatus: {
36
+ propDefinition: [
37
+ app,
38
+ "ticketStatus",
39
+ ],
40
+ },
41
+ },
42
+ methods: {
43
+ updateTicket({
44
+ ticketId, ...args
45
+ } = {}) {
46
+ return this.app.update({
47
+ path: `/tickets/${ticketId}`,
48
+ ...args,
49
+ });
50
+ },
51
+ },
52
+ async run({ $: step }) {
53
+ const {
54
+ ticketId,
55
+ ticketCommentBody,
56
+ ticketPriority,
57
+ ticketSubject,
58
+ ticketStatus,
59
+ } = this;
60
+
61
+ const response = await this.updateTicket({
62
+ step,
63
+ ticketId,
64
+ data: {
65
+ ticket: {
66
+ comment: {
67
+ body: ticketCommentBody,
68
+ },
69
+ priority: ticketPriority,
70
+ subject: ticketSubject,
71
+ status: ticketStatus,
72
+ },
73
+ },
74
+ });
75
+
76
+ step.export("$summary", `Successfully updated ticket with ID ${response.ticket.id}`);
77
+
78
+ return response;
79
+ },
80
+ };
@@ -6,11 +6,30 @@ const TRIGGER_ID = "triggerId";
6
6
  const PAGE_SIZE_PARAM = "page[size]";
7
7
  const PAGE_AFTER_PARAM = "page[after]";
8
8
  const SORT_BY_POSITION_ASC = "position";
9
+ const SORT_BY_UPDATED_AT_DESC = "-updated_at";
9
10
  const X_ZENDESK_WEBHOOK_SIGNATURE_HEADER = "x-zendesk-webhook-signature";
10
11
  const X_ZENDESK_WEBHOOK_SIGNATURE_TIMESTAMP_HEADER = "x-zendesk-webhook-signature-timestamp";
11
12
  const SIGNING_SECRET = "signingSecret";
12
13
  const SIGNING_SECRET_ALGORITHM = "sha256";
13
14
  const BASE_64 = "base64";
15
+ const DEFAULT_LIMIT = 20;
16
+ const DEFAULT_TIMEOUT = 10000;
17
+
18
+ const TICKET_PRIORITY_OPTIONS = {
19
+ URGENT: "urgent",
20
+ HIGH: "high",
21
+ NORMAL: "normal",
22
+ LOW: "low",
23
+ };
24
+
25
+ const TICKET_STATUS_OPTIONS = {
26
+ NEW: "new",
27
+ OPEN: "open",
28
+ PENDING: "pending",
29
+ HOLD: "hold",
30
+ SOLVED: "solved",
31
+ CLOSED: "closed",
32
+ };
14
33
 
15
34
  export default {
16
35
  SUBDOMAIN_PLACEHOLDER,
@@ -21,9 +40,14 @@ export default {
21
40
  PAGE_SIZE_PARAM,
22
41
  PAGE_AFTER_PARAM,
23
42
  SORT_BY_POSITION_ASC,
43
+ SORT_BY_UPDATED_AT_DESC,
24
44
  X_ZENDESK_WEBHOOK_SIGNATURE_HEADER,
25
45
  X_ZENDESK_WEBHOOK_SIGNATURE_TIMESTAMP_HEADER,
26
46
  SIGNING_SECRET,
27
47
  SIGNING_SECRET_ALGORITHM,
28
48
  BASE_64,
49
+ DEFAULT_LIMIT,
50
+ DEFAULT_TIMEOUT,
51
+ TICKET_PRIORITY_OPTIONS,
52
+ TICKET_STATUS_OPTIONS,
29
53
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pipedream/zendesk",
3
- "version": "0.3.5",
3
+ "version": "0.4.0",
4
4
  "description": "Pipedream Zendesk Components",
5
5
  "main": "zendesk.app.mjs",
6
6
  "keywords": [
@@ -1,4 +1,4 @@
1
- import common from "./base.mjs";
1
+ import common from "./webhook.mjs";
2
2
 
3
3
  export default {
4
4
  ...common,
@@ -1,15 +1,15 @@
1
1
  import crypto from "crypto";
2
- import zendesk from "../../zendesk.app.mjs";
2
+ import app from "../../zendesk.app.mjs";
3
3
  import constants from "../../common/constants.mjs";
4
4
 
5
5
  export default {
6
6
  props: {
7
- zendesk,
7
+ app,
8
8
  db: "$.service.db",
9
9
  http: "$.interface.http",
10
10
  categoryId: {
11
11
  propDefinition: [
12
- zendesk,
12
+ app,
13
13
  "categoryId",
14
14
  ],
15
15
  },
@@ -18,21 +18,21 @@ export default {
18
18
  async activate() {
19
19
  const { categoryId } = this;
20
20
 
21
- const { webhook } = await this.zendesk.createWebhook({
21
+ const { webhook } = await this.createWebhook({
22
22
  data: this.setupWebhookData(),
23
23
  });
24
24
 
25
25
  const { id: webhookId } = webhook;
26
26
  this.setWebhookId(webhookId);
27
27
 
28
- const { signing_secret: signingSecret } = await this.zendesk.showWebhookSigningSecret({
28
+ const { signing_secret: signingSecret } = await this.showWebhookSigningSecret({
29
29
  webhookId,
30
30
  });
31
31
 
32
32
  const { secret } = signingSecret;
33
33
  this.setSigningSecret(secret);
34
34
 
35
- const { trigger } = await this.zendesk.createTrigger({
35
+ const { trigger } = await this.createTrigger({
36
36
  data: this.setupTriggerData({
37
37
  webhookId,
38
38
  categoryId,
@@ -44,16 +44,52 @@ export default {
44
44
  },
45
45
  async deactivate() {
46
46
  await Promise.all([
47
- this.zendesk.deleteTrigger({
47
+ this.deleteTrigger({
48
48
  triggerId: this.getTriggerId(),
49
49
  }),
50
- this.zendesk.deleteWebhook({
50
+ this.deleteWebhook({
51
51
  webhookId: this.getWebhookId(),
52
52
  }),
53
53
  ]);
54
54
  },
55
55
  },
56
56
  methods: {
57
+ createWebhook(args = {}) {
58
+ return this.app.create({
59
+ path: "/webhooks",
60
+ ...args,
61
+ });
62
+ },
63
+ deleteWebhook({
64
+ webhookId, ...args
65
+ } = {}) {
66
+ return this.app.delete({
67
+ path: `/webhooks/${webhookId}`,
68
+ ...args,
69
+ });
70
+ },
71
+ createTrigger(args = {}) {
72
+ return this.app.create({
73
+ path: "/triggers",
74
+ ...args,
75
+ });
76
+ },
77
+ deleteTrigger({
78
+ triggerId, ...args
79
+ } = {}) {
80
+ return this.app.delete({
81
+ path: `/triggers/${triggerId}`,
82
+ ...args,
83
+ });
84
+ },
85
+ showWebhookSigningSecret({
86
+ webhookId, ...args
87
+ } = {}) {
88
+ return this.app.makeRequest({
89
+ path: `/webhooks/${webhookId}/signing_secret`,
90
+ ...args,
91
+ });
92
+ },
57
93
  setWebhookId(webhookId) {
58
94
  this.db.set(constants.WEBHOOK_ID, webhookId);
59
95
  },
@@ -6,7 +6,7 @@ export default {
6
6
  key: "zendesk-new-ticket",
7
7
  type: "source",
8
8
  description: "Emit new event when a ticket is created",
9
- version: "0.0.2",
9
+ version: "0.1.0",
10
10
  dedupe: "unique",
11
11
  methods: {
12
12
  ...common.methods,
@@ -6,7 +6,7 @@ export default {
6
6
  key: "zendesk-ticket-closed",
7
7
  type: "source",
8
8
  description: "Emit new event when a ticket has changed to closed status",
9
- version: "0.0.2",
9
+ version: "0.1.0",
10
10
  dedupe: "unique",
11
11
  methods: {
12
12
  ...common.methods,
@@ -6,7 +6,7 @@ export default {
6
6
  key: "zendesk-ticket-pended",
7
7
  type: "source",
8
8
  description: "Emit new event when a ticket has changed to pending status",
9
- version: "0.0.2",
9
+ version: "0.1.0",
10
10
  dedupe: "unique",
11
11
  methods: {
12
12
  ...common.methods,
@@ -6,7 +6,7 @@ export default {
6
6
  key: "zendesk-ticket-solved",
7
7
  type: "source",
8
8
  description: "Emit new event when a ticket has changed to solved status",
9
- version: "0.0.2",
9
+ version: "0.1.0",
10
10
  dedupe: "unique",
11
11
  methods: {
12
12
  ...common.methods,
@@ -0,0 +1,30 @@
1
+ import common from "../common/ticket.mjs";
2
+
3
+ export default {
4
+ ...common,
5
+ name: "Ticket Updated (Instant)",
6
+ key: "zendesk-ticket-updated",
7
+ type: "source",
8
+ description: "Emit new event when a ticket has been updated",
9
+ version: "0.1.0",
10
+ dedupe: "unique",
11
+ methods: {
12
+ ...common.methods,
13
+ getWebhookName() {
14
+ return "Ticket Updated Webhook";
15
+ },
16
+ getTriggerTitle() {
17
+ return "Ticket Updated Trigger";
18
+ },
19
+ getTriggerConditions() {
20
+ return {
21
+ all: [
22
+ {
23
+ field: "update_type",
24
+ value: "Change",
25
+ },
26
+ ],
27
+ };
28
+ },
29
+ },
30
+ };
package/zendesk.app.mjs CHANGED
@@ -18,7 +18,7 @@ export default {
18
18
  } =
19
19
  await this.listTriggerCategories({
20
20
  params: {
21
- [constants.PAGE_SIZE_PARAM]: 20,
21
+ [constants.PAGE_SIZE_PARAM]: constants.DEFAULT_LIMIT,
22
22
  sort: constants.SORT_BY_POSITION_ASC,
23
23
  [constants.PAGE_AFTER_PARAM]: afterCursor,
24
24
  },
@@ -37,102 +37,119 @@ export default {
37
37
  };
38
38
  },
39
39
  },
40
+ ticketId: {
41
+ type: "string",
42
+ label: "Ticket ID",
43
+ description: "The ID of the ticket.",
44
+ async options({ prevContext }) {
45
+ const { afterCursor } = prevContext;
46
+
47
+ const {
48
+ tickets,
49
+ meta,
50
+ } =
51
+ await this.listTickets({
52
+ params: {
53
+ [constants.PAGE_SIZE_PARAM]: constants.DEFAULT_LIMIT,
54
+ sort: constants.SORT_BY_UPDATED_AT_DESC,
55
+ [constants.PAGE_AFTER_PARAM]: afterCursor,
56
+ },
57
+ });
58
+
59
+ return {
60
+ context: {
61
+ afterCursor: meta.after_cursor,
62
+ },
63
+ options: tickets.map(({
64
+ id, subject,
65
+ }) => ({
66
+ label: subject || `Ticket #${id}`,
67
+ value: id,
68
+ })),
69
+ };
70
+ },
71
+ },
72
+ ticketCommentBody: {
73
+ type: "string",
74
+ label: "Comment body",
75
+ description: "The body of the comment.",
76
+ },
77
+ ticketPriority: {
78
+ type: "string",
79
+ label: "Ticket Priority",
80
+ description: "The priority of the ticket.",
81
+ optional: true,
82
+ options: Object.values(constants.TICKET_PRIORITY_OPTIONS),
83
+ },
84
+ ticketSubject: {
85
+ type: "string",
86
+ label: "Ticket Subject",
87
+ description: "The subject of the ticket.",
88
+ optional: true,
89
+ },
90
+ ticketStatus: {
91
+ type: "string",
92
+ label: "Ticket Status",
93
+ description: "The status of the ticket.",
94
+ optional: true,
95
+ options: Object.values(constants.TICKET_STATUS_OPTIONS),
96
+ },
40
97
  },
41
98
  methods: {
42
- getApiUrl({
43
- path, subdomain,
44
- }) {
99
+ getUrl(path) {
45
100
  const {
46
101
  SUBDOMAIN_PLACEHOLDER,
47
102
  BASE_URL,
48
103
  VERSION_PATH,
49
104
  } = constants;
50
- return `${BASE_URL.replace(SUBDOMAIN_PLACEHOLDER, subdomain)}${VERSION_PATH}${path}`;
105
+ const baseUrl = BASE_URL.replace(SUBDOMAIN_PLACEHOLDER, this.$auth.subdomain);
106
+ return `${baseUrl}${VERSION_PATH}${path}`;
51
107
  },
52
- async makeRequest(customConfig) {
53
- const {
54
- $,
55
- url,
56
- path,
57
- ...configProps
58
- } = customConfig;
59
-
60
- const {
61
- oauth_access_token: oauthAccessToken,
62
- subdomain,
63
- } = this.$auth;
64
-
65
- const headers = {
66
- ...configProps?.headers,
67
- authorization: `Bearer ${oauthAccessToken}`,
108
+ getHeaders(headers) {
109
+ return {
110
+ authorization: `Bearer ${this.$auth.oauth_access_token}`,
111
+ ...headers,
68
112
  };
69
-
113
+ },
114
+ makeRequest({
115
+ step = this, url, path, headers, ...args
116
+ }) {
70
117
  const config = {
71
- ...configProps,
72
- headers,
73
- url: url ?? this.getApiUrl({
74
- subdomain,
75
- path,
76
- }),
77
- timeout: 10000,
118
+ headers: this.getHeaders(headers),
119
+ url: url ?? this.getUrl(path),
120
+ timeout: constants.DEFAULT_TIMEOUT,
121
+ ...args,
78
122
  };
79
-
80
- return axios($ ?? this, config);
123
+ return axios(step, config);
81
124
  },
82
- async createTrigger({
83
- $, data,
84
- }) {
125
+ create(args = {}) {
85
126
  return this.makeRequest({
86
- $,
87
127
  method: "post",
88
- path: "/triggers",
89
- data,
128
+ ...args,
90
129
  });
91
130
  },
92
- async deleteTrigger({
93
- $, triggerId,
94
- }) {
131
+ update(args = {}) {
95
132
  return this.makeRequest({
96
- $,
97
- method: "delete",
98
- path: `/triggers/${triggerId}`,
133
+ method: "put",
134
+ ...args,
99
135
  });
100
136
  },
101
- async listTriggerCategories({
102
- $, url, params,
103
- }) {
104
- return this.makeRequest({
105
- $,
106
- url,
107
- path: "/trigger_categories",
108
- params,
109
- });
110
- },
111
- async createWebhook({
112
- $, data,
113
- }) {
137
+ delete(args = {}) {
114
138
  return this.makeRequest({
115
- $,
116
- method: "post",
117
- path: "/webhooks",
118
- data,
139
+ method: "delete",
140
+ ...args,
119
141
  });
120
142
  },
121
- async deleteWebhook({
122
- $, webhookId,
123
- }) {
143
+ listTriggerCategories(args = {}) {
124
144
  return this.makeRequest({
125
- $,
126
- method: "delete",
127
- path: `/webhooks/${webhookId}`,
145
+ path: "/trigger_categories",
146
+ ...args,
128
147
  });
129
148
  },
130
- async showWebhookSigningSecret({
131
- $, webhookId,
132
- }) {
149
+ listTickets(args = {}) {
133
150
  return this.makeRequest({
134
- $,
135
- path: `/webhooks/${webhookId}/signing_secret`,
151
+ path: "/tickets",
152
+ ...args,
136
153
  });
137
154
  },
138
155
  },