UNPKG

speedybot

Version:

<p align="center"> <a href="https://github.com/valgaze/speedybot"> <img src="https://img.shields.io/npm/v/speedybot.svg" /> </a> <a href="https://github.com/valgaze/speedybot"> <img src="https://img.shields.io/npm/dm/speedybot.svg" /> </a>

465 lines 16.5 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.SpeedyCard = exports.SpeedyCardId = exports.checkers = void 0; const index_1 = require("./index"); exports.checkers = { isSpeedyCard(input) { return (typeof input === "object" && "build" in input && typeof input.build === "function"); }, isCard(cardCandidate) { if (this.isSpeedyCard(cardCandidate)) { return true; } return ("$schema" in cardCandidate && "type" in cardCandidate && "version" in cardCandidate); }, isEmail(candidate) { const res = candidate.includes("@") && candidate.includes("."); return res; }, }; exports.SpeedyCardId = { dropdown: "addPickerDropdown_result", }; class SpeedyCard { constructor() { this.json = { $schema: "http://adaptivecards.io/schemas/adaptive-card.json", type: "AdaptiveCard", version: "1.0", body: [], }; this.tools = { checkColor(candidate) { const colorMapping = { default: "Default", dark: "Dark", light: "Light", accent: "Accent", good: "Good", warning: "Warning", attention: "Attention", blue: "Accent", red: "Attention", green: "Good", yellow: "Warning", }; const lowerCaseInput = candidate.toLowerCase(); return colorMapping[lowerCaseInput] || "Default"; }, }; this._stash = { needsSubmit: false, title: "", subTitle: "", chips: [], data: {}, submitLabel: "Submit", }; this.id = {}; } needsSubmit() { return Boolean(this._stash.needsSubmit); } checkId(id = "") { if (id in this.id) { this.id[id]++; const num = this.id[id]; const modifiedId = `${id}_${num}`; return modifiedId; } else { this.id[id] = 1; return id; } } addTitle(title) { this._stash.title = title; return this; } addSubtitle(subTitle) { this._stash.subTitle = subTitle; return this; } addTable(input, separator = false) { const payload = { type: "FactSet", separator, facts: Array.isArray(input) ? input.map(([label, value]) => ({ title: label, value })) : Object.entries(input).map(([label, value]) => ({ title: label, value, })), }; this.json.body.push(payload); return this; } addChip(payload, id = index_1.CONSTANTS.CHIP_LABEL) { return this.addChips([payload], id); } addChips(chips, id = index_1.CONSTANTS.CHIP_LABEL) { const chipPayload = chips.map((chip) => { let chipLabel = ""; let chipAction = ""; if (typeof chip === "string") { chipLabel = chip; chipAction = chip; } else { const { title, value = "" } = chip; chipLabel = title; if (value) { chipAction = value; } else { chipAction = title; } } const payload = { type: "Action.Submit", title: chipLabel, data: { [id]: chipAction, }, }; return payload; }); this.json.actions = this.json.actions ? this.json.actions.concat(chipPayload) : chipPayload; return this; } addImage(url, config = {}) { var _a, _b; if (url) { const payload = { horizontalAlignment: (_a = config.align) !== null && _a !== void 0 ? _a : "Center", size: (_b = config.size) !== null && _b !== void 0 ? _b : "ExtraLarge", type: "Image", url, }; if (config.targetURL) { const linkPayload = { type: "Action.OpenUrl", style: "positive", isPrimary: true, url: config.targetURL, }; payload.selectAction = linkPayload; } this.json.body.push(payload); } return this; } addLink(url, label) { return this.addText(`**[${label || url}](${url})**`); } addLinkButton(url, label) { const id = String(Math.random()).slice(3); const cleanId = this.checkId(id); const payload = { type: "Action.OpenUrl", id: cleanId, title: label !== null && label !== void 0 ? label : url, url: url, }; this.addAction(payload); return this; } addText(text, config = {}) { const { bold = false, size = "Medium", align = "Left", color, backgroundColor, vertAlign, } = config; const payload = Object.assign(Object.assign({ type: "TextBlock", text: text, wrap: true, size, horizontalAlignment: align }, (color && { color: this.tools.checkColor(color) })), (bold && { weight: "Bolder" })); if (backgroundColor || vertAlign) { const containerPayload = Object.assign(Object.assign(Object.assign({ type: "Container", height: "stretch", items: [payload] }, (backgroundColor && { style: this.tools.checkColor(backgroundColor), })), (color && { color: this.tools.checkColor(color) })), (vertAlign && { verticalContentAlignment: vertAlign, })); this.json.body.push(containerPayload); } else { this.json.body.push(payload); } return this; } addHeader(text, config = {}) { var _a, _b, _c, _d; const hasURL = (_a = config.iconURL) === null || _a === void 0 ? void 0 : _a.includes("http"); const textPayload = { items: [ Object.assign(Object.assign(Object.assign({ type: "TextBlock", text: text, wrap: true, size: config.textSize || "Large", horizontalAlignment: ((_b = config.textAlign) !== null && _b !== void 0 ? _b : config.rtl) ? "Right" : "Left" }, (config.textColor && { color: this.tools.checkColor(config.textColor), })), { verticalContentAlignment: "Center" }), (config.backgroundColor && { style: this.tools.checkColor(config.backgroundColor), })), ], }; const iconPayload = config.iconURL ? hasURL ? { width: "32px", items: [ Object.assign(Object.assign({ type: "Image", horizontalAlignment: (_c = config.iconAlignment) !== null && _c !== void 0 ? _c : "Left", url: config.iconURL }, (config.iconRound && { style: "person" })), { width: `${(_d = config.iconWidth) !== null && _d !== void 0 ? _d : "16"}px` }), ], } : { type: "Column", width: "auto", items: [ { type: "TextBlock", text: config.iconURL, verticalContentAlignment: "Center", }, ], } : null; const headerPayload = { type: "ColumnSet", columns: config.rtl ? [textPayload, iconPayload].filter(Boolean) : [iconPayload, textPayload].filter(Boolean), }; this._stash.header = headerPayload; return this; } addBlock(content, config = {}) { if (typeof content === "string") { return this.addText(content, config); } if (content instanceof SpeedyCard) { const { backgroundColor, vertAlign } = config; const { body } = content.build(); const containerPayload = Object.assign(Object.assign(Object.assign(Object.assign({}, (config.separator && { separator: config.separator })), { type: "Container", height: "stretch", items: body }), (backgroundColor && { style: this.tools.checkColor(backgroundColor), })), (vertAlign && { verticalContentAlignment: vertAlign, })); this._stash.needsSubmit = !this._stash.needsSubmit ? content.needsSubmit() : this._stash.needsSubmit; this.json.body.push(containerPayload); } return this; } addSubcard(card, textLabel = "") { const subCard = { type: "Action.ShowCard", title: textLabel, card: "build" in card && typeof card.build === "function" ? card.build() : card, }; this.addAction(subCard); return this; } addPickerDropdown(choices, id = exports.SpeedyCardId.dropdown) { const cleanId = this.checkId(id); this._stash.needsSubmit = true; const formattedChoices = choices.map((choice, idx) => { if (typeof choice === "object") { return choice; } return { title: String(choice), value: String(choice), }; }); const payload = { type: "Input.ChoiceSet", id: cleanId, value: "0", isMultiSelect: false, isVisible: true, choices: formattedChoices, }; this.json.body.push(payload); return this; } addSingleSelect(choices, id = "addSingleSelectresult") { return this.addSelect(choices, id, { isMultiSelect: false, style: "expanded", }); } addMultiSelect(choices, id = "addMultiSelect_result") { return this.addSelect(choices, id, { isMultiSelect: true }); } addSelect(choices, id, config = {}) { this._stash.needsSubmit = true; const cleanId = this.checkId(id); let formattedChoices; if (Array.isArray(choices) && typeof choices[0] === "string") { formattedChoices = choices.map((choice) => ({ title: String(choice), value: String(choice), })); } else { formattedChoices = choices; } const payload = Object.assign(Object.assign({ type: "Input.ChoiceSet", id: cleanId, value: "0", isMultiSelect: Boolean(config.isMultiSelect), isVisible: true }, (config.style && { style: "expanded" })), { choices: formattedChoices, style: "expanded" }); this.json.body.push(payload); return this; } addPickerDate(textLabel, id = "addPickerDate_result") { this._stash.needsSubmit = true; const cleanId = this.checkId(id); const textPayload = this.buildTextPayload(textLabel); const datePicker = { type: "Input.Date", id: cleanId, }; this.json.body.push(textPayload, datePicker); return this; } addPickerTime(textLabel, id = "addPickerTime_result") { this._stash.needsSubmit = true; const cleanId = this.checkId(id); const textPayload = this.buildTextPayload(textLabel); const timePicker = { type: "Input.Time", id: cleanId, }; this.json.body.push(textPayload, timePicker); return this; } addTextInput(placeholder, id = "addTextInput_result") { this._stash.needsSubmit = true; const cleanId = this.checkId(id); const payload = { id: cleanId, placeholder, type: "Input.Text", }; this.json.body.push(payload); return this; } addTextarea(placeholder, id = "addTextarea_result") { this._stash.needsSubmit = true; const cleanId = this.checkId(id); const payload = { id: cleanId, placeholder, type: "Input.Text", isMultiline: true, }; this.json.body.push(payload); return this; } setBackgroundImage(url) { this.json.backgroundImage = url; return this; } setSubmitButtonTitle(label) { this._stash.submitLabel = label; return this; } attachData(payload) { this._stash.needsSubmit = true; this._stash.data = payload; return this; } buildTextPayload(text, textConfig = {}) { const payload = Object.assign({ type: "TextBlock", text, size: "Medium", isSubtle: true, wrap: true, weight: "Lighter" }, textConfig); return payload; } addAction(a) { if (!this.json.actions) { this.json.actions = []; } this.json.actions.push(a); } addDeleteButton(label = index_1.CONSTANTS.destroyLabel) { return this.addButton(label, index_1.CONSTANTS.submitToken, index_1.CONSTANTS.action_delete); } addButton(label, id = "button_result", attachedData = {}) { const payload = { type: "Action.Submit", title: label, data: { [id]: attachedData, }, }; this.addAction(payload); return this; } survey(questions, title = "📝 Survey") { const card = new SpeedyCard(); card.addHeader(title); questions.forEach((question, idx) => { let id = question.id || `question_${idx + 1}`; switch (question.type) { case "text": card.addTextInput(question.question, id); break; case "single-select": card.addText(question.question); card.addSingleSelect(question.choices || [], id); break; case "multi-select": card.addText(question.question); card.addMultiSelect(question.choices || [], id); break; case "picker-dropdown": card.addText(question.question); card.addPickerDropdown(question.choices || [], id); break; case "picker-date": card.addPickerDate(question.question, id); break; case "picker-time": card.addPickerTime(question.question, id); break; case "textarea": card.addTextarea(question.question, id); break; } }); return card; } build() { const json = JSON.parse(JSON.stringify(this.json)); const needsSubmit = this._stash.needsSubmit; if (this._stash.subTitle) { json.body.unshift(this.buildTextPayload(this._stash.subTitle)); } if (this._stash.title) { json.body.unshift(this.buildTextPayload(this._stash.title, { weight: "Bolder", size: "ExtraLarge", })); } if (needsSubmit) { const payload = { type: "Action.Submit", title: this._stash.submitLabel, }; if (this._stash.data && Object.keys(this._stash.data).length > 0) { payload.data = this._stash.data; } if (!json.actions) { json.actions = []; } json.actions.push(payload); } const hasHeader = Boolean(this._stash.header); if (hasHeader) { json.body = [ this._stash.header, { separator: true, type: "Container", items: json.body, }, ]; } return json; } } exports.SpeedyCard = SpeedyCard; //# sourceMappingURL=cards.js.map