slackblock 0.4.0 → 1.0.0-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.
Files changed (139) hide show
  1. package/CHANGELOG.md +33 -26
  2. package/LICENSE +21 -21
  3. package/README.md +95 -85
  4. package/dist/block.cjs +341 -0
  5. package/dist/block.cjs.map +1 -0
  6. package/dist/block.d.mts +412 -0
  7. package/dist/block.d.ts +412 -0
  8. package/dist/block.mjs +268 -0
  9. package/dist/block.mjs.map +1 -0
  10. package/dist/index.cjs +1202 -0
  11. package/dist/index.cjs.map +1 -0
  12. package/dist/index.d.mts +6 -0
  13. package/dist/index.d.ts +6 -0
  14. package/dist/index.mjs +1170 -0
  15. package/dist/index.mjs.map +1 -0
  16. package/dist/types.d-DgQXbJte.d.mts +296 -0
  17. package/dist/types.d-DgQXbJte.d.ts +296 -0
  18. package/package.json +85 -135
  19. package/blocks.js +0 -12
  20. package/index.js +0 -7
  21. package/lib/components/block/button.js +0 -27
  22. package/lib/components/block/confirmation.js +0 -27
  23. package/lib/components/block/image.js +0 -27
  24. package/lib/components/block/text.js +0 -27
  25. package/lib/components/index.js +0 -42
  26. package/lib/components/input/date-picker.js +0 -27
  27. package/lib/components/input/option-group.js +0 -27
  28. package/lib/components/input/option.js +0 -27
  29. package/lib/components/input/overflow.js +0 -27
  30. package/lib/components/input/radio-group.js +0 -27
  31. package/lib/components/input/select.js +0 -34
  32. package/lib/components/input/text.js +0 -27
  33. package/lib/components/layout/actions.js +0 -27
  34. package/lib/components/layout/container.js +0 -27
  35. package/lib/components/layout/context.js +0 -27
  36. package/lib/components/layout/divider.js +0 -27
  37. package/lib/components/layout/file.js +0 -27
  38. package/lib/components/layout/image.js +0 -27
  39. package/lib/components/layout/input.js +0 -27
  40. package/lib/components/layout/section.js +0 -27
  41. package/lib/components/message.js +0 -27
  42. package/lib/index.js +0 -7
  43. package/lib/parser/index.js +0 -32
  44. package/lib/renderer/index.js +0 -71
  45. package/lib/transformers/block/button.js +0 -29
  46. package/lib/transformers/block/confirmation.js +0 -18
  47. package/lib/transformers/block/image.js +0 -10
  48. package/lib/transformers/block/text.js +0 -16
  49. package/lib/transformers/index.js +0 -54
  50. package/lib/transformers/input/date-picker.js +0 -30
  51. package/lib/transformers/input/option-group.js +0 -19
  52. package/lib/transformers/input/option.js +0 -19
  53. package/lib/transformers/input/overflow.js +0 -19
  54. package/lib/transformers/input/radio-group.js +0 -22
  55. package/lib/transformers/input/select.js +0 -84
  56. package/lib/transformers/input/text.js +0 -31
  57. package/lib/transformers/layout/actions.js +0 -18
  58. package/lib/transformers/layout/container.js +0 -11
  59. package/lib/transformers/layout/context.js +0 -18
  60. package/lib/transformers/layout/divider.js +0 -10
  61. package/lib/transformers/layout/file.js +0 -14
  62. package/lib/transformers/layout/image.js +0 -23
  63. package/lib/transformers/layout/input.js +0 -26
  64. package/lib/transformers/layout/section.js +0 -31
  65. package/lib/utils/get-type.js +0 -16
  66. package/lib/utils/type-helpers.js +0 -2
  67. package/src/components/block/button.tsx +0 -20
  68. package/src/components/block/confirmation.tsx +0 -19
  69. package/src/components/block/image.tsx +0 -8
  70. package/src/components/block/text.tsx +0 -10
  71. package/src/components/index.ts +0 -23
  72. package/src/components/input/date-picker.tsx +0 -11
  73. package/src/components/input/option-group.tsx +0 -9
  74. package/src/components/input/option.tsx +0 -9
  75. package/src/components/input/overflow.tsx +0 -12
  76. package/src/components/input/radio-group.tsx +0 -13
  77. package/src/components/input/select.tsx +0 -36
  78. package/src/components/input/text.tsx +0 -12
  79. package/src/components/layout/actions.tsx +0 -9
  80. package/src/components/layout/container.tsx +0 -9
  81. package/src/components/layout/context.tsx +0 -12
  82. package/src/components/layout/divider.tsx +0 -7
  83. package/src/components/layout/file.tsx +0 -8
  84. package/src/components/layout/image.tsx +0 -10
  85. package/src/components/layout/input.tsx +0 -12
  86. package/src/components/layout/section.tsx +0 -15
  87. package/src/components/message.tsx +0 -20
  88. package/src/constants/types.d.ts +0 -93
  89. package/src/index.ts +0 -3
  90. package/src/parser/index.ts +0 -32
  91. package/src/renderer/index.ts +0 -75
  92. package/src/transformers/block/button.tsx +0 -47
  93. package/src/transformers/block/confirmation.tsx +0 -26
  94. package/src/transformers/block/image.ts +0 -18
  95. package/src/transformers/block/text.ts +0 -34
  96. package/src/transformers/index.ts +0 -65
  97. package/src/transformers/input/date-picker.tsx +0 -43
  98. package/src/transformers/input/option-group.tsx +0 -26
  99. package/src/transformers/input/option.tsx +0 -27
  100. package/src/transformers/input/overflow.ts +0 -33
  101. package/src/transformers/input/radio-group.ts +0 -38
  102. package/src/transformers/input/select.tsx +0 -136
  103. package/src/transformers/input/text.tsx +0 -47
  104. package/src/transformers/layout/actions.ts +0 -29
  105. package/src/transformers/layout/container.ts +0 -16
  106. package/src/transformers/layout/context.ts +0 -35
  107. package/src/transformers/layout/divider.ts +0 -20
  108. package/src/transformers/layout/file.ts +0 -24
  109. package/src/transformers/layout/image.tsx +0 -34
  110. package/src/transformers/layout/input.tsx +0 -39
  111. package/src/transformers/layout/section.ts +0 -53
  112. package/src/tsconfig.json +0 -11
  113. package/src/utils/get-type.ts +0 -20
  114. package/src/utils/type-helpers.ts +0 -1
  115. package/test/index.test.tsx +0 -11
  116. package/test/parser/parser.test.tsx +0 -67
  117. package/test/renderer/renderer.test.tsx +0 -138
  118. package/test/transformers/block/button.test.tsx +0 -63
  119. package/test/transformers/block/confirmation.test.tsx +0 -37
  120. package/test/transformers/block/image.test.tsx +0 -20
  121. package/test/transformers/block/text.test.tsx +0 -32
  122. package/test/transformers/input/date-picker.test.tsx +0 -66
  123. package/test/transformers/input/option-group.test.tsx +0 -26
  124. package/test/transformers/input/option.test.tsx +0 -36
  125. package/test/transformers/input/overflow.test.tsx +0 -57
  126. package/test/transformers/input/radio-group.test.tsx +0 -81
  127. package/test/transformers/input/select.test.tsx +0 -249
  128. package/test/transformers/input/text.test.tsx +0 -42
  129. package/test/transformers/layout/actions.test.tsx +0 -33
  130. package/test/transformers/layout/container.test.tsx +0 -34
  131. package/test/transformers/layout/context.test.tsx +0 -43
  132. package/test/transformers/layout/divider.test.tsx +0 -20
  133. package/test/transformers/layout/file.test.tsx +0 -26
  134. package/test/transformers/layout/image.test.tsx +0 -43
  135. package/test/transformers/layout/input.test.tsx +0 -59
  136. package/test/transformers/layout/section.test.tsx +0 -89
  137. package/test/tsconfig.json +0 -9
  138. package/test/utils/get-type.test.tsx +0 -21
  139. package/tsconfig.json +0 -14
package/dist/index.mjs ADDED
@@ -0,0 +1,1170 @@
1
+ // src/utils/get-type.ts
2
+ var getType = (element) => {
3
+ if (typeof element === "string") {
4
+ return "string";
5
+ }
6
+ if (element === null || element === void 0 || typeof element === "boolean") {
7
+ return "null";
8
+ }
9
+ if (Array.isArray(element)) {
10
+ throw new TypeError("Cannot type arrays");
11
+ }
12
+ const { type } = element;
13
+ if (typeof type === "string") {
14
+ return type;
15
+ }
16
+ const { slackType, displayName, name } = type;
17
+ return slackType || displayName || name || type;
18
+ };
19
+ var get_type_default = getType;
20
+
21
+ // src/utils/validation.ts
22
+ var warn = (message) => {
23
+ console.warn(message);
24
+ };
25
+ var warnIfTooLong = (name, value, max) => {
26
+ if (!value) {
27
+ return;
28
+ }
29
+ if (value.length > max) {
30
+ warn(`${name} exceeds ${max} characters.`);
31
+ }
32
+ };
33
+ var warnIfTooMany = (name, values, max) => {
34
+ if (!values) {
35
+ return;
36
+ }
37
+ if (values.length > max) {
38
+ warn(`${name} exceeds ${max} items.`);
39
+ }
40
+ };
41
+
42
+ // src/transformers/block/text.ts
43
+ var transformText = (element) => {
44
+ const {
45
+ props: {
46
+ plainText,
47
+ children,
48
+ emoji,
49
+ verbatim
50
+ }
51
+ } = element;
52
+ const res = {
53
+ type: plainText ? "plain_text" : "mrkdwn",
54
+ text: children
55
+ };
56
+ if (typeof children === "string") {
57
+ warnIfTooLong("Text", children, 3e3);
58
+ }
59
+ if (emoji) {
60
+ res.emoji = true;
61
+ }
62
+ if (verbatim) {
63
+ res.verbatim = true;
64
+ }
65
+ return res;
66
+ };
67
+ var text_default = transformText;
68
+
69
+ // src/transformers/block/confirmation.tsx
70
+ import React2 from "react";
71
+
72
+ // src/components/block/text.tsx
73
+ import React from "react";
74
+ var Text = class extends React.Component {
75
+ };
76
+ Text.slackType = "Text";
77
+
78
+ // src/transformers/block/confirmation.tsx
79
+ var transformConfirmation = (child) => {
80
+ const { title, confirm, deny, children } = child.props;
81
+ const res = {
82
+ title: transform(/* @__PURE__ */ React2.createElement(Text, { plainText: true }, title)),
83
+ text: transform(children),
84
+ confirm: transform(/* @__PURE__ */ React2.createElement(Text, { plainText: true }, confirm)),
85
+ deny: transform(/* @__PURE__ */ React2.createElement(Text, { plainText: true }, deny))
86
+ };
87
+ return res;
88
+ };
89
+ var confirmation_default = transformConfirmation;
90
+
91
+ // src/transformers/block/button.tsx
92
+ import React3 from "react";
93
+ var transformButton = (child) => {
94
+ const { actionId, children, url, value, style, confirm, accessibilityLabel } = child.props;
95
+ warnIfTooLong("Button action_id", actionId, 255);
96
+ if (typeof children === "string") {
97
+ warnIfTooLong("Button text", children, 75);
98
+ }
99
+ warnIfTooLong("Button value", value, 2e3);
100
+ const res = {
101
+ type: "button",
102
+ text: transform(/* @__PURE__ */ React3.createElement(Text, { plainText: true }, children)),
103
+ action_id: actionId
104
+ };
105
+ if (url) {
106
+ res.url = url;
107
+ }
108
+ if (value) {
109
+ res.value = value;
110
+ }
111
+ if (style) {
112
+ res.style = style;
113
+ }
114
+ if (confirm) {
115
+ res.confirm = transform(confirm);
116
+ }
117
+ if (accessibilityLabel) {
118
+ res.accessibility_label = accessibilityLabel;
119
+ }
120
+ return res;
121
+ };
122
+ var button_default = transformButton;
123
+
124
+ // src/transformers/block/image.ts
125
+ var transformImage = (child) => {
126
+ const { url, alt } = child.props;
127
+ return {
128
+ type: "image",
129
+ image_url: url,
130
+ alt_text: alt
131
+ };
132
+ };
133
+ var image_default = transformImage;
134
+
135
+ // src/transformers/layout/container.ts
136
+ var normalizeChildren = (children) => {
137
+ const result = [];
138
+ const stack = Array.isArray(children) ? [...children] : [children];
139
+ while (stack.length > 0) {
140
+ const child = stack.shift();
141
+ if (child === null || child === void 0 || typeof child === "boolean") {
142
+ continue;
143
+ }
144
+ if (Array.isArray(child)) {
145
+ stack.unshift(...child);
146
+ continue;
147
+ }
148
+ result.push(child);
149
+ }
150
+ return result;
151
+ };
152
+ var transformContainer = (child) => {
153
+ const { children } = child.props;
154
+ const elements = normalizeChildren(children);
155
+ return elements.map((element) => transform(element));
156
+ };
157
+ var container_default = transformContainer;
158
+
159
+ // src/transformers/layout/section.ts
160
+ var transformSection = (element) => {
161
+ const {
162
+ props: {
163
+ text,
164
+ blockId,
165
+ children,
166
+ accessory
167
+ }
168
+ } = element;
169
+ warnIfTooLong("block_id", blockId, 255);
170
+ const res = {
171
+ type: "section",
172
+ text: transform(text)
173
+ };
174
+ if (blockId) {
175
+ res.block_id = blockId;
176
+ }
177
+ if (accessory) {
178
+ res.accessory = transform(accessory);
179
+ }
180
+ if (children) {
181
+ res.fields = [];
182
+ let fields = children;
183
+ if (!Array.isArray(fields)) {
184
+ fields = [fields];
185
+ }
186
+ for (const field of fields) {
187
+ if (field) {
188
+ const t = transform(field);
189
+ res.fields.push(t);
190
+ }
191
+ }
192
+ warnIfTooMany("Section fields", res.fields, 10);
193
+ }
194
+ return res;
195
+ };
196
+ var section_default = transformSection;
197
+
198
+ // src/transformers/layout/actions.ts
199
+ var transformActions = (child) => {
200
+ const { children, blockId } = child.props;
201
+ warnIfTooLong("block_id", blockId, 255);
202
+ let elements = children;
203
+ if (!Array.isArray(elements)) {
204
+ elements = [elements];
205
+ }
206
+ const res = {
207
+ type: "actions",
208
+ elements: elements.map((element) => transform(element))
209
+ };
210
+ if (blockId) {
211
+ res.block_id = blockId;
212
+ }
213
+ warnIfTooMany("Actions elements", res.elements, 25);
214
+ return res;
215
+ };
216
+ var actions_default = transformActions;
217
+
218
+ // src/transformers/layout/context.ts
219
+ var transformContext = (child) => {
220
+ const { children, blockId } = child.props;
221
+ warnIfTooLong("block_id", blockId, 255);
222
+ let elements = children;
223
+ if (!Array.isArray(elements)) {
224
+ elements = [elements];
225
+ }
226
+ const res = {
227
+ type: "context",
228
+ elements: elements.map((element) => transform(element))
229
+ };
230
+ if (blockId) {
231
+ res.block_id = blockId;
232
+ }
233
+ warnIfTooMany("Context elements", res.elements, 10);
234
+ return res;
235
+ };
236
+ var context_default = transformContext;
237
+
238
+ // src/transformers/layout/divider.ts
239
+ var transformDivider = (child) => {
240
+ const { blockId } = child.props;
241
+ warnIfTooLong("block_id", blockId, 255);
242
+ const res = { type: "divider" };
243
+ if (blockId) {
244
+ res.block_id = blockId;
245
+ }
246
+ return res;
247
+ };
248
+ var divider_default = transformDivider;
249
+
250
+ // src/transformers/layout/file.ts
251
+ var transformFile = (child) => {
252
+ const { externalId, blockId } = child.props;
253
+ warnIfTooLong("block_id", blockId, 255);
254
+ const res = {
255
+ type: "file",
256
+ source: "remote",
257
+ external_id: externalId
258
+ };
259
+ if (blockId) {
260
+ res.block_id = blockId;
261
+ }
262
+ return res;
263
+ };
264
+ var file_default = transformFile;
265
+
266
+ // src/transformers/layout/header.tsx
267
+ import React4 from "react";
268
+ var transformHeader = (child) => {
269
+ const { text, blockId, emoji } = child.props;
270
+ warnIfTooLong("block_id", blockId, 255);
271
+ const res = {
272
+ type: "header",
273
+ text: transform(/* @__PURE__ */ React4.createElement(Text, { plainText: true, emoji }, text))
274
+ };
275
+ if (blockId) {
276
+ res.block_id = blockId;
277
+ }
278
+ return res;
279
+ };
280
+ var header_default = transformHeader;
281
+
282
+ // src/transformers/layout/image.tsx
283
+ import React5 from "react";
284
+ var transformImageLayout = (child) => {
285
+ const { url, alt, title, blockId } = child.props;
286
+ warnIfTooLong("block_id", blockId, 255);
287
+ const res = {
288
+ type: "image",
289
+ image_url: url,
290
+ alt_text: alt
291
+ };
292
+ if (title) {
293
+ res.title = transform(/* @__PURE__ */ React5.createElement(Text, { plainText: true }, title));
294
+ }
295
+ if (blockId) {
296
+ res.block_id = blockId;
297
+ }
298
+ return res;
299
+ };
300
+ var image_default2 = transformImageLayout;
301
+
302
+ // src/transformers/layout/input.tsx
303
+ import React6 from "react";
304
+ var transformInput = (child) => {
305
+ const { label, element, hint, optional, blockId } = child.props;
306
+ warnIfTooLong("block_id", blockId, 255);
307
+ const res = {
308
+ type: "input",
309
+ label: transform(/* @__PURE__ */ React6.createElement(Text, { plainText: true }, label)),
310
+ element: transform(element)
311
+ };
312
+ if (hint) {
313
+ res.hint = transform(/* @__PURE__ */ React6.createElement(Text, { plainText: true }, hint));
314
+ }
315
+ if (optional) {
316
+ res.optional = true;
317
+ }
318
+ if (blockId) {
319
+ res.block_id = blockId;
320
+ }
321
+ return res;
322
+ };
323
+ var input_default = transformInput;
324
+
325
+ // src/transformers/rich-text/utils.ts
326
+ var normalizeRichTextChildren = (children) => {
327
+ const result = [];
328
+ const stack = Array.isArray(children) ? [...children] : [children];
329
+ while (stack.length > 0) {
330
+ const child = stack.shift();
331
+ if (child === null || child === void 0 || typeof child === "boolean") {
332
+ continue;
333
+ }
334
+ if (Array.isArray(child)) {
335
+ stack.unshift(...child);
336
+ continue;
337
+ }
338
+ result.push(child);
339
+ }
340
+ return result;
341
+ };
342
+ var toInlineElements = (children) => {
343
+ const items = normalizeRichTextChildren(children);
344
+ return items.map((item) => {
345
+ if (typeof item === "string") {
346
+ return { type: "text", text: item };
347
+ }
348
+ return transform(item);
349
+ });
350
+ };
351
+ var toBlockElements = (children) => {
352
+ const items = normalizeRichTextChildren(children);
353
+ return items.map((item) => {
354
+ if (typeof item === "string") {
355
+ return {
356
+ type: "rich_text_section",
357
+ elements: [{ type: "text", text: item }]
358
+ };
359
+ }
360
+ return transform(item);
361
+ });
362
+ };
363
+
364
+ // src/transformers/layout/rich-text.ts
365
+ var transformRichText = (child) => {
366
+ const { elements, children, blockId } = child.props;
367
+ warnIfTooLong("block_id", blockId, 255);
368
+ const res = {
369
+ type: "rich_text",
370
+ elements: elements != null ? elements : toBlockElements(children)
371
+ };
372
+ if (blockId) {
373
+ res.block_id = blockId;
374
+ }
375
+ return res;
376
+ };
377
+ var rich_text_default = transformRichText;
378
+
379
+ // src/transformers/layout/video.tsx
380
+ import React7 from "react";
381
+ var transformVideo = (child) => {
382
+ const {
383
+ title,
384
+ videoUrl,
385
+ thumbnailUrl,
386
+ altText,
387
+ titleUrl,
388
+ description,
389
+ authorName,
390
+ providerName,
391
+ providerIconUrl,
392
+ blockId
393
+ } = child.props;
394
+ warnIfTooLong("block_id", blockId, 255);
395
+ const res = {
396
+ type: "video",
397
+ title: transform(/* @__PURE__ */ React7.createElement(Text, { plainText: true }, title)),
398
+ video_url: videoUrl,
399
+ thumbnail_url: thumbnailUrl,
400
+ alt_text: altText
401
+ };
402
+ if (titleUrl) {
403
+ res.title_url = titleUrl;
404
+ }
405
+ if (description) {
406
+ res.description = transform(/* @__PURE__ */ React7.createElement(Text, { plainText: true }, description));
407
+ }
408
+ if (authorName) {
409
+ res.author_name = authorName;
410
+ }
411
+ if (providerName) {
412
+ res.provider_name = providerName;
413
+ }
414
+ if (providerIconUrl) {
415
+ res.provider_icon_url = providerIconUrl;
416
+ }
417
+ if (blockId) {
418
+ res.block_id = blockId;
419
+ }
420
+ return res;
421
+ };
422
+ var video_default = transformVideo;
423
+
424
+ // src/transformers/input/text.tsx
425
+ import React8 from "react";
426
+ var transformTextInput = (child) => {
427
+ const {
428
+ actionId,
429
+ placeholder,
430
+ initial,
431
+ multiline,
432
+ minLength,
433
+ maxLength,
434
+ focusOnLoad,
435
+ dispatchActionConfig
436
+ } = child.props;
437
+ warnIfTooLong("TextInput action_id", actionId, 255);
438
+ if (placeholder) {
439
+ warnIfTooLong("TextInput placeholder", placeholder, 150);
440
+ }
441
+ const res = {
442
+ type: "plain_text_input",
443
+ action_id: actionId
444
+ };
445
+ if (placeholder) {
446
+ res.placeholder = transform(/* @__PURE__ */ React8.createElement(Text, { plainText: true }, placeholder));
447
+ }
448
+ if (initial) {
449
+ res.initial_value = initial;
450
+ }
451
+ if (multiline) {
452
+ res.multiline = true;
453
+ }
454
+ if (minLength) {
455
+ res.min_length = minLength;
456
+ }
457
+ if (maxLength) {
458
+ res.max_length = maxLength;
459
+ }
460
+ if (focusOnLoad !== void 0) {
461
+ res.focus_on_load = focusOnLoad;
462
+ }
463
+ if (dispatchActionConfig && dispatchActionConfig.triggerActionsOn.length > 0) {
464
+ res.dispatch_action_config = {
465
+ trigger_actions_on: dispatchActionConfig.triggerActionsOn
466
+ };
467
+ }
468
+ return res;
469
+ };
470
+ var text_default2 = transformTextInput;
471
+
472
+ // src/transformers/input/date-time-picker.ts
473
+ var transformDateTimePicker = (child) => {
474
+ const { actionId, initialDateTime, confirm, focusOnLoad } = child.props;
475
+ warnIfTooLong("DateTimePicker action_id", actionId, 255);
476
+ const res = {
477
+ type: "datetimepicker",
478
+ action_id: actionId
479
+ };
480
+ if (initialDateTime !== void 0) {
481
+ if (!Number.isInteger(initialDateTime)) {
482
+ throw new TypeError("DateTime must be a unix timestamp in seconds.");
483
+ }
484
+ res.initial_date_time = initialDateTime;
485
+ }
486
+ if (confirm) {
487
+ res.confirm = transform(confirm);
488
+ }
489
+ if (focusOnLoad !== void 0) {
490
+ res.focus_on_load = focusOnLoad;
491
+ }
492
+ return res;
493
+ };
494
+ var date_time_picker_default = transformDateTimePicker;
495
+
496
+ // src/transformers/input/date-picker.tsx
497
+ import React9 from "react";
498
+ var isValidDateString = (value) => {
499
+ const match = /^(\d{4})-(\d{2})-(\d{2})$/.exec(value);
500
+ if (!match) {
501
+ return false;
502
+ }
503
+ const year = Number(match[1]);
504
+ const month = Number(match[2]);
505
+ const day = Number(match[3]);
506
+ if (month < 1 || month > 12) {
507
+ return false;
508
+ }
509
+ const date = new Date(Date.UTC(year, month - 1, day));
510
+ return date.getUTCFullYear() === year && date.getUTCMonth() === month - 1 && date.getUTCDate() === day;
511
+ };
512
+ var transformDatePicker = (child) => {
513
+ const { actionId, placeholder, initialDate, confirm, focusOnLoad } = child.props;
514
+ warnIfTooLong("DatePicker action_id", actionId, 255);
515
+ if (placeholder) {
516
+ warnIfTooLong("DatePicker placeholder", placeholder, 150);
517
+ }
518
+ const res = {
519
+ type: "datepicker",
520
+ action_id: actionId
521
+ };
522
+ if (placeholder) {
523
+ res.placeholder = transform(/* @__PURE__ */ React9.createElement(Text, { plainText: true }, placeholder));
524
+ }
525
+ if (initialDate) {
526
+ if (!isValidDateString(initialDate)) {
527
+ throw new Error("Date must be valid and in format YYYY-MM-DD.");
528
+ }
529
+ res.initial_date = initialDate;
530
+ }
531
+ if (confirm) {
532
+ res.confirm = transform(confirm);
533
+ }
534
+ if (focusOnLoad !== void 0) {
535
+ res.focus_on_load = focusOnLoad;
536
+ }
537
+ return res;
538
+ };
539
+ var date_picker_default = transformDatePicker;
540
+
541
+ // src/transformers/input/checkboxes.ts
542
+ var transformCheckboxes = (child) => {
543
+ const { actionId, children, initialOptions, confirm, focusOnLoad } = child.props;
544
+ warnIfTooLong("Checkboxes action_id", actionId, 255);
545
+ let elements = children;
546
+ if (!Array.isArray(elements)) {
547
+ elements = [elements];
548
+ }
549
+ const res = {
550
+ type: "checkboxes",
551
+ action_id: actionId,
552
+ options: elements.map((element) => transform(element))
553
+ };
554
+ if (initialOptions && initialOptions.length > 0) {
555
+ res.initial_options = initialOptions.map((option) => transform(option));
556
+ }
557
+ if (confirm) {
558
+ res.confirm = transform(confirm);
559
+ }
560
+ if (focusOnLoad !== void 0) {
561
+ res.focus_on_load = focusOnLoad;
562
+ }
563
+ return res;
564
+ };
565
+ var checkboxes_default = transformCheckboxes;
566
+
567
+ // src/transformers/input/select.tsx
568
+ import React11 from "react";
569
+
570
+ // src/components/input/select.tsx
571
+ import React10 from "react";
572
+ var selectTypes = {
573
+ STATIC: "static",
574
+ EXTERNAL: "external",
575
+ USER: "user",
576
+ CONVERSATION: "conversation",
577
+ CHANNEL: "channel"
578
+ };
579
+ var Select = class extends React10.Component {
580
+ };
581
+ Select.slackType = "Select";
582
+
583
+ // src/transformers/input/select.tsx
584
+ var OPTION = "Option";
585
+ var OPTION_GROUP = "OptionGroup";
586
+ var types = {
587
+ [selectTypes.STATIC]: "static_select",
588
+ [selectTypes.EXTERNAL]: "external_select",
589
+ [selectTypes.USER]: "users_select",
590
+ [selectTypes.CONVERSATION]: "conversations_select",
591
+ [selectTypes.CHANNEL]: "channels_select"
592
+ };
593
+ var MULTI_PREFIX = "multi_";
594
+ var normalizeElements = (elements) => {
595
+ if (!elements) {
596
+ return [];
597
+ }
598
+ return Array.isArray(elements) ? elements : [elements];
599
+ };
600
+ var assignStaticOptions = (elements, result) => {
601
+ const elementType = get_type_default(elements[0]);
602
+ if (elements.some((element) => get_type_default(element) !== elementType)) {
603
+ if (elementType === OPTION && elements.some((element) => get_type_default(element) !== OPTION_GROUP)) {
604
+ throw new TypeError("You cannot mix OptionGroup types with Option types in a Select block.");
605
+ } else if (elementType === OPTION_GROUP && elements.some((element) => get_type_default(element) !== OPTION)) {
606
+ throw new TypeError("You cannot mix OptionGroup types with Option types in a Select block.");
607
+ }
608
+ throw new TypeError("Only allowed types are Option OR OptionGroup");
609
+ }
610
+ if (elementType === OPTION) {
611
+ const options = elements;
612
+ result.options = options.map((element) => transform(element));
613
+ } else if (elementType === OPTION_GROUP) {
614
+ const optionGroups = elements;
615
+ result.option_groups = optionGroups.map((element) => transform(element));
616
+ }
617
+ };
618
+ var applyInitialSelections = (type, isMulti, result, initialValues) => {
619
+ const { initialOptions, initialUsers, initialConversations, initialChannels } = initialValues;
620
+ switch (type) {
621
+ case selectTypes.USER: {
622
+ if (initialUsers && initialUsers.length > 0) {
623
+ if (isMulti) {
624
+ result.initial_users = initialUsers;
625
+ } else {
626
+ result.initial_user = initialUsers[0];
627
+ }
628
+ }
629
+ break;
630
+ }
631
+ case selectTypes.CONVERSATION: {
632
+ if (initialConversations && initialConversations.length > 0) {
633
+ if (isMulti) {
634
+ result.initial_conversations = initialConversations;
635
+ } else {
636
+ result.initial_conversation = initialConversations[0];
637
+ }
638
+ }
639
+ break;
640
+ }
641
+ case selectTypes.CHANNEL: {
642
+ if (initialChannels && initialChannels.length > 0) {
643
+ if (isMulti) {
644
+ result.initial_channels = initialChannels;
645
+ } else {
646
+ result.initial_channel = initialChannels[0];
647
+ }
648
+ }
649
+ break;
650
+ }
651
+ case selectTypes.STATIC:
652
+ case selectTypes.EXTERNAL: {
653
+ if (initialOptions && initialOptions.length > 0) {
654
+ const transformedOptions = initialOptions.map((element) => transform(element));
655
+ if (isMulti) {
656
+ result.initial_options = transformedOptions;
657
+ } else {
658
+ result.initial_option = transformedOptions[0];
659
+ }
660
+ }
661
+ break;
662
+ }
663
+ }
664
+ };
665
+ var transformSelect = (child) => {
666
+ const {
667
+ placeholder,
668
+ actionId,
669
+ multi,
670
+ children,
671
+ initialOptions,
672
+ confirm,
673
+ maxSelectedItems,
674
+ type: typeProperty,
675
+ initialUsers,
676
+ initialConversations,
677
+ initialChannels,
678
+ minQueryLength,
679
+ focusOnLoad,
680
+ defaultToCurrentConversation,
681
+ responseUrlEnabled,
682
+ filter
683
+ } = child.props;
684
+ const type = typeProperty != null ? typeProperty : selectTypes.STATIC;
685
+ const typeString = `${multi ? MULTI_PREFIX : ""}${types[type]}`;
686
+ warnIfTooLong("Select action_id", actionId, 255);
687
+ warnIfTooLong("Select placeholder", placeholder, 150);
688
+ const result = {
689
+ type: typeString,
690
+ placeholder: transform(/* @__PURE__ */ React11.createElement(Text, { plainText: true }, placeholder)),
691
+ action_id: actionId
692
+ };
693
+ const elements = normalizeElements(children);
694
+ if (type === selectTypes.STATIC) {
695
+ assignStaticOptions(elements, result);
696
+ }
697
+ if (confirm) {
698
+ result.confirm = transform(confirm);
699
+ }
700
+ applyInitialSelections(type, Boolean(multi), result, {
701
+ initialOptions,
702
+ initialUsers,
703
+ initialConversations,
704
+ initialChannels
705
+ });
706
+ if (maxSelectedItems) {
707
+ result.max_selected_items = maxSelectedItems;
708
+ }
709
+ if (focusOnLoad !== void 0) {
710
+ result.focus_on_load = focusOnLoad;
711
+ }
712
+ if (type === selectTypes.EXTERNAL && minQueryLength !== void 0) {
713
+ result.min_query_length = minQueryLength;
714
+ }
715
+ if (type === selectTypes.CONVERSATION) {
716
+ if (defaultToCurrentConversation !== void 0) {
717
+ result.default_to_current_conversation = defaultToCurrentConversation;
718
+ }
719
+ if (responseUrlEnabled !== void 0) {
720
+ result.response_url_enabled = responseUrlEnabled;
721
+ }
722
+ if (filter) {
723
+ const filterValue = {};
724
+ if (filter.include && filter.include.length > 0) {
725
+ filterValue.include = filter.include;
726
+ }
727
+ if (filter.excludeExternalSharedChannels !== void 0) {
728
+ filterValue.exclude_external_shared_channels = filter.excludeExternalSharedChannels;
729
+ }
730
+ if (filter.excludeBotUsers !== void 0) {
731
+ filterValue.exclude_bot_users = filter.excludeBotUsers;
732
+ }
733
+ if (Object.keys(filterValue).length > 0) {
734
+ result.filter = filterValue;
735
+ }
736
+ }
737
+ }
738
+ return result;
739
+ };
740
+ var select_default = transformSelect;
741
+
742
+ // src/transformers/input/option.tsx
743
+ import React12 from "react";
744
+ var transformOption = (child) => {
745
+ const { children: text, value, url, description } = child.props;
746
+ warnIfTooLong("Option text", text, 75);
747
+ warnIfTooLong("Option value", value, 75);
748
+ warnIfTooLong("Option description", description, 75);
749
+ const res = {
750
+ text: transform(/* @__PURE__ */ React12.createElement(Text, { plainText: true }, text)),
751
+ value
752
+ };
753
+ if (description) {
754
+ res.description = transform(/* @__PURE__ */ React12.createElement(Text, { plainText: true }, description));
755
+ }
756
+ if (url) {
757
+ res.url = url;
758
+ }
759
+ return res;
760
+ };
761
+ var option_default = transformOption;
762
+
763
+ // src/transformers/input/option-group.tsx
764
+ import React13 from "react";
765
+ var transformOptionGroup = (child) => {
766
+ const { label, children } = child.props;
767
+ warnIfTooLong("OptionGroup label", label, 75);
768
+ let options = children;
769
+ if (!Array.isArray(options)) {
770
+ options = [options];
771
+ }
772
+ return {
773
+ label: transform(/* @__PURE__ */ React13.createElement(Text, { plainText: true }, label)),
774
+ options: options.map((option) => transform(option))
775
+ };
776
+ };
777
+ var option_group_default = transformOptionGroup;
778
+
779
+ // src/transformers/input/overflow.ts
780
+ var transformOverflow = (child) => {
781
+ const { actionId, children, confirm } = child.props;
782
+ warnIfTooLong("Overflow action_id", actionId, 255);
783
+ let elements = children;
784
+ if (!Array.isArray(elements)) {
785
+ elements = [elements];
786
+ }
787
+ const res = {
788
+ type: "overflow",
789
+ action_id: actionId,
790
+ options: elements.map((element) => transform(element))
791
+ };
792
+ if (confirm) {
793
+ res.confirm = transform(confirm);
794
+ }
795
+ return res;
796
+ };
797
+ var overflow_default = transformOverflow;
798
+
799
+ // src/transformers/input/radio-group.ts
800
+ var transformRadioGroup = (child) => {
801
+ const { actionId, children, initialOption, confirm, focusOnLoad } = child.props;
802
+ warnIfTooLong("RadioGroup action_id", actionId, 255);
803
+ let elements = children;
804
+ if (!Array.isArray(elements)) {
805
+ elements = [elements];
806
+ }
807
+ const res = {
808
+ type: "radio_buttons",
809
+ action_id: actionId,
810
+ options: elements.map((element) => transform(element))
811
+ };
812
+ if (initialOption) {
813
+ res.initial_option = transform(initialOption);
814
+ }
815
+ if (confirm) {
816
+ res.confirm = transform(confirm);
817
+ }
818
+ if (focusOnLoad !== void 0) {
819
+ res.focus_on_load = focusOnLoad;
820
+ }
821
+ return res;
822
+ };
823
+ var radio_group_default = transformRadioGroup;
824
+
825
+ // src/transformers/input/time-picker.tsx
826
+ import React14 from "react";
827
+ var isValidTimeString = (value) => {
828
+ const match = /^(\d{2}):(\d{2})$/.exec(value);
829
+ if (!match) {
830
+ return false;
831
+ }
832
+ const hours = Number(match[1]);
833
+ const minutes = Number(match[2]);
834
+ return hours >= 0 && hours <= 23 && minutes >= 0 && minutes <= 59;
835
+ };
836
+ var transformTimePicker = (child) => {
837
+ const { actionId, placeholder, initialTime, confirm, focusOnLoad } = child.props;
838
+ warnIfTooLong("TimePicker action_id", actionId, 255);
839
+ if (placeholder) {
840
+ warnIfTooLong("TimePicker placeholder", placeholder, 150);
841
+ }
842
+ const res = {
843
+ type: "timepicker",
844
+ action_id: actionId
845
+ };
846
+ if (placeholder) {
847
+ res.placeholder = transform(/* @__PURE__ */ React14.createElement(Text, { plainText: true }, placeholder));
848
+ }
849
+ if (initialTime) {
850
+ if (!isValidTimeString(initialTime)) {
851
+ throw new Error("Time must be valid and in format HH:MM.");
852
+ }
853
+ res.initial_time = initialTime;
854
+ }
855
+ if (confirm) {
856
+ res.confirm = transform(confirm);
857
+ }
858
+ if (focusOnLoad !== void 0) {
859
+ res.focus_on_load = focusOnLoad;
860
+ }
861
+ return res;
862
+ };
863
+ var time_picker_default = transformTimePicker;
864
+
865
+ // src/transformers/rich-text/section.ts
866
+ var transformRichTextSection = (child) => {
867
+ const { children } = child.props;
868
+ return {
869
+ type: "rich_text_section",
870
+ elements: toInlineElements(children)
871
+ };
872
+ };
873
+ var section_default2 = transformRichTextSection;
874
+
875
+ // src/transformers/rich-text/list.ts
876
+ var transformRichTextList = (child) => {
877
+ const { style, children, indent, border } = child.props;
878
+ const res = {
879
+ type: "rich_text_list",
880
+ style,
881
+ elements: toBlockElements(children)
882
+ };
883
+ if (indent !== void 0) {
884
+ res.indent = indent;
885
+ }
886
+ if (border !== void 0) {
887
+ res.border = border;
888
+ }
889
+ return res;
890
+ };
891
+ var list_default = transformRichTextList;
892
+
893
+ // src/transformers/rich-text/quote.ts
894
+ var transformRichTextQuote = (child) => {
895
+ const { children } = child.props;
896
+ return {
897
+ type: "rich_text_quote",
898
+ elements: toInlineElements(children)
899
+ };
900
+ };
901
+ var quote_default = transformRichTextQuote;
902
+
903
+ // src/transformers/rich-text/preformatted.ts
904
+ var transformRichTextPreformatted = (child) => {
905
+ const { children } = child.props;
906
+ return {
907
+ type: "rich_text_preformatted",
908
+ elements: toInlineElements(children)
909
+ };
910
+ };
911
+ var preformatted_default = transformRichTextPreformatted;
912
+
913
+ // src/transformers/rich-text/text.ts
914
+ var transformRichTextText = (child) => {
915
+ const { children, style } = child.props;
916
+ const res = {
917
+ type: "text",
918
+ text: children
919
+ };
920
+ if (style) {
921
+ res.style = style;
922
+ }
923
+ return res;
924
+ };
925
+ var text_default3 = transformRichTextText;
926
+
927
+ // src/transformers/rich-text/link.ts
928
+ var transformRichTextLink = (child) => {
929
+ const { url, children, style } = child.props;
930
+ const res = {
931
+ type: "link",
932
+ url
933
+ };
934
+ if (children) {
935
+ res.text = children;
936
+ }
937
+ if (style) {
938
+ res.style = style;
939
+ }
940
+ return res;
941
+ };
942
+ var link_default = transformRichTextLink;
943
+
944
+ // src/transformers/rich-text/user.ts
945
+ var transformRichTextUser = (child) => {
946
+ const { userId } = child.props;
947
+ return {
948
+ type: "user",
949
+ user_id: userId
950
+ };
951
+ };
952
+ var user_default = transformRichTextUser;
953
+
954
+ // src/transformers/rich-text/channel.ts
955
+ var transformRichTextChannel = (child) => {
956
+ const { channelId } = child.props;
957
+ return {
958
+ type: "channel",
959
+ channel_id: channelId
960
+ };
961
+ };
962
+ var channel_default = transformRichTextChannel;
963
+
964
+ // src/transformers/rich-text/emoji.ts
965
+ var transformRichTextEmoji = (child) => {
966
+ const { name } = child.props;
967
+ return {
968
+ type: "emoji",
969
+ name
970
+ };
971
+ };
972
+ var emoji_default = transformRichTextEmoji;
973
+
974
+ // src/transformers/rich-text/date.ts
975
+ var transformRichTextDate = (child) => {
976
+ const { timestamp, format, fallback, link } = child.props;
977
+ const res = {
978
+ type: "date",
979
+ timestamp,
980
+ format,
981
+ fallback
982
+ };
983
+ if (link) {
984
+ res.link = link;
985
+ }
986
+ return res;
987
+ };
988
+ var date_default = transformRichTextDate;
989
+
990
+ // src/transformers/rich-text/broadcast.ts
991
+ var transformRichTextBroadcast = (child) => {
992
+ const { range } = child.props;
993
+ return {
994
+ type: "broadcast",
995
+ range
996
+ };
997
+ };
998
+ var broadcast_default = transformRichTextBroadcast;
999
+
1000
+ // src/transformers/rich-text/user-group.ts
1001
+ var transformRichTextUserGroup = (child) => {
1002
+ const { usergroupId } = child.props;
1003
+ return {
1004
+ type: "usergroup",
1005
+ usergroup_id: usergroupId
1006
+ };
1007
+ };
1008
+ var user_group_default = transformRichTextUserGroup;
1009
+
1010
+ // src/transformers/index.ts
1011
+ var Transformers = {
1012
+ Container: container_default,
1013
+ Section: section_default,
1014
+ Actions: actions_default,
1015
+ Context: context_default,
1016
+ Divider: divider_default,
1017
+ File: file_default,
1018
+ Header: header_default,
1019
+ ImageLayout: image_default2,
1020
+ Input: input_default,
1021
+ RichText: rich_text_default,
1022
+ Video: video_default,
1023
+ Text: text_default,
1024
+ Confirmation: confirmation_default,
1025
+ Button: button_default,
1026
+ Image: image_default,
1027
+ TextInput: text_default2,
1028
+ DateTimePicker: date_time_picker_default,
1029
+ DatePicker: date_picker_default,
1030
+ Checkboxes: checkboxes_default,
1031
+ Select: select_default,
1032
+ Overflow: overflow_default,
1033
+ RadioGroup: radio_group_default,
1034
+ TimePicker: time_picker_default,
1035
+ Option: option_default,
1036
+ OptionGroup: option_group_default,
1037
+ RichTextSection: section_default2,
1038
+ RichTextList: list_default,
1039
+ RichTextQuote: quote_default,
1040
+ RichTextPreformatted: preformatted_default,
1041
+ RichTextText: text_default3,
1042
+ RichTextLink: link_default,
1043
+ RichTextUser: user_default,
1044
+ RichTextChannel: channel_default,
1045
+ RichTextEmoji: emoji_default,
1046
+ RichTextDate: date_default,
1047
+ RichTextBroadcast: broadcast_default,
1048
+ RichTextUserGroup: user_group_default
1049
+ };
1050
+ var transformers_default = Transformers;
1051
+ var transform = (element) => {
1052
+ const type = get_type_default(element);
1053
+ if (!Transformers[type]) {
1054
+ throw new Error(`No transformer exists for type '${type}'`);
1055
+ }
1056
+ return Transformers[type](element);
1057
+ };
1058
+
1059
+ // src/parser/index.ts
1060
+ var normalizeChildren2 = (children) => {
1061
+ const result = [];
1062
+ const stack = Array.isArray(children) ? [...children] : [children];
1063
+ while (stack.length > 0) {
1064
+ const child = stack.shift();
1065
+ if (child === null || child === void 0 || typeof child === "boolean") {
1066
+ continue;
1067
+ }
1068
+ if (Array.isArray(child)) {
1069
+ stack.unshift(...child);
1070
+ continue;
1071
+ }
1072
+ result.push(child);
1073
+ }
1074
+ return result;
1075
+ };
1076
+ var appendTransformed = (value, blocks) => {
1077
+ if (value === null || value === void 0 || typeof value === "boolean") {
1078
+ return;
1079
+ }
1080
+ if (Array.isArray(value)) {
1081
+ for (const item of value) {
1082
+ appendTransformed(item, blocks);
1083
+ }
1084
+ return;
1085
+ }
1086
+ blocks.push(value);
1087
+ };
1088
+ var parseChildren = (children) => {
1089
+ if (typeof children === "string") {
1090
+ return { text: children };
1091
+ }
1092
+ const normalizedChildren = normalizeChildren2(children);
1093
+ const transformedBlocks = [];
1094
+ for (const child of normalizedChildren) {
1095
+ const type = get_type_default(child);
1096
+ const transformer = transformers_default[type];
1097
+ if (transformer) {
1098
+ appendTransformed(transformer(child), transformedBlocks);
1099
+ } else if (type !== "null") {
1100
+ console.warn(`No transformer for child type '${type}' exists and will be ignored.`);
1101
+ }
1102
+ }
1103
+ if (transformedBlocks.length === 0) {
1104
+ return {};
1105
+ }
1106
+ return { blocks: transformedBlocks };
1107
+ };
1108
+ var parser_default = parseChildren;
1109
+
1110
+ // src/renderer/index.ts
1111
+ var render = (element) => {
1112
+ const { props: properties = {} } = element || {};
1113
+ const typeName = get_type_default(element);
1114
+ if (typeName !== "Message") {
1115
+ throw new TypeError("Provided top-level element must be a Message type.");
1116
+ }
1117
+ if (!properties.children) {
1118
+ throw new Error("Cannot render a Message with no children.");
1119
+ }
1120
+ const json = { ...parser_default(properties.children) };
1121
+ if (properties.replyTo) {
1122
+ json.thread_ts = properties.replyTo;
1123
+ }
1124
+ if (properties.markdown !== void 0) {
1125
+ json.mrkdwn = properties.markdown;
1126
+ }
1127
+ json.text = properties.text || "";
1128
+ if (properties.iconEmoji) {
1129
+ json.icon_emoji = properties.iconEmoji;
1130
+ }
1131
+ if (properties.iconUrl) {
1132
+ json.icon_url = properties.iconUrl;
1133
+ }
1134
+ if (properties.parse) {
1135
+ json.parse = properties.parse;
1136
+ }
1137
+ if (properties.username) {
1138
+ json.username = properties.username;
1139
+ }
1140
+ if (properties.asUser) {
1141
+ json.as_user = properties.asUser;
1142
+ }
1143
+ if (properties.replyBroadcast) {
1144
+ json.reply_broadcast = properties.replyBroadcast;
1145
+ }
1146
+ if (properties.unfurlLinks) {
1147
+ json.unfurl_links = properties.unfurlLinks;
1148
+ }
1149
+ if (properties.unfurlMedia !== void 0) {
1150
+ json.unfurl_media = properties.unfurlMedia;
1151
+ }
1152
+ if (properties.color && json.blocks) {
1153
+ json.attachments = [
1154
+ {
1155
+ color: properties.color,
1156
+ blocks: json.blocks
1157
+ }
1158
+ ];
1159
+ delete json.blocks;
1160
+ }
1161
+ if (json.blocks) {
1162
+ warnIfTooMany("Message blocks", json.blocks, 50);
1163
+ }
1164
+ return json;
1165
+ };
1166
+ var renderer_default = render;
1167
+ export {
1168
+ renderer_default as default
1169
+ };
1170
+ //# sourceMappingURL=index.mjs.map