@planningcenter/core-automations 1.13.3 → 1.13.4
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/dist/cjs/core-automations.esm.js +1 -1
- package/dist/cjs/core-automations.esm.js.map +1 -1
- package/dist/cjs/core-automations.js +1 -1
- package/dist/cjs/core-automations.js.map +1 -1
- package/dist/cjs/core-automations.modern.mjs +1 -1
- package/dist/cjs/core-automations.modern.mjs.map +1 -1
- package/dist/cjs/core-automations.umd.js +1 -1
- package/dist/cjs/core-automations.umd.js.map +1 -1
- package/dist/types/src/automation.d.ts.map +1 -1
- package/dist/types/src/automations.d.ts.map +1 -1
- package/dist/types/src/history.d.ts.map +1 -1
- package/dist/types/src/incoming_automations.d.ts.map +1 -1
- package/dist/types/src/new_automation.d.ts.map +1 -1
- package/dist/types/src/utils/fetch-automations.d.ts.map +1 -1
- package/dist/types/src/utils/pco-api-root.d.ts +2 -0
- package/dist/types/src/utils/pco-api-root.d.ts.map +1 -0
- package/dist/types/src/utils/utils.d.ts.map +1 -1
- package/dist/types/tests/utils/pco-api-root.test.d.ts +2 -0
- package/dist/types/tests/utils/pco-api-root.test.d.ts.map +1 -0
- package/package.json +2 -2
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"core-automations.umd.js","sources":["../../src/assets/svg_automations.tsx","../../src/contexts/organization_context.tsx","../../src/utils/alerts.ts","../../src/utils/utils.ts","../../src/history.tsx","../../src/history_modal.tsx","../../src/utils/logos.ts","../../src/automation.tsx","../../src/utils/fetch-automations.ts","../../src/incoming_automations.tsx","../../src/definition.tsx","../../src/field.tsx","../../src/fields.tsx","../../src/new_automation.tsx","../../src/new_automation_modal.tsx","../../src/utils/theme.ts","../../src/automations.tsx"],"sourcesContent":["const SvgAutomations = () => (\n <svg\n id=\"automations_blank\"\n data-name=\"Automations Blank\"\n xmlns=\"http://www.w3.org/2000/svg\"\n viewBox=\"0 0 111.112 84.832\"\n className=\"symbol\"\n >\n <title>Automations</title>\n <g opacity=\"0.6\">\n <path\n d=\"M107.784,46.051A57.416,57.416,0,0,1,85.26,75.058c-9.7,6.247-20.045,7.792-31.912,5.185-11.74-2.638-23.339-8-32.92-13.088-9.51-5.342-17-10.236-18.863-17.925C-.26,41.753,3.737,31.4,13.347,21.194,22.85,11.162,37.968,1.853,55.948.321,73.8-1.476,90.2,4.478,99.608,13.164,109.257,21.9,111.921,33.784,107.784,46.051Z\"\n fill=\"#e1f0f9\"\n className=\"svg-background-blob\"\n />\n </g>\n <path\n d=\"M81,27.269v31.8a2.685,2.685,0,0,1-2.685,2.685H44.564a2.685,2.685,0,0,1-2.685-2.685V15.425a2.685,2.685,0,0,1,2.685-2.685h21.91a2.681,2.681,0,0,1,1.9.786L80.217,25.371A2.685,2.685,0,0,1,81,27.269Z\"\n fill=\"#fff\"\n />\n <path\n d=\"M68.479,13.633v9.8a2.035,2.035,0,0,0,2.035,2.034h9.877Z\"\n fill=\"#c9d8e2\"\n />\n <rect\n x=\"51.214\"\n y=\"41.285\"\n width=\"20.221\"\n height=\"2.791\"\n rx=\"1.395\"\n ry=\"1.395\"\n fill=\"#dae5ed\"\n />\n <rect\n x=\"51.214\"\n y=\"48.434\"\n width=\"20.221\"\n height=\"2.791\"\n rx=\"1.395\"\n ry=\"1.395\"\n fill=\"#dae5ed\"\n />\n <rect\n x=\"51.214\"\n y=\"34.136\"\n width=\"20.221\"\n height=\"2.791\"\n rx=\"1.395\"\n ry=\"1.395\"\n fill=\"#dae5ed\"\n />\n <rect\n x=\"11.771\"\n y=\"44.005\"\n width=\"50.915\"\n height=\"6.664\"\n transform=\"translate(-22.93 44.557) rotate(-49.171)\"\n fill=\"#454942\"\n />\n <path\n d=\"M56.283,30.38l-7.557,8.745a5.968,5.968,0,0,0-2.005-2.734,6.292,6.292,0,0,0-3.036-1.624l7.555-8.743a6.275,6.275,0,0,1,3.038,1.624A5.959,5.959,0,0,1,56.283,30.38Z\"\n fill=\"#fcc846\"\n />\n <path\n d=\"M58.088,28.29l-7.556,8.745a5.968,5.968,0,0,0-2-2.734,6.3,6.3,0,0,0-3.036-1.624l7.555-8.743a6.274,6.274,0,0,1,3.037,1.624A5.959,5.959,0,0,1,58.088,28.29Z\"\n fill=\"#48a5e5\"\n />\n <path\n d=\"M58.724,10.432l1.17,2.7a2.129,2.129,0,0,0,1.4,1.207l2.843.765a.73.73,0,0,1,.1,1.375l-2.7,1.17a2.125,2.125,0,0,0-1.207,1.4L59.56,21.89a.73.73,0,0,1-1.374.1l-1.17-2.7a2.125,2.125,0,0,0-1.4-1.206l-2.843-.766a.73.73,0,0,1-.1-1.374l2.7-1.17a2.121,2.121,0,0,0,1.206-1.4l.766-2.844A.73.73,0,0,1,58.724,10.432Z\"\n fill=\"#fcc846\"\n />\n <path\n d=\"M44.544,19.294l1.024.868a.968.968,0,0,0,.814.21l1.316-.261a.333.333,0,0,1,.319.541l-.868,1.024a.968.968,0,0,0-.21.814l.261,1.316a.333.333,0,0,1-.541.319l-1.024-.868a.968.968,0,0,0-.814-.21l-1.316.261a.333.333,0,0,1-.319-.541l.868-1.024a.967.967,0,0,0,.21-.814L44,19.613A.333.333,0,0,1,44.544,19.294Z\"\n fill=\"#fcc846\"\n />\n <path\n d=\"M64.223,25.729l.869,2.005a1.575,1.575,0,0,0,1.036.895l2.109.568a.542.542,0,0,1,.075,1.02l-2,.868a1.576,1.576,0,0,0-.9,1.036l-.568,2.11a.541.541,0,0,1-1.019.074L62.955,32.3a1.572,1.572,0,0,0-1.036-.895l-2.109-.568a.542.542,0,0,1-.075-1.02l2.005-.868a1.572,1.572,0,0,0,.895-1.036L63.2,25.8A.541.541,0,0,1,64.223,25.729Z\"\n fill=\"#fcc846\"\n />\n </svg>\n)\n\nexport default SvgAutomations\n","import { createContext } from \"react\"\n\nexport const OrganizationContext = createContext({\n dateFormat: null,\n olsonTimeZone: null,\n twentyFourHourTime: null,\n})\n","import {\n createConfirmOptions,\n destroyConfirmOptions,\n errorAlertOptions,\n standardAlertOptions,\n standardConfirmOptions,\n successAlertOptions,\n} from \"@planningcenter/sweetalert2\"\nimport Swal from \"sweetalert2/dist/sweetalert2\"\n\nexport const alert = Swal.mixin(standardAlertOptions)\nexport const alertSuccess = Swal.mixin(successAlertOptions)\nexport const alertError = Swal.mixin(errorAlertOptions)\nexport const confirm = Swal.mixin(standardConfirmOptions)\nexport const confirmDestroy = Swal.mixin(destroyConfirmOptions)\nexport const confirmCreate = Swal.mixin(createConfirmOptions)\n","import { Client } from \"@planningcenter/api-client\"\nimport { isBoolean } from \"lodash\"\nimport moment from \"moment\"\n\nexport async function deobfuscateDescriptions(\n subscriptions: AutomationInstance[]\n) {\n return Promise.all(\n subscriptions.map(async (subscription) => {\n if (isDeobfuscatable(subscription)) {\n subscription.description = await deobfuscatedDescription(subscription)\n }\n return subscription\n })\n )\n}\n\nfunction isDeobfuscatable(subscription: AutomationInstance) {\n const DEOBFUSCATABLE_OPERATION_DEFINITION_CLASS_NAMES = [\n \"AddToWorkflowOperationDefinition\",\n \"CustomFieldBooleanOperationDefinition\",\n \"CustomFieldCheckboxesOperationDefinition\",\n \"CustomFieldDateOperationDefinition\",\n \"CustomFieldNumberOperationDefinition\",\n \"CustomFieldSelectOperationDefinition\",\n \"CustomFieldStringOperationDefinition\",\n \"CustomFieldTextOperationDefinition\",\n ]\n\n return DEOBFUSCATABLE_OPERATION_DEFINITION_CLASS_NAMES.includes(\n subscription.operationDefinitionClassName\n )\n}\n\nasync function deobfuscatedDescription(subscription: AutomationInstance) {\n let description = \"\"\n if (\n subscription.operationDefinitionClassName ===\n \"AddToWorkflowOperationDefinition\"\n ) {\n const data = await fetchWorkflow(subscription.operationParams.workflowId)\n const workflow = data[0]\n\n if (workflow?.name) {\n let workflowName\n\n if (workflow.archivedAt) {\n workflowName = `[archived] ${workflow.name}`\n } else {\n workflowName = workflow.name\n }\n\n description = subscription.description.replace(\n \"[Hidden Workflow]\",\n workflowName\n )\n }\n } else {\n // custom field\n const fieldDefinitionId =\n subscription.operationParams.definitionIdentifier.match(\n /(\\d+)_field_definition/\n )[1]\n const fieldDefinition = await fetchFieldDefinition(fieldDefinitionId)\n if (fieldDefinition.name) {\n description = subscription.description.replace(\n \"[Hidden Custom Field]\",\n fieldDefinition.name\n )\n description +=\n subscription.operationParams.values ||\n fieldDefinition.dataType !== \"checkboxes\"\n ? ` (${customFieldOptionDescription(subscription, fieldDefinition)})`\n : \"\"\n }\n }\n return description || subscription.description\n}\n\nfunction customFieldOptionDescription(\n subscription: AutomationInstance,\n fieldDefinition: {\n dataType: string\n fieldOptions: { id: number; value: string }[]\n }\n) {\n switch (fieldDefinition.dataType) {\n case \"checkboxes\":\n return Object.entries(subscription.operationParams.values)\n .map(([id, action]) => {\n const value =\n fieldDefinition.fieldOptions.find(\n (fieldOption) => fieldOption.id === parseInt(id, 10)\n )?.value || \"[Hidden value]\"\n return `${capitalize(action)} ${value}`\n })\n .join(\", \")\n case \"select\":\n return subscription.operationParams.value\n ? fieldDefinition.fieldOptions.find(\n (fieldOption) =>\n fieldOption.id ===\n parseInt(subscription.operationParams.value.toString(), 10)\n )?.value || \"[Hidden value]\"\n : \"Unanswered\"\n case \"boolean\":\n switch (subscription.operationParams.value) {\n case \"true\":\n return \"Yes\"\n case \"false\":\n return \"No\"\n default:\n return \"Unanswered\"\n }\n default:\n return subscription.operationParams.value ?? \"Unanswered\"\n }\n}\n\nfunction capitalize(string: string) {\n return string.charAt(0).toUpperCase() + string.slice(1)\n}\n\nconst peopleClient = new Client({ app: \"people\", version: \"2025-03-20\" })\n\nasync function fetchWorkflow(workflowId: number) {\n const { data } = await peopleClient\n .get({\n data: {\n fields: { Workflow: \"name,archived_at\" },\n where: { id: workflowId },\n },\n url: `workflows`,\n })\n .catch(() => [{ data: { name: \"\" } }])\n\n return data\n}\n\nasync function fetchFieldDefinition(fieldDefinitionId: string) {\n const { data } = await peopleClient\n .get({\n data: {\n fields: {\n FieldDefinition: \"name,data_type,field_options\",\n FieldOption: \"value\",\n },\n include: \"field_options\",\n },\n url: `field_definitions/${fieldDefinitionId}`,\n })\n .catch(() => ({ data: { name: \"\" } }))\n\n return data\n}\n\nexport function fieldListIdentifier(field: DefinitionField) {\n if (field.listClass) {\n return `${field.id}_${field.listClass}`\n } else if (field.kind === \"PersonSearch\") {\n return `${field.id}_PersonSearch`\n } else {\n return null\n }\n}\n\nexport function buildDescription({\n selectedDefinition,\n selectedFieldOptions,\n loadedLists,\n}: {\n loadedLists: { [k: string]: LoadedList[] }\n selectedDefinition: OperationDefinition\n selectedFieldOptions: SelectedFieldOptions\n}) {\n return {\n description: describeSelectedFields({\n loadedLists: loadedLists || {},\n selectedDefinition,\n selectedFieldOptions,\n }),\n name: buildDescriptionName(selectedDefinition),\n }\n}\n\nfunction obfuscateDescriptionName(definition: OperationDefinition) {\n if (definition.definitionClass.match(/^CustomField\\w+OperationDefinition$/)) {\n return \"Update [Hidden Custom Field]\"\n }\n}\n\nfunction buildDescriptionName(definition: OperationDefinition) {\n return obfuscateDescriptionName(definition) || definition.description\n}\n\nfunction hasOwnProperty(object: object, key: PropertyKey) {\n return Object.prototype.hasOwnProperty.call(object, key)\n}\n\nfunction getListForField({\n field,\n loadedLists,\n}: {\n field: DefinitionField\n loadedLists: { [k: string]: LoadedList[] }\n}) {\n if (field.list) {\n return field.list\n } else if (fieldListIdentifier(field)) {\n const list = loadedLists[fieldListIdentifier(field)]\n\n return list\n } else {\n throw new Error(`Don't know how to get list for ${JSON.stringify(field)}`)\n }\n}\n\nexport function getRenderedFields(\n definitionFields: DefinitionField[],\n selectedFieldOptions: SelectedFieldOptions\n) {\n return definitionFields.filter((field) => {\n if (Object.prototype.hasOwnProperty.call(field, \"renderIf\")) {\n const renderIf = field.renderIf\n const conditionKey = Object.keys(renderIf)[0]\n\n return isBoolean(renderIf)\n ? renderIf\n : renderIf[conditionKey] === selectedFieldOptions[conditionKey]\n } else {\n return true\n }\n })\n}\n\nfunction describeSelectedFields({\n selectedDefinition,\n selectedFieldOptions,\n loadedLists,\n}: {\n loadedLists: { [k: string]: LoadedList[] }\n selectedDefinition: OperationDefinition\n selectedFieldOptions: SelectedFieldOptions\n}) {\n const description = selectedDefinition.definitionFields\n .map((field) => {\n if (!hasOwnProperty(selectedFieldOptions, field.id)) return null\n\n const value = selectedFieldOptions[field.id]\n let list\n\n switch (field.kind) {\n case \"Select\":\n case \"SelectSearch\":\n case \"PersonSearch\":\n case \"RadioButtons\":\n list = getListForField({ field, loadedLists })\n\n return (\n list && list.find((o) => o.value.toString() === value)?.description\n )\n case \"Checkbox\":\n return value && field.label\n case \"Checkboxes\":\n list = getListForField({ field, loadedLists })\n\n return list\n .filter((e) => hasOwnProperty(value as object, e.value))\n .map((e) => `${capitalize(value[e.value])} ${e.description}`)\n .join(\", \")\n case \"NumberField\":\n case \"TextField\":\n case \"TextArea\":\n case \"DateField\":\n return value\n default:\n throw new Error(\n `Don't know how to build value for field with kind ${field.kind}`\n )\n }\n })\n .filter((x) => x)\n .join(\", \")\n\n return obfuscateSelectedFieldDescriptions({\n description,\n loadedLists,\n selectedDefinition,\n selectedFieldOptions,\n })\n}\n\nfunction obfuscateSelectedFieldDescriptions({\n selectedDefinition,\n selectedFieldOptions,\n loadedLists,\n description,\n}) {\n if (\n selectedDefinition.definitionClass === \"AddToWorkflowOperationDefinition\"\n ) {\n const list = loadedLists.workflow_id_WorkflowsList\n const sensitiveString =\n list &&\n list.find((o) => o.value.toString() === selectedFieldOptions.workflow_id)\n ?.description\n\n return description.replace(sensitiveString, \"[Hidden Workflow]\")\n } else if (\n selectedDefinition.definitionClass.match(\n /^CustomField\\w+OperationDefinition$/\n )\n ) {\n return \"\"\n } else {\n return description\n }\n}\n\nexport function dateFNSFormat(format) {\n return format\n .replace(/%m/, \"M\")\n .replace(/%d/, \"d\")\n .replace(/%Y/, \"y\")\n .replace(/%y/, \"yy\")\n}\n\nexport function momentDateFormat(format) {\n return format\n .replace(/%m/, \"MM\")\n .replace(/%d/, \"DD\")\n .replace(/%Y/, \"YYYY\")\n .replace(/%y/, \"YY\")\n}\n\nexport function momentDateTimeFormat({ dateFormat, twentyFourHourTime }) {\n return `${momentDateFormat(dateFormat)} ${\n twentyFourHourTime ? \"HH:mm\" : \"h:mm A\"\n }`\n}\n\nexport function dateLocalized(date, dateFormat) {\n const momentDate = moment(date, \"YYYY-MM-DD\")\n if (!momentDate.isValid()) {\n return \"\"\n }\n\n const format = momentDateFormat(dateFormat)\n return momentDate.format(format)\n}\n\nexport function numDaysSince(date: string) {\n const momentDate = moment(date, \"YYYY-MM-DD\")\n return moment().diff(momentDate, \"days\")\n}\n\nexport function pluralize(count: number, word: string) {\n if (count === 1) {\n return `1 ${word}`\n } else {\n return `${count} ${word}s`\n }\n}\n\nexport function singularize(string) {\n return string.replace(/s$/, \"\")\n}\n\nexport function upperFirst(string) {\n return string.charAt(0).toUpperCase() + string.slice(1)\n}\n\nexport function triggerResourceParts(triggerResource: string) {\n const triggerParts = triggerResource.split(\"/\")\n\n return {\n appName: triggerParts[0],\n resourceId: triggerParts[triggerParts.length - 1],\n resourcePath: triggerParts.slice(2, -1).join(\"/\"),\n resourceType: triggerParts[triggerParts.length - 2],\n }\n}\n\nexport function forbiddenText(error: any, action?: string) {\n if (error.errors?.[0]?.status === \"403\") {\n return `You don't have permission to ${action || \"modify\"} this automation.`\n }\n return null\n}\n","import { Client } from \"@planningcenter/api-client\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Alert,\n Badge,\n Box,\n Button,\n DataTable,\n Heading,\n Icon,\n Input,\n Link,\n Select,\n StackView,\n Text,\n} from \"@planningcenter/tapestry-react\"\nimport moment from \"moment\"\nimport React, { useCallback, useContext, useEffect, useState } from \"react\"\n\nimport SvgAutomations from \"./assets/svg_automations\"\nimport { OrganizationContext } from \"./contexts/organization_context\"\nimport * as alerts from \"./utils/alerts\"\nimport {\n dateLocalized,\n momentDateTimeFormat,\n numDaysSince,\n} from \"./utils/utils\"\n\ndeclare global {\n interface Window {\n openHelpdesk: () => void\n }\n}\n\nconst webhooksClient = new Client({ app: \"webhooks\", version: \"2022-10-20\" })\nconst peopleClient = new Client({ app: \"people\", version: \"2022-07-14\" })\n\n// values should match the webhooks Event `status` enum entries\nconst STATUS = {\n delivered: {\n label: \"Success\",\n value: [\"delivered\"],\n },\n failed: {\n label: \"Failed\",\n value: [\"failed\", \"duplicated\"],\n },\n ignored: {\n label: \"Ignored\",\n value: [\"ignored_duplicated\", \"ignored_failed\", \"ignored_skipped\"],\n },\n pending: {\n label: \"Pending\",\n value: [\"pending\"],\n },\n skipped: {\n label: \"Paused\",\n value: [\"skipped\"],\n },\n}\n\nasync function fetchEvents(\n triggerResource: EncryptedTriggerResource,\n automationId: number,\n params: {\n offset: number\n per_page: number\n where?: { status: string } | null\n }\n) {\n const response = await webhooksClient.get({\n data: {\n _e: triggerResource,\n fields: {\n Delivery: \"status,response_body,created_at\",\n Event: \"id,created_at,last_delivery,payload,status,uuid,person\",\n },\n include: \"last_delivery\",\n order: \"-created_at\",\n ...params,\n },\n url: `automation_subscriptions/${automationId}/events`,\n })\n\n return response\n}\n\nasync function fetchPeople(personIds) {\n const { data } = await peopleClient.get({\n data: {\n fields: {\n Person: \"id,name\",\n },\n where: { id: personIds.join(\",\") },\n },\n url: `people`,\n })\n\n return data\n}\n\nasync function fetchPeopleWhoTriggeredEvents(events) {\n const personIds = events.data.map((e) => eventPersonId(e))\n try {\n const people = await fetchPeople(personIds)\n return { events, people }\n } catch (error) {\n return { events, people: [] }\n }\n}\n\nfunction mergePeopleAndEvents({ events, people }) {\n const mergedData = events.data.reduce((result, e) => {\n const personId = eventPersonId(e)\n const foundPerson = people.find(\n (p) => personId.toString() === p.id.toString()\n )\n if (foundPerson) {\n result.push({\n ...e,\n person: { id: foundPerson.id, name: foundPerson.name },\n })\n } else {\n result.push({\n ...e,\n person: { id: personId, name: \"[Hidden]\" },\n })\n }\n return result\n }, [])\n\n return { ...events, data: mergedData }\n}\n\nfunction eventPersonId(event) {\n return event.personId\n}\n\nfunction useEvents(\n automationId: number,\n triggerResource: EncryptedTriggerResource,\n filterWhere?: string\n) {\n const perPage = 50\n const [_, setError] = useState()\n const [loading, setLoading] = useState(false)\n const [eventPages, setEventPages] = useState<{ [k: number]: EventPage[] }>({})\n const [params, setParams] = useState<{ where?: { status: string } | null }>(\n filterWhere ? { where: { status: filterWhere } } : {}\n )\n const [meta, setMeta] = useState<{ totalCount: number | any }>()\n const { offset, paginationProps, resetOffset } = usePagination(\n perPage,\n meta?.totalCount\n )\n useEffect(() => {\n if (loading || eventPages[offset]) return\n\n setLoading(true)\n\n fetchEvents(triggerResource, automationId, {\n offset,\n per_page: perPage,\n ...params,\n })\n .then(fetchPeopleWhoTriggeredEvents)\n .then(mergePeopleAndEvents)\n .then((events) => {\n setEventPages((pages) => ({ ...pages, [offset]: events.data }))\n setMeta(events.meta)\n setLoading(false)\n })\n .catch(bubbleErrorToBoundary)\n }, [automationId, triggerResource, loading, params, offset, eventPages])\n\n const refresh = useCallback(() => {\n setEventPages({})\n setMeta(undefined)\n resetOffset()\n }, [resetOffset])\n\n useEffect(() => {\n refresh()\n }, [refresh, params])\n\n function bubbleErrorToBoundary(error) {\n setError(() => {\n throw error\n })\n }\n\n return {\n events: eventPages[offset] || [],\n loading,\n paginationProps,\n params,\n refresh,\n setParams,\n }\n}\n\nfunction usePagination(perPage: number, totalCount: number) {\n const [offset, setOffset] = useState(0)\n\n const currentPage = Math.floor(offset / perPage) + 1\n const totalPages = Math.ceil(totalCount / perPage)\n const paginationProps = { currentPage, onPageChange, totalPages }\n\n function onPageChange(pageNum: number) {\n setOffset((pageNum - 1) * perPage)\n }\n\n const resetOffset = useCallback(() => {\n setOffset(0)\n }, [])\n\n return { offset, paginationProps, resetOffset }\n}\n\nfunction History({\n automation,\n triggerResource,\n filterWhere,\n onEventsStatusChange,\n}: {\n automation: AutomationInstance\n filterWhere?: string\n onEventsStatusChange: Function\n onRequestClose?: () => void\n triggerResource: EncryptedTriggerResource\n}) {\n const { events, loading, paginationProps, refresh, params, setParams } =\n useEvents(automation.id, triggerResource, filterWhere)\n const { dateFormat, olsonTimeZone, twentyFourHourTime } = useContext<{\n dateFormat: any\n olsonTimeZone: any\n twentyFourHourTime: any\n }>(OrganizationContext)\n\n const filteringEvents = params.where && Object.keys(params.where).length > 0\n const automationCreatedRecently = numDaysSince(automation.createdAt) <= 32\n const automationBeganOn = dateLocalized(automation.createdAt, dateFormat)\n const historyPreservationAlert = automationCreatedRecently\n ? `Automation history started on ${automationBeganOn}`\n : \"Automation history is saved for 32 days\"\n\n const columns = [\n {\n cell: (event: EventPage) => <EventStatusBadge status={event.status} />,\n css: {\n padding: \"8px 12px\",\n },\n header: \"Status\",\n },\n {\n cell: (event: EventPage) =>\n moment(event.createdAt)\n .utcOffset(olsonTimeZone)\n .format(momentDateTimeFormat({ dateFormat, twentyFourHourTime })),\n header: \"Date and time\",\n },\n {\n cell: (event: EventPage) => (\n <Link to={`/people/AC${event.person.id}`}>{event.person.name}</Link>\n ),\n css: {\n maxWidth: \"33%\",\n },\n header: \"Profile\",\n },\n {\n cell: (event: EventPage) => <EventStatusMessage event={event} />,\n css: {\n flex: 1,\n },\n header: \"Message\",\n },\n {\n cell: (event: EventPage) =>\n ![...STATUS.delivered.value, ...STATUS.pending.value].includes(\n event.status\n ) && (\n <>\n <RetryEventButton\n automationId={automation.id}\n event={event}\n triggerResource={triggerResource}\n onEventsStatusChange={onEventsStatusChange}\n />\n {![...STATUS.ignored.value].includes(event.status) && (\n <IgnoreEventButton\n automationId={automation.id}\n event={event}\n triggerResource={triggerResource}\n refreshHistory={refresh}\n onEventsStatusChange={onEventsStatusChange}\n />\n )}\n </>\n ),\n css: {\n textAlign: \"right\",\n },\n header: \"\",\n minWidth: \"84px\",\n },\n ]\n\n return (\n <StackView spacing={token(\"--t-spacing-4\")}>\n <StackView spacing={token(\"--t-spacing-half\")}>\n <Heading\n level={3}\n size=\"16px\"\n color={token(\"--t-text-color-secondary\")}\n weight={token(\"--t-font-weight-medium\")}\n >\n {automation.description}\n </Heading>\n <Text\n color={token(\"--t-text-color-secondary\")}\n size={token(\"--t-font-size-xs\")}\n italic\n >\n {historyPreservationAlert}\n </Text>\n </StackView>\n <StackView spacing={token(\"--t-spacing-2\")}>\n <Box minHeight={7}>\n {!loading && (events.length || filteringEvents) && (\n <StackView\n alignItems=\"end\"\n axis=\"horizontal\"\n distribution=\"space-between\"\n spacing={token(\"--t-spacing-1\")}\n >\n <StackView width=\"max-content\">\n <Input.InputLabel\n fontWeight={token(\"--t-font-weight-medium\")}\n color={token(\"--t-text-color\")}\n controls=\"select-status\"\n >\n Filter by status\n </Input.InputLabel>\n <Select\n id=\"select-status\"\n emptyValue={null}\n onChange={({ selectedValue }) => {\n const newWhere = selectedValue\n ? { status: selectedValue }\n : null\n setParams({ where: newWhere })\n }}\n title=\"Status\"\n value={params.where?.status}\n >\n <Select.Option value={null}>All</Select.Option>\n {Object.values(STATUS).map((status) => (\n <Select.Option\n key={status.value}\n value={status.value.join(\",\")}\n >\n {status.label}\n </Select.Option>\n ))}\n </Select>\n </StackView>\n <Button\n iconLeft={{ name: \"general.refresh\" }}\n onClick={refresh}\n theme=\"primary\"\n variant=\"outline\"\n width={12}\n >\n Refresh\n </Button>\n </StackView>\n )}\n </Box>\n <Box maxHeight=\"70vh\" minHeight={36} overflow=\"auto\">\n <DataTable\n columns={columns}\n data={events}\n empty={\n <StackView\n alignment=\"center\"\n distribution=\"center\"\n minHeight={20}\n maxWidth={45}\n spacing={token(\"--t-spacing-1\")}\n marginTop={!filteringEvents ? -8 : -4}\n marginBottom={!filteringEvents ? undefined : 4}\n >\n <Box\n css={{\n svg: {\n height: 15,\n width: 20,\n },\n }}\n >\n <SvgAutomations />\n </Box>\n <Heading\n color={token(\"--t-text-color-headline\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n level={4}\n size={token(\"--t-font-size-lg\")}\n >\n No history found\n </Heading>\n <Text fontSize={token(\"--t-font-size-md\")} textAlign=\"center\">\n No events {filteringEvents && \"matching your filters\"} were\n triggered for this automation{\" \"}\n {automationCreatedRecently\n ? `since ${automationBeganOn}.`\n : \"in the last 32 days.\"}\n </Text>\n {filteringEvents && (\n <Button\n marginTop={token(\"--t-spacing-1\")}\n onClick={() => setParams({})}\n theme=\"primary\"\n title=\"Clear filters\"\n variant=\"outline\"\n />\n )}\n </StackView>\n }\n loading={loading}\n loadingTitle=\"Loading automation history...\"\n variant={{\n bodyCell: {\n alignItems: \"start\",\n fontSize: token(\"--t-font-size-sm\"),\n lineHeight: \"20px\",\n padding: \"10px 12px\",\n },\n bodyRow: ({ rowData }) => {\n return {\n backgroundColor: [...STATUS.ignored.value].includes(\n rowData.status\n )\n ? token(\"--t-fill-color-neutral-090\")\n : undefined,\n minHeight: \"36px\",\n }\n },\n headerCell: {\n padding: \"8px 12px\",\n },\n headerRow: {\n minHeight: \"36px\",\n },\n }}\n {...paginationProps}\n />\n </Box>\n </StackView>\n </StackView>\n )\n}\n\nfunction RetryEventButton({\n automationId,\n event,\n triggerResource,\n onEventsStatusChange,\n}: {\n automationId: number\n event: EventPage\n onEventsStatusChange: Function\n triggerResource: EncryptedTriggerResource\n}) {\n const [status, setStatus] = useState(event.status)\n\n function handleRetry() {\n setStatus(STATUS.pending.value.join(\",\"))\n webhooksClient\n .post({\n data: {\n _e: triggerResource,\n data: { attributes: {} },\n },\n url: `/automation_subscriptions/${automationId}/events/${event.id}/redeliver`,\n })\n .then((response) => {\n setStatus(STATUS.delivered.value.join(\",\"))\n onEventsStatusChange(response.meta.eventsStatus)\n })\n .catch(() => {\n setStatus(STATUS.failed.value.join(\",\"))\n alerts.alertError.fire({\n text: \"There was a problem retrying this automation. Please try again in a few moments.\",\n title: \"Uh oh!\",\n })\n })\n }\n\n const retryTitleFromStatus = STATUS.pending.value.includes(status)\n ? \"Sending\"\n : STATUS.delivered.value.includes(status)\n ? \"Sent\"\n : STATUS.skipped.value.includes(status)\n ? \"Run now\"\n : \"Retry\"\n\n const statusIcon = STATUS.delivered.value.includes(status)\n ? { color: token(\"--t-text-color-status-success\"), name: \"general.check\" }\n : undefined\n\n return (\n <Button\n title={retryTitleFromStatus}\n onClick={handleRetry}\n iconLeft={statusIcon}\n disabled={status !== event.status}\n variant=\"naked\"\n color={\n STATUS.delivered.value.includes(status)\n ? token(\"--t-text-color-status-success\")\n : STATUS.pending.value.includes(status)\n ? token(\"--t-text-color-placeholder\")\n : token(\"--t-text-color-interaction\")\n }\n theme=\"primary\"\n size=\"xs\"\n />\n )\n}\n\nfunction IgnoreEventButton({\n automationId,\n event,\n triggerResource,\n refreshHistory,\n onEventsStatusChange,\n}: {\n automationId: number\n event: EventPage\n onEventsStatusChange: Function\n refreshHistory: Function\n triggerResource: EncryptedTriggerResource\n}) {\n function handleIgnore() {\n webhooksClient\n .post({\n data: {\n _e: triggerResource,\n data: { attributes: {} },\n },\n url: `/automation_subscriptions/${automationId}/events/${event.id}/ignore`,\n })\n .then((response) => {\n onEventsStatusChange(response.meta.eventsStatus)\n })\n .then(() => refreshHistory())\n .catch(() => {\n alerts.alertError.fire({\n text: \"There was a problem ignoring this event. Please try again in a few moments.\",\n title: \"Uh oh!\",\n })\n })\n }\n\n return (\n <Button\n title={\"Ignore\"}\n onClick={handleIgnore}\n variant=\"naked\"\n color={\"linkForeground\"}\n theme=\"primary\"\n size=\"xs\"\n />\n )\n}\n\nfunction EventStatusBadge({ status }: { status: string }) {\n const badgeColors = STATUS.pending.value.includes(status)\n ? {\n border: token(\"--t-border-color-dark\"),\n text: token(\"--t-text-color\"),\n }\n : STATUS.delivered.value.includes(status)\n ? {\n border: token(\"--t-border-color-status-success\"),\n text: token(\"--t-text-color-status-success\"),\n }\n : STATUS.skipped.value.includes(status)\n ? {\n border: token(\"--t-border-color-status-warning\"),\n text: token(\"--t-text-color-status-warning\"),\n }\n : STATUS.ignored.value.includes(status)\n ? {\n border: token(\"--t-border-color-dark\"),\n text: token(\"--t-text-color-secondary\"),\n }\n : {\n border: token(\"--t-border-color-status-error\"),\n text: token(\"--t-text-color-status-error\"),\n }\n\n const badgeIcon = STATUS.pending.value.includes(status)\n ? \"general.clock\"\n : STATUS.skipped.value.includes(status)\n ? \"services.pause\"\n : STATUS.delivered.value.includes(status)\n ? \"general.checkCircle\"\n : STATUS.ignored.value.includes(status)\n ? \"general.inactive\"\n : \"general.exclamationTriangle\"\n\n const badgeTitle = STATUS.failed.value.includes(status)\n ? STATUS.failed.label\n : STATUS.ignored.value.includes(status)\n ? STATUS.ignored.label\n : STATUS[status].label\n\n return (\n <Badge\n color={{ background: \"transparent\", foreground: badgeColors.text }}\n css={{ paddingLeft: 3.5, paddingRight: 1.5 }}\n fontSize={token(\"--t-font-size-xs\")}\n radius=\"pill\"\n renderLeft={\n <Icon\n name={badgeIcon}\n color={badgeColors.border}\n marginLeft={token(\"--t-spacing-1\")}\n />\n }\n size=\"sm\"\n stroke={badgeColors.border}\n strokeAlign=\"inside\"\n strokeWeight={1}\n title={badgeTitle}\n />\n )\n}\n\nfunction EventStatusMessage({ event }: { event: EventPage }) {\n const { status, lastDelivery } = event\n\n function statusMessage(status: string, lastDelivery: Delivery) {\n let message: string | JSX.Element | null = null\n\n switch (status) {\n case \"skipped\":\n case \"ignored_skipped\":\n message = \"Automation was paused and did not run on this profile\"\n break\n case \"failed\":\n case \"duplicated\":\n case \"ignored_failed\":\n case \"ignored_duplicated\":\n message = deliveryFailureReason(lastDelivery, status)\n }\n\n return message\n }\n\n function deliveryFailureReason(delivery: Delivery, status: string) {\n const ERRORS = {\n 403: \"Owner doesn't have permission to perform this action.\",\n 404: \"Owner lacks access to target product or resource doesn't exist.\",\n 422: \"The automation action failed to run\",\n default: \"An error occurred\",\n duplicated_event:\n \"Didn't run because the same action had already been performed less than 60 seconds ago\",\n failed_without_deliveries:\n \"Didn't run because the owner doesn't have permissions in this product.\",\n }\n\n function responseErrors(delivery: Delivery) {\n if (!delivery?.responseBody) return null\n let response\n\n try {\n response = JSON.parse(delivery.responseBody)\n } catch {\n response = { errors: [\"Server Error\"] }\n }\n\n return parsedErrors(response).join(\", \") || response?.message\n }\n\n function parsedErrors(response) {\n if (response?.errors) {\n return response.errors.map((error) =>\n typeof error === \"string\" && error.match(/Archived profiles/)\n ? error.replace(/Archived profiles/, \"Archived profiles.\")\n : error\n )\n } else {\n return []\n }\n }\n\n return (\n <StackView flex={1} whiteSpace=\"normal\">\n {!delivery ? (\n [\"duplicated\", \"ignored_duplicated\"].includes(status) ? (\n ERRORS.duplicated_event\n ) : (\n ERRORS.failed_without_deliveries\n )\n ) : (\n <ToggleableDetails\n details={responseErrors(delivery)}\n status={delivery.status}\n >\n {ERRORS[delivery.status] || ERRORS.default}\n </ToggleableDetails>\n )}\n </StackView>\n )\n }\n\n const message = statusMessage(status, lastDelivery)\n\n return message ? (\n <Box\n fontSize={token(\"--t-font-size-sm\")}\n fontStyle=\"italic\"\n lineHeight=\"16px\"\n maxWidth=\"100%\"\n paddingTop=\"1px\"\n whiteSpace=\"normal\"\n >\n {message}\n </Box>\n ) : null\n}\n\nfunction ToggleableDetails({\n children,\n details,\n status,\n}: {\n children: React.ReactNode\n details: string\n status: string\n}) {\n const [open, setOpen] = useState(false)\n\n function toggleOpen() {\n setOpen((was) => !was)\n }\n\n return (\n <StackView spacing={token(\"--t-spacing-1\")}>\n <Box>\n {children}{\" \"}\n {details && (\n <Button\n inline\n onClick={toggleOpen}\n size=\"xs\"\n theme=\"primary\"\n variant=\"naked\"\n fontStyle=\"normal\"\n >\n Details\n </Button>\n )}\n </Box>\n {open ? (\n <Box padding={1} background={token(\"--t-fill-color-neutral-090\")}>\n <Text\n fontFamily=\"monospace\"\n fontSize={token(\"--t-font-size-xs\")}\n lineHeight=\"1.2\"\n >\n {status && `${status}: `}\n {details}\n </Text>\n </Box>\n ) : null}\n </StackView>\n )\n}\n\ntype ErrorBoundaryProps = {\n children: React.ReactNode\n onRequestClose?: () => void\n}\n\ntype ErrorBoundaryState = {\n hasError: boolean\n}\n\nclass ErrorBoundary extends React.Component<\n ErrorBoundaryProps,\n ErrorBoundaryState\n> {\n constructor(props) {\n super(props)\n this.state = { hasError: false }\n }\n\n static getDerivedStateFromError() {\n return { hasError: true }\n }\n\n handleContactSupport = () => {\n if (this.props.onRequestClose) {\n this.props.onRequestClose()\n }\n window.openHelpdesk()\n }\n\n render() {\n if (this.state.hasError) {\n return (\n <Alert\n type=\"error\"\n marginVertical={1}\n padding={1.5}\n css={{ boxShadow: \"none\" }}\n >\n <Text lineHeight=\"1.35\">\n The application hit an unexpected error. If this persists after a\n few minutes, please let us know so we can get it fixed for you.{\" \"}\n <button\n style={{\n color: token(\"--t-text-color-interaction\"),\n whiteSpace: \"nowrap\",\n }}\n onClick={this.handleContactSupport}\n >\n Contact support\n </button>\n .\n </Text>\n </Alert>\n )\n }\n\n return this.props.children\n }\n}\n\n// eslint-disable-next-line react/display-name\nexport default (props) => (\n <ErrorBoundary onRequestClose={props.onRequestClose}>\n <History {...props}></History>\n </ErrorBoundary>\n)\n","import { token } from \"@planningcenter/tapestry\"\nimport {\n Button,\n Heading,\n Modal,\n StackView,\n ThemeProvider,\n} from \"@planningcenter/tapestry-react\"\nimport { createPortal } from \"react-dom\"\n\nfunction CloseModalIcon({ onClick }: { onClick: React.MouseEventHandler }) {\n return (\n <Button\n as=\"button\"\n height={token(\"--t-element-size-md\")}\n icon={{\n color: token(\"--t-icon-color-dim\"),\n name: \"general.x\",\n }}\n onClick={onClick}\n size=\"sm\"\n title=\"Close\"\n variant=\"naked\"\n />\n )\n}\n\nfunction HistoryModal({\n children,\n onRequestClose,\n open,\n theme,\n}: {\n children: React.ReactNode\n onRequestClose: () => void\n open: boolean\n theme: object\n}): React.ReactPortal | JSX.Element {\n return createPortal(\n <ThemeProvider theme={theme}>\n <Modal\n open={open}\n onRequestClose={onRequestClose}\n maxWidth={120}\n boxShadow=\"0 0 20px rgba(0, 0, 0, 0.15)\"\n padding={token(\"--t-spacing-4\")}\n paddingBottom={token(\"--t-spacing-3\")}\n radius={token(\"--t-border-radius-lg\")}\n >\n <StackView\n axis=\"horizontal\"\n distribution=\"space-between\"\n alignment=\"center\"\n >\n <Heading\n level={2}\n color={token(\"--t-text-color-headline\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n fontSize={token(\"--t-font-size-2xl\")}\n lineHeight=\"1.4\"\n >\n Automation history\n </Heading>\n <CloseModalIcon onClick={onRequestClose} />\n </StackView>\n {children}\n </Modal>\n </ThemeProvider>,\n document.body\n )\n}\n\nexport default HistoryModal\n","import { Logo } from \"@planningcenter/tapestry-react\"\nimport { kebabCase } from \"lodash\"\nimport type { ComponentProps } from \"react\"\n\n// Extract valid logo names from the Logo component's props\ntype ValidLogoName = NonNullable<ComponentProps<typeof Logo>[\"name\"]>\n\n// List of valid logo names from @planningcenter/tapestry-react Logo component\n// Update this list when support for new products are added to tapestry-react\nconst VALID_LOGO_NAMES: ValidLogoName[] = [\n \"api\",\n \"calendar\",\n \"check-ins\",\n \"church-center\",\n \"giving\",\n \"groups\",\n \"headcounts\",\n \"home\",\n \"login\",\n \"music-stand\",\n \"people\",\n \"planning-center\",\n \"publishing\",\n \"registrations\",\n \"services\",\n]\n\nexport const isValidLogoName = (name: string): name is ValidLogoName => {\n return VALID_LOGO_NAMES.includes(name as ValidLogoName)\n}\n\nexport const getValidLogoName = (name: string): ValidLogoName => {\n const kebabName = kebabCase(name)\n return isValidLogoName(kebabName) ? kebabName : \"planning-center\"\n}\n","import { Client } from \"@planningcenter/api-client\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Avatar,\n Box,\n Button,\n Card,\n Divider,\n Dropdown,\n Heading,\n Icon,\n Logo,\n StackView,\n Text,\n ToggleSwitch,\n Tooltip,\n} from \"@planningcenter/tapestry-react\"\nimport { lowerFirst, truncate } from \"lodash\"\nimport { createContext, useContext, useState } from \"react\"\n\nimport { OrganizationContext } from \"./contexts/organization_context\"\nimport History from \"./history\"\nimport HistoryModal from \"./history_modal\"\nimport * as alerts from \"./utils/alerts\"\nimport { getValidLogoName } from \"./utils/logos\"\nimport { dateLocalized, forbiddenText } from \"./utils/utils\"\n\nconst webhooksClient = new Client({ app: \"webhooks\", version: \"2022-10-20\" })\nconst peopleClient = new Client({ app: \"people\" })\n\ntype AutomationProps = {\n automation: AutomationInstance\n currentPersonCanCreate: boolean\n currentPersonId: number\n disabled?: boolean\n disabledReason?: string\n trigger: {\n event: AutomationTriggerEvent\n resource: EncryptedTriggerResource\n }\n updateAutomation: React.Dispatch<React.SetStateAction<AutomationInstance>>\n}\n\ntype IncomingAutomationProps = {\n automation: IncomingAutomationInstance\n}\n\ntype EditableAutomationContextType = {\n automation: AutomationInstance\n currentPersonCanCreate?: boolean\n currentPersonId?: number\n theme: object\n trigger?: {\n event: AutomationTriggerEvent\n resource: EncryptedTriggerResource\n }\n updateAutomation?: React.Dispatch<React.SetStateAction<AutomationInstance>>\n}\n\ntype IncomingAutomationContextType = {\n automation: IncomingAutomationInstance\n}\n\nconst AutomationContext = createContext<\n EditableAutomationContextType | IncomingAutomationContextType\n>(null)\n\nfunction EditableAutomation({\n updateAutomation,\n onDelete,\n theme,\n openHistoryNow = false,\n disabled,\n disabledReason,\n ...props\n}: AutomationProps & {\n disabled: boolean\n disabledReason: string\n onDelete: (id: number) => void\n openHistoryNow: boolean\n theme?: object\n}) {\n return (\n <AutomationWrapper\n theme={theme}\n updateAutomation={updateAutomation}\n {...props}\n >\n <Header>\n <Icons />\n <Manage\n onDelete={onDelete}\n openHistoryNow={openHistoryNow}\n disabled={disabled}\n disabledReason={disabledReason}\n />\n </Header>\n <Description />\n <EditableFooter />\n </AutomationWrapper>\n )\n}\n\nfunction IncomingAutomation(props: IncomingAutomationProps) {\n return (\n <AutomationWrapper automation={props.automation}>\n <Header>\n <Icons />\n <LinkToAutomation />\n </Header>\n <IncomingDescription />\n <Footer />\n </AutomationWrapper>\n )\n}\n\nfunction IncomingDescription() {\n const { automation } = useContext(\n AutomationContext\n ) as IncomingAutomationContextType\n\n const triggerEventDescription = automation.triggerEventDescription\n const { name, description } = parseDescription(automation.description)\n const cardOpacity = !automation.active ? 0.5 : undefined\n\n return (\n <StackView\n paddingVertical={token(\"--t-spacing-2\")}\n flex={1}\n opacity={cardOpacity}\n >\n <Heading\n level={3}\n size={token(\"--t-font-size-xl\")}\n weight={token(\"--t-font-weight-medium\")}\n marginBottom={token(\"--t-spacing-half\")}\n truncate\n >\n {name}\n </Heading>\n <StackView spacing={0.75}>\n <Text\n size={token(\"--t-font-size-sm\")}\n color={token(\"--t-text-color\")}\n lineHeight=\"1.2\"\n >\n {triggerEventDescription}, then {lowerFirst(name)}{\" \"}\n {conditionalSuffix(automation)}\n </Text>\n <Text\n size={token(\"--t-font-size-xs\")}\n color={token(\"--t-text-color-secondary\")}\n lineHeight=\"1.2\"\n >\n {truncate(optionallyPrettifyArchivedPrefix(description), {\n length: 160,\n separator: \" \",\n })}\n </Text>\n </StackView>\n </StackView>\n )\n}\n\nfunction LinkToAutomation() {\n const { automation } = useContext(\n AutomationContext\n ) as IncomingAutomationContextType\n\n return (\n <Button\n external\n iconLeft={{ name: \"general.newWindow\" }}\n variant=\"naked\"\n size=\"sm\"\n to={automation.triggerAdminUrl}\n disabled={!automation.canManage}\n tooltip={\n !automation.canManage\n ? \"You do not have access to this resource\"\n : undefined\n }\n color={token(\"--t-text-color-secondary\")}\n hover={{\n backgroundColor: \"highlight\",\n color: token(\"--t-text-color-secondary\"),\n }}\n >\n Manage\n </Button>\n )\n}\n\nfunction AutomationWrapper({\n automation,\n updateAutomation,\n children,\n theme,\n ...rest\n}: (AutomationProps | IncomingAutomationProps) & {\n children: React.ReactNode\n theme?: object\n updateAutomation?: (automation: AutomationInstance) => void\n}) {\n return (\n <AutomationContext.Provider\n value={{\n automation,\n theme,\n updateAutomation,\n ...rest,\n }}\n >\n <Card radius={4} padding={2}>\n {children}\n </Card>\n </AutomationContext.Provider>\n )\n}\n\nfunction Header({ children }: { children: React.ReactNode }) {\n const { automation } = useContext(AutomationContext)\n\n const cardOpacity = !automation.active ? 0.5 : undefined\n\n return (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n padding={0}\n distribution=\"space-between\"\n opacity={cardOpacity}\n >\n {children}\n </StackView>\n )\n}\n\nfunction Manage({\n onDelete,\n openHistoryNow = false,\n disabled,\n disabledReason,\n}: {\n disabled: boolean\n disabledReason: string\n onDelete: (id: number) => void\n openHistoryNow: boolean\n}) {\n const {\n automation,\n currentPersonCanCreate,\n currentPersonId,\n trigger,\n theme,\n updateAutomation,\n } = useContext(AutomationContext) as EditableAutomationContextType\n const [historyVisible, setHistoryVisible] = useState(openHistoryNow)\n const isActive = automation.active\n const { name } = parseDescription(automation.description)\n\n function showHistory() {\n setHistoryVisible(true)\n }\n\n function updateEventsStatus(newStatus: AutomationInstance[\"eventsStatus\"]) {\n updateAutomation((prev) => ({ ...prev, eventsStatus: newStatus }))\n }\n\n function handleToggleActive() {\n webhooksClient\n .patch({\n data: {\n _e: trigger.resource,\n data: {\n attributes: {\n active: !isActive,\n },\n },\n },\n url: `/automation_subscriptions/${automation.id}`,\n })\n .then((data: { data: { active: boolean } }) => {\n updateAutomation((prev) => ({ ...prev, active: data.data.active }))\n })\n .catch((error) => {\n const text =\n forbiddenText(error, \"pause\") ||\n `There was a problem ${\n isActive ? \"pausing\" : \"unpausing\"\n } this automation. Please try again in a few moments.`\n alerts.alertError.fire({\n text,\n title: \"Uh oh!\",\n })\n })\n }\n\n function handleReassign() {\n alerts.confirm\n .fire({\n text: \"This automation will run with your permission levels. Other administrators who can see this automation can grant it their permissions by reassigning it to themselves.\",\n title: \"Reassign automation?\",\n })\n .then(({ isConfirmed }) => {\n if (isConfirmed) {\n webhooksClient\n .post({\n data: {\n _e: trigger.resource,\n data: { attributes: {} },\n },\n url: `/automation_subscriptions/${automation.id}/self_assign`,\n })\n .then(({ data }) => fetchCurrentPersonAvatar(data))\n .then(({ subscription, avatar }) => {\n updateAutomation((prev) => ({\n ...prev,\n createdBy: { ...prev.createdBy, avatarUrl: avatar },\n createdById: subscription.createdById,\n createdByName: subscription.createdByName,\n }))\n })\n .catch((error) => {\n const text =\n forbiddenText(error, \"update\") ||\n \"There was a problem updating this automation. Please try again in a few moments.\"\n alerts.alertError.fire({\n text,\n title: \"Uh oh!\",\n })\n })\n }\n })\n }\n\n function handleDelete() {\n alerts.confirmDestroy\n .fire({\n confirmButtonText: \"Yes, delete automation\",\n text: `Are you sure you want to delete the \"${name}\" automation? This cannot be undone.`,\n title: \"Delete this automation?\",\n })\n .then(({ isConfirmed }) => {\n if (isConfirmed) onDelete(automation.id)\n })\n }\n\n return (\n <>\n <StackView axis=\"horizontal\" alignment=\"center\" spacing={0.75}>\n <Dropdown\n icon={{\n color: token(\"--t-icon-color\"),\n name: \"churchCenter.threeDots\",\n }}\n iconRight={false}\n title=\"Actions\"\n variant=\"naked\"\n size=\"md\"\n disabled={disabled}\n >\n <Dropdown.Item onSelect={() => showHistory()}>History</Dropdown.Item>\n {currentPersonCanCreate &&\n (automation.createdById === currentPersonId ? (\n <Dropdown.Item disabled={true}>\n <Tooltip\n placement=\"left\"\n openDelay={250}\n title=\"This automation is already assigned to you.\"\n >\n <Text>Reassign to me...</Text>\n </Tooltip>\n </Dropdown.Item>\n ) : (\n <Dropdown.Item onSelect={handleReassign}>\n Reassign to me...\n </Dropdown.Item>\n ))}\n <Dropdown.Item onSelect={handleDelete}>Delete...</Dropdown.Item>\n </Dropdown>\n <ToggleSwitch\n isChecked={isActive}\n size=\"sm\"\n onClick={handleToggleActive}\n tooltip={\n disabled\n ? disabledReason\n : isActive\n ? \"Pause automation\"\n : \"Enable automation\"\n }\n disabled={disabled}\n />\n </StackView>\n\n <HistoryModal\n open={historyVisible}\n onRequestClose={() => setHistoryVisible(false)}\n theme={theme}\n >\n <History\n automation={automation}\n triggerResource={trigger.resource}\n onEventsStatusChange={updateEventsStatus}\n onRequestClose={() => setHistoryVisible(false)}\n />\n </HistoryModal>\n </>\n )\n}\n\nfunction Icons() {\n const { automation } = useContext(AutomationContext)\n const triggerProductName = automation.name.split(\".\")[0]\n\n return (\n <StackView axis=\"horizontal\" alignment=\"center\" spacing={0.5}>\n <Logo\n markOnly={true}\n name={getValidLogoName(triggerProductName)}\n size=\"sm\"\n theme=\"color\"\n />\n <Icon name=\"general.rightArrow\" size={1.5} />\n <Logo\n markOnly={true}\n name={getValidLogoName(automation.operationAppName)}\n size=\"sm\"\n theme=\"color\"\n />\n </StackView>\n )\n}\nfunction Footer() {\n const { automation } = useContext(AutomationContext)\n const { dateFormat } = useContext(OrganizationContext)\n const createdBySuffix = !automation.createdBy?.id ? \"(deleted profile)\" : \"\"\n const createdByName = `${automation.createdByName} ${createdBySuffix}`\n\n const cardOpacity = !automation.active ? 0.5 : undefined\n\n return (\n <>\n <Divider marginHorizontal={-2} />\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n distribution=\"space-between\"\n paddingTop={1.75}\n spacing={token(\"--t-spacing-1\")}\n opacity={cardOpacity}\n >\n <Text\n size={token(\"--t-font-size-xs\")}\n color={token(\"--t-text-color-placeholder\")}\n whiteSpace=\"nowrap\"\n >\n Updated {dateLocalized(automation.createdAt, dateFormat)}\n </Text>\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-half\")}\n maxWidth=\"calc(100% - 136px)\"\n >\n {automation.createdBy?.avatarUrl && (\n <Avatar\n width={2}\n height={2}\n basis={2}\n key={createdByName}\n source={automation.createdBy.avatarUrl}\n />\n )}\n <Text size={5} truncate>\n {createdByName}\n </Text>\n </StackView>\n </StackView>\n </>\n )\n}\n\nfunction EditableFooter() {\n const { dateFormat } = useContext(OrganizationContext)\n const { automation, trigger, theme, updateAutomation } = useContext(\n AutomationContext\n ) as EditableAutomationContextType\n\n const createdBySuffix = !automation.createdBy?.id ? \"(deleted profile)\" : \"\"\n const createdByName = `${automation.createdByName} ${createdBySuffix}`\n\n const cardOpacity = !automation.active ? 0.5 : undefined\n const buttonProps = {\n color: token(\"--t-text-color-secondary\"),\n fontSize: token(\"--t-font-size-xs\"),\n fontWeight: token(\"--t-font-weight-normal\"),\n paddingHorizontal: token(\"--t-spacing-1\"),\n radius: \"pill\",\n size: \"xs\",\n variant: \"naked\",\n }\n const [historyProps, setHistoryProps] = useState({\n filter: null,\n historyVisible: false,\n })\n\n function renderSkippedHistory() {\n setHistoryProps({ filter: \"skipped\", historyVisible: true })\n }\n\n function renderFailedOrDuplicatedHistory() {\n setHistoryProps({ filter: \"failed,duplicated\", historyVisible: true })\n }\n\n function handleEventsStatusChange(\n newStatus: AutomationInstance[\"eventsStatus\"]\n ) {\n updateAutomation((prev) => ({ ...prev, eventsStatus: newStatus }))\n }\n\n return (\n <>\n <Divider marginHorizontal={-2} />\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n distribution=\"space-between\"\n paddingTop={1.75}\n spacing={token(\"--t-spacing-1\")}\n opacity={cardOpacity}\n >\n <Text\n size={token(\"--t-font-size-xs\")}\n color={token(\"--t-text-color-placeholder\")}\n whiteSpace=\"nowrap\"\n >\n Updated {dateLocalized(automation.createdAt, dateFormat)}\n </Text>\n\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-fourth\")}\n >\n {!!automation.eventsStatus?.skipped && (\n <Button\n {...buttonProps}\n aria-label={`${automation.eventsStatus.skipped} skipped`}\n onClick={renderSkippedHistory}\n tooltip={`${automation.eventsStatus.skipped?.toLocaleString()} skipped events`}\n >\n <Box\n backgroundColor={token(\"--t-fill-color-status-warning\")}\n marginRight={token(\"--t-spacing-half\")}\n radius=\"circle\"\n height=\"10px\"\n width=\"10px\"\n padding={token(\"--t-spacing-fourth\")}\n >\n <Icon\n name={\"services.pause\"}\n size={\"6px\"}\n title={\"Skipped\"}\n color=\"white\"\n />\n </Box>\n {`${automation.eventsStatus.skipped?.toLocaleString()}`}\n </Button>\n )}\n {!!automation.eventsStatus?.failed && (\n <Button\n {...buttonProps}\n aria-label={`${automation.eventsStatus.failed} failed`}\n iconLeft={{\n color: token(\"--t-icon-color-status-error\"),\n marginRight: token(\"--t-spacing-half\"),\n name: \"general.exclamationTriangle\",\n size: \"10px\",\n title: \"Failed\",\n }}\n onClick={renderFailedOrDuplicatedHistory}\n title={`${automation.eventsStatus.failed?.toLocaleString()}`}\n tooltip={`${automation.eventsStatus.failed?.toLocaleString()} failed events`}\n />\n )}\n </StackView>\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n distribution=\"end\"\n flex={1}\n spacing={token(\"--t-spacing-half\")}\n marginLeft=\"auto\"\n >\n {automation.createdBy?.avatarUrl && (\n <Avatar\n width={token(\"--t-element-size-md\")}\n height={token(\"--t-element-size-md\")}\n basis={token(\"--t-element-size-md\")}\n key={createdByName}\n source={automation.createdBy.avatarUrl}\n />\n )}\n <Text size={token(\"--t-font-size-sm\")} truncate>\n {createdByName}\n </Text>\n </StackView>\n </StackView>\n\n <HistoryModal\n open={historyProps.historyVisible}\n onRequestClose={() =>\n setHistoryProps({ filter: null, historyVisible: false })\n }\n theme={theme}\n >\n <History\n automation={automation}\n triggerResource={trigger.resource}\n filterWhere={historyProps.filter}\n onEventsStatusChange={handleEventsStatusChange}\n onRequestClose={() =>\n setHistoryProps({ filter: null, historyVisible: false })\n }\n />\n </HistoryModal>\n </>\n )\n}\n\nfunction Description() {\n const { automation, trigger } = useContext(\n AutomationContext\n ) as EditableAutomationContextType\n\n const { name, description } = parseDescription(automation.description)\n const cardOpacity = !automation.active ? 0.5 : undefined\n\n const triggerEventDescription = [\n \"When a person\",\n lowerFirst(trigger.event.description) + \",\",\n \"then\",\n lowerFirst(name),\n conditionalSuffix(automation),\n ].join(\" \")\n\n return (\n <StackView\n paddingVertical={token(\"--t-spacing-2\")}\n flex={1}\n opacity={cardOpacity}\n >\n <Heading\n level={3}\n size={token(\"--t-font-size-xl\")}\n weight={token(\"--t-font-weight-bold\")}\n marginBottom={token(\"--t-spacing-half\")}\n truncate\n >\n {name}\n </Heading>\n <StackView spacing={0.75}>\n <Text\n size={token(\"--t-font-size-sm\")}\n color={token(\"--t-text-color\")}\n lineHeight=\"1.2\"\n >\n {triggerEventDescription}\n </Text>\n <Text\n size={token(\"--t-font-size-xs\")}\n color={token(\"--t-text-color-secondary\")}\n lineHeight=\"1.2\"\n >\n {truncate(optionallyPrettifyArchivedPrefix(description), {\n length: 160,\n separator: \" \",\n })}\n </Text>\n </StackView>\n </StackView>\n )\n}\n\nfunction conditionalSuffix(automation: AutomationInstance) {\n return automation?.triggerParams?.useTriggerPersonOverride\n ? \"(also applies to joint donor)\"\n : \"\"\n}\n\nfunction parseDescription(description: string) {\n const match = /^(.+?)\\(([^()]*?)\\)$/.exec(description)\n\n if (match) {\n return { description: match[\"2\"], name: match[\"1\"].trim() }\n } else {\n return { name: description }\n }\n}\n\nfunction optionallyPrettifyArchivedPrefix(description: string) {\n if (description?.startsWith(\"[archived]\")) {\n return description.replace(\"[archived]\", \"[Archived]\")\n } else {\n return description\n }\n}\n\nasync function fetchCurrentPersonAvatar(subscription: AutomationInstance) {\n const {\n data: { avatar },\n } = await peopleClient.get({\n data: {\n fields: { Person: \"avatar\" },\n },\n url: \"me\",\n })\n\n return { avatar, subscription }\n}\n\nexport { EditableAutomation, IncomingAutomation }\n","import { Client } from \"@planningcenter/api-client\"\nimport { compact, uniq } from \"lodash\"\n\nconst webhooksClient = new Client({ app: \"webhooks\", version: \"2022-10-20\" })\nconst peopleClient = new Client({ app: \"people\" })\n\nasync function fetchAutomations(triggerResource: EncryptedTriggerResource) {\n const { data } = await webhooksClient.get({\n data: {\n _e: triggerResource,\n fields: {\n AutomationSubscription:\n \"id,description,created_at,created_by,operation_app_name,operation_definition_class_name,operation_params,active,created_by_name,name,trigger_admin_url,events_status,trigger_params\",\n Person: \"name\",\n },\n include: \"created_by\",\n },\n url: \"automation_subscriptions\",\n })\n\n return data\n}\n\nasync function fetchCreatorProfiles(subscriptions: AutomationInstance[]) {\n const personIds = compact(\n uniq(subscriptions.map((subscription) => subscription.createdById))\n )\n\n try {\n const { data: profiles } = await peopleClient.get({\n data: {\n fields: { Person: \"avatar\" },\n where: { id: personIds.join(\",\") },\n },\n url: \"people\",\n })\n return { profiles, subscriptions }\n } catch (error) {\n return { profiles: [], subscriptions }\n }\n}\n\nfunction mergeProfilesAndSubscriptions({\n profiles,\n subscriptions,\n}: {\n profiles: { avatar: string; id: number }[]\n subscriptions: AutomationInstance[]\n}) {\n const subscriptionsWithAvatars = subscriptions.map((subscription) => {\n const avatar = profiles.find(\n (profile) => profile.id === subscription.createdById\n )\n return {\n ...subscription,\n createdBy: { ...subscription.createdBy, avatarUrl: avatar?.avatar },\n }\n })\n\n return subscriptionsWithAvatars\n}\n\nasync function fetchPersonApps() {\n return peopleClient\n .get({\n data: {\n fields: { App: [\"name\"], PersonApp: [\"app\", \"allow_pco_login\"] },\n include: [\"app\"],\n },\n url: `/me/person_apps`,\n })\n .then(({ data }) => {\n return data\n .filter((personApp: PersonApp) => personApp.allowPcoLogin)\n .map((personApp: PersonApp) => personApp.app.name.toLowerCase())\n })\n}\n\nexport {\n fetchAutomations,\n fetchCreatorProfiles,\n fetchPersonApps,\n mergeProfilesAndSubscriptions,\n}\n","import { Client } from \"@planningcenter/api-client\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Box,\n Heading,\n Spinner,\n Summary,\n Text,\n TileView,\n} from \"@planningcenter/tapestry-react\"\nimport { truncate, upperFirst } from \"lodash\"\nimport { useEffect, useState } from \"react\"\n\nimport { IncomingAutomation } from \"./automation\"\nimport {\n fetchCreatorProfiles,\n fetchPersonApps,\n mergeProfilesAndSubscriptions,\n} from \"./utils/fetch-automations\"\nimport {\n deobfuscateDescriptions,\n pluralize,\n singularize,\n triggerResourceParts,\n} from \"./utils/utils\"\n\nconst webhooksClient = new Client({ app: \"webhooks\", version: \"2022-10-20\" })\n\nasync function fetchIncomingAutomations(encryptedParam) {\n const { data } = await webhooksClient.get({\n data: {\n _e: encryptedParam,\n fields: {\n AutomationSubscription:\n \"id,description,created_at,created_by,operation_app_name,operation_definition_class_name,operation_params,active,created_by_name,name,trigger_admin_url,trigger_resource,trigger_params\",\n Person: \"name\",\n },\n include: \"created_by\",\n },\n url: \"incoming_automation_subscriptions\",\n })\n\n return data\n}\n\nasync function fetchTriggerResources(automations) {\n // We can optimize the query by fetching all the resources at once if we know\n // that the endpoint supports querying by multiple ids. Otherwise, we'll have\n // to fetch each resource individually.\n const QUERYABLE_BY_MULTIPLE_IDS = {\n people: [\"forms\", \"lists\"],\n registrations: [\"events\"],\n services: [\"teams\"],\n }\n const NOT_QUERYABLE = [\"giving\"]\n\n const automationsByModel = automations.reduce((accumulator, automation) => {\n // registrations has a weird case of signup vs event\n const automationTriggerResource = automation.triggerResource.replace(\n /signup/,\n \"event\"\n )\n const { appName, resourceType, resourcePath, resourceId } =\n triggerResourceParts(automationTriggerResource)\n\n if (!accumulator[appName]) accumulator[appName] = {}\n if (!accumulator[appName][resourceType])\n accumulator[appName][resourceType] = {}\n if (!accumulator[appName][resourceType][\"resoucePath\"])\n accumulator[appName][resourceType][\"resourcePath\"] = resourcePath\n\n if (!accumulator[appName][resourceType][\"ids\"])\n accumulator[appName][resourceType][\"ids\"] = []\n\n accumulator[appName][resourceType][\"ids\"].push(resourceId)\n\n return accumulator\n }, {})\n\n const promises = Object.keys(automationsByModel).flatMap((appName) => {\n const automationsByResourceType = automationsByModel[appName]\n\n return Object.entries(automationsByResourceType).flatMap(\n ([resourceType, resourceParts]) => {\n const fetchFn = NOT_QUERYABLE.includes(appName)\n ? fetchNothing\n : QUERYABLE_BY_MULTIPLE_IDS[appName]?.includes(resourceType)\n ? fetchAllAtOnce\n : fetchOneAtATime\n\n return fetchFn({\n appName,\n ids: resourceParts[\"ids\"],\n resourcePath: resourceParts[\"resourcePath\"],\n resourceType,\n })\n }\n )\n })\n\n const results = await Promise.allSettled(promises)\n\n return {\n automations,\n triggerResources: collectSuccessfulResults(results),\n }\n}\n\nfunction collectSuccessfulResults(settledPromises) {\n return settledPromises\n .reduce((acc, result) => {\n if (result.status === \"fulfilled\") acc = acc.concat(result.value)\n\n return acc\n }, [])\n .flatMap((d) => d.data)\n}\n\nfunction fetchAllAtOnce({ appName, resourcePath, resourceType, ids }) {\n return fetchResourceName({\n appName,\n params: {\n where: { id: ids.join(\",\") },\n },\n path: resourcePath,\n resourceType,\n })\n}\n\nfunction fetchOneAtATime({ appName, resourcePath, resourceType, ids }) {\n return ids.map((id) =>\n fetchResourceName({\n appName,\n path: `${resourcePath}/${id}`,\n resourceType,\n })\n )\n}\n\nfunction fetchNothing(_props: object) {\n return new Promise((_, reject) => {\n reject()\n })\n}\n\n// TODO (maybe): move these to webhooks, return the verb in the API response,\n// so new events don't need a code change in both places\nfunction mapNameToVerb(messageName) {\n // e.g. \"groups.v2.events.membership.created\" => \"groups.membership.created\"\n const appResourceAction = messageName.replace(\"v2.events.\", \"\")\n\n switch (appResourceAction) {\n case \"groups.membership.created\":\n return \"joins\"\n case \"groups.membership.destroyed\":\n return \"leaves\"\n case \"people.list_result.created\":\n case \"services.team_person.created\":\n return \"is added to\"\n case \"people.list_result.destroyed\":\n case \"services.team_person.destroyed\":\n return \"is removed from\"\n case \"people.form_submission.created\":\n return \"submits\"\n case \"registrations.attendee.created\":\n return \"is registered as a new attendee for\"\n case \"registrations.attendee.cancelled\":\n return \"is canceled as an attendee for\"\n case \"registrations.registration.created\":\n return \"is the registration contact on a new registration for\"\n case \"registrations.registration.cancelled\":\n return \"is the registration contact on a canceled registration for\"\n default:\n return null\n }\n}\n\nfunction buildGivingDescription(automation: AutomationInstance) {\n const action = automation.name.replace(\"giving.v2.events.\", \"\")\n\n switch (action) {\n case \"donation.payment_successful\":\n return \"When a person gives\"\n case \"profile.first_donated_automation\":\n return \"When a person gives for the first time\"\n case \"recurring_donation.setup_successful\":\n return \"When a person sets up a recurring donation\"\n default:\n return null\n }\n}\n\nfunction buildDescription(automation, triggerResourceName) {\n const verb = mapNameToVerb(automation.name)\n\n const { resourceType } = triggerResourceParts(automation.triggerResource)\n\n if (!verb) {\n // No verb mapping for this message name, so just show something generic\n const resourceName = truncate(triggerResourceName, {\n length: 160,\n separator: \" \",\n })\n\n return `When the automation is triggered from ${singularize(\n resourceType\n )} \"${resourceName}\"`\n }\n\n return `When a person ${verb} ${singularize(\n resourceType\n )} \"${triggerResourceName}\"`\n}\n\nfunction fetchResourceName({\n appName,\n path,\n resourceType,\n params = {},\n}): Promise<any> {\n const client = new Client({ app: appName })\n const model = upperFirst(singularize(resourceType))\n\n return client.get({\n data: {\n fields: {\n [model]: [\"name\", \"name_or_description\"],\n },\n ...params,\n },\n url: path,\n })\n}\n\nfunction mergeTriggerResourceEventDescriptions({\n automations,\n triggerResources,\n operationApps,\n}) {\n return automations.map((automation) => {\n const { appName, resourceType, resourceId } = triggerResourceParts(\n automation.triggerResource\n )\n\n if (appName === \"giving\") {\n automation.triggerEventDescription = buildGivingDescription(automation)\n automation.canManage = operationApps.find((app) => app === \"giving\")\n\n return automation\n }\n\n // find the result that matches this automation\n const result = triggerResources.find(\n (tr) => tr.id.toString() == resourceId.toString()\n )\n\n const resourceName = result\n ? result.name || result.nameOrDescription\n : `[Hidden ${upperFirst(singularize(resourceType))}]`\n\n automation.triggerEventDescription = buildDescription(\n automation,\n resourceName\n )\n\n automation.canManage = !!result\n\n return automation\n })\n}\n\nfunction IncomingAutomations({\n encryptedParam,\n trigger,\n}: {\n encryptedParam: string\n trigger?: AutomationTrigger\n}) {\n const [loading, setLoading] = useState(true)\n const [automations, setAutomations] = useState<IncomingAutomationInstance[]>()\n\n useEffect(() => {\n fetchPersonApps().then((operationApps) => {\n fetchIncomingAutomations(encryptedParam)\n .then(fetchCreatorProfiles)\n .then(mergeProfilesAndSubscriptions)\n .then(deobfuscateDescriptions)\n .then(fetchTriggerResources)\n .then(({ automations, triggerResources }) =>\n mergeTriggerResourceEventDescriptions({\n automations,\n operationApps,\n triggerResources,\n })\n )\n .then(setAutomations)\n .then(() => setLoading(false))\n })\n }, [encryptedParam])\n\n const noResults = !loading && automations.length === 0\n\n return (\n <>\n <Box\n borderBottom={`1px solid ${token(\"--t-border-color\")}`}\n marginBottom={token(\"--t-spacing-2\")}\n marginHorizontal={-3}\n marginTop={trigger ? 12 : 0}\n paddingHorizontal={token(\"--t-spacing-3\")}\n paddingVertical={token(\"--t-spacing-2\")}\n >\n <Heading\n color={token(\"--t-text-color-headline\")}\n level={2}\n size={token(\"--t-font-size-lg\")}\n >\n {loading\n ? \"Incoming automations\"\n : pluralize(automations.length, \"incoming automation\")}\n </Heading>\n </Box>\n {noResults ? (\n <Text\n color={token(\"--t-text-color-secondary\")}\n marginVertical={token(\"--t-spacing-3\")}\n >\n Automations that perform actions on this resource will be listed here.\n </Text>\n ) : loading ? (\n <Summary\n image={<Spinner size=\"xl\" />}\n paddingVertical={10}\n title={\"Loading incoming automations...\"}\n />\n ) : (\n <TileView\n spacing={token(\"--t-spacing-3\")}\n marginVertical={token(\"--t-spacing-3\")}\n minCellWidth={45}\n >\n {automations.map((automation) => (\n <IncomingAutomation key={automation.id} automation={automation} />\n ))}\n </TileView>\n )}\n </>\n )\n}\n\nexport default IncomingAutomations\n","import { token } from \"@planningcenter/tapestry\"\nimport { Select, StackView } from \"@planningcenter/tapestry-react\"\nimport { groupBy, uniqBy } from \"lodash\"\n\nfunction operationDefinitionId(od: OperationDefinition) {\n return `OPERATION_${od.definitionClass}${od.definitionIdentifier || \"\"}`\n}\n\nfunction sectionId(section: string) {\n return `SECTION_${section}`\n}\n\nfunction idType(value: string) {\n if (value.startsWith(\"SECTION\")) {\n return \"section\"\n } else if (value.startsWith(\"OPERATION\")) {\n return \"operation\"\n } else if (!value) {\n return null\n } else {\n throw new Error(`Unexpected value: ${value}`)\n }\n}\n\nfunction renderOptionsWithoutConsideringGroup(\n options: { label: string; value: string | number }[]\n) {\n return options.map(({ label, value }) => (\n <Select.Option key={value} value={value}>\n {label}\n </Select.Option>\n ))\n}\n\nfunction renderOptions(\n options: { group?: string | null; label: string; value: string | number }[]\n) {\n const groupedOptions = groupBy(options, \"group\")\n const groupTypes = Object.keys(groupedOptions).sort()\n return groupTypes.map((gt) =>\n gt === \"null\" ? (\n renderOptionsWithoutConsideringGroup(groupedOptions[gt])\n ) : (\n <Select.OptionGroup key={gt} title={gt}>\n {renderOptionsWithoutConsideringGroup(groupedOptions[gt])}\n </Select.OptionGroup>\n )\n )\n}\n\nconst Definition = ({\n selectedOperation,\n onOperationDefinitionChange,\n operationDefinitions,\n}: {\n onOperationDefinitionChange: Function\n operationDefinitions: OperationDefinition[]\n selectedOperation: OperationDefinition\n}) => {\n const selectedSection = selectedOperation?.section\n\n const operationDefinitionsWithUniqueIds = operationDefinitions.map((od) => ({\n ...od,\n id: operationDefinitionId(od),\n }))\n\n const primaryOperations = operationDefinitionsWithUniqueIds.filter(\n (od) => od.section === null\n )\n\n const primarySectionOptions = uniqBy(operationDefinitions, \"section\")\n .filter((od) => !!od.section)\n .map((od) => ({\n group: od.sectionGroup,\n label: od.section,\n value: sectionId(od.section),\n }))\n\n const secondaryOperations = selectedSection\n ? operationDefinitionsWithUniqueIds.filter(\n (od) => od.section === selectedSection\n )\n : []\n\n function handleAnySelectChange({ selectedValue }) {\n switch (idType(selectedValue)) {\n case \"section\":\n onOperationDefinitionChange(\n operationDefinitions.find(\n (od) => sectionId(od.section) === selectedValue\n )\n )\n break\n case \"operation\":\n onOperationDefinitionChange(\n operationDefinitions.find(\n (od) => operationDefinitionId(od) === selectedValue\n )\n )\n break\n case null:\n onOperationDefinitionChange(null)\n break\n }\n }\n\n function renderOperations(operations: OperationDefinition[]) {\n const operationsAsOptions = operations.map((o) => ({\n group: o.group,\n label: o.description,\n value: o.id,\n }))\n\n return renderOptions(operationsAsOptions)\n }\n\n return (\n <StackView spacing={token(\"--t-spacing-1\")}>\n <Select\n emptyValue=\"Select an action\"\n id=\"select-action\"\n onChange={handleAnySelectChange}\n size=\"lg\"\n data-testid=\"operation-select\"\n >\n {renderOperations(primaryOperations)}\n {renderOptions(primarySectionOptions)}\n </Select>\n {secondaryOperations.length > 0 && (\n <Select\n defaultValue={secondaryOperations[0].id}\n onChange={handleAnySelectChange}\n size=\"lg\"\n >\n {renderOperations(secondaryOperations)}\n </Select>\n )}\n </StackView>\n )\n}\n\nexport default Definition\n","import { token } from \"@planningcenter/tapestry\"\nimport {\n Alert,\n Avatar,\n Badge,\n Box,\n Checkbox as TapestryCheckbox,\n Combobox as TapestryCombobox,\n DateField as TapestryDateField,\n HelperDrawer,\n Highlight,\n Icon,\n Input,\n Menu,\n NumberField as TapestryNumberField,\n Radio,\n Select as TapestrySelect,\n Spinner,\n StackView,\n Text,\n TextArea as TapestryTextArea,\n} from \"@planningcenter/tapestry-react\"\nimport { camelCase, debounce, groupBy, isEqual, sortBy, uniqBy } from \"lodash\"\nimport moment from \"moment\"\nimport { useCallback, useContext, useEffect, useMemo, useState } from \"react\"\n\nimport { OrganizationContext } from \"./contexts/organization_context\"\nimport {\n dateFNSFormat,\n dateLocalized,\n fieldListIdentifier,\n} from \"./utils/utils\"\n\nfunction fieldDependencies({\n field,\n selectedFieldOptions,\n}: {\n field: DefinitionField\n selectedFieldOptions: { [k: string]: any }\n}) {\n const dependsOn = field.dependsOn || []\n return dependsOn.reduce((acc, depKey) => {\n if (Object.prototype.hasOwnProperty.call(selectedFieldOptions, depKey)) {\n acc[camelCase(depKey)] = selectedFieldOptions[depKey]\n }\n return acc\n }, {})\n}\n\nfunction useMemoizedObject(generator) {\n const [memoizedObject, setMemoizedObject] = useState(generator)\n\n useEffect(() => {\n const newObject = generator()\n\n if (!isEqual(newObject, memoizedObject)) {\n setMemoizedObject(newObject)\n }\n }, [generator, memoizedObject])\n\n return memoizedObject\n}\n\nconst Field = ({\n canAccessPeople,\n field,\n onChange,\n value,\n selectedFieldOptions,\n loadListForField,\n loadedLists,\n loadingLists,\n}: {\n canAccessPeople: boolean\n field: DefinitionField\n loadListForField: LoadListForField\n loadedLists: { [k: string]: LoadedList[] }\n loadingLists: { [k: string]: boolean }\n onChange: Function\n selectedFieldOptions: { [k: string]: any }\n value: any\n}) => {\n const dependencies = useMemoizedObject(() =>\n fieldDependencies({ field, selectedFieldOptions })\n )\n\n useEffect(() => {\n if (field.listClass) {\n loadListForField({ dependencies, field })\n }\n }, [field, dependencies, loadListForField])\n\n const listOptions =\n field.list || loadedLists[fieldListIdentifier(field)] || []\n\n const actionAllowedOptions = listOptions.filter(\n (op) => !op.automationNotAllowed\n )\n\n const loading = field.listClass && loadingLists[fieldListIdentifier(field)]\n\n function renderField() {\n switch (field.kind) {\n case \"Select\":\n return (\n <Select\n fieldId={field.id}\n listOptions={actionAllowedOptions}\n onChange={onChange}\n value={value}\n description={field.description}\n />\n )\n case \"SelectSearch\":\n return (\n <SelectSearch\n fieldId={field.id}\n listOptions={actionAllowedOptions}\n onChange={onChange}\n value={value}\n />\n )\n case \"Checkbox\":\n return <Checkbox field={field} value={value} onChange={onChange} />\n case \"TextArea\":\n return <TextArea field={field} onChange={onChange} value={value} />\n\n case \"DateField\":\n return <DateField field={field} onChange={onChange} value={value} />\n case \"Checkboxes\":\n return (\n <Checkboxes\n fieldId={field.id}\n options={actionAllowedOptions}\n onChange={onChange}\n />\n )\n case \"NumberField\":\n return <NumberField field={field} onChange={onChange} value={value} />\n case \"PersonSearch\":\n return (\n <PersonSearch\n canAccessPeople={canAccessPeople}\n field={field}\n onChange={onChange}\n listOptions={listOptions}\n isLoading={loadingLists[fieldListIdentifier(field)]}\n loadListForField={loadListForField}\n value={value}\n />\n )\n case \"TextField\":\n return <TextField field={field} onChange={onChange} value={value} />\n case \"RadioButtons\":\n return (\n <RadioButtons\n field={field}\n options={listOptions}\n onChange={onChange}\n value={value}\n />\n )\n case \"StaticText\":\n return <Text dangerouslySetInnerHTML={{ __html: field.content }} />\n default:\n console.warn(`Unknown field kind \"${field.kind}\"`)\n return null\n }\n }\n\n return (\n <StackView marginBottom={2} spacing={0.5}>\n <Input.InputLabel\n color={token(\"--t-text-color-headline\")}\n fontSize={token(\"--t-font-size-sm\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n controls={field.id}\n >\n {field.description}\n {field.info && (\n <HelperDrawer.Toggle drawerId={`${field.id}_help`} marginLeft={1} />\n )}\n </Input.InputLabel>\n <Box>{loading ? <Loading /> : renderField()}</Box>\n {field.info && (\n <HelperDrawer\n id={`${field.id}_help`}\n marginTop={token(\"--t-spacing-half\")}\n >\n <Box dangerouslySetInnerHTML={{ __html: field.info }} />\n </HelperDrawer>\n )}\n </StackView>\n )\n}\n\nconst Select = ({\n fieldId,\n listOptions,\n onChange,\n value,\n description,\n}: {\n description?: string\n fieldId: string\n listOptions: LoadedList[]\n onChange: Function\n value: any\n}) => {\n const overridenEmptyValue = listOptions?.find(\n (option) => option.value === \"no-option\"\n )\n const groupedOptions = groupBy(listOptions, \"group\")\n const groupTypes = Object.keys(groupedOptions).sort()\n const renderOptions = () => {\n return groupTypes.map((gt) =>\n gt === \"null\" || gt === \"undefined\" ? (\n renderOptionsWithoutConsideringGroup(groupedOptions[gt])\n ) : (\n <TapestrySelect.OptionGroup key={gt} title={gt}>\n {renderOptionsWithoutConsideringGroup(groupedOptions[gt])}\n </TapestrySelect.OptionGroup>\n )\n )\n }\n\n const renderOptionsWithoutConsideringGroup = (\n items: { description: string; disabled?: boolean; value: string | number }[]\n ) => {\n return items.map((item) => (\n <TapestrySelect.Option\n key={item.value}\n value={item.value.toString()}\n disabled={item.disabled}\n >\n {item.description}\n </TapestrySelect.Option>\n ))\n }\n\n const handleSelectedValueChange = ({ selectedValue }) => {\n onChange({ fieldId, value: selectedValue })\n }\n\n const generatePrompt = (word: string) => {\n let prompt = `Select `\n if (!word) {\n prompt += \"a value\"\n } else if ([\"a\", \"e\", \"i\", \"o\", \"u\"].includes(word.charAt(0))) {\n prompt += `an ${word}`\n } else {\n prompt += `a ${word}`\n }\n return prompt\n }\n\n const renderEmptyValue = () => {\n if (renderOptions().length === 0) return \"No options available\"\n return (\n overridenEmptyValue?.description ||\n generatePrompt(description?.toLowerCase())\n )\n }\n\n return (\n <TapestrySelect\n id={fieldId}\n onChange={handleSelectedValueChange}\n disabled={renderOptions().length < 1}\n emptyValue={renderEmptyValue()}\n size=\"lg\"\n value={value || overridenEmptyValue?.value || null}\n placement=\"bottom-start\"\n >\n {renderOptions()}\n </TapestrySelect>\n )\n}\n\nconst SelectSearch = ({\n fieldId,\n listOptions,\n onChange,\n value,\n}: {\n fieldId: string\n listOptions: LoadedList[]\n onChange: Function\n value?: string\n}) => {\n const selectedOption: LoadedList = listOptions.find(\n (option) => option.value?.toString() === value\n )\n const selectedLabel = selectedOption?.description || \"\"\n const [prevSelectedLabel, setPrevSelectedLabel] = useState(\"\")\n const [query, setQuery] = useState(selectedLabel)\n const [showFilteredOptions, setShowFilteredOptions] = useState(false)\n const [showClearButton, setShowClearButton] = useState(false)\n\n if (selectedLabel !== prevSelectedLabel) {\n setPrevSelectedLabel(selectedLabel)\n setQuery(selectedLabel)\n setShowFilteredOptions(false)\n }\n\n let filteredOptions = sortBy(uniqBy(listOptions, \"value\"), \"group\")\n\n if (showFilteredOptions) {\n const formattedQuery = query.toLowerCase()\n filteredOptions = filteredOptions.filter((option) => {\n const optionText = `${option.description} ${option.group}`.toLowerCase()\n return optionText.includes(formattedQuery)\n })\n }\n\n const handleValueChange = (value: string) => {\n onChange({ fieldId, value })\n }\n\n return (\n <TapestryCombobox.Popover\n closeOnSelect\n closeButton={{ icon: { size: \"md\" } }}\n css={{\n \"[role='combobox']\": {\n cursor: listOptions.length > 0 ? \"pointer\" : \"not-allowed\",\n },\n }}\n cursor=\"pointer\"\n disabled={listOptions.length === 0}\n onBlur={() => {\n setShowClearButton(false)\n setQuery(selectedLabel)\n }}\n onChange={(e: React.ChangeEvent<HTMLInputElement>) => {\n setQuery(e.target.value)\n setShowFilteredOptions(true)\n setShowClearButton(true)\n }}\n onClear={\n showClearButton\n ? () => {\n setQuery(\"\")\n setShowFilteredOptions(false)\n }\n : undefined\n }\n onFocus={(e: React.ChangeEvent<HTMLInputElement>) => e.target.select()} // select all text on focus\n onSelect={(option: { description: string; value: string }) => {\n handleValueChange(option.value)\n setQuery(option.description)\n setShowFilteredOptions(false)\n setShowClearButton(false)\n }}\n openOnFocus\n paddingLeft={4.5}\n placeholder={\n listOptions.length > 0 ? \"Select an option\" : \"No options available\"\n }\n placement=\"bottom-start\"\n popoverProps={{\n matchWidths: \"minimum\",\n }}\n renderLeft={<Icon name=\"general.search\" size=\"md\" />}\n renderRight={<Icon name=\"general.downCaret\" />}\n size=\"lg\"\n value={query}\n >\n {listOptions.length > 0 && (\n <>\n {filteredOptions.length > 0 ? (\n filteredOptions.map((option: LoadedList, index: number) => {\n const isCurrent = option.value.toString() === value\n return (\n <TapestryCombobox.Item\n aria-label={option.description}\n disabled={option.disabled}\n index={index}\n key={option.value}\n paddingLeft={4.25}\n renderLeft={\n <Icon\n marginLeft={-0.5}\n name={isCurrent ? \"general.check\" : \"\"}\n size=\"sm\"\n />\n }\n role=\"option\"\n spacing={token(\"--t-spacing-1\")}\n value={{\n description: option.description,\n value: option.value.toString(),\n }}\n >\n <Text truncate>\n <Highlight text={option.description} query={query} />\n </Text>\n {option.group && (\n <Badge\n title={<Highlight text={option.group} query={query} />}\n size=\"sm\"\n marginLeft=\"auto\"\n />\n )}\n </TapestryCombobox.Item>\n )\n })\n ) : (\n <Menu.Item>\n <Text>No results for "{query}"</Text>\n </Menu.Item>\n )}\n </>\n )}\n </TapestryCombobox.Popover>\n )\n}\n\nconst PersonSearch = ({\n canAccessPeople,\n field,\n isLoading,\n listOptions,\n loadListForField,\n onChange,\n value,\n}: {\n canAccessPeople: boolean\n field: DefinitionField\n isLoading: boolean\n listOptions: LoadedList[]\n loadListForField: LoadListForField\n onChange: Function\n value?: string\n}) => {\n const immediateSearch = useCallback(\n (query: string) => {\n loadListForField({ dependencies: { query }, field })\n },\n [loadListForField]\n )\n\n const debouncedSearch = useMemo(\n () => debounce(immediateSearch, 300),\n [immediateSearch]\n )\n\n const search = useCallback(\n (query: string) => {\n if (!canAccessPeople) {\n return\n } else if (query.trim().length > 0) {\n debouncedSearch(query)\n } else {\n debouncedSearch.cancel()\n }\n },\n [debouncedSearch]\n )\n\n const myself: LoadedList = useMemo(\n () => ({ description: \"Myself\", value: \"self\" }),\n []\n )\n const allListOptions = useMemo(() => {\n if (!canAccessPeople) {\n return [myself]\n } else {\n return listOptions\n }\n }, [myself, listOptions])\n\n const selectedOption = allListOptions.find((option) => option.value === value)\n const selectedLabel = selectedOption?.description || \"\"\n const [query, _setQuery] = useState(selectedLabel)\n const [showClearButton, setShowClearButton] = useState(false)\n\n function setQuery(value: string) {\n _setQuery(value)\n search(value)\n if (value.trim().length === 0) {\n handleValueChange(null)\n }\n }\n\n const handleValueChange = (value: string) => {\n onChange({ fieldId: field.id, value })\n }\n\n return (\n <TapestryCombobox.Popover\n closeOnSelect\n closeButton={{ icon: { size: \"md\" } }}\n cursor=\"pointer\"\n onBlur={() => {\n setShowClearButton(false)\n setQuery(selectedLabel)\n }}\n onChange={(e: React.ChangeEvent<HTMLInputElement>) => {\n setQuery(e.target.value)\n setShowClearButton(true)\n }}\n onClear={\n showClearButton\n ? () => {\n setQuery(\"\")\n }\n : undefined\n }\n onFocus={(e: React.FocusEvent<HTMLInputElement>) => e.target.select()} // select all text on focus\n onSelect={(option: { description: string; value: string }) => {\n handleValueChange(option.value)\n setQuery(option.description)\n setShowClearButton(false)\n }}\n openOnFocus\n paddingLeft={4.5}\n placeholder=\"Search\"\n placement=\"bottom-start\"\n popoverProps={{\n matchWidths: \"minimum\",\n }}\n renderLeft={\n selectedOption && selectedOption.meta?.avatar ? (\n <Avatar size=\"sm\" source={selectedOption.meta.avatar} />\n ) : (\n <Icon name=\"general.search\" size=\"md\" />\n )\n }\n renderRight={<Icon name=\"general.downCaret\" />}\n size=\"lg\"\n value={query}\n >\n {canAccessPeople ? (\n query.trim().length > 0 ? (\n listOptions.length > 0 ? (\n listOptions.map((option, index) => {\n return (\n <TapestryCombobox.Item\n aria-label={option.description}\n index={index}\n key={option.value}\n paddingLeft={4.25}\n renderLeft={\n <Avatar\n marginLeft={-0.5}\n source={option.meta.avatar}\n size=\"sm\"\n />\n }\n role=\"option\"\n spacing={token(\"--t-spacing-1\")}\n value={option}\n >\n <Text truncate>\n <Highlight text={option.description} query={query} />\n </Text>\n </TapestryCombobox.Item>\n )\n })\n ) : isLoading ? (\n <TapestryCombobox.Item>\n <Text>Loading...</Text>\n </TapestryCombobox.Item>\n ) : (\n <TapestryCombobox.Item>\n <Text>No results</Text>\n </TapestryCombobox.Item>\n )\n ) : (\n <TapestryCombobox.Item>\n <Text>Type to search</Text>\n </TapestryCombobox.Item>\n )\n ) : (\n <TapestryCombobox.Item value={myself} index={0} role=\"option\">\n <Text>{myself.description}</Text>\n </TapestryCombobox.Item>\n )}\n </TapestryCombobox.Popover>\n )\n}\n\nconst Checkbox = ({\n field,\n value,\n onChange,\n}: {\n field: DefinitionField\n onChange: Function\n value: any\n}) => {\n const handleCheckedValueChange = (e) => {\n const value = e.target.checked\n onChange({ fieldId: field.id, value })\n }\n\n return (\n <TapestryCheckbox\n disabled={field.disabled}\n label={field.label}\n checked={value || false}\n onChange={handleCheckedValueChange}\n />\n )\n}\n\nconst TextArea = ({\n field,\n value,\n onChange,\n}: {\n field: DefinitionField\n onChange: Function\n value: any\n}) => {\n const handleTextChange = (e) => {\n const val = e.target.value\n onChange({ fieldId: field.id, value: val })\n }\n return (\n <Box>\n <TapestryTextArea\n value={value}\n placeholder={field.placeholder}\n onChange={handleTextChange}\n size=\"lg\"\n />\n </Box>\n )\n}\n\nconst DateField = ({\n field,\n value,\n onChange,\n}: {\n field: DefinitionField\n onChange: Function\n value: any\n}) => {\n const { dateFormat } = useContext(OrganizationContext)\n const [specificDate, setSpecificDate] = useState(false)\n const todaysValue = field.customValue || \"Day automation runs\"\n const dateBeforeValue = \"Day before automation runs\"\n const orgFormat = dateFNSFormat(dateFormat)\n const [dateFieldValue, setDateFieldValue] = useState(moment(value).toDate())\n const allowUnansweredOption = field.allowUnansweredOption ?? false\n\n const handleSelectChange = ({ selectedValue }) => {\n if (selectedValue === todaysValue || selectedValue === dateBeforeValue) {\n setSpecificDate(false)\n onChange({ fieldId: field.id, value: selectedValue })\n } else if (selectedValue === \"specific-date\") {\n onChange({ fieldId: field.id, value: null })\n setSpecificDate(true)\n } else {\n setSpecificDate(false)\n onChange({ fieldId: field.id, value: null })\n }\n }\n\n const handleValueChanged = (date: Date) => {\n onChange({ fieldId: field.id, value: dateLocalized(date, dateFormat) })\n setDateFieldValue(date)\n }\n\n return (\n <StackView axis=\"horizontal\">\n <TapestrySelect\n onChange={handleSelectChange}\n size=\"lg\"\n placement=\"bottom-start\"\n >\n <TapestrySelect.Option value={todaysValue}>\n {todaysValue}\n </TapestrySelect.Option>\n {!field.customValue && (\n <TapestrySelect.Option value={dateBeforeValue}>\n {dateBeforeValue}\n </TapestrySelect.Option>\n )}\n <TapestrySelect.Option value=\"specific-date\">\n A specific date\n </TapestrySelect.Option>\n {allowUnansweredOption && (\n <TapestrySelect.Option value=\"unanswered\">\n Unanswered\n </TapestrySelect.Option>\n )}\n </TapestrySelect>\n {specificDate && (\n <Box>\n <TapestryDateField\n defaultOpen\n formatValue={orgFormat}\n marginLeft={1}\n onChange={handleValueChanged}\n size=\"lg\"\n value={dateFieldValue}\n />\n </Box>\n )}\n </StackView>\n )\n}\n\nconst Checkboxes = ({\n fieldId,\n options,\n onChange,\n}: {\n fieldId: string\n onChange: Function\n options: { description: string; value: string | number }[]\n}) => {\n const [selectedValues, setSelectedValues] = useState({})\n\n const handleCheckboxesChange = (selectedValue, value) => {\n const newSelectedValues = { ...selectedValues }\n newSelectedValues[value] = selectedValue\n setSelectedValues(newSelectedValues)\n onChange({ fieldId, value: newSelectedValues })\n }\n\n return (\n <StackView spacing={1}>\n {options.map((item) => (\n <Box key={item.value}>\n <Input.InputLabel controls={`checkboxes_${fieldId}_${item.value}`}>\n {item.description || item.value}\n </Input.InputLabel>\n <TapestrySelect\n id={`checkboxes_${fieldId}_${item.value}`}\n onChange={({ selectedValue }) =>\n handleCheckboxesChange(selectedValue, item.value)\n }\n size=\"lg\"\n emptyValue={\"Don't change\"}\n >\n <TapestrySelect.Option value=\"check\">Check</TapestrySelect.Option>\n <TapestrySelect.Option value=\"uncheck\">\n Uncheck\n </TapestrySelect.Option>\n </TapestrySelect>\n </Box>\n ))}\n </StackView>\n )\n}\n\nconst NumberField = ({\n field,\n onChange,\n value,\n}: {\n field: DefinitionField\n onChange: Function\n value: string\n}) => {\n const minimumValue = field.minValue >= 0 ? field.minValue : 1\n const maximumValue =\n field.maxValue >= 1 && field.maxValue <= 365 ? field.maxValue : 365\n\n const [inputValue, setInputValue] = useState(Number(field.defaultValue) || 1)\n\n useEffect(() => {\n onChange({ fieldId: field.id, value: field.defaultValue || 1 })\n }, [field])\n\n return (\n <StackView>\n <Input.InputBox>\n <TapestryNumberField\n onChange={(value: string) => {\n const newNumberValue = Number(value) || 0\n setInputValue(newNumberValue)\n\n onChange({\n fieldId: field.id,\n value: Math.min(\n Math.max(newNumberValue, minimumValue),\n maximumValue\n ),\n })\n }}\n placeholder={field.placeholder}\n size=\"lg\"\n value={value}\n min={minimumValue}\n max={maximumValue}\n hasControls={true}\n />\n </Input.InputBox>\n {inputValue > maximumValue && (\n <Alert\n type=\"error\"\n paddingHorizontal={token(\"--t-spacing-1\")}\n paddingVertical={token(\"--t-spacing-half\")}\n display=\"inline-block\"\n marginTop={1.5}\n >\n <StackView axis=\"horizontal\" alignment=\"center\" spacing={0.75}>\n <Icon\n name=\"general.exclamationTriangle\"\n size=\"sm\"\n color=\"delete45\"\n />\n <Text size={token(\"--t-font-size-md\")}>\n Value cannot exceed {maximumValue}.\n </Text>\n </StackView>\n </Alert>\n )}\n </StackView>\n )\n}\n\nconst TextField = ({\n field,\n value,\n onChange,\n}: {\n field: DefinitionField\n onChange: Function\n value: any\n}) => {\n const handleTextChange = (e) => {\n const val = e.target.value\n onChange({ fieldId: field.id, value: val })\n }\n return (\n <Box>\n <Input\n size=\"lg\"\n value={value}\n id={field.id}\n placeholder={field.placeholder}\n onChange={handleTextChange}\n />\n </Box>\n )\n}\n\nconst RadioButtons = ({\n field,\n options,\n onChange,\n value,\n}: {\n field: DefinitionField\n onChange: Function\n options: LoadedList[]\n value: any\n}) => {\n const handleCheckedChange = (e) => {\n onChange({ fieldId: field.id, value: e.target.value })\n }\n\n return (\n <StackView marginTop={1} spacing={0.5}>\n {options.map((option) => (\n <Radio\n checked={value === option.value}\n key={option.value}\n label={option.description || option.value}\n onChange={handleCheckedChange}\n size=\"md\"\n value={option.value}\n />\n ))}\n </StackView>\n )\n}\n\nconst Loading = () => (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n paddingHorizontal={1.75}\n paddingVertical={token(\"--t-spacing-1\")}\n radius={token(\"--t-border-radius-md\")}\n border={`1px solid ${token(\"--t-border-color\")}`}\n >\n <Spinner size=\"xs\" />\n <Text fontSize={token(\"--t-font-size-md\")} lineHeight={2.75}>\n Loading\n </Text>\n </StackView>\n)\n\nexport default Field\n","import { useEffect } from \"react\"\n\nimport Field from \"./field\"\nimport { getRenderedFields } from \"./utils/utils\"\n\ninterface FieldsProps {\n canAccessPeople: boolean\n definitionFields: DefinitionField[]\n loadListForField: LoadListForField\n loadedLists: { [k: string]: LoadedList[] }\n loadingLists: { [k: string]: boolean }\n onChange: Function\n selectedFieldOptions: SelectedFieldOptions\n}\n\nconst Fields = ({\n canAccessPeople,\n definitionFields,\n onChange,\n selectedFieldOptions,\n loadListForField,\n loadedLists,\n loadingLists,\n}: FieldsProps): JSX.Element => {\n useEffect(() => {\n const newSelections = definitionFields.reduce((acc, field) => {\n if (Object.prototype.hasOwnProperty.call(field, \"defaultValue\")) {\n acc[field.id] = field.defaultValue\n } else if (field.kind === \"DateField\") {\n acc[field.id] = field.customValue || \"Date automation runs\"\n }\n\n return acc\n }, {})\n onChange(newSelections)\n }, [definitionFields, onChange])\n\n const renderableFields = getRenderedFields(\n definitionFields,\n selectedFieldOptions\n )\n\n const handleSelectedFieldOptionsChange = ({ fieldId, value }) => {\n const newSelections = { ...selectedFieldOptions }\n const dependents = definitionFields.filter((field) => field.dependsOn)\n dependents.map((dependent) => {\n if (dependent.dependsOn.includes(fieldId)) {\n const deeper = dependents.find((d) =>\n d.dependsOn.includes(dependent.id)\n )\n if (deeper) {\n delete newSelections[deeper.id]\n }\n delete newSelections[dependent.id]\n\n if (\n dependent.defaultValue !== undefined &&\n newSelections[dependent.id] === undefined\n ) {\n newSelections[dependent.id] = dependent.defaultValue\n }\n }\n })\n\n if (value === \"no-option\") {\n delete newSelections[fieldId]\n } else {\n newSelections[fieldId] = value\n }\n\n onChange({ ...newSelections })\n }\n\n if (definitionFields.length) {\n return (\n <div>\n {renderableFields.map((field) => {\n return (\n <Field\n canAccessPeople={canAccessPeople}\n field={field}\n key={field.id}\n onChange={handleSelectedFieldOptionsChange}\n value={selectedFieldOptions[field.id]}\n selectedFieldOptions={selectedFieldOptions}\n loadListForField={loadListForField}\n loadedLists={loadedLists}\n loadingLists={loadingLists}\n />\n )\n })}\n </div>\n )\n } else {\n return null\n }\n}\n\nexport default Fields\n","import { Client } from \"@planningcenter/api-client\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Alert,\n Box,\n Button,\n Checkbox,\n Icon,\n Input,\n Link,\n Select,\n Spinner,\n StackView,\n Text,\n} from \"@planningcenter/tapestry-react\"\nimport { cloneDeep, set } from \"lodash\"\nimport { useCallback, useEffect, useMemo, useRef, useState } from \"react\"\n\nimport Definition from \"./definition\"\nimport Fields from \"./fields\"\nimport * as alerts from \"./utils/alerts\"\nimport {\n buildDescription,\n fieldListIdentifier,\n getRenderedFields,\n} from \"./utils/utils\"\n\nconst client = new Client({\n app: \"people\",\n env: (window as any).railsEnv,\n version: \"LATEST\",\n})\nconst webhooksClient = new Client({\n app: \"webhooks\",\n env: (window as any).railsEnv,\n version: \"LATEST\",\n})\nconst errorAlertProps = {\n css: { borderRadius: token(\"--t-border-radius-md\") },\n paddingHorizontal: 1.75,\n paddingVertical: 1.25,\n type: \"error\",\n}\n\ntype TopbarResponse = {\n data: {\n apps: Array<{ name: string }>\n type: \"Topbar\"\n }\n}\n\nasync function getVisibleApps() {\n return client\n .get<TopbarResponse>({\n data: {\n fields: { Topbar: \"apps\" },\n },\n url: \"/me/topbar\",\n })\n .then(({ data }) => data.apps.map((a) => a.name))\n}\n\nasync function getWebhooksApps() {\n return webhooksClient\n .get<{ data: Array<{ name: string; type: \"OperationApp\" }> }>({\n data: { fields: { OperationApp: \"name\" } },\n url: \"/operation_apps\",\n })\n .then(({ data }) => data.map((a) => a.name))\n}\n\nasync function getOperationApps() {\n const [visibleApps, webhooksApps] = await Promise.all([\n getVisibleApps(),\n getWebhooksApps(),\n ])\n\n return visibleApps\n .filter((app) => webhooksApps.includes(app))\n .sort()\n .map((app: string) => ({ id: app.toLowerCase(), name: app }))\n}\n\nasync function getOperationDefinitions(app: string) {\n return webhooksClient\n .get({\n data: {\n fields: {\n OperationDefinition:\n \"definition_class,definition_fields,definition_identifier,description,group,section,section_group,footer_message\",\n },\n filter: \"automation_allowed\",\n },\n url: `/operation_apps/${app}/operation_definitions`,\n })\n .then(({ data }) => data)\n}\n\nasync function getListOptions({\n app,\n field,\n definitionIdentifier,\n dependencies,\n}: {\n app: string\n definitionIdentifier: string\n dependencies: { [k: string]: string }\n field: DefinitionField\n}): Promise<LoadedList[]> {\n if (field.kind === \"PersonSearch\") {\n const { data: people } = await client.get<{\n data: { avatar: string; id: number; name: string }[]\n }>({\n data: {\n fields: { Person: \"avatar,name\" },\n where: { search_name_or_email: dependencies.query, status: \"active\" },\n },\n url: \"/people\",\n })\n\n return people.map((p) => ({\n description: p.name,\n meta: { avatar: p.avatar },\n value: p.id.toString(),\n }))\n } else {\n const { data } = await webhooksClient.get({\n data: {\n ...dependencies,\n definitionIdentifier,\n fields: {\n OperationDefinitionList: \"values\",\n },\n },\n url: `/operation_apps/${app}/operation_definition_lists/${field.listClass}`,\n })\n return data.values\n }\n}\n\nconst NewAutomation = ({\n afterCreateOptions,\n blankStateLink,\n debugMode = false,\n defaultApp,\n description,\n onRequestClose,\n trigger,\n}: {\n afterCreateOptions?: AfterCreateOptions\n blankStateLink: string\n debugMode?: boolean\n defaultApp: string\n description: string\n onRequestClose: () => void\n trigger: AutomationTrigger\n}) => {\n const [selectedTriggerEvent, setSelectedTriggerEvent] = useState(\n trigger.events[0]\n )\n const [dynamicTriggerConditions, setDynamicTriggerConditions] = useState({})\n const [selectedApp, setSelectedApp] = useState(defaultApp)\n const [operationApps, setOperationApps] = useState<\n { id: string; name: string }[]\n >([])\n const [operationDefinitions, setOperationDefinitions] = useState<\n OperationDefinition[]\n >([])\n const [loadingOperationDefinitions, setLoadingOperationDefinitions] =\n useState(true)\n const [selectedDefinition, setSelectedDefinition] =\n useState<OperationDefinition>()\n const [selectedFieldOptions, setSelectedFieldOptions] =\n useState<SelectedFieldOptions>({})\n const [loadedLists, setLoadedLists] = useState<{ [k: string]: LoadedList[] }>(\n {}\n )\n const [loadingLists, setLoadingLists] = useState<{ [k: string]: boolean }>({})\n const [submitting, setSubmitting] = useState(false)\n const [error, setError] = useState<{\n automation?: string | string[]\n definitions?: string | string[]\n selected_definition?: string | string[]\n }>({})\n const [callAfterCreate, setCallAfterCreate] = useState(false)\n const [triggerParams, setTriggerParams] = useState<{ [k: string]: string }>(\n {}\n )\n const activeAppRef = useRef(null)\n\n const canAccessPeople = useMemo(\n () => operationApps.map((a) => a.id).includes(\"people\"),\n [operationApps]\n )\n\n const definitionIdentifier = selectedDefinition?.definitionIdentifier\n const dangerAlertPresent =\n selectedDefinition?.footerMessage?.kind === \"danger\"\n\n const loadListForField = useCallback<LoadListForField>(\n ({ field, dependencies }) => {\n setLoadingLists((prev) => ({\n ...prev,\n [fieldListIdentifier(field)]: true,\n }))\n getListOptions({\n app: selectedApp,\n definitionIdentifier,\n dependencies,\n field,\n })\n .then((ret) => {\n setLoadedLists((prev) => ({\n ...prev,\n [fieldListIdentifier(field)]: ret,\n }))\n setLoadingLists((prev) => ({\n ...prev,\n [fieldListIdentifier(field)]: false,\n }))\n })\n .catch((error) => setError({ selected_definition: error }))\n },\n [selectedApp, definitionIdentifier]\n )\n\n const handleChangeSelectedApp = (app: string) => {\n setSelectedApp(app)\n setLoadingOperationDefinitions(true)\n setOperationDefinitions([])\n activeAppRef.current = app\n setSelectedDefinition(null)\n setSelectedFieldOptions({})\n setError({})\n getOperationDefinitions(app)\n .then(setOperationDefinitions)\n .then(() => setLoadingOperationDefinitions(false))\n .catch((error) => setError({ definitions: error }))\n }\n\n const handleChangeTriggerEvent = (\n selectedValue: typeof selectedTriggerEvent\n ) => {\n setSelectedTriggerEvent(selectedValue)\n setDynamicTriggerConditions({})\n }\n\n useEffect(() => {\n setError({})\n getOperationApps().then((apps) => {\n setOperationApps(apps)\n const defaultSelection = apps.find((app) => app.id === defaultApp)\n ? defaultApp\n : apps[0].id\n setSelectedApp(defaultSelection)\n getOperationDefinitions(defaultSelection)\n .then((definitions) => {\n if (!activeAppRef.current) {\n setOperationDefinitions(definitions)\n setLoadingOperationDefinitions(false)\n }\n })\n .catch((error) => setError({ definitions: error }))\n })\n }, [defaultApp])\n\n useEffect(() => {\n setError({})\n }, [selectedFieldOptions])\n\n const triggerConditions = cloneDeep(\n \"conditions\" in selectedTriggerEvent\n ? selectedTriggerEvent.conditions\n : trigger.conditions\n )\n for (const key in dynamicTriggerConditions) {\n set(triggerConditions, key, dynamicTriggerConditions[key])\n }\n const dynamicConditions =\n \"dynamicConditions\" in selectedTriggerEvent\n ? selectedTriggerEvent.dynamicConditions\n : trigger.dynamicConditions\n\n const handleSelectedDefinitionChange = (\n newDefinition: OperationDefinition\n ) => {\n setSelectedDefinition(newDefinition)\n setError({})\n setSelectedFieldOptions({})\n }\n\n function getDescription(): string {\n const descriptionParts = buildDescription({\n loadedLists,\n selectedDefinition,\n selectedFieldOptions,\n })\n\n let description = descriptionParts.name\n\n if (descriptionParts.description) {\n description += ` (${descriptionParts.description})`\n }\n\n return description\n }\n\n function handleSubmit() {\n if (submitting) {\n return\n }\n const operation_params = { ...selectedFieldOptions }\n\n if (selectedDefinition.definitionIdentifier) {\n operation_params.definition_identifier =\n selectedDefinition.definitionIdentifier\n }\n\n const data = {\n _e: trigger.resource,\n data: {\n attributes: {\n description: getDescription(),\n name: selectedTriggerEvent.name,\n operation_app_name: selectedApp,\n operation_definition_class_name: selectedDefinition.definitionClass,\n operation_params,\n trigger_conditions: triggerConditions,\n trigger_params: triggerParams,\n },\n type: \"AutomationSubscription\",\n },\n }\n if (callAfterCreate) {\n alerts.confirmCreate\n .fire({\n cancelButtonText: \"Cancel\",\n confirmButtonText: \"Yes, perform action\",\n text: \"This will happen immediately after creating your new automation. Are you sure?\",\n title: `${afterCreateOptions.label}?`,\n })\n .then((result: { value: any }) => {\n if (result.value) {\n submitCreate(data)\n } else {\n setSubmitting(false)\n setCallAfterCreate(false)\n }\n })\n } else {\n submitCreate(data)\n }\n }\n\n function submitCreate(data) {\n setSubmitting(true)\n webhooksClient\n .post({\n data,\n url: \"/me/automation_subscriptions\",\n })\n .then(() => {\n if (afterCreateOptions?.onConfirm && callAfterCreate) {\n onRequestClose()\n afterCreateOptions.onConfirm({ ...data })\n } else {\n window.location.reload()\n }\n })\n .catch((error) => {\n setSubmitting(false)\n if (error.errors) {\n setError({ automation: error.errors })\n } else {\n alert(\"something even worse happened!\")\n }\n })\n }\n\n return (\n <StackView paddingTop={4} spacing={2}>\n {description && (\n <Box>\n <Text\n style={{\n color: token(\"--t-text-color\"),\n fontSize: token(\"--t-font-size-md\"),\n lineHeight: 1.65,\n marginBottom: token(\"--t-spacing-2\"),\n }}\n >\n {description}{\" \"}\n <Link external to={blankStateLink}>\n Learn more\n </Link>\n </Text>\n </Box>\n )}\n {error.automation && (\n <Alert {...errorAlertProps}>\n <Text>\n There was an error creating your automation. Please change your\n selections and try again or contact support if the problem persists.\n </Text>\n </Alert>\n )}\n <StackView spacing={1}>\n <Input.InputLabel\n color={token(\"--t-text-color\")}\n controls=\"select-trigger-event\"\n fontSize={token(\"--t-font-size-md\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n >\n When a person...\n </Input.InputLabel>\n <Select\n id=\"select-trigger-event\"\n onChange={({ selectedValue }) =>\n handleChangeTriggerEvent(selectedValue)\n }\n size=\"lg\"\n value={selectedTriggerEvent}\n >\n {trigger.events.map((triggerEvent, idx) => (\n <Select.Option\n key={`${triggerEvent.name}_${idx}`}\n value={triggerEvent}\n >\n {triggerEvent.description}\n </Select.Option>\n ))}\n </Select>\n\n {dynamicConditions?.length > 0 && (\n <Fields\n canAccessPeople={canAccessPeople}\n definitionFields={dynamicConditions}\n selectedFieldOptions={dynamicTriggerConditions}\n onChange={setDynamicTriggerConditions}\n loadedLists={{}}\n loadingLists={{}}\n loadListForField={() => null}\n />\n )}\n </StackView>\n\n <StackView spacing={1}>\n {operationApps.length > 0 ? (\n <Application\n selectedApp={selectedApp}\n operationApps={operationApps}\n onOperationAppChange={handleChangeSelectedApp}\n />\n ) : (\n <StackView spacing={1}>\n <Text\n color={token(\"--t-text-color-headline\")}\n fontSize={token(\"--t-font-size-md\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n >\n Then perform an action in...\n </Text>\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n paddingHorizontal={1.75}\n paddingVertical={token(\"--t-spacing-1\")}\n radius={4}\n border={`1px solid ${token(\"--t-border-color\")}`}\n >\n <Spinner size=\"xs\" />\n <Text fontSize={token(\"--t-font-size-md\")} lineHeight={2.75}>\n Loading\n </Text>\n </StackView>\n </StackView>\n )}\n {error.definitions ? (\n <Alert marginTop={token(\"--t-spacing-1\")} {...errorAlertProps}>\n <Text>\n There was a problem looking up automations. Please contact support\n if the problem persists.\n </Text>\n </Alert>\n ) : loadingOperationDefinitions ? (\n <LoadingOperationDefinitions />\n ) : (\n <Definition\n selectedOperation={selectedDefinition}\n operationDefinitions={operationDefinitions}\n onOperationDefinitionChange={handleSelectedDefinitionChange}\n />\n )}\n </StackView>\n\n {selectedDefinition &&\n (error.selected_definition ? (\n <Alert {...errorAlertProps}>\n <Text>\n There was a problem looking up automation options. Please contact\n support if the problem persists.\n </Text>\n </Alert>\n ) : (\n <>\n <Fields\n canAccessPeople={canAccessPeople}\n definitionFields={selectedDefinition.definitionFields || []}\n onChange={setSelectedFieldOptions}\n selectedFieldOptions={selectedFieldOptions}\n loadedLists={loadedLists}\n loadListForField={loadListForField}\n loadingLists={loadingLists}\n />\n {afterCreateOptions?.label && (\n <Checkbox\n disabled={\n submitting ||\n disableSubmit(selectedDefinition, selectedFieldOptions)\n }\n label={afterCreateOptions.label}\n checked={callAfterCreate}\n onChange={() => setCallAfterCreate(!callAfterCreate)}\n />\n )}\n {selectedTriggerEvent?.triggerParams?.map((param, idx) => (\n <Checkbox\n key={`${param.key}_${idx}`}\n label={param.description}\n checked={\n (triggerParams && triggerParams[param.key]) ||\n param.defaultValue\n }\n onChange={(e) => {\n setTriggerParams((prev) => ({\n ...prev,\n [`${param.key}`]: e.target.checked,\n }))\n }}\n />\n ))}\n {dangerAlertPresent && (\n <Alert {...errorAlertProps}>\n <StackView axis=\"horizontal\" spacing={1.5}>\n <Icon\n size={token(\"--t-element-size-lg\")}\n name=\"general.exclamationTriangle\"\n color={token(\"--t-icon-color-status-error\")}\n />\n <Text\n dangerouslySetInnerHTML={{\n __html: selectedDefinition.footerMessage?.html,\n }}\n />\n </StackView>\n </Alert>\n )}\n </>\n ))}\n\n {debugMode && (\n <pre>\n {JSON.stringify(\n {\n description: selectedDefinition && getDescription(),\n loadedLists,\n selectedDefinition,\n selectedFieldOptions,\n triggerConditions,\n },\n null,\n 4\n )}\n </pre>\n )}\n\n <StackView\n alignment=\"center\"\n axis=\"horizontal\"\n borderTop={`1px solid ${token(\"--t-border-color\")}`}\n distribution=\"end\"\n marginTop={2}\n marginHorizontal={-4}\n paddingHorizontal={4}\n paddingTop={3}\n spacing={2}\n >\n <Button\n color={token(\"--t-text-color-headline\")}\n // for temporary backwards compatibility\n data-modal-close\n fontWeight={token(\"--t-font-weight-normal\")}\n onClick={onRequestClose}\n size=\"md\"\n title=\"Cancel\"\n variant=\"naked\"\n />\n <Button\n disabled={\n submitting ||\n dangerAlertPresent ||\n disableSubmit(selectedDefinition, selectedFieldOptions)\n }\n onClick={handleSubmit}\n size=\"md\"\n theme=\"primary\"\n title={getButtonText(selectedDefinition, selectedFieldOptions)}\n variant=\"fill\"\n data-testid=\"create-automation\"\n />\n </StackView>\n </StackView>\n )\n}\n\nfunction disableSubmit(\n selectedDefinition: OperationDefinition,\n selectedFieldOptions: SelectedFieldOptions\n) {\n if (selectedDefinition) {\n const renderedFields = getRenderedFields(\n selectedDefinition.definitionFields,\n selectedFieldOptions\n )\n\n const requiredFields = renderedFields.filter((field) => field.required)\n const selectFields = renderedFields.filter((field) => fieldIsSelect(field))\n\n return (\n !requiredFields.every((field) =>\n fieldIsFilled(field, selectedFieldOptions)\n ) ||\n !selectFields.every((field) => fieldIsFilled(field, selectedFieldOptions))\n )\n } else {\n return true\n }\n}\n\nfunction fieldIsSelect(field: DefinitionField) {\n return field.kind === \"Select\" || field.kind === \"SelectSearch\"\n}\n\nfunction fieldIsFilled(\n field: DefinitionField,\n selectedFieldOptions: SelectedFieldOptions\n) {\n if (fieldIsSelect(field)) {\n return selectedFieldOptions.hasOwnProperty(field.id)\n } else {\n return (\n selectedFieldOptions.hasOwnProperty(field.id) &&\n selectedFieldOptions[field.id] &&\n selectedFieldOptions[field.id].toString().trim() !== \"\"\n )\n }\n}\n\nfunction getNextRequiredDescription(\n selectedDefinition: OperationDefinition,\n selectedFieldOptions: SelectedFieldOptions\n) {\n if (!selectedDefinition?.definitionFields) return\n\n const renderedFields = getRenderedFields(\n selectedDefinition.definitionFields,\n selectedFieldOptions\n )\n\n for (const field of renderedFields) {\n if (field.required && !fieldIsFilled(field, selectedFieldOptions))\n return field.description\n }\n}\n\nfunction getButtonText(\n selectedDefinition: OperationDefinition,\n selectedFieldOptions: SelectedFieldOptions\n) {\n const nextRequiredDescription = getNextRequiredDescription(\n selectedDefinition,\n selectedFieldOptions\n )\n\n if (!selectedDefinition) {\n return \"Select an action\"\n } else if (nextRequiredDescription) {\n return `Select a${\n nextRequiredDescription.charAt(0).match(/[aeiou]/i) ? \"n\" : \"\"\n } ${nextRequiredDescription.toLowerCase()}`\n } else {\n return \"Create automation\"\n }\n}\n\nconst Application = ({\n onOperationAppChange,\n operationApps,\n selectedApp,\n}: {\n onOperationAppChange: (selectedValue: string) => void\n operationApps: Array<{ id: string; name: string }>\n selectedApp: string\n}) => {\n const handleChange = ({ selectedValue }) => {\n onOperationAppChange(selectedValue)\n }\n\n return (\n <StackView spacing={1}>\n <Input.InputLabel\n color={token(\"--t-text-color-headline\")}\n controls=\"select-product\"\n fontSize={token(\"--t-font-size-md\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n >\n Then perform an action in...\n </Input.InputLabel>\n <Select\n autoFocus\n id=\"select-product\"\n onChange={handleChange}\n size=\"lg\"\n value={selectedApp}\n >\n {operationApps.map((app) => (\n <Select.Option key={app.id} value={app.id}>\n {app.name}\n </Select.Option>\n ))}\n </Select>\n </StackView>\n )\n}\n\nconst LoadingOperationDefinitions = () => (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n paddingHorizontal={1.75}\n paddingVertical={token(\"--t-spacing-1\")}\n radius={token(\"--t-border-radius-md\")}\n border={`1px solid ${token(\"--t-border-color\")}`}\n >\n <Spinner size=\"xs\" />\n <Text fontSize={token(\"--t-font-size-md\")} lineHeight={2.75}>\n Loading\n </Text>\n </StackView>\n)\n\nexport default NewAutomation\n","import { token } from \"@planningcenter/tapestry\"\nimport {\n Button,\n Heading,\n Modal,\n StackView,\n ThemeProvider,\n} from \"@planningcenter/tapestry-react\"\nimport React from \"react\"\nimport { createPortal } from \"react-dom\"\n\nfunction CloseModalIcon({\n onClick,\n}: {\n onClick: React.MouseEventHandler\n}): JSX.Element {\n return (\n <Button\n as=\"button\"\n height={token(\"--t-element-size-md\")}\n icon={{ color: token(\"--t-icon-color-dim\"), name: \"general.x\" }}\n onClick={onClick}\n size={\"sm\"}\n title=\"Close\"\n variant=\"naked\"\n />\n )\n}\n\nfunction NewAutomationModal({\n children,\n onRequestClose,\n open,\n theme,\n}: {\n children: React.ReactNode\n onRequestClose: () => void\n open: boolean\n theme: object\n}): React.ReactPortal | JSX.Element {\n return createPortal(\n <ThemeProvider theme={theme}>\n <Modal\n open={open}\n onRequestClose={onRequestClose}\n maxWidth={75}\n boxShadow=\"0 0 20px rgba(0, 0, 0, 0.15)\"\n padding={token(\"--t-spacing-4\")}\n paddingBottom={token(\"--t-spacing-3\")}\n radius={token(\"--t-border-radius-lg\")}\n zIndex={10009}\n >\n <StackView\n axis=\"horizontal\"\n distribution=\"space-between\"\n alignment=\"center\"\n >\n <Heading\n level={2}\n color={token(\"--t-text-color-headline\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n fontSize={token(\"--t-font-size-2xl\")}\n lineHeight=\"1.4\"\n >\n Create automation\n </Heading>\n <CloseModalIcon onClick={onRequestClose} />\n </StackView>\n {children}\n </Modal>\n <style>{`\n .swal2-container.swal2-backdrop-show { z-index: 10001 }\n `}</style>\n </ThemeProvider>,\n document.body\n )\n}\n\nexport default NewAutomationModal\n","import * as churchCenter from \"@planningcenter/icons/paths/church-center\"\nimport * as logomark from \"@planningcenter/icons/paths/logomark\"\nimport * as services from \"@planningcenter/icons/paths/services\"\n\nexport const icons = {\n churchCenter,\n logomark,\n services,\n}\n","import { Client } from \"@planningcenter/api-client\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Box,\n Button,\n Heading,\n Icon,\n Spinner,\n StackView,\n Summary,\n Text,\n ThemeProvider,\n TileView,\n} from \"@planningcenter/tapestry-react\"\nimport { useEffect, useState } from \"react\"\nimport sortBy from \"lodash/sortBy\"\n\nimport SvgAutomations from \"./assets/svg_automations\"\nimport { EditableAutomation } from \"./automation\"\nimport { OrganizationContext } from \"./contexts/organization_context\"\nimport IncomingAutomations from \"./incoming_automations\"\nimport NewAutomation from \"./new_automation\"\nimport NewAutomationModal from \"./new_automation_modal\"\nimport styles from \"./styles.scss\"\nimport * as alerts from \"./utils/alerts\"\nimport {\n fetchAutomations,\n fetchCreatorProfiles,\n mergeProfilesAndSubscriptions,\n} from \"./utils/fetch-automations\"\nimport { icons } from \"./utils/theme\"\nimport {\n deobfuscateDescriptions,\n pluralize,\n forbiddenText,\n} from \"./utils/utils\"\n\nconst webhooksClient = new Client({ app: \"webhooks\", version: \"2022-10-20\" })\n\nfunction Header({\n afterCreateOptions,\n automations,\n blankStateLink,\n canCreate,\n defaultApp,\n description,\n hasActiveAutomations,\n loading,\n onPauseAutomations,\n theme,\n trigger,\n}: {\n afterCreateOptions?: AfterCreateOptions\n automations: AutomationInstance[]\n blankStateLink: string\n canCreate: boolean\n defaultApp: string\n description: string\n hasActiveAutomations: boolean\n loading: boolean\n onPauseAutomations: Function\n theme: object\n trigger: AutomationTrigger\n}) {\n const [newModalVisible, setNewModalVisible] = useState(false)\n const isPaused = canCreate && !hasActiveAutomations\n\n const activeCount = automations.filter(\n (automation) => automation.active\n ).length\n const pausedCount = automations.filter(\n (automation) => !automation.active\n ).length\n\n return (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n backgroundColor={\n isPaused ? token(\"--t-fill-color-status-warning-ghost\") : undefined\n }\n borderBottom={\n isPaused\n ? undefined\n : `1px solid ${token(\"--t-border-color\")}`\n }\n data-testid=\"automations-header\"\n distribution=\"space-between\"\n marginHorizontal={-3}\n marginBottom={token(\"--t-spacing-2\")}\n marginTop={-3}\n paddingHorizontal={token(\"--t-spacing-3\")}\n paddingVertical={token(\"--t-spacing-2\")}\n spacing={token(\"--t-spacing-2\")}\n wrap\n zIndex={2}\n >\n {canCreate && !hasActiveAutomations ? (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n marginHorizontal={1}\n spacing={1}\n >\n <Icon\n size={2}\n color={token(\"--t-icon-color-status-warning\")}\n name=\"general.exclamationTriangle\"\n />\n <Heading\n color={token(\"--t-text-color-headline\")}\n level={2}\n size={token(\"--t-font-size-lg\")}\n >\n Automations are currently paused\n </Heading>\n </StackView>\n ) : (\n <Heading\n color={token(\"--t-text-color-headline\")}\n level={2}\n size={token(\"--t-font-size-lg\")}\n >\n {loading\n ? \"Active automations\"\n : pluralize(activeCount, \"active automation\")}\n {pausedCount > 0 ? ` (${pausedCount} paused)` : \"\"}\n </Heading>\n )}\n {canCreate &&\n (hasActiveAutomations ? (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n >\n {automations.length > 0 && (\n <Button onClick={onPauseAutomations} variant=\"outline\">\n Pause automations\n </Button>\n )}\n <Button\n theme=\"primary\"\n variant=\"fill\"\n onClick={() => setNewModalVisible(true)}\n >\n Create automation\n </Button>\n <NewAutomationModal\n open={newModalVisible}\n onRequestClose={() => setNewModalVisible(false)}\n theme={theme}\n >\n <NewAutomation\n description={description}\n blankStateLink={blankStateLink}\n defaultApp={defaultApp}\n trigger={trigger}\n onRequestClose={() => setNewModalVisible(false)}\n afterCreateOptions={afterCreateOptions}\n />\n </NewAutomationModal>\n </StackView>\n ) : (\n <Box>\n <StackView axis=\"horizontal\" alignment=\"center\" spacing={1}>\n <Button\n onClick={onPauseAutomations}\n theme=\"primary\"\n variant=\"outline\"\n >\n Enable automations\n </Button>\n <Button\n theme=\"primary\"\n disabled\n tooltip={{\n title: \"Automations must be enabled to create new ones\",\n }}\n >\n Create automation\n </Button>\n </StackView>\n </Box>\n ))}\n </StackView>\n )\n}\n\nexport default function Automations({\n afterCreateOptions,\n blankStateDescription,\n blankStateLink = \"https://pcopeople.zendesk.com/hc/en-us/articles/217582148-Automations\",\n currentPersonId,\n currentPersonCanCreate,\n defaultApp,\n incomingAutomationsParam,\n theme,\n trigger,\n currentOrganization,\n permissionDeniedReason = \"You need permissions of Editor or above to add an automation.\",\n disabled = false,\n disabledReason = \"Not allowed\",\n}: {\n afterCreateOptions?: AfterCreateOptions\n blankStateDescription: string\n blankStateLink?: string\n currentOrganization: {\n dateFormat: string\n olsonTimeZone: string\n twentyFourHourTime: boolean\n }\n currentPersonCanCreate: boolean\n currentPersonId: number\n defaultApp: string\n incomingAutomationsParam?: string\n permissionDeniedReason?: string\n theme?: object\n trigger?: AutomationTrigger\n disabled?: boolean\n disabledReason?: string\n}) {\n useEffect(() => {\n if (!trigger) return setLoading(false)\n fetchAutomations(trigger.resource)\n .then(fetchCreatorProfiles)\n .then(mergeProfilesAndSubscriptions)\n .then(deobfuscateDescriptions)\n .then(setAutomations)\n .then(() => setLoading(false))\n }, [trigger?.resource])\n\n const [automations, setAutomations] = useState([])\n const [loading, setLoading] = useState(true)\n const [newModalVisible, setNewModalVisible] = useState(false)\n\n const { dateFormat, twentyFourHourTime, olsonTimeZone } = currentOrganization\n\n const params = new URLSearchParams(window.location.search)\n\n const automationId = params.get(\"automation_id\")\n\n // make sure necessary icons are added to theme\n const customTheme = { ...theme, ...{ icons: { ...icons } } }\n\n useEffect(() => {\n document.body.toggleAttribute(\"data-loading-automations\", loading)\n }, [loading])\n\n const hasActiveAutomations = automations.length\n ? automations.some((a) => a.active)\n : true\n\n function handleDelete(id: number) {\n webhooksClient\n .delete({\n data: { _e: trigger.resource },\n url: `/automation_subscriptions/${id}`,\n })\n .then(() =>\n setAutomations(automations.filter((automation) => automation.id !== id))\n )\n .catch((error) => {\n const text =\n forbiddenText(error, \"delete\") ||\n \"There was a problem deleting this automation. Please try again in a few moments.\"\n alerts.alertError.fire({\n text,\n title: \"Uh oh!\",\n })\n })\n }\n\n function handlePauseAutomations() {\n webhooksClient\n .post({\n data: {\n data: {\n attributes: {\n _e: trigger.resource,\n active: !hasActiveAutomations,\n },\n },\n },\n url: \"/pause_automations\",\n })\n .then(() => {\n window.location.reload()\n })\n }\n\n const BlankStateHeadingProps = {\n color: token(\"--t-text-color\"),\n level: 2,\n size: token(\"--t-font-size-2xl\"),\n weight: token(\"--t-font-weight-bold\"),\n }\n\n const BlankStateTextProps = {\n color: token(\"--t-text-color-secondary\"),\n lineHeight: 3,\n size: token(\"--t-font-size-md\"),\n }\n\n function automationTriggerEvent(automation: AutomationInstance) {\n return trigger.events.find((event) => event.name === automation.name)\n }\n\n const handleUpdateAutomation =\n (originalAutomation: AutomationInstance) =>\n (newState: React.SetStateAction<AutomationInstance>) => {\n const updated =\n typeof newState == \"function\" ? newState(originalAutomation) : newState\n const newAutomations = [\n ...automations.filter((automation) => automation.id !== updated.id),\n updated,\n ]\n\n setAutomations(newAutomations)\n }\n\n return (\n <ThemeProvider theme={customTheme}>\n <OrganizationContext.Provider\n value={{ dateFormat, olsonTimeZone, twentyFourHourTime }}\n >\n {trigger && (\n <Header\n automations={automations}\n blankStateLink={blankStateLink}\n canCreate={currentPersonCanCreate && !disabled}\n loading={loading}\n defaultApp={defaultApp}\n description={blankStateDescription}\n theme={customTheme}\n trigger={trigger}\n hasActiveAutomations={hasActiveAutomations}\n onPauseAutomations={handlePauseAutomations}\n afterCreateOptions={afterCreateOptions}\n />\n )}\n {loading ? (\n <Summary\n image={<Spinner size=\"xl\" />}\n paddingVertical={10}\n title={\"Loading automations...\"}\n />\n ) : !trigger ? (\n <></>\n ) : (\n <Box data-testid=\"automations-section\">\n {automations?.length > 0 ? (\n <TileView spacing={3} marginVertical={3} minCellWidth={45}>\n {sortBy(automations, \"id\").map((a) => (\n <EditableAutomation\n key={a.id}\n automation={a}\n updateAutomation={handleUpdateAutomation(a)}\n onDelete={handleDelete}\n theme={customTheme}\n openHistoryNow={a.id === Number(automationId)}\n trigger={{\n event: automationTriggerEvent(a),\n resource: trigger.resource,\n }}\n currentPersonId={currentPersonId}\n currentPersonCanCreate={currentPersonCanCreate}\n disabled={disabled}\n disabledReason={disabledReason}\n />\n ))}\n </TileView>\n ) : (\n <StackView\n margin={token(\"--t-spacing-6\")}\n spacing={token(\"--t-spacing-2\")}\n alignment=\"center\"\n mediaQueries={{\n lg: {\n axis: \"horizontal\",\n distribution: \"center\",\n spacing: token(\"--t-spacing-6\"),\n },\n }}\n >\n <Box\n css={{\n \".symbol\": {\n height: \"100%\",\n width: \"100%\",\n },\n }}\n maxWidth={24}\n mediaQueries={{\n lg: {\n maxWidth: 40,\n },\n }}\n >\n <SvgAutomations />\n </Box>\n <StackView\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n maxWidth={45}\n mediaQueries={{\n lg: {\n alignment: \"start\",\n textAlign: \"left\",\n },\n }}\n textAlign=\"center\"\n >\n {currentPersonCanCreate ? (\n <>\n <Heading {...BlankStateHeadingProps}>\n Add an automation\n </Heading>\n <StackView\n alignment=\"center\"\n marginBottom={token(\"--t-spacing-1\")}\n mediaQueries={{\n lg: {\n alignment: \"start\",\n },\n }}\n spacing={1}\n >\n <Text {...BlankStateTextProps}>\n {blankStateDescription}\n </Text>\n </StackView>\n <StackView\n axis=\"horizontal\"\n spacing={token(\"--t-spacing-1\")}\n >\n <Button\n variant=\"outline\"\n to={blankStateLink}\n color={`${token(\n \"--t-text-color-status-neutral\"\n )} !important`}\n >\n Learn more\n </Button>\n <Button\n as=\"button\"\n theme=\"primary\"\n variant=\"fill\"\n onClick={() => setNewModalVisible(true)}\n >\n Create automation\n </Button>\n </StackView>\n <NewAutomationModal\n open={newModalVisible}\n onRequestClose={() => setNewModalVisible(false)}\n theme={customTheme}\n >\n <NewAutomation\n defaultApp={defaultApp}\n description={blankStateDescription}\n blankStateLink={blankStateLink}\n onRequestClose={() => setNewModalVisible(false)}\n trigger={trigger}\n afterCreateOptions={afterCreateOptions}\n />\n </NewAutomationModal>\n </>\n ) : (\n <>\n <Heading {...BlankStateHeadingProps}>Automations</Heading>\n <Text {...BlankStateTextProps}>\n {permissionDeniedReason}\n </Text>\n </>\n )}\n </StackView>\n </StackView>\n )}\n </Box>\n )}\n {incomingAutomationsParam && (\n <IncomingAutomations\n encryptedParam={incomingAutomationsParam}\n trigger={trigger}\n />\n )}\n </OrganizationContext.Provider>\n <style>{styles}</style>\n </ThemeProvider>\n )\n}\n"],"names":["SvgAutomations","React","createElement","id","xmlns","viewBox","className","opacity","d","fill","x","y","width","height","rx","ry","transform","OrganizationContext","createContext","dateFormat","olsonTimeZone","twentyFourHourTime","Swal__default","mixin","standardAlertOptions","Swal","successAlertOptions","alertError","errorAlertOptions","confirm","standardConfirmOptions","confirmDestroy","destroyConfirmOptions","confirmCreate","createConfirmOptions","deobfuscateDescriptions","subscriptions","Promise","all","map","subscription","_temp","includes","operationDefinitionClassName","isDeobfuscatable","resolve","deobfuscatedDescription","_temp3","description","_temp2","fetchWorkflow","workflowId","peopleClient","get","data","fields","Workflow","where","url","catch","name","then","e","reject","operationParams","workflow","workflowName","archivedAt","replace","fieldDefinitionId","definitionIdentifier","match","FieldDefinition","FieldOption","include","fetchFieldDefinition","fieldDefinition","values","dataType","Object","entries","action","value","fieldOptions","find","fieldOption","parseInt","capitalize","join","toString","customFieldOptionDescription","_deobfuscatedDescript","string","charAt","toUpperCase","slice","Client","app","version","fieldListIdentifier","field","listClass","kind","obfuscateDescriptionName","definition","definitionClass","hasOwnProperty","object","key","prototype","call","getListForField","loadedLists","list","Error","JSON","stringify","getRenderedFields","definitionFields","selectedFieldOptions","filter","renderIf","conditionKey","keys","isBoolean","describeSelectedFields","selectedDefinition","workflow_id_WorkflowsList","sensitiveString","o","workflow_id","obfuscateSelectedFieldDescriptions","label","momentDateFormat","format","dateLocalized","date","momentDate","moment","isValid","pluralize","count","word","singularize","triggerResourceParts","triggerResource","triggerParts","split","appName","resourceId","length","resourcePath","resourceType","forbiddenText","error","errors","status","fetchPeopleWhoTriggeredEvents","events","personIds","eventPersonId","body","recover","result","fetchPeople","people","_catch","Person","fetchEvents","automationId","params","webhooksClient","_e","Delivery","Event","order","STATUS","delivered","failed","ignored","pending","skipped","mergePeopleAndEvents","mergedData","reduce","personId","foundPerson","p","push","person","event","History","automation","filterWhere","onEventsStatusChange","loading","paginationProps","refresh","setParams","_","setError","useState","setLoading","eventPages","setEventPages","meta","setMeta","offset","resetOffset","perPage","totalCount","setOffset","currentPage","Math","floor","onPageChange","pageNum","totalPages","ceil","useCallback","usePagination","useEffect","per_page","pages","bubbleErrorToBoundary","undefined","useEvents","useContext","filteringEvents","automationCreatedRecently","diff","numDaysSince","createdAt","automationBeganOn","historyPreservationAlert","columns","cell","EventStatusBadge","css","padding","header","utcOffset","momentDateTimeFormat","Link","to","maxWidth","EventStatusMessage","flex","Fragment","RetryEventButton","IgnoreEventButton","refreshHistory","textAlign","minWidth","StackView","spacing","token","Heading","level","size","color","weight","Text","italic","Box","minHeight","alignItems","axis","distribution","Input","InputLabel","fontWeight","controls","Select","emptyValue","onChange","selectedValue","title","Option","Button","iconLeft","onClick","theme","variant","maxHeight","overflow","DataTable","_extends","empty","alignment","marginTop","marginBottom","svg","fontSize","loadingTitle","bodyCell","lineHeight","bodyRow","rowData","backgroundColor","headerCell","headerRow","setStatus","retryTitleFromStatus","statusIcon","post","attributes","response","eventsStatus","alerts","fire","text","disabled","badgeColors","border","badgeIcon","badgeTitle","Badge","background","foreground","paddingLeft","paddingRight","radius","renderLeft","Icon","marginLeft","stroke","strokeAlign","strokeWeight","lastDelivery","message","delivery","ERRORS","default","duplicated_event","failed_without_deliveries","whiteSpace","ToggleableDetails","details","responseBody","parse","parsedErrors","responseErrors","deliveryFailureReason","statusMessage","fontStyle","paddingTop","children","open","setOpen","inline","was","fontFamily","ErrorBoundary","Component","constructor","props","super","handleContactSupport","this","onRequestClose","window","openHelpdesk","state","hasError","static","render","Alert","type","marginVertical","boxShadow","style","CloseModalIcon","as","icon","HistoryModal","createPortal","ThemeProvider","Modal","paddingBottom","document","VALID_LOGO_NAMES","getValidLogoName","kebabName","kebabCase","isValidLogoName","fetchCurrentPersonAvatar","avatar","AutomationContext","EditableAutomation","updateAutomation","onDelete","openHistoryNow","disabledReason","AutomationWrapper","Header","Icons","Manage","Description","EditableFooter","IncomingAutomation","LinkToAutomation","IncomingDescription","Footer","triggerEventDescription","parseDescription","cardOpacity","active","paddingVertical","truncate","lowerFirst","conditionalSuffix","optionallyPrettifyArchivedPrefix","separator","external","triggerAdminUrl","canManage","tooltip","hover","rest","Provider","Card","currentPersonCanCreate","currentPersonId","trigger","historyVisible","setHistoryVisible","isActive","Dropdown","iconRight","Item","onSelect","createdById","Tooltip","placement","openDelay","isConfirmed","resource","prev","createdBy","avatarUrl","createdByName","confirmButtonText","ToggleSwitch","isChecked","patch","newStatus","triggerProductName","Logo","markOnly","operationAppName","Divider","marginHorizontal","Avatar","basis","source","buttonProps","paddingHorizontal","historyProps","setHistoryProps","toLocaleString","marginRight","triggerParams","useTriggerPersonOverride","exec","trim","startsWith","fetchPersonApps","App","PersonApp","personApp","allowPcoLogin","toLowerCase","fetchCreatorProfiles","compact","uniq","profiles","mergeProfilesAndSubscriptions","profile","fetchTriggerResources","automations","QUERYABLE_BY_MULTIPLE_IDS","registrations","services","NOT_QUERYABLE","automationsByModel","accumulator","automationTriggerResource","promises","flatMap","resourceParts","fetchNothing","fetchAllAtOnce","fetchOneAtATime","ids","allSettled","results","triggerResources","settledPromises","acc","concat","fetchIncomingAutomations","encryptedParam","AutomationSubscription","fetchResourceName","path","_props","client","model","upperFirst","IncomingAutomations","setAutomations","operationApps","buildGivingDescription","tr","resourceName","nameOrDescription","triggerResourceName","verb","messageName","mapNameToVerb","buildDescription","mergeTriggerResourceEventDescriptions","noResults","borderBottom","Summary","image","Spinner","TileView","minCellWidth","operationDefinitionId","od","sectionId","section","renderOptionsWithoutConsideringGroup","options","renderOptions","groupedOptions","groupBy","sort","gt","OptionGroup","Definition","selectedOperation","onOperationDefinitionChange","operationDefinitions","selectedSection","operationDefinitionsWithUniqueIds","primaryOperations","primarySectionOptions","uniqBy","group","sectionGroup","secondaryOperations","handleAnySelectChange","idType","renderOperations","operations","defaultValue","Field","canAccessPeople","loadListForField","loadingLists","dependencies","generator","memoizedObject","setMemoizedObject","newObject","isEqual","useMemoizedObject","dependsOn","depKey","camelCase","fieldDependencies","listOptions","actionAllowedOptions","op","automationNotAllowed","info","HelperDrawer","Toggle","drawerId","Loading","fieldId","SelectSearch","Checkbox","TextArea","DateField","Checkboxes","NumberField","PersonSearch","isLoading","TextField","RadioButtons","dangerouslySetInnerHTML","__html","content","console","warn","renderField","overridenEmptyValue","option","groupTypes","TapestrySelect","items","item","handleSelectedValueChange","prompt","generatePrompt","selectedOption","selectedLabel","prevSelectedLabel","setPrevSelectedLabel","query","setQuery","showFilteredOptions","setShowFilteredOptions","showClearButton","setShowClearButton","filteredOptions","sortBy","formattedQuery","TapestryCombobox","Combobox","Popover","closeOnSelect","closeButton","cursor","onBlur","target","onClear","onFocus","select","handleValueChange","openOnFocus","placeholder","popoverProps","matchWidths","renderRight","index","isCurrent","role","Highlight","Menu","immediateSearch","debouncedSearch","useMemo","debounce","search","cancel","myself","_setQuery","TapestryCheckbox","checked","TapestryTextArea","specificDate","setSpecificDate","todaysValue","customValue","dateBeforeValue","orgFormat","dateFieldValue","setDateFieldValue","toDate","allowUnansweredOption","handleSelectChange","TapestryDateField","defaultOpen","formatValue","selectedValues","setSelectedValues","handleCheckboxesChange","newSelectedValues","minimumValue","minValue","maximumValue","maxValue","inputValue","setInputValue","Number","InputBox","TapestryNumberField","newNumberValue","min","max","hasControls","display","handleCheckedChange","Radio","Fields","newSelections","renderableFields","handleSelectedFieldOptionsChange","dependents","dependent","deeper","getOperationDefinitions","OperationDefinition","getWebhooksApps","OperationApp","a","getVisibleApps","Topbar","apps","env","railsEnv","errorAlertProps","borderRadius","NewAutomation","afterCreateOptions","blankStateLink","debugMode","defaultApp","selectedTriggerEvent","setSelectedTriggerEvent","dynamicTriggerConditions","setDynamicTriggerConditions","selectedApp","setSelectedApp","setOperationApps","setOperationDefinitions","loadingOperationDefinitions","setLoadingOperationDefinitions","setSelectedDefinition","setSelectedFieldOptions","setLoadedLists","setLoadingLists","submitting","setSubmitting","callAfterCreate","setCallAfterCreate","setTriggerParams","activeAppRef","useRef","dangerAlertPresent","footerMessage","search_name_or_email","OperationDefinitionList","getListOptions","ret","selected_definition","visibleApps","webhooksApps","getOperationApps","defaultSelection","definitions","current","triggerConditions","cloneDeep","conditions","set","dynamicConditions","getDescription","descriptionParts","submitCreate","onConfirm","location","reload","alert","handleChangeTriggerEvent","triggerEvent","idx","Application","onOperationAppChange","LoadingOperationDefinitions","newDefinition","disableSubmit","param","html","borderTop","operation_params","definition_identifier","operation_app_name","operation_definition_class_name","trigger_conditions","trigger_params","cancelButtonText","getButtonText","renderedFields","requiredFields","required","selectFields","fieldIsSelect","every","fieldIsFilled","nextRequiredDescription","getNextRequiredDescription","autoFocus","handleChange","NewAutomationModal","zIndex","icons","churchCenter","logomark","canCreate","hasActiveAutomations","onPauseAutomations","newModalVisible","setNewModalVisible","isPaused","activeCount","pausedCount","wrap","blankStateDescription","incomingAutomationsParam","currentOrganization","permissionDeniedReason","fetchAutomations","URLSearchParams","customTheme","toggleAttribute","some","handleDelete","delete","BlankStateHeadingProps","BlankStateTextProps","originalAutomation","newState","updated","newAutomations","margin","mediaQueries","lg"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"core-automations.umd.js","sources":["../../src/utils/pco-api-root.ts","../../src/assets/svg_automations.tsx","../../src/contexts/organization_context.tsx","../../src/utils/alerts.ts","../../src/utils/utils.ts","../../src/history.tsx","../../src/history_modal.tsx","../../src/utils/logos.ts","../../src/automation.tsx","../../src/utils/fetch-automations.ts","../../src/incoming_automations.tsx","../../src/definition.tsx","../../src/field.tsx","../../src/fields.tsx","../../src/new_automation.tsx","../../src/new_automation_modal.tsx","../../src/utils/theme.ts","../../src/automations.tsx"],"sourcesContent":["// Derives the API root URL from the current page's location, so that API\n// requests always use the same protocol as the page (preventing mixed content\n// errors when the page is served over HTTPS).\n//\n// For real hostnames (anything with a dot), the leading subdomain is replaced\n// with \"api\": e.g. people.pco.test → api.pco.test,\n// pco-box.pco.dev → api.pco.dev, people.planningcenteronline.com →\n// api.planningcenteronline.com.\n//\n// Hostnames without a dot (e.g. \"localhost\" in jsdom/test environments) fall\n// back to the production API with https, since there is no real subdomain to\n// derive from and no actual network request is made in tests.\nexport function pcoApiRoot(app: string): string {\n const { protocol, hostname } = window.location\n if (!hostname.includes(\".\")) {\n return `https://api.planningcenteronline.com/${app}/v2`\n }\n return `${protocol}//${hostname.replace(/^[^.]+/, \"api\")}/${app}/v2`\n}\n","const SvgAutomations = () => (\n <svg\n id=\"automations_blank\"\n data-name=\"Automations Blank\"\n xmlns=\"http://www.w3.org/2000/svg\"\n viewBox=\"0 0 111.112 84.832\"\n className=\"symbol\"\n >\n <title>Automations</title>\n <g opacity=\"0.6\">\n <path\n d=\"M107.784,46.051A57.416,57.416,0,0,1,85.26,75.058c-9.7,6.247-20.045,7.792-31.912,5.185-11.74-2.638-23.339-8-32.92-13.088-9.51-5.342-17-10.236-18.863-17.925C-.26,41.753,3.737,31.4,13.347,21.194,22.85,11.162,37.968,1.853,55.948.321,73.8-1.476,90.2,4.478,99.608,13.164,109.257,21.9,111.921,33.784,107.784,46.051Z\"\n fill=\"#e1f0f9\"\n className=\"svg-background-blob\"\n />\n </g>\n <path\n d=\"M81,27.269v31.8a2.685,2.685,0,0,1-2.685,2.685H44.564a2.685,2.685,0,0,1-2.685-2.685V15.425a2.685,2.685,0,0,1,2.685-2.685h21.91a2.681,2.681,0,0,1,1.9.786L80.217,25.371A2.685,2.685,0,0,1,81,27.269Z\"\n fill=\"#fff\"\n />\n <path\n d=\"M68.479,13.633v9.8a2.035,2.035,0,0,0,2.035,2.034h9.877Z\"\n fill=\"#c9d8e2\"\n />\n <rect\n x=\"51.214\"\n y=\"41.285\"\n width=\"20.221\"\n height=\"2.791\"\n rx=\"1.395\"\n ry=\"1.395\"\n fill=\"#dae5ed\"\n />\n <rect\n x=\"51.214\"\n y=\"48.434\"\n width=\"20.221\"\n height=\"2.791\"\n rx=\"1.395\"\n ry=\"1.395\"\n fill=\"#dae5ed\"\n />\n <rect\n x=\"51.214\"\n y=\"34.136\"\n width=\"20.221\"\n height=\"2.791\"\n rx=\"1.395\"\n ry=\"1.395\"\n fill=\"#dae5ed\"\n />\n <rect\n x=\"11.771\"\n y=\"44.005\"\n width=\"50.915\"\n height=\"6.664\"\n transform=\"translate(-22.93 44.557) rotate(-49.171)\"\n fill=\"#454942\"\n />\n <path\n d=\"M56.283,30.38l-7.557,8.745a5.968,5.968,0,0,0-2.005-2.734,6.292,6.292,0,0,0-3.036-1.624l7.555-8.743a6.275,6.275,0,0,1,3.038,1.624A5.959,5.959,0,0,1,56.283,30.38Z\"\n fill=\"#fcc846\"\n />\n <path\n d=\"M58.088,28.29l-7.556,8.745a5.968,5.968,0,0,0-2-2.734,6.3,6.3,0,0,0-3.036-1.624l7.555-8.743a6.274,6.274,0,0,1,3.037,1.624A5.959,5.959,0,0,1,58.088,28.29Z\"\n fill=\"#48a5e5\"\n />\n <path\n d=\"M58.724,10.432l1.17,2.7a2.129,2.129,0,0,0,1.4,1.207l2.843.765a.73.73,0,0,1,.1,1.375l-2.7,1.17a2.125,2.125,0,0,0-1.207,1.4L59.56,21.89a.73.73,0,0,1-1.374.1l-1.17-2.7a2.125,2.125,0,0,0-1.4-1.206l-2.843-.766a.73.73,0,0,1-.1-1.374l2.7-1.17a2.121,2.121,0,0,0,1.206-1.4l.766-2.844A.73.73,0,0,1,58.724,10.432Z\"\n fill=\"#fcc846\"\n />\n <path\n d=\"M44.544,19.294l1.024.868a.968.968,0,0,0,.814.21l1.316-.261a.333.333,0,0,1,.319.541l-.868,1.024a.968.968,0,0,0-.21.814l.261,1.316a.333.333,0,0,1-.541.319l-1.024-.868a.968.968,0,0,0-.814-.21l-1.316.261a.333.333,0,0,1-.319-.541l.868-1.024a.967.967,0,0,0,.21-.814L44,19.613A.333.333,0,0,1,44.544,19.294Z\"\n fill=\"#fcc846\"\n />\n <path\n d=\"M64.223,25.729l.869,2.005a1.575,1.575,0,0,0,1.036.895l2.109.568a.542.542,0,0,1,.075,1.02l-2,.868a1.576,1.576,0,0,0-.9,1.036l-.568,2.11a.541.541,0,0,1-1.019.074L62.955,32.3a1.572,1.572,0,0,0-1.036-.895l-2.109-.568a.542.542,0,0,1-.075-1.02l2.005-.868a1.572,1.572,0,0,0,.895-1.036L63.2,25.8A.541.541,0,0,1,64.223,25.729Z\"\n fill=\"#fcc846\"\n />\n </svg>\n)\n\nexport default SvgAutomations\n","import { createContext } from \"react\"\n\nexport const OrganizationContext = createContext({\n dateFormat: null,\n olsonTimeZone: null,\n twentyFourHourTime: null,\n})\n","import {\n createConfirmOptions,\n destroyConfirmOptions,\n errorAlertOptions,\n standardAlertOptions,\n standardConfirmOptions,\n successAlertOptions,\n} from \"@planningcenter/sweetalert2\"\nimport Swal from \"sweetalert2/dist/sweetalert2\"\n\nexport const alert = Swal.mixin(standardAlertOptions)\nexport const alertSuccess = Swal.mixin(successAlertOptions)\nexport const alertError = Swal.mixin(errorAlertOptions)\nexport const confirm = Swal.mixin(standardConfirmOptions)\nexport const confirmDestroy = Swal.mixin(destroyConfirmOptions)\nexport const confirmCreate = Swal.mixin(createConfirmOptions)\n","import { Client } from \"@planningcenter/api-client\"\nimport { isBoolean } from \"lodash\"\nimport moment from \"moment\"\n\nimport { pcoApiRoot } from \"./pco-api-root\"\n\nexport async function deobfuscateDescriptions(\n subscriptions: AutomationInstance[]\n) {\n return Promise.all(\n subscriptions.map(async (subscription) => {\n if (isDeobfuscatable(subscription)) {\n subscription.description = await deobfuscatedDescription(subscription)\n }\n return subscription\n })\n )\n}\n\nfunction isDeobfuscatable(subscription: AutomationInstance) {\n const DEOBFUSCATABLE_OPERATION_DEFINITION_CLASS_NAMES = [\n \"AddToWorkflowOperationDefinition\",\n \"CustomFieldBooleanOperationDefinition\",\n \"CustomFieldCheckboxesOperationDefinition\",\n \"CustomFieldDateOperationDefinition\",\n \"CustomFieldNumberOperationDefinition\",\n \"CustomFieldSelectOperationDefinition\",\n \"CustomFieldStringOperationDefinition\",\n \"CustomFieldTextOperationDefinition\",\n ]\n\n return DEOBFUSCATABLE_OPERATION_DEFINITION_CLASS_NAMES.includes(\n subscription.operationDefinitionClassName\n )\n}\n\nasync function deobfuscatedDescription(subscription: AutomationInstance) {\n let description = \"\"\n if (\n subscription.operationDefinitionClassName ===\n \"AddToWorkflowOperationDefinition\"\n ) {\n const data = await fetchWorkflow(subscription.operationParams.workflowId)\n const workflow = data[0]\n\n if (workflow?.name) {\n let workflowName\n\n if (workflow.archivedAt) {\n workflowName = `[archived] ${workflow.name}`\n } else {\n workflowName = workflow.name\n }\n\n description = subscription.description.replace(\n \"[Hidden Workflow]\",\n workflowName\n )\n }\n } else {\n // custom field\n const fieldDefinitionId =\n subscription.operationParams.definitionIdentifier.match(\n /(\\d+)_field_definition/\n )[1]\n const fieldDefinition = await fetchFieldDefinition(fieldDefinitionId)\n if (fieldDefinition.name) {\n description = subscription.description.replace(\n \"[Hidden Custom Field]\",\n fieldDefinition.name\n )\n description +=\n subscription.operationParams.values ||\n fieldDefinition.dataType !== \"checkboxes\"\n ? ` (${customFieldOptionDescription(subscription, fieldDefinition)})`\n : \"\"\n }\n }\n return description || subscription.description\n}\n\nfunction customFieldOptionDescription(\n subscription: AutomationInstance,\n fieldDefinition: {\n dataType: string\n fieldOptions: { id: number; value: string }[]\n }\n) {\n switch (fieldDefinition.dataType) {\n case \"checkboxes\":\n return Object.entries(subscription.operationParams.values)\n .map(([id, action]) => {\n const value =\n fieldDefinition.fieldOptions.find(\n (fieldOption) => fieldOption.id === parseInt(id, 10)\n )?.value || \"[Hidden value]\"\n return `${capitalize(action)} ${value}`\n })\n .join(\", \")\n case \"select\":\n return subscription.operationParams.value\n ? fieldDefinition.fieldOptions.find(\n (fieldOption) =>\n fieldOption.id ===\n parseInt(subscription.operationParams.value.toString(), 10)\n )?.value || \"[Hidden value]\"\n : \"Unanswered\"\n case \"boolean\":\n switch (subscription.operationParams.value) {\n case \"true\":\n return \"Yes\"\n case \"false\":\n return \"No\"\n default:\n return \"Unanswered\"\n }\n default:\n return subscription.operationParams.value ?? \"Unanswered\"\n }\n}\n\nfunction capitalize(string: string) {\n return string.charAt(0).toUpperCase() + string.slice(1)\n}\n\nconst peopleClient = new Client({\n root: pcoApiRoot(\"people\"),\n version: \"2025-03-20\",\n})\n\nasync function fetchWorkflow(workflowId: number) {\n const { data } = await peopleClient\n .get({\n data: {\n fields: { Workflow: \"name,archived_at\" },\n where: { id: workflowId },\n },\n url: `workflows`,\n })\n .catch(() => [{ data: { name: \"\" } }])\n\n return data\n}\n\nasync function fetchFieldDefinition(fieldDefinitionId: string) {\n const { data } = await peopleClient\n .get({\n data: {\n fields: {\n FieldDefinition: \"name,data_type,field_options\",\n FieldOption: \"value\",\n },\n include: \"field_options\",\n },\n url: `field_definitions/${fieldDefinitionId}`,\n })\n .catch(() => ({ data: { name: \"\" } }))\n\n return data\n}\n\nexport function fieldListIdentifier(field: DefinitionField) {\n if (field.listClass) {\n return `${field.id}_${field.listClass}`\n } else if (field.kind === \"PersonSearch\") {\n return `${field.id}_PersonSearch`\n } else {\n return null\n }\n}\n\nexport function buildDescription({\n selectedDefinition,\n selectedFieldOptions,\n loadedLists,\n}: {\n loadedLists: { [k: string]: LoadedList[] }\n selectedDefinition: OperationDefinition\n selectedFieldOptions: SelectedFieldOptions\n}) {\n return {\n description: describeSelectedFields({\n loadedLists: loadedLists || {},\n selectedDefinition,\n selectedFieldOptions,\n }),\n name: buildDescriptionName(selectedDefinition),\n }\n}\n\nfunction obfuscateDescriptionName(definition: OperationDefinition) {\n if (definition.definitionClass.match(/^CustomField\\w+OperationDefinition$/)) {\n return \"Update [Hidden Custom Field]\"\n }\n}\n\nfunction buildDescriptionName(definition: OperationDefinition) {\n return obfuscateDescriptionName(definition) || definition.description\n}\n\nfunction hasOwnProperty(object: object, key: PropertyKey) {\n return Object.prototype.hasOwnProperty.call(object, key)\n}\n\nfunction getListForField({\n field,\n loadedLists,\n}: {\n field: DefinitionField\n loadedLists: { [k: string]: LoadedList[] }\n}) {\n if (field.list) {\n return field.list\n } else if (fieldListIdentifier(field)) {\n const list = loadedLists[fieldListIdentifier(field)]\n\n return list\n } else {\n throw new Error(`Don't know how to get list for ${JSON.stringify(field)}`)\n }\n}\n\nexport function getRenderedFields(\n definitionFields: DefinitionField[],\n selectedFieldOptions: SelectedFieldOptions\n) {\n return definitionFields.filter((field) => {\n if (Object.prototype.hasOwnProperty.call(field, \"renderIf\")) {\n const renderIf = field.renderIf\n const conditionKey = Object.keys(renderIf)[0]\n\n return isBoolean(renderIf)\n ? renderIf\n : renderIf[conditionKey] === selectedFieldOptions[conditionKey]\n } else {\n return true\n }\n })\n}\n\nfunction describeSelectedFields({\n selectedDefinition,\n selectedFieldOptions,\n loadedLists,\n}: {\n loadedLists: { [k: string]: LoadedList[] }\n selectedDefinition: OperationDefinition\n selectedFieldOptions: SelectedFieldOptions\n}) {\n const description = selectedDefinition.definitionFields\n .map((field) => {\n if (!hasOwnProperty(selectedFieldOptions, field.id)) return null\n\n const value = selectedFieldOptions[field.id]\n let list\n\n switch (field.kind) {\n case \"Select\":\n case \"SelectSearch\":\n case \"PersonSearch\":\n case \"RadioButtons\":\n list = getListForField({ field, loadedLists })\n\n return (\n list && list.find((o) => o.value.toString() === value)?.description\n )\n case \"Checkbox\":\n return value && field.label\n case \"Checkboxes\":\n list = getListForField({ field, loadedLists })\n\n return list\n .filter((e) => hasOwnProperty(value as object, e.value))\n .map((e) => `${capitalize(value[e.value])} ${e.description}`)\n .join(\", \")\n case \"NumberField\":\n case \"TextField\":\n case \"TextArea\":\n case \"DateField\":\n return value\n default:\n throw new Error(\n `Don't know how to build value for field with kind ${field.kind}`\n )\n }\n })\n .filter((x) => x)\n .join(\", \")\n\n return obfuscateSelectedFieldDescriptions({\n description,\n loadedLists,\n selectedDefinition,\n selectedFieldOptions,\n })\n}\n\nfunction obfuscateSelectedFieldDescriptions({\n selectedDefinition,\n selectedFieldOptions,\n loadedLists,\n description,\n}) {\n if (\n selectedDefinition.definitionClass === \"AddToWorkflowOperationDefinition\"\n ) {\n const list = loadedLists.workflow_id_WorkflowsList\n const sensitiveString =\n list &&\n list.find((o) => o.value.toString() === selectedFieldOptions.workflow_id)\n ?.description\n\n return description.replace(sensitiveString, \"[Hidden Workflow]\")\n } else if (\n selectedDefinition.definitionClass.match(\n /^CustomField\\w+OperationDefinition$/\n )\n ) {\n return \"\"\n } else {\n return description\n }\n}\n\nexport function dateFNSFormat(format) {\n return format\n .replace(/%m/, \"M\")\n .replace(/%d/, \"d\")\n .replace(/%Y/, \"y\")\n .replace(/%y/, \"yy\")\n}\n\nexport function momentDateFormat(format) {\n return format\n .replace(/%m/, \"MM\")\n .replace(/%d/, \"DD\")\n .replace(/%Y/, \"YYYY\")\n .replace(/%y/, \"YY\")\n}\n\nexport function momentDateTimeFormat({ dateFormat, twentyFourHourTime }) {\n return `${momentDateFormat(dateFormat)} ${\n twentyFourHourTime ? \"HH:mm\" : \"h:mm A\"\n }`\n}\n\nexport function dateLocalized(date, dateFormat) {\n const momentDate = moment(date, \"YYYY-MM-DD\")\n if (!momentDate.isValid()) {\n return \"\"\n }\n\n const format = momentDateFormat(dateFormat)\n return momentDate.format(format)\n}\n\nexport function numDaysSince(date: string) {\n const momentDate = moment(date, \"YYYY-MM-DD\")\n return moment().diff(momentDate, \"days\")\n}\n\nexport function pluralize(count: number, word: string) {\n if (count === 1) {\n return `1 ${word}`\n } else {\n return `${count} ${word}s`\n }\n}\n\nexport function singularize(string) {\n return string.replace(/s$/, \"\")\n}\n\nexport function upperFirst(string) {\n return string.charAt(0).toUpperCase() + string.slice(1)\n}\n\nexport function triggerResourceParts(triggerResource: string) {\n const triggerParts = triggerResource.split(\"/\")\n\n return {\n appName: triggerParts[0],\n resourceId: triggerParts[triggerParts.length - 1],\n resourcePath: triggerParts.slice(2, -1).join(\"/\"),\n resourceType: triggerParts[triggerParts.length - 2],\n }\n}\n\nexport function forbiddenText(error: any, action?: string) {\n if (error.errors?.[0]?.status === \"403\") {\n return `You don't have permission to ${action || \"modify\"} this automation.`\n }\n return null\n}\n","import { Client } from \"@planningcenter/api-client\"\nimport { pcoApiRoot } from \"./utils/pco-api-root\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Alert,\n Badge,\n Box,\n Button,\n DataTable,\n Heading,\n Icon,\n Input,\n Link,\n Select,\n StackView,\n Text,\n} from \"@planningcenter/tapestry-react\"\nimport moment from \"moment\"\nimport React, { useCallback, useContext, useEffect, useState } from \"react\"\n\nimport SvgAutomations from \"./assets/svg_automations\"\nimport { OrganizationContext } from \"./contexts/organization_context\"\nimport * as alerts from \"./utils/alerts\"\nimport {\n dateLocalized,\n momentDateTimeFormat,\n numDaysSince,\n} from \"./utils/utils\"\n\ndeclare global {\n interface Window {\n openHelpdesk: () => void\n }\n}\n\nconst webhooksClient = new Client({\n root: pcoApiRoot(\"webhooks\"),\n version: \"2022-10-20\",\n})\nconst peopleClient = new Client({ root: pcoApiRoot(\"people\"), version: \"2022-07-14\" })\n\n// values should match the webhooks Event `status` enum entries\nconst STATUS = {\n delivered: {\n label: \"Success\",\n value: [\"delivered\"],\n },\n failed: {\n label: \"Failed\",\n value: [\"failed\", \"duplicated\"],\n },\n ignored: {\n label: \"Ignored\",\n value: [\"ignored_duplicated\", \"ignored_failed\", \"ignored_skipped\"],\n },\n pending: {\n label: \"Pending\",\n value: [\"pending\"],\n },\n skipped: {\n label: \"Paused\",\n value: [\"skipped\"],\n },\n}\n\nasync function fetchEvents(\n triggerResource: EncryptedTriggerResource,\n automationId: number,\n params: {\n offset: number\n per_page: number\n where?: { status: string } | null\n }\n) {\n const response = await webhooksClient.get({\n data: {\n _e: triggerResource,\n fields: {\n Delivery: \"status,response_body,created_at\",\n Event: \"id,created_at,last_delivery,payload,status,uuid,person\",\n },\n include: \"last_delivery\",\n order: \"-created_at\",\n ...params,\n },\n url: `automation_subscriptions/${automationId}/events`,\n })\n\n return response\n}\n\nasync function fetchPeople(personIds) {\n const { data } = await peopleClient.get({\n data: {\n fields: {\n Person: \"id,name\",\n },\n where: { id: personIds.join(\",\") },\n },\n url: `people`,\n })\n\n return data\n}\n\nasync function fetchPeopleWhoTriggeredEvents(events) {\n const personIds = events.data.map((e) => eventPersonId(e))\n try {\n const people = await fetchPeople(personIds)\n return { events, people }\n } catch (error) {\n return { events, people: [] }\n }\n}\n\nfunction mergePeopleAndEvents({ events, people }) {\n const mergedData = events.data.reduce((result, e) => {\n const personId = eventPersonId(e)\n const foundPerson = people.find(\n (p) => personId.toString() === p.id.toString()\n )\n if (foundPerson) {\n result.push({\n ...e,\n person: { id: foundPerson.id, name: foundPerson.name },\n })\n } else {\n result.push({\n ...e,\n person: { id: personId, name: \"[Hidden]\" },\n })\n }\n return result\n }, [])\n\n return { ...events, data: mergedData }\n}\n\nfunction eventPersonId(event) {\n return event.personId\n}\n\nfunction useEvents(\n automationId: number,\n triggerResource: EncryptedTriggerResource,\n filterWhere?: string\n) {\n const perPage = 50\n const [_, setError] = useState()\n const [loading, setLoading] = useState(false)\n const [eventPages, setEventPages] = useState<{ [k: number]: EventPage[] }>({})\n const [params, setParams] = useState<{ where?: { status: string } | null }>(\n filterWhere ? { where: { status: filterWhere } } : {}\n )\n const [meta, setMeta] = useState<{ totalCount: number | any }>()\n const { offset, paginationProps, resetOffset } = usePagination(\n perPage,\n meta?.totalCount\n )\n useEffect(() => {\n if (loading || eventPages[offset]) return\n\n setLoading(true)\n\n fetchEvents(triggerResource, automationId, {\n offset,\n per_page: perPage,\n ...params,\n })\n .then(fetchPeopleWhoTriggeredEvents)\n .then(mergePeopleAndEvents)\n .then((events) => {\n setEventPages((pages) => ({ ...pages, [offset]: events.data }))\n setMeta(events.meta)\n setLoading(false)\n })\n .catch(bubbleErrorToBoundary)\n }, [automationId, triggerResource, loading, params, offset, eventPages])\n\n const refresh = useCallback(() => {\n setEventPages({})\n setMeta(undefined)\n resetOffset()\n }, [resetOffset])\n\n useEffect(() => {\n refresh()\n }, [refresh, params])\n\n function bubbleErrorToBoundary(error) {\n setError(() => {\n throw error\n })\n }\n\n return {\n events: eventPages[offset] || [],\n loading,\n paginationProps,\n params,\n refresh,\n setParams,\n }\n}\n\nfunction usePagination(perPage: number, totalCount: number) {\n const [offset, setOffset] = useState(0)\n\n const currentPage = Math.floor(offset / perPage) + 1\n const totalPages = Math.ceil(totalCount / perPage)\n const paginationProps = { currentPage, onPageChange, totalPages }\n\n function onPageChange(pageNum: number) {\n setOffset((pageNum - 1) * perPage)\n }\n\n const resetOffset = useCallback(() => {\n setOffset(0)\n }, [])\n\n return { offset, paginationProps, resetOffset }\n}\n\nfunction History({\n automation,\n triggerResource,\n filterWhere,\n onEventsStatusChange,\n}: {\n automation: AutomationInstance\n filterWhere?: string\n onEventsStatusChange: Function\n onRequestClose?: () => void\n triggerResource: EncryptedTriggerResource\n}) {\n const { events, loading, paginationProps, refresh, params, setParams } =\n useEvents(automation.id, triggerResource, filterWhere)\n const { dateFormat, olsonTimeZone, twentyFourHourTime } = useContext<{\n dateFormat: any\n olsonTimeZone: any\n twentyFourHourTime: any\n }>(OrganizationContext)\n\n const filteringEvents = params.where && Object.keys(params.where).length > 0\n const automationCreatedRecently = numDaysSince(automation.createdAt) <= 32\n const automationBeganOn = dateLocalized(automation.createdAt, dateFormat)\n const historyPreservationAlert = automationCreatedRecently\n ? `Automation history started on ${automationBeganOn}`\n : \"Automation history is saved for 32 days\"\n\n const columns = [\n {\n cell: (event: EventPage) => <EventStatusBadge status={event.status} />,\n css: {\n padding: \"8px 12px\",\n },\n header: \"Status\",\n },\n {\n cell: (event: EventPage) =>\n moment(event.createdAt)\n .utcOffset(olsonTimeZone)\n .format(momentDateTimeFormat({ dateFormat, twentyFourHourTime })),\n header: \"Date and time\",\n },\n {\n cell: (event: EventPage) => (\n <Link to={`/people/AC${event.person.id}`}>{event.person.name}</Link>\n ),\n css: {\n maxWidth: \"33%\",\n },\n header: \"Profile\",\n },\n {\n cell: (event: EventPage) => <EventStatusMessage event={event} />,\n css: {\n flex: 1,\n },\n header: \"Message\",\n },\n {\n cell: (event: EventPage) =>\n ![...STATUS.delivered.value, ...STATUS.pending.value].includes(\n event.status\n ) && (\n <>\n <RetryEventButton\n automationId={automation.id}\n event={event}\n triggerResource={triggerResource}\n onEventsStatusChange={onEventsStatusChange}\n />\n {![...STATUS.ignored.value].includes(event.status) && (\n <IgnoreEventButton\n automationId={automation.id}\n event={event}\n triggerResource={triggerResource}\n refreshHistory={refresh}\n onEventsStatusChange={onEventsStatusChange}\n />\n )}\n </>\n ),\n css: {\n textAlign: \"right\",\n },\n header: \"\",\n minWidth: \"84px\",\n },\n ]\n\n return (\n <StackView spacing={token(\"--t-spacing-4\")}>\n <StackView spacing={token(\"--t-spacing-half\")}>\n <Heading\n level={3}\n size=\"16px\"\n color={token(\"--t-text-color-secondary\")}\n weight={token(\"--t-font-weight-medium\")}\n >\n {automation.description}\n </Heading>\n <Text\n color={token(\"--t-text-color-secondary\")}\n size={token(\"--t-font-size-xs\")}\n italic\n >\n {historyPreservationAlert}\n </Text>\n </StackView>\n <StackView spacing={token(\"--t-spacing-2\")}>\n <Box minHeight={7}>\n {!loading && (events.length || filteringEvents) && (\n <StackView\n alignItems=\"end\"\n axis=\"horizontal\"\n distribution=\"space-between\"\n spacing={token(\"--t-spacing-1\")}\n >\n <StackView width=\"max-content\">\n <Input.InputLabel\n fontWeight={token(\"--t-font-weight-medium\")}\n color={token(\"--t-text-color\")}\n controls=\"select-status\"\n >\n Filter by status\n </Input.InputLabel>\n <Select\n id=\"select-status\"\n emptyValue={null}\n onChange={({ selectedValue }) => {\n const newWhere = selectedValue\n ? { status: selectedValue }\n : null\n setParams({ where: newWhere })\n }}\n title=\"Status\"\n value={params.where?.status}\n >\n <Select.Option value={null}>All</Select.Option>\n {Object.values(STATUS).map((status) => (\n <Select.Option\n key={status.value}\n value={status.value.join(\",\")}\n >\n {status.label}\n </Select.Option>\n ))}\n </Select>\n </StackView>\n <Button\n iconLeft={{ name: \"general.refresh\" }}\n onClick={refresh}\n theme=\"primary\"\n variant=\"outline\"\n width={12}\n >\n Refresh\n </Button>\n </StackView>\n )}\n </Box>\n <Box maxHeight=\"70vh\" minHeight={36} overflow=\"auto\">\n <DataTable\n columns={columns}\n data={events}\n empty={\n <StackView\n alignment=\"center\"\n distribution=\"center\"\n minHeight={20}\n maxWidth={45}\n spacing={token(\"--t-spacing-1\")}\n marginTop={!filteringEvents ? -8 : -4}\n marginBottom={!filteringEvents ? undefined : 4}\n >\n <Box\n css={{\n svg: {\n height: 15,\n width: 20,\n },\n }}\n >\n <SvgAutomations />\n </Box>\n <Heading\n color={token(\"--t-text-color-headline\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n level={4}\n size={token(\"--t-font-size-lg\")}\n >\n No history found\n </Heading>\n <Text fontSize={token(\"--t-font-size-md\")} textAlign=\"center\">\n No events {filteringEvents && \"matching your filters\"} were\n triggered for this automation{\" \"}\n {automationCreatedRecently\n ? `since ${automationBeganOn}.`\n : \"in the last 32 days.\"}\n </Text>\n {filteringEvents && (\n <Button\n marginTop={token(\"--t-spacing-1\")}\n onClick={() => setParams({})}\n theme=\"primary\"\n title=\"Clear filters\"\n variant=\"outline\"\n />\n )}\n </StackView>\n }\n loading={loading}\n loadingTitle=\"Loading automation history...\"\n variant={{\n bodyCell: {\n alignItems: \"start\",\n fontSize: token(\"--t-font-size-sm\"),\n lineHeight: \"20px\",\n padding: \"10px 12px\",\n },\n bodyRow: ({ rowData }) => {\n return {\n backgroundColor: [...STATUS.ignored.value].includes(\n rowData.status\n )\n ? token(\"--t-fill-color-neutral-090\")\n : undefined,\n minHeight: \"36px\",\n }\n },\n headerCell: {\n padding: \"8px 12px\",\n },\n headerRow: {\n minHeight: \"36px\",\n },\n }}\n {...paginationProps}\n />\n </Box>\n </StackView>\n </StackView>\n )\n}\n\nfunction RetryEventButton({\n automationId,\n event,\n triggerResource,\n onEventsStatusChange,\n}: {\n automationId: number\n event: EventPage\n onEventsStatusChange: Function\n triggerResource: EncryptedTriggerResource\n}) {\n const [status, setStatus] = useState(event.status)\n\n function handleRetry() {\n setStatus(STATUS.pending.value.join(\",\"))\n webhooksClient\n .post({\n data: {\n _e: triggerResource,\n data: { attributes: {} },\n },\n url: `/automation_subscriptions/${automationId}/events/${event.id}/redeliver`,\n })\n .then((response) => {\n setStatus(STATUS.delivered.value.join(\",\"))\n onEventsStatusChange(response.meta.eventsStatus)\n })\n .catch(() => {\n setStatus(STATUS.failed.value.join(\",\"))\n alerts.alertError.fire({\n text: \"There was a problem retrying this automation. Please try again in a few moments.\",\n title: \"Uh oh!\",\n })\n })\n }\n\n const retryTitleFromStatus = STATUS.pending.value.includes(status)\n ? \"Sending\"\n : STATUS.delivered.value.includes(status)\n ? \"Sent\"\n : STATUS.skipped.value.includes(status)\n ? \"Run now\"\n : \"Retry\"\n\n const statusIcon = STATUS.delivered.value.includes(status)\n ? { color: token(\"--t-text-color-status-success\"), name: \"general.check\" }\n : undefined\n\n return (\n <Button\n title={retryTitleFromStatus}\n onClick={handleRetry}\n iconLeft={statusIcon}\n disabled={status !== event.status}\n variant=\"naked\"\n color={\n STATUS.delivered.value.includes(status)\n ? token(\"--t-text-color-status-success\")\n : STATUS.pending.value.includes(status)\n ? token(\"--t-text-color-placeholder\")\n : token(\"--t-text-color-interaction\")\n }\n theme=\"primary\"\n size=\"xs\"\n />\n )\n}\n\nfunction IgnoreEventButton({\n automationId,\n event,\n triggerResource,\n refreshHistory,\n onEventsStatusChange,\n}: {\n automationId: number\n event: EventPage\n onEventsStatusChange: Function\n refreshHistory: Function\n triggerResource: EncryptedTriggerResource\n}) {\n function handleIgnore() {\n webhooksClient\n .post({\n data: {\n _e: triggerResource,\n data: { attributes: {} },\n },\n url: `/automation_subscriptions/${automationId}/events/${event.id}/ignore`,\n })\n .then((response) => {\n onEventsStatusChange(response.meta.eventsStatus)\n })\n .then(() => refreshHistory())\n .catch(() => {\n alerts.alertError.fire({\n text: \"There was a problem ignoring this event. Please try again in a few moments.\",\n title: \"Uh oh!\",\n })\n })\n }\n\n return (\n <Button\n title={\"Ignore\"}\n onClick={handleIgnore}\n variant=\"naked\"\n color={\"linkForeground\"}\n theme=\"primary\"\n size=\"xs\"\n />\n )\n}\n\nfunction EventStatusBadge({ status }: { status: string }) {\n const badgeColors = STATUS.pending.value.includes(status)\n ? {\n border: token(\"--t-border-color-dark\"),\n text: token(\"--t-text-color\"),\n }\n : STATUS.delivered.value.includes(status)\n ? {\n border: token(\"--t-border-color-status-success\"),\n text: token(\"--t-text-color-status-success\"),\n }\n : STATUS.skipped.value.includes(status)\n ? {\n border: token(\"--t-border-color-status-warning\"),\n text: token(\"--t-text-color-status-warning\"),\n }\n : STATUS.ignored.value.includes(status)\n ? {\n border: token(\"--t-border-color-dark\"),\n text: token(\"--t-text-color-secondary\"),\n }\n : {\n border: token(\"--t-border-color-status-error\"),\n text: token(\"--t-text-color-status-error\"),\n }\n\n const badgeIcon = STATUS.pending.value.includes(status)\n ? \"general.clock\"\n : STATUS.skipped.value.includes(status)\n ? \"services.pause\"\n : STATUS.delivered.value.includes(status)\n ? \"general.checkCircle\"\n : STATUS.ignored.value.includes(status)\n ? \"general.inactive\"\n : \"general.exclamationTriangle\"\n\n const badgeTitle = STATUS.failed.value.includes(status)\n ? STATUS.failed.label\n : STATUS.ignored.value.includes(status)\n ? STATUS.ignored.label\n : STATUS[status].label\n\n return (\n <Badge\n color={{ background: \"transparent\", foreground: badgeColors.text }}\n css={{ paddingLeft: 3.5, paddingRight: 1.5 }}\n fontSize={token(\"--t-font-size-xs\")}\n radius=\"pill\"\n renderLeft={\n <Icon\n name={badgeIcon}\n color={badgeColors.border}\n marginLeft={token(\"--t-spacing-1\")}\n />\n }\n size=\"sm\"\n stroke={badgeColors.border}\n strokeAlign=\"inside\"\n strokeWeight={1}\n title={badgeTitle}\n />\n )\n}\n\nfunction EventStatusMessage({ event }: { event: EventPage }) {\n const { status, lastDelivery } = event\n\n function statusMessage(status: string, lastDelivery: Delivery) {\n let message: string | JSX.Element | null = null\n\n switch (status) {\n case \"skipped\":\n case \"ignored_skipped\":\n message = \"Automation was paused and did not run on this profile\"\n break\n case \"failed\":\n case \"duplicated\":\n case \"ignored_failed\":\n case \"ignored_duplicated\":\n message = deliveryFailureReason(lastDelivery, status)\n }\n\n return message\n }\n\n function deliveryFailureReason(delivery: Delivery, status: string) {\n const ERRORS = {\n 403: \"Owner doesn't have permission to perform this action.\",\n 404: \"Owner lacks access to target product or resource doesn't exist.\",\n 422: \"The automation action failed to run\",\n default: \"An error occurred\",\n duplicated_event:\n \"Didn't run because the same action had already been performed less than 60 seconds ago\",\n failed_without_deliveries:\n \"Didn't run because the owner doesn't have permissions in this product.\",\n }\n\n function responseErrors(delivery: Delivery) {\n if (!delivery?.responseBody) return null\n let response\n\n try {\n response = JSON.parse(delivery.responseBody)\n } catch {\n response = { errors: [\"Server Error\"] }\n }\n\n return parsedErrors(response).join(\", \") || response?.message\n }\n\n function parsedErrors(response) {\n if (response?.errors) {\n return response.errors.map((error) =>\n typeof error === \"string\" && error.match(/Archived profiles/)\n ? error.replace(/Archived profiles/, \"Archived profiles.\")\n : error\n )\n } else {\n return []\n }\n }\n\n return (\n <StackView flex={1} whiteSpace=\"normal\">\n {!delivery ? (\n [\"duplicated\", \"ignored_duplicated\"].includes(status) ? (\n ERRORS.duplicated_event\n ) : (\n ERRORS.failed_without_deliveries\n )\n ) : (\n <ToggleableDetails\n details={responseErrors(delivery)}\n status={delivery.status}\n >\n {ERRORS[delivery.status] || ERRORS.default}\n </ToggleableDetails>\n )}\n </StackView>\n )\n }\n\n const message = statusMessage(status, lastDelivery)\n\n return message ? (\n <Box\n fontSize={token(\"--t-font-size-sm\")}\n fontStyle=\"italic\"\n lineHeight=\"16px\"\n maxWidth=\"100%\"\n paddingTop=\"1px\"\n whiteSpace=\"normal\"\n >\n {message}\n </Box>\n ) : null\n}\n\nfunction ToggleableDetails({\n children,\n details,\n status,\n}: {\n children: React.ReactNode\n details: string\n status: string\n}) {\n const [open, setOpen] = useState(false)\n\n function toggleOpen() {\n setOpen((was) => !was)\n }\n\n return (\n <StackView spacing={token(\"--t-spacing-1\")}>\n <Box>\n {children}{\" \"}\n {details && (\n <Button\n inline\n onClick={toggleOpen}\n size=\"xs\"\n theme=\"primary\"\n variant=\"naked\"\n fontStyle=\"normal\"\n >\n Details\n </Button>\n )}\n </Box>\n {open ? (\n <Box padding={1} background={token(\"--t-fill-color-neutral-090\")}>\n <Text\n fontFamily=\"monospace\"\n fontSize={token(\"--t-font-size-xs\")}\n lineHeight=\"1.2\"\n >\n {status && `${status}: `}\n {details}\n </Text>\n </Box>\n ) : null}\n </StackView>\n )\n}\n\ntype ErrorBoundaryProps = {\n children: React.ReactNode\n onRequestClose?: () => void\n}\n\ntype ErrorBoundaryState = {\n hasError: boolean\n}\n\nclass ErrorBoundary extends React.Component<\n ErrorBoundaryProps,\n ErrorBoundaryState\n> {\n constructor(props) {\n super(props)\n this.state = { hasError: false }\n }\n\n static getDerivedStateFromError() {\n return { hasError: true }\n }\n\n handleContactSupport = () => {\n if (this.props.onRequestClose) {\n this.props.onRequestClose()\n }\n window.openHelpdesk()\n }\n\n render() {\n if (this.state.hasError) {\n return (\n <Alert\n type=\"error\"\n marginVertical={1}\n padding={1.5}\n css={{ boxShadow: \"none\" }}\n >\n <Text lineHeight=\"1.35\">\n The application hit an unexpected error. If this persists after a\n few minutes, please let us know so we can get it fixed for you.{\" \"}\n <button\n style={{\n color: token(\"--t-text-color-interaction\"),\n whiteSpace: \"nowrap\",\n }}\n onClick={this.handleContactSupport}\n >\n Contact support\n </button>\n .\n </Text>\n </Alert>\n )\n }\n\n return this.props.children\n }\n}\n\n// eslint-disable-next-line react/display-name\nexport default (props) => (\n <ErrorBoundary onRequestClose={props.onRequestClose}>\n <History {...props}></History>\n </ErrorBoundary>\n)\n","import { token } from \"@planningcenter/tapestry\"\nimport {\n Button,\n Heading,\n Modal,\n StackView,\n ThemeProvider,\n} from \"@planningcenter/tapestry-react\"\nimport { createPortal } from \"react-dom\"\n\nfunction CloseModalIcon({ onClick }: { onClick: React.MouseEventHandler }) {\n return (\n <Button\n as=\"button\"\n height={token(\"--t-element-size-md\")}\n icon={{\n color: token(\"--t-icon-color-dim\"),\n name: \"general.x\",\n }}\n onClick={onClick}\n size=\"sm\"\n title=\"Close\"\n variant=\"naked\"\n />\n )\n}\n\nfunction HistoryModal({\n children,\n onRequestClose,\n open,\n theme,\n}: {\n children: React.ReactNode\n onRequestClose: () => void\n open: boolean\n theme: object\n}): React.ReactPortal | JSX.Element {\n return createPortal(\n <ThemeProvider theme={theme}>\n <Modal\n open={open}\n onRequestClose={onRequestClose}\n maxWidth={120}\n boxShadow=\"0 0 20px rgba(0, 0, 0, 0.15)\"\n padding={token(\"--t-spacing-4\")}\n paddingBottom={token(\"--t-spacing-3\")}\n radius={token(\"--t-border-radius-lg\")}\n >\n <StackView\n axis=\"horizontal\"\n distribution=\"space-between\"\n alignment=\"center\"\n >\n <Heading\n level={2}\n color={token(\"--t-text-color-headline\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n fontSize={token(\"--t-font-size-2xl\")}\n lineHeight=\"1.4\"\n >\n Automation history\n </Heading>\n <CloseModalIcon onClick={onRequestClose} />\n </StackView>\n {children}\n </Modal>\n </ThemeProvider>,\n document.body\n )\n}\n\nexport default HistoryModal\n","import { Logo } from \"@planningcenter/tapestry-react\"\nimport { kebabCase } from \"lodash\"\nimport type { ComponentProps } from \"react\"\n\n// Extract valid logo names from the Logo component's props\ntype ValidLogoName = NonNullable<ComponentProps<typeof Logo>[\"name\"]>\n\n// List of valid logo names from @planningcenter/tapestry-react Logo component\n// Update this list when support for new products are added to tapestry-react\nconst VALID_LOGO_NAMES: ValidLogoName[] = [\n \"api\",\n \"calendar\",\n \"check-ins\",\n \"church-center\",\n \"giving\",\n \"groups\",\n \"headcounts\",\n \"home\",\n \"login\",\n \"music-stand\",\n \"people\",\n \"planning-center\",\n \"publishing\",\n \"registrations\",\n \"services\",\n]\n\nexport const isValidLogoName = (name: string): name is ValidLogoName => {\n return VALID_LOGO_NAMES.includes(name as ValidLogoName)\n}\n\nexport const getValidLogoName = (name: string): ValidLogoName => {\n const kebabName = kebabCase(name)\n return isValidLogoName(kebabName) ? kebabName : \"planning-center\"\n}\n","import { Client } from \"@planningcenter/api-client\"\nimport { pcoApiRoot } from \"./utils/pco-api-root\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Avatar,\n Box,\n Button,\n Card,\n Divider,\n Dropdown,\n Heading,\n Icon,\n Logo,\n StackView,\n Text,\n ToggleSwitch,\n Tooltip,\n} from \"@planningcenter/tapestry-react\"\nimport { lowerFirst, truncate } from \"lodash\"\nimport { createContext, useContext, useState } from \"react\"\n\nimport { OrganizationContext } from \"./contexts/organization_context\"\nimport History from \"./history\"\nimport HistoryModal from \"./history_modal\"\nimport * as alerts from \"./utils/alerts\"\nimport { getValidLogoName } from \"./utils/logos\"\nimport { dateLocalized, forbiddenText } from \"./utils/utils\"\n\nconst webhooksClient = new Client({\n root: pcoApiRoot(\"webhooks\"),\n version: \"2022-10-20\",\n})\nconst peopleClient = new Client({ root: pcoApiRoot(\"people\") })\n\ntype AutomationProps = {\n automation: AutomationInstance\n currentPersonCanCreate: boolean\n currentPersonId: number\n disabled?: boolean\n disabledReason?: string\n trigger: {\n event: AutomationTriggerEvent\n resource: EncryptedTriggerResource\n }\n updateAutomation: React.Dispatch<React.SetStateAction<AutomationInstance>>\n}\n\ntype IncomingAutomationProps = {\n automation: IncomingAutomationInstance\n}\n\ntype EditableAutomationContextType = {\n automation: AutomationInstance\n currentPersonCanCreate?: boolean\n currentPersonId?: number\n theme: object\n trigger?: {\n event: AutomationTriggerEvent\n resource: EncryptedTriggerResource\n }\n updateAutomation?: React.Dispatch<React.SetStateAction<AutomationInstance>>\n}\n\ntype IncomingAutomationContextType = {\n automation: IncomingAutomationInstance\n}\n\nconst AutomationContext = createContext<\n EditableAutomationContextType | IncomingAutomationContextType\n>(null)\n\nfunction EditableAutomation({\n updateAutomation,\n onDelete,\n theme,\n openHistoryNow = false,\n disabled,\n disabledReason,\n ...props\n}: AutomationProps & {\n disabled: boolean\n disabledReason: string\n onDelete: (id: number) => void\n openHistoryNow: boolean\n theme?: object\n}) {\n return (\n <AutomationWrapper\n theme={theme}\n updateAutomation={updateAutomation}\n {...props}\n >\n <Header>\n <Icons />\n <Manage\n onDelete={onDelete}\n openHistoryNow={openHistoryNow}\n disabled={disabled}\n disabledReason={disabledReason}\n />\n </Header>\n <Description />\n <EditableFooter />\n </AutomationWrapper>\n )\n}\n\nfunction IncomingAutomation(props: IncomingAutomationProps) {\n return (\n <AutomationWrapper automation={props.automation}>\n <Header>\n <Icons />\n <LinkToAutomation />\n </Header>\n <IncomingDescription />\n <Footer />\n </AutomationWrapper>\n )\n}\n\nfunction IncomingDescription() {\n const { automation } = useContext(\n AutomationContext\n ) as IncomingAutomationContextType\n\n const triggerEventDescription = automation.triggerEventDescription\n const { name, description } = parseDescription(automation.description)\n const cardOpacity = !automation.active ? 0.5 : undefined\n\n return (\n <StackView\n paddingVertical={token(\"--t-spacing-2\")}\n flex={1}\n opacity={cardOpacity}\n >\n <Heading\n level={3}\n size={token(\"--t-font-size-xl\")}\n weight={token(\"--t-font-weight-medium\")}\n marginBottom={token(\"--t-spacing-half\")}\n truncate\n >\n {name}\n </Heading>\n <StackView spacing={0.75}>\n <Text\n size={token(\"--t-font-size-sm\")}\n color={token(\"--t-text-color\")}\n lineHeight=\"1.2\"\n >\n {triggerEventDescription}, then {lowerFirst(name)}{\" \"}\n {conditionalSuffix(automation)}\n </Text>\n <Text\n size={token(\"--t-font-size-xs\")}\n color={token(\"--t-text-color-secondary\")}\n lineHeight=\"1.2\"\n >\n {truncate(optionallyPrettifyArchivedPrefix(description), {\n length: 160,\n separator: \" \",\n })}\n </Text>\n </StackView>\n </StackView>\n )\n}\n\nfunction LinkToAutomation() {\n const { automation } = useContext(\n AutomationContext\n ) as IncomingAutomationContextType\n\n return (\n <Button\n external\n iconLeft={{ name: \"general.newWindow\" }}\n variant=\"naked\"\n size=\"sm\"\n to={automation.triggerAdminUrl}\n disabled={!automation.canManage}\n tooltip={\n !automation.canManage\n ? \"You do not have access to this resource\"\n : undefined\n }\n color={token(\"--t-text-color-secondary\")}\n hover={{\n backgroundColor: \"highlight\",\n color: token(\"--t-text-color-secondary\"),\n }}\n >\n Manage\n </Button>\n )\n}\n\nfunction AutomationWrapper({\n automation,\n updateAutomation,\n children,\n theme,\n ...rest\n}: (AutomationProps | IncomingAutomationProps) & {\n children: React.ReactNode\n theme?: object\n updateAutomation?: (automation: AutomationInstance) => void\n}) {\n return (\n <AutomationContext.Provider\n value={{\n automation,\n theme,\n updateAutomation,\n ...rest,\n }}\n >\n <Card radius={4} padding={2}>\n {children}\n </Card>\n </AutomationContext.Provider>\n )\n}\n\nfunction Header({ children }: { children: React.ReactNode }) {\n const { automation } = useContext(AutomationContext)\n\n const cardOpacity = !automation.active ? 0.5 : undefined\n\n return (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n padding={0}\n distribution=\"space-between\"\n opacity={cardOpacity}\n >\n {children}\n </StackView>\n )\n}\n\nfunction Manage({\n onDelete,\n openHistoryNow = false,\n disabled,\n disabledReason,\n}: {\n disabled: boolean\n disabledReason: string\n onDelete: (id: number) => void\n openHistoryNow: boolean\n}) {\n const {\n automation,\n currentPersonCanCreate,\n currentPersonId,\n trigger,\n theme,\n updateAutomation,\n } = useContext(AutomationContext) as EditableAutomationContextType\n const [historyVisible, setHistoryVisible] = useState(openHistoryNow)\n const isActive = automation.active\n const { name } = parseDescription(automation.description)\n\n function showHistory() {\n setHistoryVisible(true)\n }\n\n function updateEventsStatus(newStatus: AutomationInstance[\"eventsStatus\"]) {\n updateAutomation((prev) => ({ ...prev, eventsStatus: newStatus }))\n }\n\n function handleToggleActive() {\n webhooksClient\n .patch({\n data: {\n _e: trigger.resource,\n data: {\n attributes: {\n active: !isActive,\n },\n },\n },\n url: `/automation_subscriptions/${automation.id}`,\n })\n .then((data: { data: { active: boolean } }) => {\n updateAutomation((prev) => ({ ...prev, active: data.data.active }))\n })\n .catch((error) => {\n const text =\n forbiddenText(error, \"pause\") ||\n `There was a problem ${\n isActive ? \"pausing\" : \"unpausing\"\n } this automation. Please try again in a few moments.`\n alerts.alertError.fire({\n text,\n title: \"Uh oh!\",\n })\n })\n }\n\n function handleReassign() {\n alerts.confirm\n .fire({\n text: \"This automation will run with your permission levels. Other administrators who can see this automation can grant it their permissions by reassigning it to themselves.\",\n title: \"Reassign automation?\",\n })\n .then(({ isConfirmed }) => {\n if (isConfirmed) {\n webhooksClient\n .post({\n data: {\n _e: trigger.resource,\n data: { attributes: {} },\n },\n url: `/automation_subscriptions/${automation.id}/self_assign`,\n })\n .then(({ data }) => fetchCurrentPersonAvatar(data))\n .then(({ subscription, avatar }) => {\n updateAutomation((prev) => ({\n ...prev,\n createdBy: { ...prev.createdBy, avatarUrl: avatar },\n createdById: subscription.createdById,\n createdByName: subscription.createdByName,\n }))\n })\n .catch((error) => {\n const text =\n forbiddenText(error, \"update\") ||\n \"There was a problem updating this automation. Please try again in a few moments.\"\n alerts.alertError.fire({\n text,\n title: \"Uh oh!\",\n })\n })\n }\n })\n }\n\n function handleDelete() {\n alerts.confirmDestroy\n .fire({\n confirmButtonText: \"Yes, delete automation\",\n text: `Are you sure you want to delete the \"${name}\" automation? This cannot be undone.`,\n title: \"Delete this automation?\",\n })\n .then(({ isConfirmed }) => {\n if (isConfirmed) onDelete(automation.id)\n })\n }\n\n return (\n <>\n <StackView axis=\"horizontal\" alignment=\"center\" spacing={0.75}>\n <Dropdown\n icon={{\n color: token(\"--t-icon-color\"),\n name: \"churchCenter.threeDots\",\n }}\n iconRight={false}\n title=\"Actions\"\n variant=\"naked\"\n size=\"md\"\n disabled={disabled}\n >\n <Dropdown.Item onSelect={() => showHistory()}>History</Dropdown.Item>\n {currentPersonCanCreate &&\n (automation.createdById === currentPersonId ? (\n <Dropdown.Item disabled={true}>\n <Tooltip\n placement=\"left\"\n openDelay={250}\n title=\"This automation is already assigned to you.\"\n >\n <Text>Reassign to me...</Text>\n </Tooltip>\n </Dropdown.Item>\n ) : (\n <Dropdown.Item onSelect={handleReassign}>\n Reassign to me...\n </Dropdown.Item>\n ))}\n <Dropdown.Item onSelect={handleDelete}>Delete...</Dropdown.Item>\n </Dropdown>\n <ToggleSwitch\n isChecked={isActive}\n size=\"sm\"\n onClick={handleToggleActive}\n tooltip={\n disabled\n ? disabledReason\n : isActive\n ? \"Pause automation\"\n : \"Enable automation\"\n }\n disabled={disabled}\n />\n </StackView>\n\n <HistoryModal\n open={historyVisible}\n onRequestClose={() => setHistoryVisible(false)}\n theme={theme}\n >\n <History\n automation={automation}\n triggerResource={trigger.resource}\n onEventsStatusChange={updateEventsStatus}\n onRequestClose={() => setHistoryVisible(false)}\n />\n </HistoryModal>\n </>\n )\n}\n\nfunction Icons() {\n const { automation } = useContext(AutomationContext)\n const triggerProductName = automation.name.split(\".\")[0]\n\n return (\n <StackView axis=\"horizontal\" alignment=\"center\" spacing={0.5}>\n <Logo\n markOnly={true}\n name={getValidLogoName(triggerProductName)}\n size=\"sm\"\n theme=\"color\"\n />\n <Icon name=\"general.rightArrow\" size={1.5} />\n <Logo\n markOnly={true}\n name={getValidLogoName(automation.operationAppName)}\n size=\"sm\"\n theme=\"color\"\n />\n </StackView>\n )\n}\nfunction Footer() {\n const { automation } = useContext(AutomationContext)\n const { dateFormat } = useContext(OrganizationContext)\n const createdBySuffix = !automation.createdBy?.id ? \"(deleted profile)\" : \"\"\n const createdByName = `${automation.createdByName} ${createdBySuffix}`\n\n const cardOpacity = !automation.active ? 0.5 : undefined\n\n return (\n <>\n <Divider marginHorizontal={-2} />\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n distribution=\"space-between\"\n paddingTop={1.75}\n spacing={token(\"--t-spacing-1\")}\n opacity={cardOpacity}\n >\n <Text\n size={token(\"--t-font-size-xs\")}\n color={token(\"--t-text-color-placeholder\")}\n whiteSpace=\"nowrap\"\n >\n Updated {dateLocalized(automation.createdAt, dateFormat)}\n </Text>\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-half\")}\n maxWidth=\"calc(100% - 136px)\"\n >\n {automation.createdBy?.avatarUrl && (\n <Avatar\n width={2}\n height={2}\n basis={2}\n key={createdByName}\n source={automation.createdBy.avatarUrl}\n />\n )}\n <Text size={5} truncate>\n {createdByName}\n </Text>\n </StackView>\n </StackView>\n </>\n )\n}\n\nfunction EditableFooter() {\n const { dateFormat } = useContext(OrganizationContext)\n const { automation, trigger, theme, updateAutomation } = useContext(\n AutomationContext\n ) as EditableAutomationContextType\n\n const createdBySuffix = !automation.createdBy?.id ? \"(deleted profile)\" : \"\"\n const createdByName = `${automation.createdByName} ${createdBySuffix}`\n\n const cardOpacity = !automation.active ? 0.5 : undefined\n const buttonProps = {\n color: token(\"--t-text-color-secondary\"),\n fontSize: token(\"--t-font-size-xs\"),\n fontWeight: token(\"--t-font-weight-normal\"),\n paddingHorizontal: token(\"--t-spacing-1\"),\n radius: \"pill\",\n size: \"xs\",\n variant: \"naked\",\n }\n const [historyProps, setHistoryProps] = useState({\n filter: null,\n historyVisible: false,\n })\n\n function renderSkippedHistory() {\n setHistoryProps({ filter: \"skipped\", historyVisible: true })\n }\n\n function renderFailedOrDuplicatedHistory() {\n setHistoryProps({ filter: \"failed,duplicated\", historyVisible: true })\n }\n\n function handleEventsStatusChange(\n newStatus: AutomationInstance[\"eventsStatus\"]\n ) {\n updateAutomation((prev) => ({ ...prev, eventsStatus: newStatus }))\n }\n\n return (\n <>\n <Divider marginHorizontal={-2} />\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n distribution=\"space-between\"\n paddingTop={1.75}\n spacing={token(\"--t-spacing-1\")}\n opacity={cardOpacity}\n >\n <Text\n size={token(\"--t-font-size-xs\")}\n color={token(\"--t-text-color-placeholder\")}\n whiteSpace=\"nowrap\"\n >\n Updated {dateLocalized(automation.createdAt, dateFormat)}\n </Text>\n\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-fourth\")}\n >\n {!!automation.eventsStatus?.skipped && (\n <Button\n {...buttonProps}\n aria-label={`${automation.eventsStatus.skipped} skipped`}\n onClick={renderSkippedHistory}\n tooltip={`${automation.eventsStatus.skipped?.toLocaleString()} skipped events`}\n >\n <Box\n backgroundColor={token(\"--t-fill-color-status-warning\")}\n marginRight={token(\"--t-spacing-half\")}\n radius=\"circle\"\n height=\"10px\"\n width=\"10px\"\n padding={token(\"--t-spacing-fourth\")}\n >\n <Icon\n name={\"services.pause\"}\n size={\"6px\"}\n title={\"Skipped\"}\n color=\"white\"\n />\n </Box>\n {`${automation.eventsStatus.skipped?.toLocaleString()}`}\n </Button>\n )}\n {!!automation.eventsStatus?.failed && (\n <Button\n {...buttonProps}\n aria-label={`${automation.eventsStatus.failed} failed`}\n iconLeft={{\n color: token(\"--t-icon-color-status-error\"),\n marginRight: token(\"--t-spacing-half\"),\n name: \"general.exclamationTriangle\",\n size: \"10px\",\n title: \"Failed\",\n }}\n onClick={renderFailedOrDuplicatedHistory}\n title={`${automation.eventsStatus.failed?.toLocaleString()}`}\n tooltip={`${automation.eventsStatus.failed?.toLocaleString()} failed events`}\n />\n )}\n </StackView>\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n distribution=\"end\"\n flex={1}\n spacing={token(\"--t-spacing-half\")}\n marginLeft=\"auto\"\n >\n {automation.createdBy?.avatarUrl && (\n <Avatar\n width={token(\"--t-element-size-md\")}\n height={token(\"--t-element-size-md\")}\n basis={token(\"--t-element-size-md\")}\n key={createdByName}\n source={automation.createdBy.avatarUrl}\n />\n )}\n <Text size={token(\"--t-font-size-sm\")} truncate>\n {createdByName}\n </Text>\n </StackView>\n </StackView>\n\n <HistoryModal\n open={historyProps.historyVisible}\n onRequestClose={() =>\n setHistoryProps({ filter: null, historyVisible: false })\n }\n theme={theme}\n >\n <History\n automation={automation}\n triggerResource={trigger.resource}\n filterWhere={historyProps.filter}\n onEventsStatusChange={handleEventsStatusChange}\n onRequestClose={() =>\n setHistoryProps({ filter: null, historyVisible: false })\n }\n />\n </HistoryModal>\n </>\n )\n}\n\nfunction Description() {\n const { automation, trigger } = useContext(\n AutomationContext\n ) as EditableAutomationContextType\n\n const { name, description } = parseDescription(automation.description)\n const cardOpacity = !automation.active ? 0.5 : undefined\n\n const triggerEventDescription = [\n \"When a person\",\n lowerFirst(trigger.event.description) + \",\",\n \"then\",\n lowerFirst(name),\n conditionalSuffix(automation),\n ].join(\" \")\n\n return (\n <StackView\n paddingVertical={token(\"--t-spacing-2\")}\n flex={1}\n opacity={cardOpacity}\n >\n <Heading\n level={3}\n size={token(\"--t-font-size-xl\")}\n weight={token(\"--t-font-weight-bold\")}\n marginBottom={token(\"--t-spacing-half\")}\n truncate\n >\n {name}\n </Heading>\n <StackView spacing={0.75}>\n <Text\n size={token(\"--t-font-size-sm\")}\n color={token(\"--t-text-color\")}\n lineHeight=\"1.2\"\n >\n {triggerEventDescription}\n </Text>\n <Text\n size={token(\"--t-font-size-xs\")}\n color={token(\"--t-text-color-secondary\")}\n lineHeight=\"1.2\"\n >\n {truncate(optionallyPrettifyArchivedPrefix(description), {\n length: 160,\n separator: \" \",\n })}\n </Text>\n </StackView>\n </StackView>\n )\n}\n\nfunction conditionalSuffix(automation: AutomationInstance) {\n return automation?.triggerParams?.useTriggerPersonOverride\n ? \"(also applies to joint donor)\"\n : \"\"\n}\n\nfunction parseDescription(description: string) {\n const match = /^(.+?)\\(([^()]*?)\\)$/.exec(description)\n\n if (match) {\n return { description: match[\"2\"], name: match[\"1\"].trim() }\n } else {\n return { name: description }\n }\n}\n\nfunction optionallyPrettifyArchivedPrefix(description: string) {\n if (description?.startsWith(\"[archived]\")) {\n return description.replace(\"[archived]\", \"[Archived]\")\n } else {\n return description\n }\n}\n\nasync function fetchCurrentPersonAvatar(subscription: AutomationInstance) {\n const {\n data: { avatar },\n } = await peopleClient.get({\n data: {\n fields: { Person: \"avatar\" },\n },\n url: \"me\",\n })\n\n return { avatar, subscription }\n}\n\nexport { EditableAutomation, IncomingAutomation }\n","import { Client } from \"@planningcenter/api-client\"\nimport { compact, uniq } from \"lodash\"\n\nimport { pcoApiRoot } from \"./pco-api-root\"\n\nconst webhooksClient = new Client({\n root: pcoApiRoot(\"webhooks\"),\n version: \"2022-10-20\",\n})\nconst peopleClient = new Client({ root: pcoApiRoot(\"people\") })\n\nasync function fetchAutomations(triggerResource: EncryptedTriggerResource) {\n const { data } = await webhooksClient.get({\n data: {\n _e: triggerResource,\n fields: {\n AutomationSubscription:\n \"id,description,created_at,created_by,operation_app_name,operation_definition_class_name,operation_params,active,created_by_name,name,trigger_admin_url,events_status,trigger_params\",\n Person: \"name\",\n },\n include: \"created_by\",\n },\n url: \"automation_subscriptions\",\n })\n\n return data\n}\n\nasync function fetchCreatorProfiles(subscriptions: AutomationInstance[]) {\n const personIds = compact(\n uniq(subscriptions.map((subscription) => subscription.createdById))\n )\n\n try {\n const { data: profiles } = await peopleClient.get({\n data: {\n fields: { Person: \"avatar\" },\n where: { id: personIds.join(\",\") },\n },\n url: \"people\",\n })\n return { profiles, subscriptions }\n } catch (error) {\n return { profiles: [], subscriptions }\n }\n}\n\nfunction mergeProfilesAndSubscriptions({\n profiles,\n subscriptions,\n}: {\n profiles: { avatar: string; id: number }[]\n subscriptions: AutomationInstance[]\n}) {\n const subscriptionsWithAvatars = subscriptions.map((subscription) => {\n const avatar = profiles.find(\n (profile) => profile.id === subscription.createdById\n )\n return {\n ...subscription,\n createdBy: { ...subscription.createdBy, avatarUrl: avatar?.avatar },\n }\n })\n\n return subscriptionsWithAvatars\n}\n\nasync function fetchPersonApps() {\n return peopleClient\n .get({\n data: {\n fields: { App: [\"name\"], PersonApp: [\"app\", \"allow_pco_login\"] },\n include: [\"app\"],\n },\n url: `/me/person_apps`,\n })\n .then(({ data }) => {\n return data\n .filter((personApp: PersonApp) => personApp.allowPcoLogin)\n .map((personApp: PersonApp) => personApp.app.name.toLowerCase())\n })\n}\n\nexport {\n fetchAutomations,\n fetchCreatorProfiles,\n fetchPersonApps,\n mergeProfilesAndSubscriptions,\n}\n","import { Client } from \"@planningcenter/api-client\"\nimport { pcoApiRoot } from \"./utils/pco-api-root\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Box,\n Heading,\n Spinner,\n Summary,\n Text,\n TileView,\n} from \"@planningcenter/tapestry-react\"\nimport { truncate, upperFirst } from \"lodash\"\nimport { useEffect, useState } from \"react\"\n\nimport { IncomingAutomation } from \"./automation\"\nimport {\n fetchCreatorProfiles,\n fetchPersonApps,\n mergeProfilesAndSubscriptions,\n} from \"./utils/fetch-automations\"\nimport {\n deobfuscateDescriptions,\n pluralize,\n singularize,\n triggerResourceParts,\n} from \"./utils/utils\"\n\nconst webhooksClient = new Client({\n root: pcoApiRoot(\"webhooks\"),\n version: \"2022-10-20\",\n})\n\nasync function fetchIncomingAutomations(encryptedParam) {\n const { data } = await webhooksClient.get({\n data: {\n _e: encryptedParam,\n fields: {\n AutomationSubscription:\n \"id,description,created_at,created_by,operation_app_name,operation_definition_class_name,operation_params,active,created_by_name,name,trigger_admin_url,trigger_resource,trigger_params\",\n Person: \"name\",\n },\n include: \"created_by\",\n },\n url: \"incoming_automation_subscriptions\",\n })\n\n return data\n}\n\nasync function fetchTriggerResources(automations) {\n // We can optimize the query by fetching all the resources at once if we know\n // that the endpoint supports querying by multiple ids. Otherwise, we'll have\n // to fetch each resource individually.\n const QUERYABLE_BY_MULTIPLE_IDS = {\n people: [\"forms\", \"lists\"],\n registrations: [\"events\"],\n services: [\"teams\"],\n }\n const NOT_QUERYABLE = [\"giving\"]\n\n const automationsByModel = automations.reduce((accumulator, automation) => {\n // registrations has a weird case of signup vs event\n const automationTriggerResource = automation.triggerResource.replace(\n /signup/,\n \"event\"\n )\n const { appName, resourceType, resourcePath, resourceId } =\n triggerResourceParts(automationTriggerResource)\n\n if (!accumulator[appName]) accumulator[appName] = {}\n if (!accumulator[appName][resourceType])\n accumulator[appName][resourceType] = {}\n if (!accumulator[appName][resourceType][\"resoucePath\"])\n accumulator[appName][resourceType][\"resourcePath\"] = resourcePath\n\n if (!accumulator[appName][resourceType][\"ids\"])\n accumulator[appName][resourceType][\"ids\"] = []\n\n accumulator[appName][resourceType][\"ids\"].push(resourceId)\n\n return accumulator\n }, {})\n\n const promises = Object.keys(automationsByModel).flatMap((appName) => {\n const automationsByResourceType = automationsByModel[appName]\n\n return Object.entries(automationsByResourceType).flatMap(\n ([resourceType, resourceParts]) => {\n const fetchFn = NOT_QUERYABLE.includes(appName)\n ? fetchNothing\n : QUERYABLE_BY_MULTIPLE_IDS[appName]?.includes(resourceType)\n ? fetchAllAtOnce\n : fetchOneAtATime\n\n return fetchFn({\n appName,\n ids: resourceParts[\"ids\"],\n resourcePath: resourceParts[\"resourcePath\"],\n resourceType,\n })\n }\n )\n })\n\n const results = await Promise.allSettled(promises)\n\n return {\n automations,\n triggerResources: collectSuccessfulResults(results),\n }\n}\n\nfunction collectSuccessfulResults(settledPromises) {\n return settledPromises\n .reduce((acc, result) => {\n if (result.status === \"fulfilled\") acc = acc.concat(result.value)\n\n return acc\n }, [])\n .flatMap((d) => d.data)\n}\n\nfunction fetchAllAtOnce({ appName, resourcePath, resourceType, ids }) {\n return fetchResourceName({\n appName,\n params: {\n where: { id: ids.join(\",\") },\n },\n path: resourcePath,\n resourceType,\n })\n}\n\nfunction fetchOneAtATime({ appName, resourcePath, resourceType, ids }) {\n return ids.map((id) =>\n fetchResourceName({\n appName,\n path: `${resourcePath}/${id}`,\n resourceType,\n })\n )\n}\n\nfunction fetchNothing(_props: object) {\n return new Promise((_, reject) => {\n reject()\n })\n}\n\n// TODO (maybe): move these to webhooks, return the verb in the API response,\n// so new events don't need a code change in both places\nfunction mapNameToVerb(messageName) {\n // e.g. \"groups.v2.events.membership.created\" => \"groups.membership.created\"\n const appResourceAction = messageName.replace(\"v2.events.\", \"\")\n\n switch (appResourceAction) {\n case \"groups.membership.created\":\n return \"joins\"\n case \"groups.membership.destroyed\":\n return \"leaves\"\n case \"people.list_result.created\":\n case \"services.team_person.created\":\n return \"is added to\"\n case \"people.list_result.destroyed\":\n case \"services.team_person.destroyed\":\n return \"is removed from\"\n case \"people.form_submission.created\":\n return \"submits\"\n case \"registrations.attendee.created\":\n return \"is registered as a new attendee for\"\n case \"registrations.attendee.cancelled\":\n return \"is canceled as an attendee for\"\n case \"registrations.registration.created\":\n return \"is the registration contact on a new registration for\"\n case \"registrations.registration.cancelled\":\n return \"is the registration contact on a canceled registration for\"\n default:\n return null\n }\n}\n\nfunction buildGivingDescription(automation: AutomationInstance) {\n const action = automation.name.replace(\"giving.v2.events.\", \"\")\n\n switch (action) {\n case \"donation.payment_successful\":\n return \"When a person gives\"\n case \"profile.first_donated_automation\":\n return \"When a person gives for the first time\"\n case \"recurring_donation.setup_successful\":\n return \"When a person sets up a recurring donation\"\n default:\n return null\n }\n}\n\nfunction buildDescription(automation, triggerResourceName) {\n const verb = mapNameToVerb(automation.name)\n\n const { resourceType } = triggerResourceParts(automation.triggerResource)\n\n if (!verb) {\n // No verb mapping for this message name, so just show something generic\n const resourceName = truncate(triggerResourceName, {\n length: 160,\n separator: \" \",\n })\n\n return `When the automation is triggered from ${singularize(\n resourceType\n )} \"${resourceName}\"`\n }\n\n return `When a person ${verb} ${singularize(\n resourceType\n )} \"${triggerResourceName}\"`\n}\n\nfunction fetchResourceName({\n appName,\n path,\n resourceType,\n params = {},\n}): Promise<any> {\n const client = new Client({ root: pcoApiRoot(appName) })\n const model = upperFirst(singularize(resourceType))\n\n return client.get({\n data: {\n fields: {\n [model]: [\"name\", \"name_or_description\"],\n },\n ...params,\n },\n url: path,\n })\n}\n\nfunction mergeTriggerResourceEventDescriptions({\n automations,\n triggerResources,\n operationApps,\n}) {\n return automations.map((automation) => {\n const { appName, resourceType, resourceId } = triggerResourceParts(\n automation.triggerResource\n )\n\n if (appName === \"giving\") {\n automation.triggerEventDescription = buildGivingDescription(automation)\n automation.canManage = operationApps.find((app) => app === \"giving\")\n\n return automation\n }\n\n // find the result that matches this automation\n const result = triggerResources.find(\n (tr) => tr.id.toString() == resourceId.toString()\n )\n\n const resourceName = result\n ? result.name || result.nameOrDescription\n : `[Hidden ${upperFirst(singularize(resourceType))}]`\n\n automation.triggerEventDescription = buildDescription(\n automation,\n resourceName\n )\n\n automation.canManage = !!result\n\n return automation\n })\n}\n\nfunction IncomingAutomations({\n encryptedParam,\n trigger,\n}: {\n encryptedParam: string\n trigger?: AutomationTrigger\n}) {\n const [loading, setLoading] = useState(true)\n const [automations, setAutomations] = useState<IncomingAutomationInstance[]>()\n\n useEffect(() => {\n fetchPersonApps().then((operationApps) => {\n fetchIncomingAutomations(encryptedParam)\n .then(fetchCreatorProfiles)\n .then(mergeProfilesAndSubscriptions)\n .then(deobfuscateDescriptions)\n .then(fetchTriggerResources)\n .then(({ automations, triggerResources }) =>\n mergeTriggerResourceEventDescriptions({\n automations,\n operationApps,\n triggerResources,\n })\n )\n .then(setAutomations)\n .then(() => setLoading(false))\n })\n }, [encryptedParam])\n\n const noResults = !loading && automations.length === 0\n\n return (\n <>\n <Box\n borderBottom={`1px solid ${token(\"--t-border-color\")}`}\n marginBottom={token(\"--t-spacing-2\")}\n marginHorizontal={-3}\n marginTop={trigger ? 12 : 0}\n paddingHorizontal={token(\"--t-spacing-3\")}\n paddingVertical={token(\"--t-spacing-2\")}\n >\n <Heading\n color={token(\"--t-text-color-headline\")}\n level={2}\n size={token(\"--t-font-size-lg\")}\n >\n {loading\n ? \"Incoming automations\"\n : pluralize(automations.length, \"incoming automation\")}\n </Heading>\n </Box>\n {noResults ? (\n <Text\n color={token(\"--t-text-color-secondary\")}\n marginVertical={token(\"--t-spacing-3\")}\n >\n Automations that perform actions on this resource will be listed here.\n </Text>\n ) : loading ? (\n <Summary\n image={<Spinner size=\"xl\" />}\n paddingVertical={10}\n title={\"Loading incoming automations...\"}\n />\n ) : (\n <TileView\n spacing={token(\"--t-spacing-3\")}\n marginVertical={token(\"--t-spacing-3\")}\n minCellWidth={45}\n >\n {automations.map((automation) => (\n <IncomingAutomation key={automation.id} automation={automation} />\n ))}\n </TileView>\n )}\n </>\n )\n}\n\nexport default IncomingAutomations\n","import { token } from \"@planningcenter/tapestry\"\nimport { Select, StackView } from \"@planningcenter/tapestry-react\"\nimport { groupBy, uniqBy } from \"lodash\"\n\nfunction operationDefinitionId(od: OperationDefinition) {\n return `OPERATION_${od.definitionClass}${od.definitionIdentifier || \"\"}`\n}\n\nfunction sectionId(section: string) {\n return `SECTION_${section}`\n}\n\nfunction idType(value: string) {\n if (value.startsWith(\"SECTION\")) {\n return \"section\"\n } else if (value.startsWith(\"OPERATION\")) {\n return \"operation\"\n } else if (!value) {\n return null\n } else {\n throw new Error(`Unexpected value: ${value}`)\n }\n}\n\nfunction renderOptionsWithoutConsideringGroup(\n options: { label: string; value: string | number }[]\n) {\n return options.map(({ label, value }) => (\n <Select.Option key={value} value={value}>\n {label}\n </Select.Option>\n ))\n}\n\nfunction renderOptions(\n options: { group?: string | null; label: string; value: string | number }[]\n) {\n const groupedOptions = groupBy(options, \"group\")\n const groupTypes = Object.keys(groupedOptions).sort()\n return groupTypes.map((gt) =>\n gt === \"null\" ? (\n renderOptionsWithoutConsideringGroup(groupedOptions[gt])\n ) : (\n <Select.OptionGroup key={gt} title={gt}>\n {renderOptionsWithoutConsideringGroup(groupedOptions[gt])}\n </Select.OptionGroup>\n )\n )\n}\n\nconst Definition = ({\n selectedOperation,\n onOperationDefinitionChange,\n operationDefinitions,\n}: {\n onOperationDefinitionChange: Function\n operationDefinitions: OperationDefinition[]\n selectedOperation: OperationDefinition\n}) => {\n const selectedSection = selectedOperation?.section\n\n const operationDefinitionsWithUniqueIds = operationDefinitions.map((od) => ({\n ...od,\n id: operationDefinitionId(od),\n }))\n\n const primaryOperations = operationDefinitionsWithUniqueIds.filter(\n (od) => od.section === null\n )\n\n const primarySectionOptions = uniqBy(operationDefinitions, \"section\")\n .filter((od) => !!od.section)\n .map((od) => ({\n group: od.sectionGroup,\n label: od.section,\n value: sectionId(od.section),\n }))\n\n const secondaryOperations = selectedSection\n ? operationDefinitionsWithUniqueIds.filter(\n (od) => od.section === selectedSection\n )\n : []\n\n function handleAnySelectChange({ selectedValue }) {\n switch (idType(selectedValue)) {\n case \"section\":\n onOperationDefinitionChange(\n operationDefinitions.find(\n (od) => sectionId(od.section) === selectedValue\n )\n )\n break\n case \"operation\":\n onOperationDefinitionChange(\n operationDefinitions.find(\n (od) => operationDefinitionId(od) === selectedValue\n )\n )\n break\n case null:\n onOperationDefinitionChange(null)\n break\n }\n }\n\n function renderOperations(operations: OperationDefinition[]) {\n const operationsAsOptions = operations.map((o) => ({\n group: o.group,\n label: o.description,\n value: o.id,\n }))\n\n return renderOptions(operationsAsOptions)\n }\n\n return (\n <StackView spacing={token(\"--t-spacing-1\")}>\n <Select\n emptyValue=\"Select an action\"\n id=\"select-action\"\n onChange={handleAnySelectChange}\n size=\"lg\"\n data-testid=\"operation-select\"\n >\n {renderOperations(primaryOperations)}\n {renderOptions(primarySectionOptions)}\n </Select>\n {secondaryOperations.length > 0 && (\n <Select\n defaultValue={secondaryOperations[0].id}\n onChange={handleAnySelectChange}\n size=\"lg\"\n >\n {renderOperations(secondaryOperations)}\n </Select>\n )}\n </StackView>\n )\n}\n\nexport default Definition\n","import { token } from \"@planningcenter/tapestry\"\nimport {\n Alert,\n Avatar,\n Badge,\n Box,\n Checkbox as TapestryCheckbox,\n Combobox as TapestryCombobox,\n DateField as TapestryDateField,\n HelperDrawer,\n Highlight,\n Icon,\n Input,\n Menu,\n NumberField as TapestryNumberField,\n Radio,\n Select as TapestrySelect,\n Spinner,\n StackView,\n Text,\n TextArea as TapestryTextArea,\n} from \"@planningcenter/tapestry-react\"\nimport { camelCase, debounce, groupBy, isEqual, sortBy, uniqBy } from \"lodash\"\nimport moment from \"moment\"\nimport { useCallback, useContext, useEffect, useMemo, useState } from \"react\"\n\nimport { OrganizationContext } from \"./contexts/organization_context\"\nimport {\n dateFNSFormat,\n dateLocalized,\n fieldListIdentifier,\n} from \"./utils/utils\"\n\nfunction fieldDependencies({\n field,\n selectedFieldOptions,\n}: {\n field: DefinitionField\n selectedFieldOptions: { [k: string]: any }\n}) {\n const dependsOn = field.dependsOn || []\n return dependsOn.reduce((acc, depKey) => {\n if (Object.prototype.hasOwnProperty.call(selectedFieldOptions, depKey)) {\n acc[camelCase(depKey)] = selectedFieldOptions[depKey]\n }\n return acc\n }, {})\n}\n\nfunction useMemoizedObject(generator) {\n const [memoizedObject, setMemoizedObject] = useState(generator)\n\n useEffect(() => {\n const newObject = generator()\n\n if (!isEqual(newObject, memoizedObject)) {\n setMemoizedObject(newObject)\n }\n }, [generator, memoizedObject])\n\n return memoizedObject\n}\n\nconst Field = ({\n canAccessPeople,\n field,\n onChange,\n value,\n selectedFieldOptions,\n loadListForField,\n loadedLists,\n loadingLists,\n}: {\n canAccessPeople: boolean\n field: DefinitionField\n loadListForField: LoadListForField\n loadedLists: { [k: string]: LoadedList[] }\n loadingLists: { [k: string]: boolean }\n onChange: Function\n selectedFieldOptions: { [k: string]: any }\n value: any\n}) => {\n const dependencies = useMemoizedObject(() =>\n fieldDependencies({ field, selectedFieldOptions })\n )\n\n useEffect(() => {\n if (field.listClass) {\n loadListForField({ dependencies, field })\n }\n }, [field, dependencies, loadListForField])\n\n const listOptions =\n field.list || loadedLists[fieldListIdentifier(field)] || []\n\n const actionAllowedOptions = listOptions.filter(\n (op) => !op.automationNotAllowed\n )\n\n const loading = field.listClass && loadingLists[fieldListIdentifier(field)]\n\n function renderField() {\n switch (field.kind) {\n case \"Select\":\n return (\n <Select\n fieldId={field.id}\n listOptions={actionAllowedOptions}\n onChange={onChange}\n value={value}\n description={field.description}\n />\n )\n case \"SelectSearch\":\n return (\n <SelectSearch\n fieldId={field.id}\n listOptions={actionAllowedOptions}\n onChange={onChange}\n value={value}\n />\n )\n case \"Checkbox\":\n return <Checkbox field={field} value={value} onChange={onChange} />\n case \"TextArea\":\n return <TextArea field={field} onChange={onChange} value={value} />\n\n case \"DateField\":\n return <DateField field={field} onChange={onChange} value={value} />\n case \"Checkboxes\":\n return (\n <Checkboxes\n fieldId={field.id}\n options={actionAllowedOptions}\n onChange={onChange}\n />\n )\n case \"NumberField\":\n return <NumberField field={field} onChange={onChange} value={value} />\n case \"PersonSearch\":\n return (\n <PersonSearch\n canAccessPeople={canAccessPeople}\n field={field}\n onChange={onChange}\n listOptions={listOptions}\n isLoading={loadingLists[fieldListIdentifier(field)]}\n loadListForField={loadListForField}\n value={value}\n />\n )\n case \"TextField\":\n return <TextField field={field} onChange={onChange} value={value} />\n case \"RadioButtons\":\n return (\n <RadioButtons\n field={field}\n options={listOptions}\n onChange={onChange}\n value={value}\n />\n )\n case \"StaticText\":\n return <Text dangerouslySetInnerHTML={{ __html: field.content }} />\n default:\n console.warn(`Unknown field kind \"${field.kind}\"`)\n return null\n }\n }\n\n return (\n <StackView marginBottom={2} spacing={0.5}>\n <Input.InputLabel\n color={token(\"--t-text-color-headline\")}\n fontSize={token(\"--t-font-size-sm\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n controls={field.id}\n >\n {field.description}\n {field.info && (\n <HelperDrawer.Toggle drawerId={`${field.id}_help`} marginLeft={1} />\n )}\n </Input.InputLabel>\n <Box>{loading ? <Loading /> : renderField()}</Box>\n {field.info && (\n <HelperDrawer\n id={`${field.id}_help`}\n marginTop={token(\"--t-spacing-half\")}\n >\n <Box dangerouslySetInnerHTML={{ __html: field.info }} />\n </HelperDrawer>\n )}\n </StackView>\n )\n}\n\nconst Select = ({\n fieldId,\n listOptions,\n onChange,\n value,\n description,\n}: {\n description?: string\n fieldId: string\n listOptions: LoadedList[]\n onChange: Function\n value: any\n}) => {\n const overridenEmptyValue = listOptions?.find(\n (option) => option.value === \"no-option\"\n )\n const groupedOptions = groupBy(listOptions, \"group\")\n const groupTypes = Object.keys(groupedOptions).sort()\n const renderOptions = () => {\n return groupTypes.map((gt) =>\n gt === \"null\" || gt === \"undefined\" ? (\n renderOptionsWithoutConsideringGroup(groupedOptions[gt])\n ) : (\n <TapestrySelect.OptionGroup key={gt} title={gt}>\n {renderOptionsWithoutConsideringGroup(groupedOptions[gt])}\n </TapestrySelect.OptionGroup>\n )\n )\n }\n\n const renderOptionsWithoutConsideringGroup = (\n items: { description: string; disabled?: boolean; value: string | number }[]\n ) => {\n return items.map((item) => (\n <TapestrySelect.Option\n key={item.value}\n value={item.value.toString()}\n disabled={item.disabled}\n >\n {item.description}\n </TapestrySelect.Option>\n ))\n }\n\n const handleSelectedValueChange = ({ selectedValue }) => {\n onChange({ fieldId, value: selectedValue })\n }\n\n const generatePrompt = (word: string) => {\n let prompt = `Select `\n if (!word) {\n prompt += \"a value\"\n } else if ([\"a\", \"e\", \"i\", \"o\", \"u\"].includes(word.charAt(0))) {\n prompt += `an ${word}`\n } else {\n prompt += `a ${word}`\n }\n return prompt\n }\n\n const renderEmptyValue = () => {\n if (renderOptions().length === 0) return \"No options available\"\n return (\n overridenEmptyValue?.description ||\n generatePrompt(description?.toLowerCase())\n )\n }\n\n return (\n <TapestrySelect\n id={fieldId}\n onChange={handleSelectedValueChange}\n disabled={renderOptions().length < 1}\n emptyValue={renderEmptyValue()}\n size=\"lg\"\n value={value || overridenEmptyValue?.value || null}\n placement=\"bottom-start\"\n >\n {renderOptions()}\n </TapestrySelect>\n )\n}\n\nconst SelectSearch = ({\n fieldId,\n listOptions,\n onChange,\n value,\n}: {\n fieldId: string\n listOptions: LoadedList[]\n onChange: Function\n value?: string\n}) => {\n const selectedOption: LoadedList = listOptions.find(\n (option) => option.value?.toString() === value\n )\n const selectedLabel = selectedOption?.description || \"\"\n const [prevSelectedLabel, setPrevSelectedLabel] = useState(\"\")\n const [query, setQuery] = useState(selectedLabel)\n const [showFilteredOptions, setShowFilteredOptions] = useState(false)\n const [showClearButton, setShowClearButton] = useState(false)\n\n if (selectedLabel !== prevSelectedLabel) {\n setPrevSelectedLabel(selectedLabel)\n setQuery(selectedLabel)\n setShowFilteredOptions(false)\n }\n\n let filteredOptions = sortBy(uniqBy(listOptions, \"value\"), \"group\")\n\n if (showFilteredOptions) {\n const formattedQuery = query.toLowerCase()\n filteredOptions = filteredOptions.filter((option) => {\n const optionText = `${option.description} ${option.group}`.toLowerCase()\n return optionText.includes(formattedQuery)\n })\n }\n\n const handleValueChange = (value: string) => {\n onChange({ fieldId, value })\n }\n\n return (\n <TapestryCombobox.Popover\n closeOnSelect\n closeButton={{ icon: { size: \"md\" } }}\n css={{\n \"[role='combobox']\": {\n cursor: listOptions.length > 0 ? \"pointer\" : \"not-allowed\",\n },\n }}\n cursor=\"pointer\"\n disabled={listOptions.length === 0}\n onBlur={() => {\n setShowClearButton(false)\n setQuery(selectedLabel)\n }}\n onChange={(e: React.ChangeEvent<HTMLInputElement>) => {\n setQuery(e.target.value)\n setShowFilteredOptions(true)\n setShowClearButton(true)\n }}\n onClear={\n showClearButton\n ? () => {\n setQuery(\"\")\n setShowFilteredOptions(false)\n }\n : undefined\n }\n onFocus={(e: React.ChangeEvent<HTMLInputElement>) => e.target.select()} // select all text on focus\n onSelect={(option: { description: string; value: string }) => {\n handleValueChange(option.value)\n setQuery(option.description)\n setShowFilteredOptions(false)\n setShowClearButton(false)\n }}\n openOnFocus\n paddingLeft={4.5}\n placeholder={\n listOptions.length > 0 ? \"Select an option\" : \"No options available\"\n }\n placement=\"bottom-start\"\n popoverProps={{\n matchWidths: \"minimum\",\n }}\n renderLeft={<Icon name=\"general.search\" size=\"md\" />}\n renderRight={<Icon name=\"general.downCaret\" />}\n size=\"lg\"\n value={query}\n >\n {listOptions.length > 0 && (\n <>\n {filteredOptions.length > 0 ? (\n filteredOptions.map((option: LoadedList, index: number) => {\n const isCurrent = option.value.toString() === value\n return (\n <TapestryCombobox.Item\n aria-label={option.description}\n disabled={option.disabled}\n index={index}\n key={option.value}\n paddingLeft={4.25}\n renderLeft={\n <Icon\n marginLeft={-0.5}\n name={isCurrent ? \"general.check\" : \"\"}\n size=\"sm\"\n />\n }\n role=\"option\"\n spacing={token(\"--t-spacing-1\")}\n value={{\n description: option.description,\n value: option.value.toString(),\n }}\n >\n <Text truncate>\n <Highlight text={option.description} query={query} />\n </Text>\n {option.group && (\n <Badge\n title={<Highlight text={option.group} query={query} />}\n size=\"sm\"\n marginLeft=\"auto\"\n />\n )}\n </TapestryCombobox.Item>\n )\n })\n ) : (\n <Menu.Item>\n <Text>No results for "{query}"</Text>\n </Menu.Item>\n )}\n </>\n )}\n </TapestryCombobox.Popover>\n )\n}\n\nconst PersonSearch = ({\n canAccessPeople,\n field,\n isLoading,\n listOptions,\n loadListForField,\n onChange,\n value,\n}: {\n canAccessPeople: boolean\n field: DefinitionField\n isLoading: boolean\n listOptions: LoadedList[]\n loadListForField: LoadListForField\n onChange: Function\n value?: string\n}) => {\n const immediateSearch = useCallback(\n (query: string) => {\n loadListForField({ dependencies: { query }, field })\n },\n [loadListForField]\n )\n\n const debouncedSearch = useMemo(\n () => debounce(immediateSearch, 300),\n [immediateSearch]\n )\n\n const search = useCallback(\n (query: string) => {\n if (!canAccessPeople) {\n return\n } else if (query.trim().length > 0) {\n debouncedSearch(query)\n } else {\n debouncedSearch.cancel()\n }\n },\n [debouncedSearch]\n )\n\n const myself: LoadedList = useMemo(\n () => ({ description: \"Myself\", value: \"self\" }),\n []\n )\n const allListOptions = useMemo(() => {\n if (!canAccessPeople) {\n return [myself]\n } else {\n return listOptions\n }\n }, [myself, listOptions])\n\n const selectedOption = allListOptions.find((option) => option.value === value)\n const selectedLabel = selectedOption?.description || \"\"\n const [query, _setQuery] = useState(selectedLabel)\n const [showClearButton, setShowClearButton] = useState(false)\n\n function setQuery(value: string) {\n _setQuery(value)\n search(value)\n if (value.trim().length === 0) {\n handleValueChange(null)\n }\n }\n\n const handleValueChange = (value: string) => {\n onChange({ fieldId: field.id, value })\n }\n\n return (\n <TapestryCombobox.Popover\n closeOnSelect\n closeButton={{ icon: { size: \"md\" } }}\n cursor=\"pointer\"\n onBlur={() => {\n setShowClearButton(false)\n setQuery(selectedLabel)\n }}\n onChange={(e: React.ChangeEvent<HTMLInputElement>) => {\n setQuery(e.target.value)\n setShowClearButton(true)\n }}\n onClear={\n showClearButton\n ? () => {\n setQuery(\"\")\n }\n : undefined\n }\n onFocus={(e: React.FocusEvent<HTMLInputElement>) => e.target.select()} // select all text on focus\n onSelect={(option: { description: string; value: string }) => {\n handleValueChange(option.value)\n setQuery(option.description)\n setShowClearButton(false)\n }}\n openOnFocus\n paddingLeft={4.5}\n placeholder=\"Search\"\n placement=\"bottom-start\"\n popoverProps={{\n matchWidths: \"minimum\",\n }}\n renderLeft={\n selectedOption && selectedOption.meta?.avatar ? (\n <Avatar size=\"sm\" source={selectedOption.meta.avatar} />\n ) : (\n <Icon name=\"general.search\" size=\"md\" />\n )\n }\n renderRight={<Icon name=\"general.downCaret\" />}\n size=\"lg\"\n value={query}\n >\n {canAccessPeople ? (\n query.trim().length > 0 ? (\n listOptions.length > 0 ? (\n listOptions.map((option, index) => {\n return (\n <TapestryCombobox.Item\n aria-label={option.description}\n index={index}\n key={option.value}\n paddingLeft={4.25}\n renderLeft={\n <Avatar\n marginLeft={-0.5}\n source={option.meta.avatar}\n size=\"sm\"\n />\n }\n role=\"option\"\n spacing={token(\"--t-spacing-1\")}\n value={option}\n >\n <Text truncate>\n <Highlight text={option.description} query={query} />\n </Text>\n </TapestryCombobox.Item>\n )\n })\n ) : isLoading ? (\n <TapestryCombobox.Item>\n <Text>Loading...</Text>\n </TapestryCombobox.Item>\n ) : (\n <TapestryCombobox.Item>\n <Text>No results</Text>\n </TapestryCombobox.Item>\n )\n ) : (\n <TapestryCombobox.Item>\n <Text>Type to search</Text>\n </TapestryCombobox.Item>\n )\n ) : (\n <TapestryCombobox.Item value={myself} index={0} role=\"option\">\n <Text>{myself.description}</Text>\n </TapestryCombobox.Item>\n )}\n </TapestryCombobox.Popover>\n )\n}\n\nconst Checkbox = ({\n field,\n value,\n onChange,\n}: {\n field: DefinitionField\n onChange: Function\n value: any\n}) => {\n const handleCheckedValueChange = (e) => {\n const value = e.target.checked\n onChange({ fieldId: field.id, value })\n }\n\n return (\n <TapestryCheckbox\n disabled={field.disabled}\n label={field.label}\n checked={value || false}\n onChange={handleCheckedValueChange}\n />\n )\n}\n\nconst TextArea = ({\n field,\n value,\n onChange,\n}: {\n field: DefinitionField\n onChange: Function\n value: any\n}) => {\n const handleTextChange = (e) => {\n const val = e.target.value\n onChange({ fieldId: field.id, value: val })\n }\n return (\n <Box>\n <TapestryTextArea\n value={value}\n placeholder={field.placeholder}\n onChange={handleTextChange}\n size=\"lg\"\n />\n </Box>\n )\n}\n\nconst DateField = ({\n field,\n value,\n onChange,\n}: {\n field: DefinitionField\n onChange: Function\n value: any\n}) => {\n const { dateFormat } = useContext(OrganizationContext)\n const [specificDate, setSpecificDate] = useState(false)\n const todaysValue = field.customValue || \"Day automation runs\"\n const dateBeforeValue = \"Day before automation runs\"\n const orgFormat = dateFNSFormat(dateFormat)\n const [dateFieldValue, setDateFieldValue] = useState(moment(value).toDate())\n const allowUnansweredOption = field.allowUnansweredOption ?? false\n\n const handleSelectChange = ({ selectedValue }) => {\n if (selectedValue === todaysValue || selectedValue === dateBeforeValue) {\n setSpecificDate(false)\n onChange({ fieldId: field.id, value: selectedValue })\n } else if (selectedValue === \"specific-date\") {\n onChange({ fieldId: field.id, value: null })\n setSpecificDate(true)\n } else {\n setSpecificDate(false)\n onChange({ fieldId: field.id, value: null })\n }\n }\n\n const handleValueChanged = (date: Date) => {\n onChange({ fieldId: field.id, value: dateLocalized(date, dateFormat) })\n setDateFieldValue(date)\n }\n\n return (\n <StackView axis=\"horizontal\">\n <TapestrySelect\n onChange={handleSelectChange}\n size=\"lg\"\n placement=\"bottom-start\"\n >\n <TapestrySelect.Option value={todaysValue}>\n {todaysValue}\n </TapestrySelect.Option>\n {!field.customValue && (\n <TapestrySelect.Option value={dateBeforeValue}>\n {dateBeforeValue}\n </TapestrySelect.Option>\n )}\n <TapestrySelect.Option value=\"specific-date\">\n A specific date\n </TapestrySelect.Option>\n {allowUnansweredOption && (\n <TapestrySelect.Option value=\"unanswered\">\n Unanswered\n </TapestrySelect.Option>\n )}\n </TapestrySelect>\n {specificDate && (\n <Box>\n <TapestryDateField\n defaultOpen\n formatValue={orgFormat}\n marginLeft={1}\n onChange={handleValueChanged}\n size=\"lg\"\n value={dateFieldValue}\n />\n </Box>\n )}\n </StackView>\n )\n}\n\nconst Checkboxes = ({\n fieldId,\n options,\n onChange,\n}: {\n fieldId: string\n onChange: Function\n options: { description: string; value: string | number }[]\n}) => {\n const [selectedValues, setSelectedValues] = useState({})\n\n const handleCheckboxesChange = (selectedValue, value) => {\n const newSelectedValues = { ...selectedValues }\n newSelectedValues[value] = selectedValue\n setSelectedValues(newSelectedValues)\n onChange({ fieldId, value: newSelectedValues })\n }\n\n return (\n <StackView spacing={1}>\n {options.map((item) => (\n <Box key={item.value}>\n <Input.InputLabel controls={`checkboxes_${fieldId}_${item.value}`}>\n {item.description || item.value}\n </Input.InputLabel>\n <TapestrySelect\n id={`checkboxes_${fieldId}_${item.value}`}\n onChange={({ selectedValue }) =>\n handleCheckboxesChange(selectedValue, item.value)\n }\n size=\"lg\"\n emptyValue={\"Don't change\"}\n >\n <TapestrySelect.Option value=\"check\">Check</TapestrySelect.Option>\n <TapestrySelect.Option value=\"uncheck\">\n Uncheck\n </TapestrySelect.Option>\n </TapestrySelect>\n </Box>\n ))}\n </StackView>\n )\n}\n\nconst NumberField = ({\n field,\n onChange,\n value,\n}: {\n field: DefinitionField\n onChange: Function\n value: string\n}) => {\n const minimumValue = field.minValue >= 0 ? field.minValue : 1\n const maximumValue =\n field.maxValue >= 1 && field.maxValue <= 365 ? field.maxValue : 365\n\n const [inputValue, setInputValue] = useState(Number(field.defaultValue) || 1)\n\n useEffect(() => {\n onChange({ fieldId: field.id, value: field.defaultValue || 1 })\n }, [field])\n\n return (\n <StackView>\n <Input.InputBox>\n <TapestryNumberField\n onChange={(value: string) => {\n const newNumberValue = Number(value) || 0\n setInputValue(newNumberValue)\n\n onChange({\n fieldId: field.id,\n value: Math.min(\n Math.max(newNumberValue, minimumValue),\n maximumValue\n ),\n })\n }}\n placeholder={field.placeholder}\n size=\"lg\"\n value={value}\n min={minimumValue}\n max={maximumValue}\n hasControls={true}\n />\n </Input.InputBox>\n {inputValue > maximumValue && (\n <Alert\n type=\"error\"\n paddingHorizontal={token(\"--t-spacing-1\")}\n paddingVertical={token(\"--t-spacing-half\")}\n display=\"inline-block\"\n marginTop={1.5}\n >\n <StackView axis=\"horizontal\" alignment=\"center\" spacing={0.75}>\n <Icon\n name=\"general.exclamationTriangle\"\n size=\"sm\"\n color=\"delete45\"\n />\n <Text size={token(\"--t-font-size-md\")}>\n Value cannot exceed {maximumValue}.\n </Text>\n </StackView>\n </Alert>\n )}\n </StackView>\n )\n}\n\nconst TextField = ({\n field,\n value,\n onChange,\n}: {\n field: DefinitionField\n onChange: Function\n value: any\n}) => {\n const handleTextChange = (e) => {\n const val = e.target.value\n onChange({ fieldId: field.id, value: val })\n }\n return (\n <Box>\n <Input\n size=\"lg\"\n value={value}\n id={field.id}\n placeholder={field.placeholder}\n onChange={handleTextChange}\n />\n </Box>\n )\n}\n\nconst RadioButtons = ({\n field,\n options,\n onChange,\n value,\n}: {\n field: DefinitionField\n onChange: Function\n options: LoadedList[]\n value: any\n}) => {\n const handleCheckedChange = (e) => {\n onChange({ fieldId: field.id, value: e.target.value })\n }\n\n return (\n <StackView marginTop={1} spacing={0.5}>\n {options.map((option) => (\n <Radio\n checked={value === option.value}\n key={option.value}\n label={option.description || option.value}\n onChange={handleCheckedChange}\n size=\"md\"\n value={option.value}\n />\n ))}\n </StackView>\n )\n}\n\nconst Loading = () => (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n paddingHorizontal={1.75}\n paddingVertical={token(\"--t-spacing-1\")}\n radius={token(\"--t-border-radius-md\")}\n border={`1px solid ${token(\"--t-border-color\")}`}\n >\n <Spinner size=\"xs\" />\n <Text fontSize={token(\"--t-font-size-md\")} lineHeight={2.75}>\n Loading\n </Text>\n </StackView>\n)\n\nexport default Field\n","import { useEffect } from \"react\"\n\nimport Field from \"./field\"\nimport { getRenderedFields } from \"./utils/utils\"\n\ninterface FieldsProps {\n canAccessPeople: boolean\n definitionFields: DefinitionField[]\n loadListForField: LoadListForField\n loadedLists: { [k: string]: LoadedList[] }\n loadingLists: { [k: string]: boolean }\n onChange: Function\n selectedFieldOptions: SelectedFieldOptions\n}\n\nconst Fields = ({\n canAccessPeople,\n definitionFields,\n onChange,\n selectedFieldOptions,\n loadListForField,\n loadedLists,\n loadingLists,\n}: FieldsProps): JSX.Element => {\n useEffect(() => {\n const newSelections = definitionFields.reduce((acc, field) => {\n if (Object.prototype.hasOwnProperty.call(field, \"defaultValue\")) {\n acc[field.id] = field.defaultValue\n } else if (field.kind === \"DateField\") {\n acc[field.id] = field.customValue || \"Date automation runs\"\n }\n\n return acc\n }, {})\n onChange(newSelections)\n }, [definitionFields, onChange])\n\n const renderableFields = getRenderedFields(\n definitionFields,\n selectedFieldOptions\n )\n\n const handleSelectedFieldOptionsChange = ({ fieldId, value }) => {\n const newSelections = { ...selectedFieldOptions }\n const dependents = definitionFields.filter((field) => field.dependsOn)\n dependents.map((dependent) => {\n if (dependent.dependsOn.includes(fieldId)) {\n const deeper = dependents.find((d) =>\n d.dependsOn.includes(dependent.id)\n )\n if (deeper) {\n delete newSelections[deeper.id]\n }\n delete newSelections[dependent.id]\n\n if (\n dependent.defaultValue !== undefined &&\n newSelections[dependent.id] === undefined\n ) {\n newSelections[dependent.id] = dependent.defaultValue\n }\n }\n })\n\n if (value === \"no-option\") {\n delete newSelections[fieldId]\n } else {\n newSelections[fieldId] = value\n }\n\n onChange({ ...newSelections })\n }\n\n if (definitionFields.length) {\n return (\n <div>\n {renderableFields.map((field) => {\n return (\n <Field\n canAccessPeople={canAccessPeople}\n field={field}\n key={field.id}\n onChange={handleSelectedFieldOptionsChange}\n value={selectedFieldOptions[field.id]}\n selectedFieldOptions={selectedFieldOptions}\n loadListForField={loadListForField}\n loadedLists={loadedLists}\n loadingLists={loadingLists}\n />\n )\n })}\n </div>\n )\n } else {\n return null\n }\n}\n\nexport default Fields\n","import { Client } from \"@planningcenter/api-client\"\nimport { pcoApiRoot } from \"./utils/pco-api-root\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Alert,\n Box,\n Button,\n Checkbox,\n Icon,\n Input,\n Link,\n Select,\n Spinner,\n StackView,\n Text,\n} from \"@planningcenter/tapestry-react\"\nimport { cloneDeep, set } from \"lodash\"\nimport { useCallback, useEffect, useMemo, useRef, useState } from \"react\"\n\nimport Definition from \"./definition\"\nimport Fields from \"./fields\"\nimport * as alerts from \"./utils/alerts\"\nimport {\n buildDescription,\n fieldListIdentifier,\n getRenderedFields,\n} from \"./utils/utils\"\n\nconst client = new Client({ root: pcoApiRoot(\"people\"), version: \"LATEST\" })\nconst webhooksClient = new Client({\n root: pcoApiRoot(\"webhooks\"),\n version: \"LATEST\",\n})\nconst errorAlertProps = {\n css: { borderRadius: token(\"--t-border-radius-md\") },\n paddingHorizontal: 1.75,\n paddingVertical: 1.25,\n type: \"error\",\n}\n\ntype TopbarResponse = {\n data: {\n apps: Array<{ name: string }>\n type: \"Topbar\"\n }\n}\n\nasync function getVisibleApps() {\n return client\n .get<TopbarResponse>({\n data: {\n fields: { Topbar: \"apps\" },\n },\n url: \"/me/topbar\",\n })\n .then(({ data }) => data.apps.map((a) => a.name))\n}\n\nasync function getWebhooksApps() {\n return webhooksClient\n .get<{ data: Array<{ name: string; type: \"OperationApp\" }> }>({\n data: { fields: { OperationApp: \"name\" } },\n url: \"/operation_apps\",\n })\n .then(({ data }) => data.map((a) => a.name))\n}\n\nasync function getOperationApps() {\n const [visibleApps, webhooksApps] = await Promise.all([\n getVisibleApps(),\n getWebhooksApps(),\n ])\n\n return visibleApps\n .filter((app) => webhooksApps.includes(app))\n .sort()\n .map((app: string) => ({ id: app.toLowerCase(), name: app }))\n}\n\nasync function getOperationDefinitions(app: string) {\n return webhooksClient\n .get({\n data: {\n fields: {\n OperationDefinition:\n \"definition_class,definition_fields,definition_identifier,description,group,section,section_group,footer_message\",\n },\n filter: \"automation_allowed\",\n },\n url: `/operation_apps/${app}/operation_definitions`,\n })\n .then(({ data }) => data)\n}\n\nasync function getListOptions({\n app,\n field,\n definitionIdentifier,\n dependencies,\n}: {\n app: string\n definitionIdentifier: string\n dependencies: { [k: string]: string }\n field: DefinitionField\n}): Promise<LoadedList[]> {\n if (field.kind === \"PersonSearch\") {\n const { data: people } = await client.get<{\n data: { avatar: string; id: number; name: string }[]\n }>({\n data: {\n fields: { Person: \"avatar,name\" },\n where: { search_name_or_email: dependencies.query, status: \"active\" },\n },\n url: \"/people\",\n })\n\n return people.map((p) => ({\n description: p.name,\n meta: { avatar: p.avatar },\n value: p.id.toString(),\n }))\n } else {\n const { data } = await webhooksClient.get({\n data: {\n ...dependencies,\n definitionIdentifier,\n fields: {\n OperationDefinitionList: \"values\",\n },\n },\n url: `/operation_apps/${app}/operation_definition_lists/${field.listClass}`,\n })\n return data.values\n }\n}\n\nconst NewAutomation = ({\n afterCreateOptions,\n blankStateLink,\n debugMode = false,\n defaultApp,\n description,\n onRequestClose,\n trigger,\n}: {\n afterCreateOptions?: AfterCreateOptions\n blankStateLink: string\n debugMode?: boolean\n defaultApp: string\n description: string\n onRequestClose: () => void\n trigger: AutomationTrigger\n}) => {\n const [selectedTriggerEvent, setSelectedTriggerEvent] = useState(\n trigger.events[0]\n )\n const [dynamicTriggerConditions, setDynamicTriggerConditions] = useState({})\n const [selectedApp, setSelectedApp] = useState(defaultApp)\n const [operationApps, setOperationApps] = useState<\n { id: string; name: string }[]\n >([])\n const [operationDefinitions, setOperationDefinitions] = useState<\n OperationDefinition[]\n >([])\n const [loadingOperationDefinitions, setLoadingOperationDefinitions] =\n useState(true)\n const [selectedDefinition, setSelectedDefinition] =\n useState<OperationDefinition>()\n const [selectedFieldOptions, setSelectedFieldOptions] =\n useState<SelectedFieldOptions>({})\n const [loadedLists, setLoadedLists] = useState<{ [k: string]: LoadedList[] }>(\n {}\n )\n const [loadingLists, setLoadingLists] = useState<{ [k: string]: boolean }>({})\n const [submitting, setSubmitting] = useState(false)\n const [error, setError] = useState<{\n automation?: string | string[]\n definitions?: string | string[]\n selected_definition?: string | string[]\n }>({})\n const [callAfterCreate, setCallAfterCreate] = useState(false)\n const [triggerParams, setTriggerParams] = useState<{ [k: string]: string }>(\n {}\n )\n const activeAppRef = useRef(null)\n\n const canAccessPeople = useMemo(\n () => operationApps.map((a) => a.id).includes(\"people\"),\n [operationApps]\n )\n\n const definitionIdentifier = selectedDefinition?.definitionIdentifier\n const dangerAlertPresent =\n selectedDefinition?.footerMessage?.kind === \"danger\"\n\n const loadListForField = useCallback<LoadListForField>(\n ({ field, dependencies }) => {\n setLoadingLists((prev) => ({\n ...prev,\n [fieldListIdentifier(field)]: true,\n }))\n getListOptions({\n app: selectedApp,\n definitionIdentifier,\n dependencies,\n field,\n })\n .then((ret) => {\n setLoadedLists((prev) => ({\n ...prev,\n [fieldListIdentifier(field)]: ret,\n }))\n setLoadingLists((prev) => ({\n ...prev,\n [fieldListIdentifier(field)]: false,\n }))\n })\n .catch((error) => setError({ selected_definition: error }))\n },\n [selectedApp, definitionIdentifier]\n )\n\n const handleChangeSelectedApp = (app: string) => {\n setSelectedApp(app)\n setLoadingOperationDefinitions(true)\n setOperationDefinitions([])\n activeAppRef.current = app\n setSelectedDefinition(null)\n setSelectedFieldOptions({})\n setError({})\n getOperationDefinitions(app)\n .then(setOperationDefinitions)\n .then(() => setLoadingOperationDefinitions(false))\n .catch((error) => setError({ definitions: error }))\n }\n\n const handleChangeTriggerEvent = (\n selectedValue: typeof selectedTriggerEvent\n ) => {\n setSelectedTriggerEvent(selectedValue)\n setDynamicTriggerConditions({})\n }\n\n useEffect(() => {\n setError({})\n getOperationApps().then((apps) => {\n setOperationApps(apps)\n const defaultSelection = apps.find((app) => app.id === defaultApp)\n ? defaultApp\n : apps[0].id\n setSelectedApp(defaultSelection)\n getOperationDefinitions(defaultSelection)\n .then((definitions) => {\n if (!activeAppRef.current) {\n setOperationDefinitions(definitions)\n setLoadingOperationDefinitions(false)\n }\n })\n .catch((error) => setError({ definitions: error }))\n })\n }, [defaultApp])\n\n useEffect(() => {\n setError({})\n }, [selectedFieldOptions])\n\n const triggerConditions = cloneDeep(\n \"conditions\" in selectedTriggerEvent\n ? selectedTriggerEvent.conditions\n : trigger.conditions\n )\n for (const key in dynamicTriggerConditions) {\n set(triggerConditions, key, dynamicTriggerConditions[key])\n }\n const dynamicConditions =\n \"dynamicConditions\" in selectedTriggerEvent\n ? selectedTriggerEvent.dynamicConditions\n : trigger.dynamicConditions\n\n const handleSelectedDefinitionChange = (\n newDefinition: OperationDefinition\n ) => {\n setSelectedDefinition(newDefinition)\n setError({})\n setSelectedFieldOptions({})\n }\n\n function getDescription(): string {\n const descriptionParts = buildDescription({\n loadedLists,\n selectedDefinition,\n selectedFieldOptions,\n })\n\n let description = descriptionParts.name\n\n if (descriptionParts.description) {\n description += ` (${descriptionParts.description})`\n }\n\n return description\n }\n\n function handleSubmit() {\n if (submitting) {\n return\n }\n const operation_params = { ...selectedFieldOptions }\n\n if (selectedDefinition.definitionIdentifier) {\n operation_params.definition_identifier =\n selectedDefinition.definitionIdentifier\n }\n\n const data = {\n _e: trigger.resource,\n data: {\n attributes: {\n description: getDescription(),\n name: selectedTriggerEvent.name,\n operation_app_name: selectedApp,\n operation_definition_class_name: selectedDefinition.definitionClass,\n operation_params,\n trigger_conditions: triggerConditions,\n trigger_params: triggerParams,\n },\n type: \"AutomationSubscription\",\n },\n }\n if (callAfterCreate) {\n alerts.confirmCreate\n .fire({\n cancelButtonText: \"Cancel\",\n confirmButtonText: \"Yes, perform action\",\n text: \"This will happen immediately after creating your new automation. Are you sure?\",\n title: `${afterCreateOptions.label}?`,\n })\n .then((result: { value: any }) => {\n if (result.value) {\n submitCreate(data)\n } else {\n setSubmitting(false)\n setCallAfterCreate(false)\n }\n })\n } else {\n submitCreate(data)\n }\n }\n\n function submitCreate(data) {\n setSubmitting(true)\n webhooksClient\n .post({\n data,\n url: \"/me/automation_subscriptions\",\n })\n .then(() => {\n if (afterCreateOptions?.onConfirm && callAfterCreate) {\n onRequestClose()\n afterCreateOptions.onConfirm({ ...data })\n } else {\n window.location.reload()\n }\n })\n .catch((error) => {\n setSubmitting(false)\n if (error.errors) {\n setError({ automation: error.errors })\n } else {\n alert(\"something even worse happened!\")\n }\n })\n }\n\n return (\n <StackView paddingTop={4} spacing={2}>\n {description && (\n <Box>\n <Text\n style={{\n color: token(\"--t-text-color\"),\n fontSize: token(\"--t-font-size-md\"),\n lineHeight: 1.65,\n marginBottom: token(\"--t-spacing-2\"),\n }}\n >\n {description}{\" \"}\n <Link external to={blankStateLink}>\n Learn more\n </Link>\n </Text>\n </Box>\n )}\n {error.automation && (\n <Alert {...errorAlertProps}>\n <Text>\n There was an error creating your automation. Please change your\n selections and try again or contact support if the problem persists.\n </Text>\n </Alert>\n )}\n <StackView spacing={1}>\n <Input.InputLabel\n color={token(\"--t-text-color\")}\n controls=\"select-trigger-event\"\n fontSize={token(\"--t-font-size-md\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n >\n When a person...\n </Input.InputLabel>\n <Select\n id=\"select-trigger-event\"\n onChange={({ selectedValue }) =>\n handleChangeTriggerEvent(selectedValue)\n }\n size=\"lg\"\n value={selectedTriggerEvent}\n >\n {trigger.events.map((triggerEvent, idx) => (\n <Select.Option\n key={`${triggerEvent.name}_${idx}`}\n value={triggerEvent}\n >\n {triggerEvent.description}\n </Select.Option>\n ))}\n </Select>\n\n {dynamicConditions?.length > 0 && (\n <Fields\n canAccessPeople={canAccessPeople}\n definitionFields={dynamicConditions}\n selectedFieldOptions={dynamicTriggerConditions}\n onChange={setDynamicTriggerConditions}\n loadedLists={{}}\n loadingLists={{}}\n loadListForField={() => null}\n />\n )}\n </StackView>\n\n <StackView spacing={1}>\n {operationApps.length > 0 ? (\n <Application\n selectedApp={selectedApp}\n operationApps={operationApps}\n onOperationAppChange={handleChangeSelectedApp}\n />\n ) : (\n <StackView spacing={1}>\n <Text\n color={token(\"--t-text-color-headline\")}\n fontSize={token(\"--t-font-size-md\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n >\n Then perform an action in...\n </Text>\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n paddingHorizontal={1.75}\n paddingVertical={token(\"--t-spacing-1\")}\n radius={4}\n border={`1px solid ${token(\"--t-border-color\")}`}\n >\n <Spinner size=\"xs\" />\n <Text fontSize={token(\"--t-font-size-md\")} lineHeight={2.75}>\n Loading\n </Text>\n </StackView>\n </StackView>\n )}\n {error.definitions ? (\n <Alert marginTop={token(\"--t-spacing-1\")} {...errorAlertProps}>\n <Text>\n There was a problem looking up automations. Please contact support\n if the problem persists.\n </Text>\n </Alert>\n ) : loadingOperationDefinitions ? (\n <LoadingOperationDefinitions />\n ) : (\n <Definition\n selectedOperation={selectedDefinition}\n operationDefinitions={operationDefinitions}\n onOperationDefinitionChange={handleSelectedDefinitionChange}\n />\n )}\n </StackView>\n\n {selectedDefinition &&\n (error.selected_definition ? (\n <Alert {...errorAlertProps}>\n <Text>\n There was a problem looking up automation options. Please contact\n support if the problem persists.\n </Text>\n </Alert>\n ) : (\n <>\n <Fields\n canAccessPeople={canAccessPeople}\n definitionFields={selectedDefinition.definitionFields || []}\n onChange={setSelectedFieldOptions}\n selectedFieldOptions={selectedFieldOptions}\n loadedLists={loadedLists}\n loadListForField={loadListForField}\n loadingLists={loadingLists}\n />\n {afterCreateOptions?.label && (\n <Checkbox\n disabled={\n submitting ||\n disableSubmit(selectedDefinition, selectedFieldOptions)\n }\n label={afterCreateOptions.label}\n checked={callAfterCreate}\n onChange={() => setCallAfterCreate(!callAfterCreate)}\n />\n )}\n {selectedTriggerEvent?.triggerParams?.map((param, idx) => (\n <Checkbox\n key={`${param.key}_${idx}`}\n label={param.description}\n checked={\n (triggerParams && triggerParams[param.key]) ||\n param.defaultValue\n }\n onChange={(e) => {\n setTriggerParams((prev) => ({\n ...prev,\n [`${param.key}`]: e.target.checked,\n }))\n }}\n />\n ))}\n {dangerAlertPresent && (\n <Alert {...errorAlertProps}>\n <StackView axis=\"horizontal\" spacing={1.5}>\n <Icon\n size={token(\"--t-element-size-lg\")}\n name=\"general.exclamationTriangle\"\n color={token(\"--t-icon-color-status-error\")}\n />\n <Text\n dangerouslySetInnerHTML={{\n __html: selectedDefinition.footerMessage?.html,\n }}\n />\n </StackView>\n </Alert>\n )}\n </>\n ))}\n\n {debugMode && (\n <pre>\n {JSON.stringify(\n {\n description: selectedDefinition && getDescription(),\n loadedLists,\n selectedDefinition,\n selectedFieldOptions,\n triggerConditions,\n },\n null,\n 4\n )}\n </pre>\n )}\n\n <StackView\n alignment=\"center\"\n axis=\"horizontal\"\n borderTop={`1px solid ${token(\"--t-border-color\")}`}\n distribution=\"end\"\n marginTop={2}\n marginHorizontal={-4}\n paddingHorizontal={4}\n paddingTop={3}\n spacing={2}\n >\n <Button\n color={token(\"--t-text-color-headline\")}\n // for temporary backwards compatibility\n data-modal-close\n fontWeight={token(\"--t-font-weight-normal\")}\n onClick={onRequestClose}\n size=\"md\"\n title=\"Cancel\"\n variant=\"naked\"\n />\n <Button\n disabled={\n submitting ||\n dangerAlertPresent ||\n disableSubmit(selectedDefinition, selectedFieldOptions)\n }\n onClick={handleSubmit}\n size=\"md\"\n theme=\"primary\"\n title={getButtonText(selectedDefinition, selectedFieldOptions)}\n variant=\"fill\"\n data-testid=\"create-automation\"\n />\n </StackView>\n </StackView>\n )\n}\n\nfunction disableSubmit(\n selectedDefinition: OperationDefinition,\n selectedFieldOptions: SelectedFieldOptions\n) {\n if (selectedDefinition) {\n const renderedFields = getRenderedFields(\n selectedDefinition.definitionFields,\n selectedFieldOptions\n )\n\n const requiredFields = renderedFields.filter((field) => field.required)\n const selectFields = renderedFields.filter((field) => fieldIsSelect(field))\n\n return (\n !requiredFields.every((field) =>\n fieldIsFilled(field, selectedFieldOptions)\n ) ||\n !selectFields.every((field) => fieldIsFilled(field, selectedFieldOptions))\n )\n } else {\n return true\n }\n}\n\nfunction fieldIsSelect(field: DefinitionField) {\n return field.kind === \"Select\" || field.kind === \"SelectSearch\"\n}\n\nfunction fieldIsFilled(\n field: DefinitionField,\n selectedFieldOptions: SelectedFieldOptions\n) {\n if (fieldIsSelect(field)) {\n return selectedFieldOptions.hasOwnProperty(field.id)\n } else {\n return (\n selectedFieldOptions.hasOwnProperty(field.id) &&\n selectedFieldOptions[field.id] &&\n selectedFieldOptions[field.id].toString().trim() !== \"\"\n )\n }\n}\n\nfunction getNextRequiredDescription(\n selectedDefinition: OperationDefinition,\n selectedFieldOptions: SelectedFieldOptions\n) {\n if (!selectedDefinition?.definitionFields) return\n\n const renderedFields = getRenderedFields(\n selectedDefinition.definitionFields,\n selectedFieldOptions\n )\n\n for (const field of renderedFields) {\n if (field.required && !fieldIsFilled(field, selectedFieldOptions))\n return field.description\n }\n}\n\nfunction getButtonText(\n selectedDefinition: OperationDefinition,\n selectedFieldOptions: SelectedFieldOptions\n) {\n const nextRequiredDescription = getNextRequiredDescription(\n selectedDefinition,\n selectedFieldOptions\n )\n\n if (!selectedDefinition) {\n return \"Select an action\"\n } else if (nextRequiredDescription) {\n return `Select a${\n nextRequiredDescription.charAt(0).match(/[aeiou]/i) ? \"n\" : \"\"\n } ${nextRequiredDescription.toLowerCase()}`\n } else {\n return \"Create automation\"\n }\n}\n\nconst Application = ({\n onOperationAppChange,\n operationApps,\n selectedApp,\n}: {\n onOperationAppChange: (selectedValue: string) => void\n operationApps: Array<{ id: string; name: string }>\n selectedApp: string\n}) => {\n const handleChange = ({ selectedValue }) => {\n onOperationAppChange(selectedValue)\n }\n\n return (\n <StackView spacing={1}>\n <Input.InputLabel\n color={token(\"--t-text-color-headline\")}\n controls=\"select-product\"\n fontSize={token(\"--t-font-size-md\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n >\n Then perform an action in...\n </Input.InputLabel>\n <Select\n autoFocus\n id=\"select-product\"\n onChange={handleChange}\n size=\"lg\"\n value={selectedApp}\n >\n {operationApps.map((app) => (\n <Select.Option key={app.id} value={app.id}>\n {app.name}\n </Select.Option>\n ))}\n </Select>\n </StackView>\n )\n}\n\nconst LoadingOperationDefinitions = () => (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n paddingHorizontal={1.75}\n paddingVertical={token(\"--t-spacing-1\")}\n radius={token(\"--t-border-radius-md\")}\n border={`1px solid ${token(\"--t-border-color\")}`}\n >\n <Spinner size=\"xs\" />\n <Text fontSize={token(\"--t-font-size-md\")} lineHeight={2.75}>\n Loading\n </Text>\n </StackView>\n)\n\nexport default NewAutomation\n","import { token } from \"@planningcenter/tapestry\"\nimport {\n Button,\n Heading,\n Modal,\n StackView,\n ThemeProvider,\n} from \"@planningcenter/tapestry-react\"\nimport React from \"react\"\nimport { createPortal } from \"react-dom\"\n\nfunction CloseModalIcon({\n onClick,\n}: {\n onClick: React.MouseEventHandler\n}): JSX.Element {\n return (\n <Button\n as=\"button\"\n height={token(\"--t-element-size-md\")}\n icon={{ color: token(\"--t-icon-color-dim\"), name: \"general.x\" }}\n onClick={onClick}\n size={\"sm\"}\n title=\"Close\"\n variant=\"naked\"\n />\n )\n}\n\nfunction NewAutomationModal({\n children,\n onRequestClose,\n open,\n theme,\n}: {\n children: React.ReactNode\n onRequestClose: () => void\n open: boolean\n theme: object\n}): React.ReactPortal | JSX.Element {\n return createPortal(\n <ThemeProvider theme={theme}>\n <Modal\n open={open}\n onRequestClose={onRequestClose}\n maxWidth={75}\n boxShadow=\"0 0 20px rgba(0, 0, 0, 0.15)\"\n padding={token(\"--t-spacing-4\")}\n paddingBottom={token(\"--t-spacing-3\")}\n radius={token(\"--t-border-radius-lg\")}\n zIndex={10009}\n >\n <StackView\n axis=\"horizontal\"\n distribution=\"space-between\"\n alignment=\"center\"\n >\n <Heading\n level={2}\n color={token(\"--t-text-color-headline\")}\n fontWeight={token(\"--t-font-weight-medium\")}\n fontSize={token(\"--t-font-size-2xl\")}\n lineHeight=\"1.4\"\n >\n Create automation\n </Heading>\n <CloseModalIcon onClick={onRequestClose} />\n </StackView>\n {children}\n </Modal>\n <style>{`\n .swal2-container.swal2-backdrop-show { z-index: 10001 }\n `}</style>\n </ThemeProvider>,\n document.body\n )\n}\n\nexport default NewAutomationModal\n","import * as churchCenter from \"@planningcenter/icons/paths/church-center\"\nimport * as logomark from \"@planningcenter/icons/paths/logomark\"\nimport * as services from \"@planningcenter/icons/paths/services\"\n\nexport const icons = {\n churchCenter,\n logomark,\n services,\n}\n","import { Client } from \"@planningcenter/api-client\"\nimport { pcoApiRoot } from \"./utils/pco-api-root\"\nimport { token } from \"@planningcenter/tapestry\"\nimport {\n Box,\n Button,\n Heading,\n Icon,\n Spinner,\n StackView,\n Summary,\n Text,\n ThemeProvider,\n TileView,\n} from \"@planningcenter/tapestry-react\"\nimport { useEffect, useState } from \"react\"\nimport sortBy from \"lodash/sortBy\"\n\nimport SvgAutomations from \"./assets/svg_automations\"\nimport { EditableAutomation } from \"./automation\"\nimport { OrganizationContext } from \"./contexts/organization_context\"\nimport IncomingAutomations from \"./incoming_automations\"\nimport NewAutomation from \"./new_automation\"\nimport NewAutomationModal from \"./new_automation_modal\"\nimport styles from \"./styles.scss\"\nimport * as alerts from \"./utils/alerts\"\nimport {\n fetchAutomations,\n fetchCreatorProfiles,\n mergeProfilesAndSubscriptions,\n} from \"./utils/fetch-automations\"\nimport { icons } from \"./utils/theme\"\nimport {\n deobfuscateDescriptions,\n pluralize,\n forbiddenText,\n} from \"./utils/utils\"\n\nconst webhooksClient = new Client({\n root: pcoApiRoot(\"webhooks\"),\n version: \"2022-10-20\",\n})\n\nfunction Header({\n afterCreateOptions,\n automations,\n blankStateLink,\n canCreate,\n defaultApp,\n description,\n hasActiveAutomations,\n loading,\n onPauseAutomations,\n theme,\n trigger,\n}: {\n afterCreateOptions?: AfterCreateOptions\n automations: AutomationInstance[]\n blankStateLink: string\n canCreate: boolean\n defaultApp: string\n description: string\n hasActiveAutomations: boolean\n loading: boolean\n onPauseAutomations: Function\n theme: object\n trigger: AutomationTrigger\n}) {\n const [newModalVisible, setNewModalVisible] = useState(false)\n const isPaused = canCreate && !hasActiveAutomations\n\n const activeCount = automations.filter(\n (automation) => automation.active\n ).length\n const pausedCount = automations.filter(\n (automation) => !automation.active\n ).length\n\n return (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n backgroundColor={\n isPaused ? token(\"--t-fill-color-status-warning-ghost\") : undefined\n }\n borderBottom={\n isPaused\n ? undefined\n : `1px solid ${token(\"--t-border-color\")}`\n }\n data-testid=\"automations-header\"\n distribution=\"space-between\"\n marginHorizontal={-3}\n marginBottom={token(\"--t-spacing-2\")}\n marginTop={-3}\n paddingHorizontal={token(\"--t-spacing-3\")}\n paddingVertical={token(\"--t-spacing-2\")}\n spacing={token(\"--t-spacing-2\")}\n wrap\n zIndex={2}\n >\n {canCreate && !hasActiveAutomations ? (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n marginHorizontal={1}\n spacing={1}\n >\n <Icon\n size={2}\n color={token(\"--t-icon-color-status-warning\")}\n name=\"general.exclamationTriangle\"\n />\n <Heading\n color={token(\"--t-text-color-headline\")}\n level={2}\n size={token(\"--t-font-size-lg\")}\n >\n Automations are currently paused\n </Heading>\n </StackView>\n ) : (\n <Heading\n color={token(\"--t-text-color-headline\")}\n level={2}\n size={token(\"--t-font-size-lg\")}\n >\n {loading\n ? \"Active automations\"\n : pluralize(activeCount, \"active automation\")}\n {pausedCount > 0 ? ` (${pausedCount} paused)` : \"\"}\n </Heading>\n )}\n {canCreate &&\n (hasActiveAutomations ? (\n <StackView\n axis=\"horizontal\"\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n >\n {automations.length > 0 && (\n <Button onClick={onPauseAutomations} variant=\"outline\">\n Pause automations\n </Button>\n )}\n <Button\n theme=\"primary\"\n variant=\"fill\"\n onClick={() => setNewModalVisible(true)}\n >\n Create automation\n </Button>\n <NewAutomationModal\n open={newModalVisible}\n onRequestClose={() => setNewModalVisible(false)}\n theme={theme}\n >\n <NewAutomation\n description={description}\n blankStateLink={blankStateLink}\n defaultApp={defaultApp}\n trigger={trigger}\n onRequestClose={() => setNewModalVisible(false)}\n afterCreateOptions={afterCreateOptions}\n />\n </NewAutomationModal>\n </StackView>\n ) : (\n <Box>\n <StackView axis=\"horizontal\" alignment=\"center\" spacing={1}>\n <Button\n onClick={onPauseAutomations}\n theme=\"primary\"\n variant=\"outline\"\n >\n Enable automations\n </Button>\n <Button\n theme=\"primary\"\n disabled\n tooltip={{\n title: \"Automations must be enabled to create new ones\",\n }}\n >\n Create automation\n </Button>\n </StackView>\n </Box>\n ))}\n </StackView>\n )\n}\n\nexport default function Automations({\n afterCreateOptions,\n blankStateDescription,\n blankStateLink = \"https://pcopeople.zendesk.com/hc/en-us/articles/217582148-Automations\",\n currentPersonId,\n currentPersonCanCreate,\n defaultApp,\n incomingAutomationsParam,\n theme,\n trigger,\n currentOrganization,\n permissionDeniedReason = \"You need permissions of Editor or above to add an automation.\",\n disabled = false,\n disabledReason = \"Not allowed\",\n}: {\n afterCreateOptions?: AfterCreateOptions\n blankStateDescription: string\n blankStateLink?: string\n currentOrganization: {\n dateFormat: string\n olsonTimeZone: string\n twentyFourHourTime: boolean\n }\n currentPersonCanCreate: boolean\n currentPersonId: number\n defaultApp: string\n incomingAutomationsParam?: string\n permissionDeniedReason?: string\n theme?: object\n trigger?: AutomationTrigger\n disabled?: boolean\n disabledReason?: string\n}) {\n useEffect(() => {\n if (!trigger) return setLoading(false)\n fetchAutomations(trigger.resource)\n .then(fetchCreatorProfiles)\n .then(mergeProfilesAndSubscriptions)\n .then(deobfuscateDescriptions)\n .then(setAutomations)\n .then(() => setLoading(false))\n }, [trigger?.resource])\n\n const [automations, setAutomations] = useState([])\n const [loading, setLoading] = useState(true)\n const [newModalVisible, setNewModalVisible] = useState(false)\n\n const { dateFormat, twentyFourHourTime, olsonTimeZone } = currentOrganization\n\n const params = new URLSearchParams(window.location.search)\n\n const automationId = params.get(\"automation_id\")\n\n // make sure necessary icons are added to theme\n const customTheme = { ...theme, ...{ icons: { ...icons } } }\n\n useEffect(() => {\n document.body.toggleAttribute(\"data-loading-automations\", loading)\n }, [loading])\n\n const hasActiveAutomations = automations.length\n ? automations.some((a) => a.active)\n : true\n\n function handleDelete(id: number) {\n webhooksClient\n .delete({\n data: { _e: trigger.resource },\n url: `/automation_subscriptions/${id}`,\n })\n .then(() =>\n setAutomations(automations.filter((automation) => automation.id !== id))\n )\n .catch((error) => {\n const text =\n forbiddenText(error, \"delete\") ||\n \"There was a problem deleting this automation. Please try again in a few moments.\"\n alerts.alertError.fire({\n text,\n title: \"Uh oh!\",\n })\n })\n }\n\n function handlePauseAutomations() {\n webhooksClient\n .post({\n data: {\n data: {\n attributes: {\n _e: trigger.resource,\n active: !hasActiveAutomations,\n },\n },\n },\n url: \"/pause_automations\",\n })\n .then(() => {\n window.location.reload()\n })\n }\n\n const BlankStateHeadingProps = {\n color: token(\"--t-text-color\"),\n level: 2,\n size: token(\"--t-font-size-2xl\"),\n weight: token(\"--t-font-weight-bold\"),\n }\n\n const BlankStateTextProps = {\n color: token(\"--t-text-color-secondary\"),\n lineHeight: 3,\n size: token(\"--t-font-size-md\"),\n }\n\n function automationTriggerEvent(automation: AutomationInstance) {\n return trigger.events.find((event) => event.name === automation.name)\n }\n\n const handleUpdateAutomation =\n (originalAutomation: AutomationInstance) =>\n (newState: React.SetStateAction<AutomationInstance>) => {\n const updated =\n typeof newState == \"function\" ? newState(originalAutomation) : newState\n const newAutomations = [\n ...automations.filter((automation) => automation.id !== updated.id),\n updated,\n ]\n\n setAutomations(newAutomations)\n }\n\n return (\n <ThemeProvider theme={customTheme}>\n <OrganizationContext.Provider\n value={{ dateFormat, olsonTimeZone, twentyFourHourTime }}\n >\n {trigger && (\n <Header\n automations={automations}\n blankStateLink={blankStateLink}\n canCreate={currentPersonCanCreate && !disabled}\n loading={loading}\n defaultApp={defaultApp}\n description={blankStateDescription}\n theme={customTheme}\n trigger={trigger}\n hasActiveAutomations={hasActiveAutomations}\n onPauseAutomations={handlePauseAutomations}\n afterCreateOptions={afterCreateOptions}\n />\n )}\n {loading ? (\n <Summary\n image={<Spinner size=\"xl\" />}\n paddingVertical={10}\n title={\"Loading automations...\"}\n />\n ) : !trigger ? (\n <></>\n ) : (\n <Box data-testid=\"automations-section\">\n {automations?.length > 0 ? (\n <TileView spacing={3} marginVertical={3} minCellWidth={45}>\n {sortBy(automations, \"id\").map((a) => (\n <EditableAutomation\n key={a.id}\n automation={a}\n updateAutomation={handleUpdateAutomation(a)}\n onDelete={handleDelete}\n theme={customTheme}\n openHistoryNow={a.id === Number(automationId)}\n trigger={{\n event: automationTriggerEvent(a),\n resource: trigger.resource,\n }}\n currentPersonId={currentPersonId}\n currentPersonCanCreate={currentPersonCanCreate}\n disabled={disabled}\n disabledReason={disabledReason}\n />\n ))}\n </TileView>\n ) : (\n <StackView\n margin={token(\"--t-spacing-6\")}\n spacing={token(\"--t-spacing-2\")}\n alignment=\"center\"\n mediaQueries={{\n lg: {\n axis: \"horizontal\",\n distribution: \"center\",\n spacing: token(\"--t-spacing-6\"),\n },\n }}\n >\n <Box\n css={{\n \".symbol\": {\n height: \"100%\",\n width: \"100%\",\n },\n }}\n maxWidth={24}\n mediaQueries={{\n lg: {\n maxWidth: 40,\n },\n }}\n >\n <SvgAutomations />\n </Box>\n <StackView\n alignment=\"center\"\n spacing={token(\"--t-spacing-1\")}\n maxWidth={45}\n mediaQueries={{\n lg: {\n alignment: \"start\",\n textAlign: \"left\",\n },\n }}\n textAlign=\"center\"\n >\n {currentPersonCanCreate ? (\n <>\n <Heading {...BlankStateHeadingProps}>\n Add an automation\n </Heading>\n <StackView\n alignment=\"center\"\n marginBottom={token(\"--t-spacing-1\")}\n mediaQueries={{\n lg: {\n alignment: \"start\",\n },\n }}\n spacing={1}\n >\n <Text {...BlankStateTextProps}>\n {blankStateDescription}\n </Text>\n </StackView>\n <StackView\n axis=\"horizontal\"\n spacing={token(\"--t-spacing-1\")}\n >\n <Button\n variant=\"outline\"\n to={blankStateLink}\n color={`${token(\n \"--t-text-color-status-neutral\"\n )} !important`}\n >\n Learn more\n </Button>\n <Button\n as=\"button\"\n theme=\"primary\"\n variant=\"fill\"\n onClick={() => setNewModalVisible(true)}\n >\n Create automation\n </Button>\n </StackView>\n <NewAutomationModal\n open={newModalVisible}\n onRequestClose={() => setNewModalVisible(false)}\n theme={customTheme}\n >\n <NewAutomation\n defaultApp={defaultApp}\n description={blankStateDescription}\n blankStateLink={blankStateLink}\n onRequestClose={() => setNewModalVisible(false)}\n trigger={trigger}\n afterCreateOptions={afterCreateOptions}\n />\n </NewAutomationModal>\n </>\n ) : (\n <>\n <Heading {...BlankStateHeadingProps}>Automations</Heading>\n <Text {...BlankStateTextProps}>\n {permissionDeniedReason}\n </Text>\n </>\n )}\n </StackView>\n </StackView>\n )}\n </Box>\n )}\n {incomingAutomationsParam && (\n <IncomingAutomations\n encryptedParam={incomingAutomationsParam}\n trigger={trigger}\n />\n )}\n </OrganizationContext.Provider>\n <style>{styles}</style>\n </ThemeProvider>\n )\n}\n"],"names":["pcoApiRoot","app","protocol","hostname","window","location","includes","replace","SvgAutomations","React","createElement","id","xmlns","viewBox","className","opacity","d","fill","x","y","width","height","rx","ry","transform","OrganizationContext","createContext","dateFormat","olsonTimeZone","twentyFourHourTime","Swal__default","mixin","standardAlertOptions","Swal","successAlertOptions","alertError","errorAlertOptions","confirm","standardConfirmOptions","confirmDestroy","destroyConfirmOptions","confirmCreate","createConfirmOptions","deobfuscateDescriptions","subscriptions","Promise","all","map","subscription","_temp","operationDefinitionClassName","isDeobfuscatable","resolve","_temp3","description","_temp2","fetchWorkflow","workflowId","peopleClient","get","data","fields","Workflow","where","url","catch","name","then","e","reject","operationParams","workflow","workflowName","archivedAt","fieldDefinitionId","definitionIdentifier","match","fetchFieldDefinition","FieldDefinition","FieldOption","include","fieldDefinition","values","dataType","Object","entries","action","value","fieldOptions","find","fieldOption","parseInt","capitalize","join","toString","customFieldOptionDescription","deobfuscatedDescription","_deobfuscatedDescript","string","charAt","toUpperCase","slice","Client","root","version","fieldListIdentifier","field","listClass","kind","obfuscateDescriptionName","definition","definitionClass","hasOwnProperty","object","key","prototype","call","getListForField","loadedLists","list","Error","JSON","stringify","getRenderedFields","definitionFields","selectedFieldOptions","filter","renderIf","conditionKey","keys","isBoolean","describeSelectedFields","selectedDefinition","workflow_id_WorkflowsList","sensitiveString","o","workflow_id","obfuscateSelectedFieldDescriptions","label","momentDateFormat","format","dateLocalized","date","momentDate","moment","isValid","pluralize","count","word","singularize","triggerResourceParts","triggerResource","triggerParts","split","appName","resourceId","length","resourcePath","resourceType","forbiddenText","error","errors","status","fetchPeopleWhoTriggeredEvents","events","personIds","eventPersonId","body","recover","result","fetchPeople","people","_catch","Person","fetchEvents","automationId","params","webhooksClient","_e","Delivery","Event","order","STATUS","delivered","failed","ignored","pending","skipped","mergePeopleAndEvents","mergedData","reduce","personId","foundPerson","p","push","person","event","History","automation","filterWhere","onEventsStatusChange","loading","paginationProps","refresh","setParams","_","setError","useState","setLoading","eventPages","setEventPages","meta","setMeta","offset","resetOffset","perPage","totalCount","setOffset","currentPage","Math","floor","onPageChange","pageNum","totalPages","ceil","useCallback","usePagination","useEffect","per_page","pages","bubbleErrorToBoundary","undefined","useEvents","useContext","filteringEvents","automationCreatedRecently","diff","numDaysSince","createdAt","automationBeganOn","historyPreservationAlert","columns","cell","EventStatusBadge","css","padding","header","utcOffset","momentDateTimeFormat","Link","to","maxWidth","EventStatusMessage","flex","Fragment","RetryEventButton","IgnoreEventButton","refreshHistory","textAlign","minWidth","StackView","spacing","token","Heading","level","size","color","weight","Text","italic","Box","minHeight","alignItems","axis","distribution","Input","InputLabel","fontWeight","controls","Select","emptyValue","onChange","selectedValue","title","Option","Button","iconLeft","onClick","theme","variant","maxHeight","overflow","DataTable","_extends","empty","alignment","marginTop","marginBottom","svg","fontSize","loadingTitle","bodyCell","lineHeight","bodyRow","rowData","backgroundColor","headerCell","headerRow","setStatus","retryTitleFromStatus","statusIcon","post","attributes","response","eventsStatus","alerts","fire","text","disabled","badgeColors","border","badgeIcon","badgeTitle","Badge","background","foreground","paddingLeft","paddingRight","radius","renderLeft","Icon","marginLeft","stroke","strokeAlign","strokeWeight","lastDelivery","message","delivery","ERRORS","default","duplicated_event","failed_without_deliveries","whiteSpace","ToggleableDetails","details","responseBody","parse","parsedErrors","responseErrors","deliveryFailureReason","statusMessage","fontStyle","paddingTop","children","open","setOpen","inline","was","fontFamily","ErrorBoundary","Component","constructor","props","super","handleContactSupport","this","onRequestClose","openHelpdesk","state","hasError","static","render","Alert","type","marginVertical","boxShadow","style","CloseModalIcon","as","icon","HistoryModal","createPortal","ThemeProvider","Modal","paddingBottom","document","VALID_LOGO_NAMES","getValidLogoName","kebabName","kebabCase","isValidLogoName","fetchCurrentPersonAvatar","avatar","AutomationContext","EditableAutomation","updateAutomation","onDelete","openHistoryNow","disabledReason","AutomationWrapper","Header","Icons","Manage","Description","EditableFooter","IncomingAutomation","LinkToAutomation","IncomingDescription","Footer","triggerEventDescription","parseDescription","cardOpacity","active","paddingVertical","truncate","lowerFirst","conditionalSuffix","optionallyPrettifyArchivedPrefix","separator","external","triggerAdminUrl","canManage","tooltip","hover","rest","Provider","Card","currentPersonCanCreate","currentPersonId","trigger","historyVisible","setHistoryVisible","isActive","Dropdown","iconRight","Item","onSelect","createdById","Tooltip","placement","openDelay","isConfirmed","resource","prev","createdBy","avatarUrl","createdByName","confirmButtonText","ToggleSwitch","isChecked","patch","newStatus","triggerProductName","Logo","markOnly","operationAppName","Divider","marginHorizontal","Avatar","basis","source","buttonProps","paddingHorizontal","historyProps","setHistoryProps","toLocaleString","marginRight","triggerParams","useTriggerPersonOverride","exec","trim","startsWith","fetchPersonApps","App","PersonApp","personApp","allowPcoLogin","toLowerCase","fetchCreatorProfiles","compact","uniq","profiles","mergeProfilesAndSubscriptions","profile","fetchTriggerResources","automations","QUERYABLE_BY_MULTIPLE_IDS","registrations","services","NOT_QUERYABLE","automationsByModel","accumulator","automationTriggerResource","promises","flatMap","resourceParts","fetchNothing","fetchAllAtOnce","fetchOneAtATime","ids","allSettled","results","triggerResources","settledPromises","acc","concat","fetchIncomingAutomations","encryptedParam","AutomationSubscription","fetchResourceName","path","_props","client","model","upperFirst","IncomingAutomations","setAutomations","operationApps","buildGivingDescription","tr","resourceName","nameOrDescription","triggerResourceName","verb","messageName","mapNameToVerb","buildDescription","mergeTriggerResourceEventDescriptions","noResults","borderBottom","Summary","image","Spinner","TileView","minCellWidth","operationDefinitionId","od","sectionId","section","renderOptionsWithoutConsideringGroup","options","renderOptions","groupedOptions","groupBy","sort","gt","OptionGroup","Definition","selectedOperation","onOperationDefinitionChange","operationDefinitions","selectedSection","operationDefinitionsWithUniqueIds","primaryOperations","primarySectionOptions","uniqBy","group","sectionGroup","secondaryOperations","handleAnySelectChange","idType","renderOperations","operations","defaultValue","Field","canAccessPeople","loadListForField","loadingLists","dependencies","generator","memoizedObject","setMemoizedObject","newObject","isEqual","useMemoizedObject","dependsOn","depKey","camelCase","fieldDependencies","listOptions","actionAllowedOptions","op","automationNotAllowed","info","HelperDrawer","Toggle","drawerId","Loading","fieldId","SelectSearch","Checkbox","TextArea","DateField","Checkboxes","NumberField","PersonSearch","isLoading","TextField","RadioButtons","dangerouslySetInnerHTML","__html","content","console","warn","renderField","overridenEmptyValue","option","groupTypes","TapestrySelect","items","item","handleSelectedValueChange","prompt","generatePrompt","selectedOption","selectedLabel","prevSelectedLabel","setPrevSelectedLabel","query","setQuery","showFilteredOptions","setShowFilteredOptions","showClearButton","setShowClearButton","filteredOptions","sortBy","formattedQuery","TapestryCombobox","Combobox","Popover","closeOnSelect","closeButton","cursor","onBlur","target","onClear","onFocus","select","handleValueChange","openOnFocus","placeholder","popoverProps","matchWidths","renderRight","index","isCurrent","role","Highlight","Menu","immediateSearch","debouncedSearch","useMemo","debounce","search","cancel","myself","_setQuery","TapestryCheckbox","checked","TapestryTextArea","specificDate","setSpecificDate","todaysValue","customValue","dateBeforeValue","orgFormat","dateFieldValue","setDateFieldValue","toDate","allowUnansweredOption","handleSelectChange","TapestryDateField","defaultOpen","formatValue","selectedValues","setSelectedValues","handleCheckboxesChange","newSelectedValues","minimumValue","minValue","maximumValue","maxValue","inputValue","setInputValue","Number","InputBox","TapestryNumberField","newNumberValue","min","max","hasControls","display","handleCheckedChange","Radio","Fields","newSelections","renderableFields","handleSelectedFieldOptionsChange","dependents","dependent","deeper","getOperationDefinitions","OperationDefinition","getWebhooksApps","OperationApp","a","getVisibleApps","Topbar","apps","errorAlertProps","borderRadius","NewAutomation","afterCreateOptions","blankStateLink","debugMode","defaultApp","selectedTriggerEvent","setSelectedTriggerEvent","dynamicTriggerConditions","setDynamicTriggerConditions","selectedApp","setSelectedApp","setOperationApps","setOperationDefinitions","loadingOperationDefinitions","setLoadingOperationDefinitions","setSelectedDefinition","setSelectedFieldOptions","setLoadedLists","setLoadingLists","submitting","setSubmitting","callAfterCreate","setCallAfterCreate","setTriggerParams","activeAppRef","useRef","dangerAlertPresent","footerMessage","search_name_or_email","OperationDefinitionList","getListOptions","ret","selected_definition","visibleApps","webhooksApps","getOperationApps","defaultSelection","definitions","current","triggerConditions","cloneDeep","conditions","set","dynamicConditions","getDescription","descriptionParts","submitCreate","onConfirm","reload","alert","handleChangeTriggerEvent","triggerEvent","idx","Application","onOperationAppChange","LoadingOperationDefinitions","newDefinition","disableSubmit","param","html","borderTop","operation_params","definition_identifier","operation_app_name","operation_definition_class_name","trigger_conditions","trigger_params","cancelButtonText","getButtonText","renderedFields","requiredFields","required","selectFields","fieldIsSelect","every","fieldIsFilled","nextRequiredDescription","getNextRequiredDescription","autoFocus","handleChange","NewAutomationModal","zIndex","icons","churchCenter","logomark","canCreate","hasActiveAutomations","onPauseAutomations","newModalVisible","setNewModalVisible","isPaused","activeCount","pausedCount","wrap","blankStateDescription","incomingAutomationsParam","currentOrganization","permissionDeniedReason","fetchAutomations","URLSearchParams","customTheme","toggleAttribute","some","handleDelete","delete","BlankStateHeadingProps","BlankStateTextProps","originalAutomation","newState","updated","newAutomations","margin","mediaQueries","lg"],"mappings":"ynDAYO,SAASA,EAAWC,GACzB,MAAMC,SAAEA,EAAQC,SAAEA,GAAaC,OAAOC,SACtC,OAAKF,EAASG,SAAS,KAGf,GAAEJ,MAAaC,EAASI,QAAQ,SAAU,UAAUN,OAFlD,wCAAuCA,MAGnD,CClBA,MAAMO,EAAiBA,iBACrBC,MAAAC,cAAA,MAAA,CACEC,GAAG,oBACH,YAAU,oBACVC,MAAM,6BACNC,QAAQ,qBACRC,UAAU,uBAEVL,MAAAC,cAAA,QAAA,KAAO,4BACPD,MAAAC,cAAA,IAAA,CAAGK,QAAQ,oBACTN,MAAAC,cACEM,OAAAA,CAAAA,EAAE,uTACFC,KAAK,UACLH,UAAU,sCAGdL,MAAAC,cACEM,OAAAA,CAAAA,EAAE,qMACFC,KAAK,sBAEPR,MAAAC,cACEM,OAAAA,CAAAA,EAAE,0DACFC,KAAK,yBAEPR,MAAAC,cAAA,OAAA,CACEQ,EAAE,SACFC,EAAE,SACFC,MAAM,SACNC,OAAO,QACPC,GAAG,QACHC,GAAG,QACHN,KAAK,yBAEPR,MAAAC,cAAA,OAAA,CACEQ,EAAE,SACFC,EAAE,SACFC,MAAM,SACNC,OAAO,QACPC,GAAG,QACHC,GAAG,QACHN,KAAK,yBAEPR,MAAAC,cAAA,OAAA,CACEQ,EAAE,SACFC,EAAE,SACFC,MAAM,SACNC,OAAO,QACPC,GAAG,QACHC,GAAG,QACHN,KAAK,yBAEPR,MAAAC,sBACEQ,EAAE,SACFC,EAAE,SACFC,MAAM,SACNC,OAAO,QACPG,UAAU,2CACVP,KAAK,yBAEPR,MAAAC,cAAA,OAAA,CACEM,EAAE,mKACFC,KAAK,yBAEPR,MAAAC,cAAA,OAAA,CACEM,EAAE,2JACFC,KAAK,yBAEPR,MAAAC,cAAA,OAAA,CACEM,EAAE,iTACFC,KAAK,yBAEPR,MAAAC,cAAA,OAAA,CACEM,EAAE,8SACFC,KAAK,yBAEPR,MAAAC,cAAA,OAAA,CACEM,EAAE,gUACFC,KAAK,2OC3EEQ,eAAsBC,EAAAA,cAAc,CAC/CC,WAAY,KACZC,cAAe,KACfC,mBAAoB,OCKGC,EAAA,QAACC,MAAMC,EAAAA,sBACJC,EAAI,QAACF,MAAMG,EAAmBA,qBAC7C,MAAAC,EAAaF,UAAKF,MAAMK,EAAiBA,mBACzCC,EAAUJ,UAAKF,MAAMO,EAAsBA,wBAC3CC,EAAiBN,EAAAA,QAAKF,MAAMS,EAAqBA,uBACjDC,EAAgBR,UAAKF,MAAMW,EAAAA,sBCTlBC,EAAuBA,SAC3CC,GACA,IACA,OAAOC,QAAQC,IACbF,EAAcG,IAAWC,SAAAA,OAAiBC,MAAAA,gBAS9C,SAA0BD,GAYxB,MAXwD,CACtD,mCACA,wCACA,2CACA,qCACA,uCACA,uCACA,uCACA,sCAGqD1C,SACrD0C,EAAaE,6BAEjB,CAvBUC,CAAiBH,GAAa,OAAAH,QAAAO,iBAyBDJ,GAAkC,IAAA,SAAAK,IA0CvE,OAAOC,GAAeN,EAAaM,WAAW,CAzC9C,IAAIA,EAAc,SAAEC,EAAA,WAAA,GAGlB,qCADAP,EAAaE,6BACqBL,OAAAA,QAAAO,QA0FVI,SAACC,GAAkB,WAAEZ,QAAAO,QACxBM,EACpBC,IAAI,CACHC,KAAM,CACJC,OAAQ,CAAEC,SAAU,oBACpBC,MAAO,CAAEpD,GAAI8C,IAEfO,IAAM,cAEPC,MAAM,IAAM,CAAC,CAAEL,KAAM,CAAEM,KAAM,QAAQC,KAAA,UARlCP,KAAEA,IAUR,OAAOA,CAAI,EACb,CAAC,MAAAQ,GAAAvB,OAAAA,QAAAwB,OAAAD,EAAA,CAAA,CApGsBZ,CAAcR,EAAasB,gBAAgBb,aAAWU,KAAnEP,SAAAA,GACN,MAAMW,EAAWX,EAAK,GAElBW,GAAAA,GAAUL,KACZ,CAAA,IAAIM,EAGFA,EADED,EAASE,WACK,cAAaF,EAASL,OAEvBK,EAASL,KAG1BZ,EAAcN,EAAaM,YAAY/C,QACrC,oBACAiE,EACD,CAAA,GAAA,CAIH,MAAME,EACJ1B,EAAasB,gBAAgBK,qBAAqBC,MAChD,0BACA,GAAE/B,OAAAA,QAAAO,QAgFyByB,SAACH,GAA2B,IAAA,OAAA7B,QAAAO,QACtCM,EACpBC,IAAI,CACHC,KAAM,CACJC,OAAQ,CACNiB,gBAAiB,+BACjBC,YAAa,SAEfC,QAAS,iBAEXhB,IAAM,qBAAoBU,MAE3BT,MAAM,KAAA,CAASL,KAAM,CAAEM,KAAM,QAAQC,KAAA,UAXlCP,KAAEA,IAaR,OAAOA,CAAI,EACb,CAAC,MAAAQ,GAAAvB,OAAAA,QAAAwB,OAAAD,IA9FiCS,CAAqBH,IAAkBP,KAAA,SAA/Dc,GACFA,EAAgBf,OAClBZ,EAAcN,EAAaM,YAAY/C,QACrC,wBACA0E,EAAgBf,MAElBZ,GACEN,EAAasB,gBAAgBY,QACA,eAA7BD,EAAgBE,SACX,KAOb,SACEnC,EACAiC,GAKA,OAAQA,EAAgBE,UACtB,IAAK,aACH,OAAOC,OAAOC,QAAQrC,EAAasB,gBAAgBY,QAChDnC,IAAI,EAAEpC,EAAI2E,MACT,MAAMC,EACJN,EAAgBO,aAAaC,KAC1BC,GAAgBA,EAAY/E,KAAOgF,SAAShF,EAAI,MAChD4E,OAAS,iBACd,MAAQ,GAAEK,EAAWN,MAAWC,GAAM,GAEvCM,KAAK,MACV,IAAK,SACH,OAAO7C,EAAasB,gBAAgBiB,MAChCN,EAAgBO,aAAaC,KAC1BC,GACCA,EAAY/E,KACZgF,SAAS3C,EAAasB,gBAAgBiB,MAAMO,WAAY,MACzDP,OAAS,iBACZ,aACN,IAAK,UACH,OAAQvC,EAAasB,gBAAgBiB,OACnC,IAAK,OACH,MAAO,MACT,IAAK,QACH,MAAO,KACT,QACE,MAAO,aAEb,QACE,OAAOvC,EAAasB,gBAAgBiB,OAAS,aAEnD,CA7CiBQ,CAA6B/C,EAAciC,MAChD,GAAEpC,EAAAA,CAAAA,CAtCQ,GAsCRA,OAAAA,QAAAO,QAAAG,GAAAA,EAAAY,KAAAZ,EAAAY,KAAAd,GAAAA,IAId,CAAC,MAAAe,GAAAvB,OAAAA,QAAAwB,OAAAD,EAzED,CAAA,CAMyC4B,CAAwBhD,IAAamB,KAAA,SAAA8B,GAAtEjD,EAAaM,YAAW2C,CAA8C,aAAApD,QAAAO,QAAAH,GAAAA,EAAAkB,KAAAlB,EAAAkB,KAExE,WAAA,OAAOnB,CAAY,GAAZA,EACT,CAAC,MAAAoB,GAAAvB,OAAAA,QAAAwB,OAAAD,EACH,CAAA,GACF,CAAC,MAAAA,GAAAvB,OAAAA,QAAAwB,OAAAD,EAAA,CAAA,EAwGD,SAASwB,EAAWM,GAClB,OAAOA,EAAOC,OAAO,GAAGC,cAAgBF,EAAOG,MAAM,EACvD,CAEA,MAAM3C,EAAe,IAAI4C,EAAAA,OAAO,CAC9BC,KAAMvG,EAAW,UACjBwG,QAAS,eAkCK,SAAAC,EAAoBC,GAClC,OAAIA,EAAMC,UACA,GAAED,EAAM/F,MAAM+F,EAAMC,YACJ,iBAAfD,EAAME,KACP,GAAEF,EAAM/F,sBAIpB,CAqBA,SAASkG,EAAyBC,GAChC,GAAIA,EAAWC,gBAAgBnC,MAAM,uCACnC,MAAO,8BAEX,CAMA,SAASoC,EAAeC,EAAgBC,GACtC,OAAO9B,OAAO+B,UAAUH,eAAeI,KAAKH,EAAQC,EACtD,CAEA,SAASG,GAAgBX,MACvBA,EAAKY,YACLA,IAKA,GAAIZ,EAAMa,KACR,OAAOb,EAAMa,KACR,GAAId,EAAoBC,GAG7B,OAFaY,EAAYb,EAAoBC,IAI7C,MAAU,IAAAc,MAAO,kCAAiCC,KAAKC,UAAUhB,KAErE,CAEgB,SAAAiB,EACdC,EACAC,GAEA,OAAOD,EAAiBE,OAAQpB,IAC9B,GAAItB,OAAO+B,UAAUH,eAAeI,KAAKV,EAAO,YAAa,CAC3D,MAAMqB,EAAWrB,EAAMqB,SACjBC,EAAe5C,OAAO6C,KAAKF,GAAU,GAE3C,OAAOG,EAASA,UAACH,GACbA,EACAA,EAASC,KAAkBH,EAAqBG,EACtD,CACE,QACF,EAEJ,CAEA,SAASG,GAAuBC,mBAC9BA,EAAkBP,qBAClBA,EAAoBP,YACpBA,IA8CA,OAQF,UAA4Cc,mBAC1CA,EAAkBP,qBAClBA,EAAoBP,YACpBA,EAAWhE,YACXA,IAEA,GACyC,qCAAvC8E,EAAmBrB,gBACnB,CACA,MAAMQ,EAAOD,EAAYe,0BACnBC,EACJf,GACAA,EAAK9B,KAAM8C,GAAMA,EAAEhD,MAAMO,aAAe+B,EAAqBW,cACzDlF,YAEN,OAAOA,EAAY/C,QAAQ+H,EAAiB,oBAC9C,CACEF,OAAAA,EAAmBrB,gBAAgBnC,MACjC,uCAGK,GAEAtB,CAEX,CAjCSmF,CAAmC,CACxCnF,YAzCkB8E,EAAmBR,iBACpC7E,IAAK2D,IACJ,IAAKM,EAAea,EAAsBnB,EAAM/F,IAAK,OAAO,KAE5D,MAAM4E,EAAQsC,EAAqBnB,EAAM/F,IACzC,IAAI4G,EAEJ,OAAQb,EAAME,MACZ,IAAK,SACL,IAAK,eACL,IAAK,eACL,IAAK,eAGH,OAFAW,EAAOF,EAAgB,CAAEX,QAAOY,gBAG9BC,GAAQA,EAAK9B,KAAM8C,GAAMA,EAAEhD,MAAMO,aAAeP,IAAQjC,YAE5D,IAAK,WACH,OAAOiC,GAASmB,EAAMgC,MACxB,IAAK,aAGH,OAFAnB,EAAOF,EAAgB,CAAEX,QAAOY,gBAEzBC,EACJO,OAAQ1D,GAAM4C,EAAezB,EAAiBnB,EAAEmB,QAChDxC,IAAKqB,GAAO,GAAEwB,EAAWL,EAAMnB,EAAEmB,WAAWnB,EAAEd,eAC9CuC,KAAK,MACV,IAAK,cACL,IAAK,YACL,IAAK,WACL,IAAK,YACH,OAAON,EACT,QACE,MAAM,IAAIiC,MACP,qDAAoDd,EAAME,QAEjE,GAEDkB,OAAQ5G,GAAMA,GACd2E,KAAK,MAINyB,cACAc,qBACAP,wBAEJ,CAqCO,SAASc,EAAiBC,GAC/B,OAAOA,EACJrI,QAAQ,KAAM,MACdA,QAAQ,KAAM,MACdA,QAAQ,KAAM,QACdA,QAAQ,KAAM,KACnB,CAQgB,SAAAsI,EAAcC,EAAMnH,GAClC,MAAMoH,EAAaC,UAAOF,EAAM,cAChC,IAAKC,EAAWE,UACd,MAAO,GAGT,MAAML,EAASD,EAAiBhH,GAChC,OAAOoH,EAAWH,OAAOA,EAC3B,CAOgB,SAAAM,EAAUC,EAAeC,GACvC,OAAc,IAAVD,EACM,KAAIC,IAEJ,GAAED,KAASC,IAEvB,CAEO,SAASC,EAAYnD,GAC1B,OAAOA,EAAO3F,QAAQ,KAAM,GAC9B,CAMO,SAAS+I,EAAqBC,GACnC,MAAMC,EAAeD,EAAgBE,MAAM,KAE3C,MAAO,CACLC,QAASF,EAAa,GACtBG,WAAYH,EAAaA,EAAaI,OAAS,GAC/CC,aAAcL,EAAanD,MAAM,GAAI,GAAGR,KAAK,KAC7CiE,aAAcN,EAAaA,EAAaI,OAAS,GAErD,CAEO,SAASG,EAAcC,EAAY1E,GACxC,MAAkC,QAA9B0E,EAAMC,SAAS,IAAIC,OACb,gCAA+B5E,GAAU,4BAGrD,IAAA,CCmLC,MAndc6E,EAA6BA,SAACC,GAAM,IACjD,MAAMC,EAAYD,EAAOxG,KAAKb,IAAKqB,GAAMkG,EAAclG,IAAGvB,OAAAA,QAAAO,QAwcrD,SAAgBmH,EAAMC,GAC5B,IACC,IAAIC,EAzcA5H,QAAAO,QACmBsH,EAAYL,IAAUlG,KAAA,SAArCwG,GACN,MAAO,CAAEP,SAAQO,SAAQ,EAwc5B,CAAE,MAAMvG,GACP,OAAOoG,GACR,CACA,OAAIC,GAAUA,EAAOtG,KACbsG,EAAOtG,UAAK,EAAQqG,GAErBC,CACR,CAld4DG,CAAA,EAIzD,WACC,MAAO,CAAER,SAAQO,OAAQ,GAC3B,GACF,CAAC,MAAAvG,UAAAvB,QAAAwB,OAAAD,EAAA,CAAA,EAtBcsG,EAAW,SAACL,GAAS,WAAExH,QAAAO,QACbM,EAAaC,IAAI,CACtCC,KAAM,CACJC,OAAQ,CACNgH,OAAQ,WAEV9G,MAAO,CAAEpD,GAAI0J,EAAUxE,KAAK,OAE9B7B,IAAM,YACNG,eARIP,KAAEA,IAUR,OAAOA,CAAI,EACb,CAAC,MAAAQ,GAAA,OAAAvB,QAAAwB,OAAAD,EAtCc,CAAA,EAAA0G,EAAWA,SACxBvB,EACAwB,EACAC,GAKA,IAAA,OAAAnI,QAAAO,QACuB6H,EAAetH,IAAI,CACxCC,KAAM,CACJsH,GAAI3B,EACJ1F,OAAQ,CACNsH,SAAU,kCACVC,MAAO,0DAETpG,QAAS,gBACTqG,MAAO,iBACJL,GAELhH,IAAM,4BAA2B+G,aAIrC,CAAC,MAAA3G,GAAA,OAAAvB,QAAAwB,OAAAD,EAtDD,CAAA,EAAM6G,EAAiB,IAAI3E,EAAAA,OAAO,CAChCC,KAAMvG,EAAW,YACjBwG,QAAS,eAEL9C,EAAe,IAAI4C,EAAMA,OAAC,CAAEC,KAAMvG,EAAW,UAAWwG,QAAS,eAGjE8E,EAAS,CACbC,UAAW,CACT7C,MAAO,UACPnD,MAAO,CAAC,cAEViG,OAAQ,CACN9C,MAAO,SACPnD,MAAO,CAAC,SAAU,eAEpBkG,QAAS,CACP/C,MAAO,UACPnD,MAAO,CAAC,qBAAsB,iBAAkB,oBAElDmG,QAAS,CACPhD,MAAO,UACPnD,MAAO,CAAC,YAEVoG,QAAS,CACPjD,MAAO,SACPnD,MAAO,CAAC,aAsDZ,SAASqG,GAAqBxB,OAAEA,EAAMO,OAAEA,IACtC,MAAMkB,EAAazB,EAAOxG,KAAKkI,OAAO,CAACrB,EAAQrG,KAC7C,MAAM2H,EAAWzB,EAAclG,GACzB4H,EAAcrB,EAAOlF,KACxBwG,GAAMF,EAASjG,aAAemG,EAAEtL,GAAGmF,YAatC,OAVE2E,EAAOyB,KADLF,EACU,IACP5H,EACH+H,OAAQ,CAAExL,GAAIqL,EAAYrL,GAAIuD,KAAM8H,EAAY9H,OAGtC,IACPE,EACH+H,OAAQ,CAAExL,GAAIoL,EAAU7H,KAAM,cAG3BuG,GACN,IAEH,MAAO,IAAKL,EAAQxG,KAAMiI,EAC5B,CAEA,SAASvB,EAAc8B,GACrB,OAAOA,EAAML,QACf,CAmFA,SAASM,IAAQC,WACfA,EAAU/C,gBACVA,EAAegD,YACfA,EAAWC,qBACXA,IAQA,MAAMpC,OAAEA,EAAMqC,QAAEA,EAAOC,gBAAEA,EAAeC,QAAEA,EAAO3B,OAAEA,EAAM4B,UAAEA,GA7F7D,SACE7B,EACAxB,EACAgD,GAEA,MACOM,EAAGC,GAAYC,EAAAA,YACfN,EAASO,GAAcD,EAAAA,UAAS,IAChCE,EAAYC,GAAiBH,WAAuC,CAAA,IACpE/B,EAAQ4B,GAAaG,EAAAA,SAC1BR,EAAc,CAAExI,MAAO,CAAEmG,OAAQqC,IAAkB,CAAA,IAE9CY,EAAMC,GAAWL,EAAAA,YAClBM,OAAEA,EAAMX,gBAAEA,EAAeY,YAAEA,GAkDnC,SAAuBC,EAAiBC,GACtC,MAAOH,EAAQI,GAAaV,EAAQA,SAAC,GAcrC,MAAO,CAAEM,SAAQX,gBAVO,CAAEgB,YAFNC,KAAKC,MAAMP,EA7Df,IA6DmC,EAEZQ,aAEvC,SAAsBC,GACpBL,EAlEc,IAkEHK,EAAU,GACvB,EAJqDC,WADlCJ,KAAKK,KAAKR,EA9Db,KAyEkBF,YAJdW,EAAWA,YAAC,KAC9BR,EAAU,EACZ,EAAG,IAGL,CAlEmDS,CARjC,EAUdf,GAAMK,YAERW,EAAAA,UAAU,KACJ1B,GAAWQ,EAAWI,KAE1BL,GAAW,GAEXlC,EAAYvB,EAAiBwB,EAAc,CACzCsC,SACAe,SAnBY,MAoBTpD,IAEF7G,KAAKgG,GACLhG,KAAKyH,GACLzH,KAAMiG,IACL8C,EAAemB,IAAK,IAAWA,EAAOhB,CAACA,GAASjD,EAAOxG,QACvDwJ,EAAQhD,EAAO+C,MACfH,GAAW,KAEZ/I,MAAMqK,KACR,CAACvD,EAAcxB,EAAiBkD,EAASzB,EAAQqC,EAAQJ,IAE5D,MAAMN,EAAUsB,cAAY,KAC1Bf,EAAc,IACdE,OAAQmB,GACRjB,GAAW,EACV,CAACA,IAMJ,SAASgB,EAAsBtE,GAC7B8C,EAAS,KACP,MAAM9C,GAEV,CAEA,OAVAmE,EAASA,UAAC,KACRxB,GACF,EAAG,CAACA,EAAS3B,IAQN,CACLZ,OAAQ6C,EAAWI,IAAW,GAC9BZ,UACAC,kBACA1B,SACA2B,UACAC,YAEJ,CAiCI4B,CAAUlC,EAAW3L,GAAI4I,EAAiBgD,IACtC5K,WAAEA,EAAUC,cAAEA,EAAaC,mBAAEA,GAAuB4M,aAIvDhN,GAEGiN,EAAkB1D,EAAOjH,OAASqB,OAAO6C,KAAK+C,EAAOjH,OAAO6F,OAAS,EACrE+E,WDgHqB7F,GAC3B,MAAMC,EAAaC,EAAAA,QAAOF,EAAM,cAChC,OAAOE,YAAS4F,KAAK7F,EAAY,OACnC,CCnHoC8F,CAAavC,EAAWwC,YAAc,GAClEC,EAAoBlG,EAAcyD,EAAWwC,UAAWnN,GACxDqN,EAA2BL,EAC5B,iCAAgCI,IACjC,0CAEEE,EAAU,CACd,CACEC,KAAO9C,gBAAqB3L,UAAAC,cAACyO,GAAiBjF,CAAAA,OAAQkC,EAAMlC,SAC5DkF,IAAK,CACHC,QAAS,YAEXC,OAAQ,UAEV,CACEJ,KAAO9C,GACLpD,EAAM,QAACoD,EAAM0C,WACVS,UAAU3N,GACVgH,OD8EJ,UAA8BjH,WAAEA,EAAUE,mBAAEA,IACjD,MAAQ,GAAE8G,EAAiBhH,MACzBE,EAAqB,QAAU,UAEnC,CClFkB2N,CAAqB,CAAE7N,aAAYE,wBAC/CyN,OAAQ,iBAEV,CACEJ,KAAO9C,gBACL3L,EAAAA,QAAAC,cAAC+O,EAAIA,KAACC,CAAAA,GAAK,aAAYtD,EAAMD,OAAOxL,MAAOyL,EAAMD,OAAOjI,MAE1DkL,IAAK,CACHO,SAAU,OAEZL,OAAQ,WAEV,CACEJ,KAAO9C,gBAAqB3L,EAAAA,QAAAC,cAACkP,GAAkB,CAACxD,MAAOA,IACvDgD,IAAK,CACHS,KAAM,GAERP,OAAQ,WAEV,CACEJ,KAAO9C,IACJ,IAAId,EAAOC,UAAUhG,SAAU+F,EAAOI,QAAQnG,OAAOjF,SACpD8L,EAAMlC,sBAENzJ,EAAAA,QAAAC,cAAAD,EAAA,QAAAqP,SAAA,kBACErP,UAAAC,cAACqP,GACChF,CAAAA,aAAcuB,EAAW3L,GACzByL,MAAOA,EACP7C,gBAAiBA,EACjBiD,qBAAsBA,KAEtB,IAAIlB,EAAOG,QAAQlG,OAAOjF,SAAS8L,EAAMlC,sBACzCzJ,EAAA,QAAAC,cAACsP,GACCjF,CAAAA,aAAcuB,EAAW3L,GACzByL,MAAOA,EACP7C,gBAAiBA,EACjB0G,eAAgBtD,EAChBH,qBAAsBA,KAKhC4C,IAAK,CACHc,UAAW,SAEbZ,OAAQ,GACRa,SAAU,sBAId,OACE1P,EAAAA,QAAAC,cAAC0P,EAASA,UAACC,CAAAA,QAASC,EAAKA,MAAC,+BACxB7P,EAAA,QAAAC,cAAC0P,EAASA,UAAA,CAACC,QAASC,EAAKA,MAAC,kCACxB7P,EAAAA,QAAAC,cAAC6P,EAAAA,QAAO,CACNC,MAAO,EACPC,KAAK,OACLC,MAAOJ,EAAAA,MAAM,4BACbK,OAAQL,EAAAA,MAAM,2BAEbhE,EAAWhJ,0BAEd7C,EAAA,QAAAC,cAACkQ,OAAI,CACHF,MAAOJ,EAAKA,MAAC,4BACbG,KAAMH,EAAKA,MAAC,oBACZO,QAAM,GAEL7B,iBAGLvO,EAAAA,QAAAC,cAAC0P,EAASA,WAACC,QAASC,EAAKA,MAAC,+BACxB7P,UAAAC,cAACoQ,EAAAA,IAAG,CAACC,UAAW,IACZtE,IAAYrC,EAAOR,QAAU8E,iBAC7BjO,EAAA,QAAAC,cAAC0P,EAASA,UACRY,CAAAA,WAAW,MACXC,KAAK,aACLC,aAAa,gBACbb,QAASC,EAAAA,MAAM,+BAEf7P,EAAA,QAAAC,cAAC0P,EAASA,UAAChP,CAAAA,MAAM,4BACfX,EAAAA,QAAAC,cAACyQ,EAAKA,MAACC,WACLC,CAAAA,WAAYf,EAAKA,MAAC,0BAClBI,MAAOJ,EAAKA,MAAC,kBACbgB,SAAS,iBACV,iCAGD7Q,EAAAA,QAAAC,cAAC6Q,UACC5Q,GAAG,gBACH6Q,WAAY,KACZC,SAAUA,EAAGC,oBAIX9E,EAAU,CAAE7I,MAHK2N,EACb,CAAExH,OAAQwH,GACV,MAEN,EACAC,MAAM,SACNpM,MAAOyF,EAAOjH,OAAOmG,qBAErBzJ,EAAA,QAAAC,cAAC6Q,EAAMA,OAACK,OAAM,CAACrM,MAAO,MAAM,OAC3BH,OAAOF,OAAOoG,GAAQvI,IAAKmH,gBAC1BzJ,EAAA,QAAAC,cAAC6Q,EAAMA,OAACK,OAAM,CACZ1K,IAAKgD,EAAO3E,MACZA,MAAO2E,EAAO3E,MAAMM,KAAK,MAExBqE,EAAOxB,uBAKhBjI,EAAAA,QAAAC,cAACmR,EAAAA,QACCC,SAAU,CAAE5N,KAAM,mBAClB6N,QAASpF,EACTqF,MAAM,UACNC,QAAQ,UACR7Q,MAAO,IACR,0BAMPX,EAAAA,QAAAC,cAACoQ,EAAGA,KAACoB,UAAU,OAAOnB,UAAW,GAAIoB,SAAS,qBAC5C1R,EAAAA,QAAAC,cAAC0R,EAASA,UAAAC,GACRpD,QAASA,EACTrL,KAAMwG,EACNkI,mBACE7R,EAAAA,QAAAC,cAAC0P,EAAAA,UAAS,CACRmC,UAAU,SACVrB,aAAa,SACbH,UAAW,GACXpB,SAAU,GACVU,QAASC,QAAM,iBACfkC,UAAY9D,GAAwB,GAAL,EAC/B+D,aAAe/D,EAA8B,OAAZH,gBAEjC9N,EAAAA,QAAAC,cAACoQ,EAAGA,IACF1B,CAAAA,IAAK,CACHsD,IAAK,CACHrR,OAAQ,GACRD,MAAO,mBAIXX,EAAAA,QAAAC,cAACF,EAAc,oBAEjBC,EAAAA,QAAAC,cAAC6P,EAAOA,QAAA,CACNG,MAAOJ,EAAKA,MAAC,2BACbe,WAAYf,EAAKA,MAAC,0BAClBE,MAAO,EACPC,KAAMH,EAAKA,MAAC,qBACb,iCAGD7P,UAAAC,cAACkQ,EAAAA,KAAI,CAAC+B,SAAUrC,EAAAA,MAAM,oBAAqBJ,UAAU,UAAS,aACjDxB,GAAmB,wBAAwB,sCACxB,IAC7BC,EACI,SAAQI,KACT,wBAELL,gBACCjO,EAAA,QAAAC,cAACmR,SACCW,CAAAA,UAAWlC,EAAKA,MAAC,iBACjByB,QAASA,IAAMnF,EAAU,CAAE,GAC3BoF,MAAM,UACNL,MAAM,gBACNM,QAAQ,aAKhBxF,QAASA,EACTmG,aAAa,gCACbX,QAAS,CACPY,SAAU,CACR7B,WAAY,QACZ2B,SAAUrC,EAAKA,MAAC,oBAChBwC,WAAY,OACZzD,QAAS,aAEX0D,QAASA,EAAGC,cACH,CACLC,gBAAiB,IAAI3H,EAAOG,QAAQlG,OAAOjF,SACzC0S,EAAQ9I,QAENoG,EAAAA,MAAM,mCACN/B,EACJwC,UAAW,SAGfmC,WAAY,CACV7D,QAAS,YAEX8D,UAAW,CACTpC,UAAW,UAGXrE,MAMhB,CAEA,SAASqD,IAAiBhF,aACxBA,EAAYqB,MACZA,EAAK7C,gBACLA,EAAeiD,qBACfA,IAOA,MAAOtC,EAAQkJ,GAAarG,EAAAA,SAASX,EAAMlC,QAyBrCmJ,EAAuB/H,EAAOI,QAAQnG,MAAMjF,SAAS4J,GACvD,UACAoB,EAAOC,UAAUhG,MAAMjF,SAAS4J,GAChC,OACAoB,EAAOK,QAAQpG,MAAMjF,SAAS4J,GAC9B,UACA,QAEEoJ,EAAahI,EAAOC,UAAUhG,MAAMjF,SAAS4J,GAC/C,CAAEwG,MAAOJ,EAAAA,MAAM,iCAAkCpM,KAAM,sBACvDqK,eAEJ,OACE9N,EAAAA,QAAAC,cAACmR,EAAAA,QACCF,MAAO0B,EACPtB,QAtCJ,WACEqB,EAAU9H,EAAOI,QAAQnG,MAAMM,KAAK,MACpCoF,EACGsI,KAAK,CACJ3P,KAAM,CACJsH,GAAI3B,EACJ3F,KAAM,CAAE4P,WAAY,CAAG,IAEzBxP,IAAM,6BAA4B+G,YAAuBqB,EAAMzL,iBAEhEwD,KAAMsP,IACLL,EAAU9H,EAAOC,UAAUhG,MAAMM,KAAK,MACtC2G,EAAqBiH,EAAStG,KAAKuG,aACrC,GACCzP,MAAM,KACLmP,EAAU9H,EAAOE,OAAOjG,MAAMM,KAAK,MACnC8N,EAAkBC,KAAK,CACrBC,KAAM,mFACNlC,MAAO,UAEX,EACJ,EAkBIG,SAAUwB,EACVQ,SAAU5J,IAAWkC,EAAMlC,OAC3B+H,QAAQ,QACRvB,MACEpF,EAAOC,UAAUhG,MAAMjF,SAAS4J,GAC5BoG,EAAKA,MAAC,iCACNhF,EAAOI,QAAQnG,MAAMjF,SAAS4J,GAC5BoG,QAAM,8BACNA,EAAKA,MAAC,8BAEd0B,MAAM,UACNvB,KAAK,MAGX,CAEA,SAAST,IAAkBjF,aACzBA,EAAYqB,MACZA,EAAK7C,gBACLA,EAAe0G,eACfA,EAAczD,qBACdA,iBA6BA,OACE/L,EAAA,QAAAC,cAACmR,EAAMA,OACLF,CAAAA,MAAO,SACPI,QAxBJ,WACE9G,EACGsI,KAAK,CACJ3P,KAAM,CACJsH,GAAI3B,EACJ3F,KAAM,CAAE4P,WAAY,CAAA,IAEtBxP,IAAM,6BAA4B+G,YAAuBqB,EAAMzL,cAEhEwD,KAAMsP,IACLjH,EAAqBiH,EAAStG,KAAKuG,aACrC,GACCvP,KAAK,IAAM8L,KACXhM,MAAM,KACL0P,EAAkBC,KAAK,CACrBC,KAAM,8EACNlC,MAAO,UACR,EAEP,EAMIM,QAAQ,QACRvB,MAAO,iBACPsB,MAAM,UACNvB,KAAK,MAGX,CAEA,SAAStB,IAAiBjF,OAAEA,IAC1B,MAAM6J,EAAczI,EAAOI,QAAQnG,MAAMjF,SAAS4J,GAC9C,CACA8J,OAAQ1D,EAAAA,MAAM,yBACduD,KAAMvD,EAAAA,MAAM,mBAEZhF,EAAOC,UAAUhG,MAAMjF,SAAS4J,GAChC,CACE8J,OAAQ1D,EAAAA,MAAM,mCACduD,KAAMvD,EAAAA,MAAM,kCAEZhF,EAAOK,QAAQpG,MAAMjF,SAAS4J,GAC5B,CACA8J,OAAQ1D,EAAKA,MAAC,mCACduD,KAAMvD,EAAKA,MAAC,kCAEZhF,EAAOG,QAAQlG,MAAMjF,SAAS4J,GAC5B,CACA8J,OAAQ1D,EAAKA,MAAC,yBACduD,KAAMvD,EAAKA,MAAC,6BAEZ,CACA0D,OAAQ1D,EAAKA,MAAC,iCACduD,KAAMvD,EAAKA,MAAC,gCAGhB2D,EAAY3I,EAAOI,QAAQnG,MAAMjF,SAAS4J,GAC5C,gBACAoB,EAAOK,QAAQpG,MAAMjF,SAAS4J,GAC9B,iBACAoB,EAAOC,UAAUhG,MAAMjF,SAAS4J,GAChC,sBACAoB,EAAOG,QAAQlG,MAAMjF,SAAS4J,GAC9B,mBACA,8BAEEgK,EAAa5I,EAAOE,OAAOjG,MAAMjF,SAAS4J,GAC5CoB,EAAOE,OAAO9C,MACd4C,EAAOG,QAAQlG,MAAMjF,SAAS4J,GAC9BoB,EAAOG,QAAQ/C,MACf4C,EAAOpB,GAAQxB,mBAEnB,OACEjI,EAAAA,QAAAC,cAACyT,EAAKA,MACJzD,CAAAA,MAAO,CAAE0D,WAAY,cAAeC,WAAYN,EAAYF,MAC5DzE,IAAK,CAAEkF,YAAa,IAAKC,aAAc,KACvC5B,SAAUrC,EAAKA,MAAC,oBAChBkE,OAAO,OACPC,wBACEhU,EAAAA,QAAAC,cAACgU,EAAAA,KACCxQ,CAAAA,KAAM+P,EACNvD,MAAOqD,EAAYC,OACnBW,WAAYrE,QAAM,mBAGtBG,KAAK,KACLmE,OAAQb,EAAYC,OACpBa,YAAY,SACZC,aAAc,EACdnD,MAAOuC,GAGb,CAEA,SAAStE,IAAmBxD,MAAEA,IAC5B,MAAMlC,OAAEA,EAAM6K,aAAEA,GAAiB3I,EA6E3B4I,EA3EN,SAAuB9K,EAAgB6K,GACrC,IAAIC,EAAuC,KAE3C,OAAQ9K,GACN,IAAK,UACL,IAAK,kBACH8K,EAAU,wDACV,MACF,IAAK,SACL,IAAK,aACL,IAAK,iBACL,IAAK,qBACHA,EAMN,SAA+BC,EAAoB/K,GACjD,MAAMgL,EAAS,CACb,IAAK,wDACL,IAAK,kEACL,IAAK,sCACLC,QAAS,oBACTC,iBACE,yFACFC,0BACE,uFA4BJ,OACE5U,UAAAC,cAAC0P,EAAAA,UAAS,CAACP,KAAM,EAAGyF,WAAW,UAC3BL,eAOAxU,EAAA,QAAAC,cAAC6U,GAAiB,CAChBC,QAnCR,SAAwBP,GACtB,IAAKA,GAAUQ,aAAc,OAAW,KACxC,IAAIhC,EAEJ,IACEA,EAAWhM,KAAKiO,MAAMT,EAASQ,aACjC,CAAE,MACAhC,EAAW,CAAExJ,OAAQ,CAAC,gBACxB,CAEA,OAGF,SAAsBwJ,GACpB,OAAIA,GAAUxJ,OACLwJ,EAASxJ,OAAOlH,IAAKiH,GACT,iBAAVA,GAAsBA,EAAMpF,MAAM,qBACrCoF,EAAMzJ,QAAQ,oBAAqB,sBACnCyJ,GAGC,EAEX,CAbS2L,CAAalC,GAAU5N,KAAK,OAAS4N,GAAUuB,OACxD,CAwBiBY,CAAeX,GACxB/K,OAAQ+K,EAAS/K,QAEhBgL,EAAOD,EAAS/K,SAAWgL,EAAOC,SAVrC,CAAC,aAAc,sBAAsB7U,SAAS4J,GAC5CgL,EAAOE,iBAEPF,EAAOG,0BAYjB,CA7DgBQ,CAAsBd,EAAc7K,GAGlD,OAAO8K,CACT,CA2DgBc,CAAc5L,EAAQ6K,GAEtC,OAAOC,eACLvU,EAAA,QAAAC,cAACoQ,MACC6B,CAAAA,SAAUrC,EAAKA,MAAC,oBAChByF,UAAU,SACVjD,WAAW,OACXnD,SAAS,OACTqG,WAAW,MACXV,WAAW,UAEVN,GAED,IACN,CAEA,SAASO,IAAkBU,SACzBA,EAAQT,QACRA,EAAOtL,OACPA,IAMA,MAAOgM,EAAMC,GAAWpJ,YAAS,gBAMjC,OACEtM,EAAA,QAAAC,cAAC0P,EAAAA,WAAUC,QAASC,QAAM,+BACxB7P,EAAAA,QAAAC,cAACoQ,EAAGA,IAAA,KACDmF,EAAU,IACVT,gBACC/U,EAAAA,QAAAC,cAACmR,EAAMA,OAAA,CACLuE,QAAM,EACNrE,QAXV,WACEoE,EAASE,IAASA,EACpB,EAUU5F,KAAK,KACLuB,MAAM,UACNC,QAAQ,QACR8D,UAAU,UACX,YAKJG,eACCzV,EAAA,QAAAC,cAACoQ,MAAIzB,CAAAA,QAAS,EAAG+E,WAAY9D,EAAAA,MAAM,4CACjC7P,EAAA,QAAAC,cAACkQ,EAAIA,MACH0F,WAAW,YACX3D,SAAUrC,QAAM,oBAChBwC,WAAW,OAEV5I,GAAW,GAAEA,MACbsL,IAGH,KAGV,CAWA,MAAMe,WAAsB9V,EAAAA,QAAM+V,UAIhCC,YAAYC,GACVC,MAAMD,GAQRE,KAAAA,qBAAuB,KACjBC,KAAKH,MAAMI,gBACbD,KAAKH,MAAMI,iBAEb1W,OAAO2W,gBAXPF,KAAKG,MAAQ,CAAEC,UAAU,EAC3B,CAEAC,kCACE,MAAO,CAAED,UAAU,EACrB,CASAE,SACE,OAAIN,KAAKG,MAAMC,sBAEXxW,EAAA,QAAAC,cAAC0W,EAAKA,MAAA,CACJC,KAAK,QACLC,eAAgB,EAChBjI,QAAS,IACTD,IAAK,CAAEmI,UAAW,sBAElB9W,EAAAA,QAAAC,cAACkQ,EAAAA,KAAI,CAACkC,WAAW,QAAO,oIAE0C,iBAChErS,EAAAA,QAAAC,cAAA,SAAA,CACE8W,MAAO,CACL9G,MAAOJ,EAAAA,MAAM,8BACbgF,WAAY,UAEdvD,QAAS8E,KAAKD,sBACf,mBAIG,MAKDC,KAACH,MAAMT,QACpB,EAIF,OAAgBS,gBACdjW,EAAAA,QAAAC,cAAC6V,GAAa,CAACO,eAAgBJ,EAAMI,6BACnCrW,EAAAA,QAAAC,cAAC2L,GAAYqK,ICx0BjB,SAASe,IAAe1F,QAAEA,iBACxB,OACEtR,MAAAC,cAACmR,EAAMA,OAAA,CACL6F,GAAG,SACHrW,OAAQiP,EAAKA,MAAC,uBACdqH,KAAM,CACJjH,MAAOJ,QAAM,sBACbpM,KAAM,aAER6N,QAASA,EACTtB,KAAK,KACLkB,MAAM,QACNM,QAAQ,SAGd,CAEA,SAAS2F,IAAa3B,SACpBA,EAAQa,eACRA,EAAcZ,KACdA,EAAIlE,MACJA,iBAOA,OAAO6F,EAAAA,0BACLpX,MAAAC,cAACoX,EAAaA,cAAA,CAAC9F,MAAOA,gBACpBvR,MAAAC,cAACqX,EAAAA,MAAK,CACJ7B,KAAMA,EACNY,eAAgBA,EAChBnH,SAAU,IACV4H,UAAU,+BACVlI,QAASiB,QAAM,iBACf0H,cAAe1H,QAAM,iBACrBkE,OAAQlE,QAAM,sCAEd7P,MAAAC,cAAC0P,YACCa,CAAAA,KAAK,aACLC,aAAa,gBACbqB,UAAU,uBAEV9R,MAAAC,cAAC6P,EAAOA,QACNC,CAAAA,MAAO,EACPE,MAAOJ,EAAAA,MAAM,2BACbe,WAAYf,EAAAA,MAAM,0BAClBqC,SAAUrC,EAAAA,MAAM,qBAChBwC,WAAW,OACZ,mCAGDrS,MAAAC,cAAC+W,GAAe1F,CAAAA,QAAS+E,KAE1Bb,IAGLgC,SAAS1N,KAEb,CC7DA,MAAM2N,GAAoC,CACxC,MACA,WACA,YACA,gBACA,SACA,SACA,aACA,OACA,QACA,cACA,SACA,kBACA,aACA,gBACA,YAOWC,GAAoBjU,IAC/B,MAAMkU,EAAYC,EAAAA,UAAUnU,GAC5B,MAN8BA,IACvBgU,GAAiB5X,SAAS4D,GAK1BoU,CAAgBF,GAAaA,EAAY,mBCyqBnCG,GAAwB,SAACvV,OAAkCH,OAAAA,QAAAO,QAG9DM,GAAaC,IAAI,CACzBC,KAAM,CACJC,OAAQ,CAAEgH,OAAQ,WAEpB7G,IAAK,QACLG,KAPI,UACJP,MAAM4U,OAAEA,KAQV,MAAO,CAAEA,SAAQxV,eAAc,EACjC,CAAC,MAAAoB,GAAAvB,OAAAA,QAAAwB,OAAAD,EAAA,CAAA,EAzrBK6G,GAAiB,IAAI3E,EAAMA,OAAC,CAChCC,KAAMvG,EAAW,YACjBwG,QAAS,eAEL9C,GAAe,IAAI4C,EAAMA,OAAC,CAAEC,KAAMvG,EAAW,YAmC7CyY,gBAAoB/W,gBAExB,MAEF,SAASgX,IAAmBC,iBAC1BA,EAAgBC,SAChBA,EAAQ5G,MACRA,EAAK6G,eACLA,GAAiB,EAAK/E,SACtBA,EAAQgF,eACRA,KACGpC,iBAQH,OACEjW,MAAAC,cAACqY,GAAiB1G,GAChBL,MAAOA,EACP2G,iBAAkBA,GACdjC,gBAEJjW,MAAAC,cAACsY,GAAM,kBACLvY,MAAAC,cAACuY,GAAK,mBACNxY,MAAAC,cAACwY,GAAM,CACLN,SAAUA,EACVC,eAAgBA,EAChB/E,SAAUA,EACVgF,eAAgBA,kBAGpBrY,MAAAC,cAACyY,GAAW,mBACZ1Y,MAAAC,cAAC0Y,GAAgB,MAGvB,CAEA,SAASC,GAAmB3C,gBAC1B,OACEjW,MAAAC,cAACqY,GAAkBzM,CAAAA,WAAYoK,EAAMpK,yBACnC7L,MAAAC,cAACsY,GAAM,kBACLvY,MAAAC,cAACuY,sBACDxY,MAAAC,cAAC4Y,GAAgB,oBAEnB7Y,MAAAC,cAAC6Y,GAAmB,mBACpB9Y,MAAAC,cAAC8Y,GAAM,MAGb,CAEA,SAASD,KACP,MAAMjN,WAAEA,GAAemC,aACrBgK,IAGIgB,EAA0BnN,EAAWmN,yBACrCvV,KAAEA,EAAIZ,YAAEA,GAAgBoW,GAAiBpN,EAAWhJ,aACpDqW,EAAerN,EAAWsN,YAAerL,EAAN,gBAEzC,OACE9N,MAAAC,cAAC0P,EAASA,UAAA,CACRyJ,gBAAiBvJ,QAAM,iBACvBT,KAAM,EACN9O,QAAS4Y,gBAETlZ,MAAAC,cAAC6P,EAAOA,SACNC,MAAO,EACPC,KAAMH,EAAAA,MAAM,oBACZK,OAAQL,EAAKA,MAAC,0BACdmC,aAAcnC,EAAAA,MAAM,oBACpBwJ,aAEC5V,gBAEHzD,MAAAC,cAAC0P,aAAUC,QAAS,kBAClB5P,MAAAC,cAACkQ,EAAIA,KACHH,CAAAA,KAAMH,EAAKA,MAAC,oBACZI,MAAOJ,EAAAA,MAAM,kBACbwC,WAAW,OAEV2G,EAAwB,UAAQM,EAAUA,WAAC7V,GAAO,IAClD8V,GAAkB1N,iBAErB7L,MAAAC,cAACkQ,EAAAA,MACCH,KAAMH,EAAKA,MAAC,oBACZI,MAAOJ,QAAM,4BACbwC,WAAW,OAEVgH,EAAQA,SAACG,GAAiC3W,GAAc,CACvDsG,OAAQ,IACRsQ,UAAW,QAMvB,CAEA,SAASZ,KACP,MAAMhN,WAAEA,GAAemC,EAAUA,WAC/BgK,iBAGF,OACEhY,MAAAC,cAACmR,EAAAA,OACCsI,CAAAA,YACArI,SAAU,CAAE5N,KAAM,qBAClB+N,QAAQ,QACRxB,KAAK,KACLf,GAAIpD,EAAW8N,gBACftG,UAAWxH,EAAW+N,UACtBC,QACGhO,EAAW+N,eAER9L,EADA,0CAGNmC,MAAOJ,EAAKA,MAAC,4BACbiK,MAAO,CACLtH,gBAAiB,YACjBvC,MAAOJ,EAAKA,MAAC,8BAEhB,SAIL,CAEA,SAASyI,IAAkBzM,WACzBA,EAAUqM,iBACVA,EAAgB1C,SAChBA,EAAQjE,MACRA,KACGwI,iBAMH,OACE/Z,MAAAC,cAAC+X,GAAkBgC,SAAQ,CACzBlV,MAAO,CACL+G,aACA0F,QACA2G,sBACG6B,iBAGL/Z,MAAAC,cAACga,OAAKlG,CAAAA,OAAQ,EAAGnF,QAAS,GACvB4G,GAIT,CAEA,SAAS+C,IAAO/C,SAAEA,IAChB,MAAM3J,WAAEA,GAAemC,EAAUA,WAACgK,iBAIlC,OACEhY,MAAAC,cAAC0P,EAASA,UAAA,CACRa,KAAK,aACLsB,UAAU,SACVlD,QAAS,EACT6B,aAAa,gBACbnQ,QARiBuL,EAAWsN,YAAerL,EAAN,IAUpC0H,EAGP,CAEA,SAASiD,IAAON,SACdA,EAAQC,eACRA,GAAiB,EAAK/E,SACtBA,EAAQgF,eACRA,IAOA,MAAMxM,WACJA,EAAUqO,uBACVA,EAAsBC,gBACtBA,EAAeC,QACfA,EAAO7I,MACPA,EAAK2G,iBACLA,GACElK,aAAWgK,KACRqC,EAAgBC,GAAqBhO,EAAQA,SAAC8L,GAC/CmC,EAAW1O,EAAWsN,QACtB1V,KAAEA,GAASwV,GAAiBpN,EAAWhJ,0BAyF7C,OACE7C,MAAAC,cAAAD,MAAAqP,SACErP,kBAAAA,MAAAC,cAAC0P,EAASA,UAAA,CAACa,KAAK,aAAasB,UAAU,SAASlC,QAAS,kBACvD5P,MAAAC,cAACua,EAAAA,UACCtD,KAAM,CACJjH,MAAOJ,EAAAA,MAAM,kBACbpM,KAAM,0BAERgX,WAAW,EACXvJ,MAAM,UACNM,QAAQ,QACRxB,KAAK,KACLqD,SAAUA,gBAEVrT,MAAAC,cAACua,WAASE,KAAKC,CAAAA,SAAUA,KApG/BL,GAAkB,EAoGiC,GAAC,WAC7CJ,IACErO,EAAW+O,cAAgBT,eAC1Bna,MAAAC,cAACua,EAAQA,SAACE,MAAKrH,UAAU,gBACvBrT,MAAAC,cAAC4a,EAAOA,QAAA,CACNC,UAAU,OACVC,UAAW,IACX7J,MAAM,4DAENlR,MAAAC,cAACkQ,EAAAA,KAAI,KAAC,oCAIVnQ,MAAAC,cAACua,WAASE,KAAKC,CAAAA,SA7E3B,WACEzH,EACGC,KAAK,CACJC,KAAM,yKACNlC,MAAO,yBAERxN,KAAK,EAAGsX,kBACHA,GACFxQ,GACGsI,KAAK,CACJ3P,KAAM,CACJsH,GAAI2P,EAAQa,SACZ9X,KAAM,CAAE4P,WAAY,CAAA,IAEtBxP,IAAM,6BAA4BsI,EAAW3L,mBAE9CwD,KAAK,EAAGP,UAAW2U,GAAyB3U,IAC5CO,KAAK,EAAGnB,eAAcwV,aACrBG,EAAkBgD,IAAU,IACvBA,EACHC,UAAW,IAAKD,EAAKC,UAAWC,UAAWrD,GAC3C6C,YAAarY,EAAaqY,YAC1BS,cAAe9Y,EAAa8Y,gBAC5B,GAEH7X,MAAO+F,IACN,MAAM6J,EACJ9J,EAAcC,EAAO,WACrB,mFACF2J,EAAkBC,KAAK,CACrBC,OACAlC,MAAO,YAGf,EAEN,GAyCqD,mCAI7ClR,MAAAC,cAACua,EAAAA,SAASE,KAAKC,CAAAA,SA3CvB,WACEzH,EACGC,KAAK,CACJmI,kBAAmB,yBACnBlI,KAAO,wCAAuC3P,wCAC9CyN,MAAO,4BAERxN,KAAK,EAAGsX,kBACHA,GAAa7C,EAAStM,EAAW3L,GAAE,EAE7C,GAiC+C,2BAEzCF,MAAAC,cAACsb,gBACCC,UAAWjB,EACXvK,KAAK,KACLsB,QAnHR,WACE9G,GACGiR,MAAM,CACLtY,KAAM,CACJsH,GAAI2P,EAAQa,SACZ9X,KAAM,CACJ4P,WAAY,CACVoG,QAASoB,KAIfhX,IAAM,6BAA4BsI,EAAW3L,OAE9CwD,KAAMP,IACL+U,EAAkBgD,IAAU,IAAKA,EAAM/B,OAAQhW,EAAKA,KAAKgW,SAC3D,GACC3V,MAAO+F,IACN,MAAM6J,EACJ9J,EAAcC,EAAO,UACpB,uBACCgR,EAAW,UAAY,kEAE3BrH,EAAkBC,KAAK,CACrBC,OACAlC,MAAO,UAEX,EACJ,EAyFQ2I,QACExG,EACIgF,EACAkC,EACA,mBACA,oBAENlH,SAAUA,kBAIdrT,MAAAC,cAACkX,GACC1B,CAAAA,KAAM4E,EACNhE,eAAgBA,IAAMiE,GAAkB,GACxC/I,MAAOA,gBAEPvR,MAAAC,cAAC2L,GACCC,CAAAA,WAAYA,EACZ/C,gBAAiBsR,EAAQa,SACzBlP,qBA3IR,SAA4B2P,GAC1BxD,EAAkBgD,IAAU,IAAKA,EAAMjI,aAAcyI,IACvD,EA0IQrF,eAAgBA,IAAMiE,GAAkB,MAKlD,CAEA,SAAS9B,KACP,MAAM3M,WAAEA,GAAemC,EAAUA,WAACgK,IAC5B2D,EAAqB9P,EAAWpI,KAAKuF,MAAM,KAAK,gBAEtD,OACEhJ,MAAAC,cAAC0P,EAAAA,UAAUa,CAAAA,KAAK,aAAasB,UAAU,SAASlC,QAAS,iBACvD5P,MAAAC,cAAC2b,EAAAA,KAAI,CACHC,UAAU,EACVpY,KAAMiU,GAAiBiE,GACvB3L,KAAK,KACLuB,MAAM,uBAERvR,MAAAC,cAACgU,OAAKxQ,CAAAA,KAAK,qBAAqBuM,KAAM,mBACtChQ,MAAAC,cAAC2b,EAAAA,MACCC,UAAU,EACVpY,KAAMiU,GAAiB7L,EAAWiQ,kBAClC9L,KAAK,KACLuB,MAAM,UAId,CACA,SAASwH,KACP,MAAMlN,WAAEA,GAAemC,EAAAA,WAAWgK,KAC5B9W,WAAEA,GAAe8M,EAAUA,WAAChN,GAE5Bqa,EAAiB,GAAExP,EAAWwP,iBADXxP,EAAWsP,WAAWjb,GAA2B,GAAtB,sBAG9CgZ,EAAerN,EAAWsN,YAAerL,EAAN,gBAEzC,OACE9N,MAAAC,cAAAD,MAAAqP,SAAA,kBACErP,MAAAC,cAAC8b,UAAO,CAACC,kBAAmB,iBAC5Bhc,MAAAC,cAAC0P,YACCa,CAAAA,KAAK,aACLsB,UAAU,SACVrB,aAAa,gBACb8E,WAAY,KACZ3F,QAASC,EAAAA,MAAM,iBACfvP,QAAS4Y,gBAETlZ,MAAAC,cAACkQ,EAAAA,MACCH,KAAMH,EAAAA,MAAM,oBACZI,MAAOJ,QAAM,8BACbgF,WAAW,UACZ,WACUzM,EAAcyD,EAAWwC,UAAWnN,iBAE/ClB,MAAAC,cAAC0P,EAASA,UAAA,CACRa,KAAK,aACLsB,UAAU,SACVlC,QAASC,QAAM,oBACfX,SAAS,sBAERrD,EAAWsP,WAAWC,wBACrBpb,MAAAC,cAACgc,SAAM,CACLtb,MAAO,EACPC,OAAQ,EACRsb,MAAO,EACPzV,IAAK4U,EACLc,OAAQtQ,EAAWsP,UAAUC,yBAGjCpb,MAAAC,cAACkQ,EAAAA,KAAKH,CAAAA,KAAM,EAAGqJ,UAAQ,GACpBgC,KAMb,CAEA,SAAS1C,KACP,MAAMzX,WAAEA,GAAe8M,EAAUA,WAAChN,IAC5B6K,WAAEA,EAAUuO,QAAEA,EAAO7I,MAAEA,EAAK2G,iBAAEA,GAAqBlK,EAAUA,WACjEgK,IAIIqD,EAAiB,GAAExP,EAAWwP,iBADXxP,EAAWsP,WAAWjb,GAA2B,GAAtB,sBAG9CgZ,EAAerN,EAAWsN,YAAerL,EAAN,GACnCsO,EAAc,CAClBnM,MAAOJ,EAAAA,MAAM,4BACbqC,SAAUrC,EAAKA,MAAC,oBAChBe,WAAYf,EAAAA,MAAM,0BAClBwM,kBAAmBxM,EAAKA,MAAC,iBACzBkE,OAAQ,OACR/D,KAAM,KACNwB,QAAS,UAEJ8K,EAAcC,GAAmBjQ,WAAS,CAC/CjF,OAAQ,KACRgT,gBAAgB,iBAiBlB,OACEra,MAAAC,cAAAD,MAAAqP,SAAA,kBACErP,MAAAC,cAAC8b,UAAO,CAACC,kBAAmB,iBAC5Bhc,MAAAC,cAAC0P,aACCa,KAAK,aACLsB,UAAU,SACVrB,aAAa,gBACb8E,WAAY,KACZ3F,QAASC,EAAAA,MAAM,iBACfvP,QAAS4Y,gBAETlZ,MAAAC,cAACkQ,EAAIA,MACHH,KAAMH,EAAKA,MAAC,oBACZI,MAAOJ,EAAAA,MAAM,8BACbgF,WAAW,UACZ,WACUzM,EAAcyD,EAAWwC,UAAWnN,iBAG/ClB,MAAAC,cAAC0P,YAAS,CACRa,KAAK,aACLsB,UAAU,SACVlC,QAASC,EAAAA,MAAM,yBAEZhE,EAAWoH,cAAc/H,sBAC1BlL,MAAAC,cAACmR,SAAMQ,EAAA,CAAA,EACDwK,EACJ,CAAA,aAAa,GAAEvQ,EAAWoH,aAAa/H,kBACvCoG,QA1CZ,WACEiL,EAAgB,CAAElV,OAAQ,UAAWgT,gBAAgB,GACvD,EAyCYR,QAAU,GAAEhO,EAAWoH,aAAa/H,SAASsR,iDAE7Cxc,MAAAC,cAACoQ,EAAGA,IACFmC,CAAAA,gBAAiB3C,QAAM,iCACvB4M,YAAa5M,EAAAA,MAAM,oBACnBkE,OAAO,SACPnT,OAAO,OACPD,MAAM,OACNiO,QAASiB,EAAKA,MAAC,oCAEf7P,MAAAC,cAACgU,OACCxQ,CAAAA,KAAM,iBACNuM,KAAM,MACNkB,MAAO,UACPjB,MAAM,WAGR,GAAEpE,EAAWoH,aAAa/H,SAASsR,sBAGtC3Q,EAAWoH,cAAclI,qBAC1B/K,MAAAC,cAACmR,EAAMA,OAAAQ,EACDwK,CAAAA,EAAAA,GACJ,aAAa,GAAEvQ,EAAWoH,aAAalI,gBACvCsG,SAAU,CACRpB,MAAOJ,EAAAA,MAAM,+BACb4M,YAAa5M,EAAKA,MAAC,oBACnBpM,KAAM,8BACNuM,KAAM,OACNkB,MAAO,UAETI,QAtEZ,WACEiL,EAAgB,CAAElV,OAAQ,oBAAqBgT,gBAAgB,GACjE,EAqEYnJ,MAAQ,GAAErF,EAAWoH,aAAalI,QAAQyR,mBAC1C3C,QAAU,GAAEhO,EAAWoH,aAAalI,QAAQyR,kDAIlDxc,MAAAC,cAAC0P,YAAS,CACRa,KAAK,aACLsB,UAAU,SACVrB,aAAa,MACbrB,KAAM,EACNQ,QAASC,EAAAA,MAAM,oBACfqE,WAAW,QAEVrI,EAAWsP,WAAWC,wBACrBpb,MAAAC,cAACgc,SAAM,CACLtb,MAAOkP,EAAAA,MAAM,uBACbjP,OAAQiP,QAAM,uBACdqM,MAAOrM,EAAKA,MAAC,uBACbpJ,IAAK4U,EACLc,OAAQtQ,EAAWsP,UAAUC,yBAGjCpb,MAAAC,cAACkQ,EAAAA,KAAKH,CAAAA,KAAMH,EAAAA,MAAM,oBAAqBwJ,UACpCgC,GAAAA,kBAKPrb,MAAAC,cAACkX,IACC1B,KAAM6G,EAAajC,eACnBhE,eAAgBA,IACdkG,EAAgB,CAAElV,OAAQ,KAAMgT,gBAAgB,IAElD9I,MAAOA,gBAEPvR,MAAAC,cAAC2L,IACCC,WAAYA,EACZ/C,gBAAiBsR,EAAQa,SACzBnP,YAAawQ,EAAajV,OAC1B0E,qBA1GR,SACE2P,GAEAxD,EAAkBgD,QAAeA,EAAMjI,aAAcyI,IACvD,EAuGQrF,eAAgBA,IACdkG,EAAgB,CAAElV,OAAQ,KAAMgT,gBAAgB,OAM5D,CAEA,SAAS3B,KACP,MAAM7M,WAAEA,EAAUuO,QAAEA,GAAYpM,EAAAA,WAC9BgK,KAGIvU,KAAEA,EAAIZ,YAAEA,GAAgBoW,GAAiBpN,EAAWhJ,aACpDqW,EAAerN,EAAWsN,YAAerL,EAAN,GAEnCkL,EAA0B,CAC9B,gBACAM,aAAWc,EAAQzO,MAAM9I,aAAe,IACxC,OACAyW,EAAAA,WAAW7V,GACX8V,GAAkB1N,IAClBzG,KAAK,kBAEP,OACEpF,MAAAC,cAAC0P,EAASA,UACRyJ,CAAAA,gBAAiBvJ,QAAM,iBACvBT,KAAM,EACN9O,QAAS4Y,gBAETlZ,MAAAC,cAAC6P,EAAOA,QAAA,CACNC,MAAO,EACPC,KAAMH,EAAAA,MAAM,oBACZK,OAAQL,QAAM,wBACdmC,aAAcnC,EAAAA,MAAM,oBACpBwJ,UAEC5V,GAAAA,gBAEHzD,MAAAC,cAAC0P,EAASA,UAACC,CAAAA,QAAS,kBAClB5P,MAAAC,cAACkQ,EAAAA,MACCH,KAAMH,EAAAA,MAAM,oBACZI,MAAOJ,EAAKA,MAAC,kBACbwC,WAAW,OAEV2G,gBAEHhZ,MAAAC,cAACkQ,OAAI,CACHH,KAAMH,EAAAA,MAAM,oBACZI,MAAOJ,EAAKA,MAAC,4BACbwC,WAAW,OAEVgH,WAASG,GAAiC3W,GAAc,CACvDsG,OAAQ,IACRsQ,UAAW,QAMvB,CAEA,SAASF,GAAkB1N,GACzB,OAAOA,GAAY6Q,eAAeC,yBAC9B,gCACA,EACN,CAEA,SAAS1D,GAAiBpW,GACxB,MAAMsB,EAAQ,uBAAuByY,KAAK/Z,GAE1C,OAAIsB,EACK,CAAEtB,YAAasB,EAAM,GAAMV,KAAMU,EAAM,GAAK0Y,QAE5C,CAAEpZ,KAAMZ,EAEnB,CAEA,SAAS2W,GAAiC3W,GACxC,OAAIA,GAAaia,WAAW,cACnBja,EAAY/C,QAAQ,aAAc,cAElC+C,CAEX,CC5IC,MAzfcka,GAAeA,WAAG,IAC/B,OAAA3a,QAAAO,QAAOM,GACJC,IAAI,CACHC,KAAM,CACJC,OAAQ,CAAE4Z,IAAK,CAAC,QAASC,UAAW,CAAC,MAAO,oBAC5C1Y,QAAS,CAAC,QAEZhB,IAAM,oBAEPG,KAAK,EAAGP,UACAA,EACJkE,OAAQ6V,GAAyBA,EAAUC,eAC3C7a,IAAK4a,GAAyBA,EAAU1d,IAAIiE,KAAK2Z,gBAE1D,CAAC,MAAAzZ,GAAAvB,OAAAA,QAAAwB,OAAAD,EArDc,CAAA,EAAA0Z,GAAoB,SAAClb,GAAmC,IACrE,MAAMyH,EAAY0T,EAAOA,QACvBC,EAAIA,KAACpb,EAAcG,IAAKC,GAAiBA,EAAaqY,eACvD,OAAAxY,QAAAO,QAmhBI,SAAgBmH,EAAMC,GAC5B,IACC,IAAIC,EAnhBA5H,QAAAO,QAC+BM,GAAaC,IAAI,CAChDC,KAAM,CACJC,OAAQ,CAAEgH,OAAQ,UAClB9G,MAAO,CAAEpD,GAAI0J,EAAUxE,KAAK,OAE9B7B,IAAK,YACLG,eANMP,KAAMqa,IAOd,MAAO,CAAEA,WAAUrb,gBAAe,EA4gBrC,CAAE,MAAMwB,GACP,OAAOoG,GACR,CACA,OAAIC,GAAUA,EAAOtG,KACbsG,EAAOtG,UAAK,EAAQqG,GAErBC,CACR,CA7hBGG,CAEG,aAUF,MAAO,CAAEqT,SAAU,GAAIrb,gBACzB,GACF,CAAC,MAAAwB,GAAAvB,OAAAA,QAAAwB,OAAAD,EAlCc,CAAA,EANT6G,GAAiB,IAAI3E,EAAMA,OAAC,CAChCC,KAAMvG,EAAW,YACjBwG,QAAS,eAEL9C,GAAe,IAAI4C,EAAAA,OAAO,CAAEC,KAAMvG,EAAW,YAsCnD,SAASke,IAA8BD,SACrCA,EAAQrb,cACRA,IAeA,OAViCA,EAAcG,IAAKC,IAClD,MAAMwV,EAASyF,EAASxY,KACrB0Y,GAAYA,EAAQxd,KAAOqC,EAAaqY,aAE3C,MAAO,IACFrY,EACH4Y,UAAW,IAAK5Y,EAAa4Y,UAAWC,UAAWrD,GAAQA,QAC7D,EAIJ,CChBe,MAAA4F,GAAqBA,SAACC,GAAa,IAIhD,MAAMC,EAA4B,CAChC3T,OAAQ,CAAC,QAAS,SAClB4T,cAAe,CAAC,UAChBC,SAAU,CAAC,UAEPC,EAAgB,CAAC,UAEjBC,EAAqBL,EAAYvS,OAAO,CAAC6S,EAAarS,KAE1D,MAAMsS,EAA4BtS,EAAW/C,gBAAgBhJ,QAC3D,SACA,UAEImJ,QAAEA,EAAOI,aAAEA,EAAYD,aAAEA,EAAYF,WAAEA,GAC3CL,EAAqBsV,GAavB,OAXKD,EAAYjV,KAAUiV,EAAYjV,GAAW,CAAA,GAC7CiV,EAAYjV,GAASI,KACxB6U,EAAYjV,GAASI,GAAgB,CAAA,GAClC6U,EAAYjV,GAASI,GAA2B,cACnD6U,EAAYjV,GAASI,GAA4B,aAAID,GAElD8U,EAAYjV,GAASI,GAAmB,MAC3C6U,EAAYjV,GAASI,GAAmB,IAAI,IAE9C6U,EAAYjV,GAASI,GAAmB,IAAEoC,KAAKvC,GAExCgV,GACN,CAAE,GAECE,EAAWzZ,OAAO6C,KAAKyW,GAAoBI,QAASpV,GAGjDtE,OAAOC,QAFoBqZ,EAAmBhV,IAEJoV,QAC/C,EAAEhV,EAAciV,MACEN,EAAcne,SAASoJ,GACnCsV,GACAV,EAA0B5U,IAAUpJ,SAASwJ,GAC7CmV,GACAC,IAEW,CACbxV,UACAyV,IAAKJ,EAAmB,IACxBlV,aAAckV,EAA4B,aAC1CjV,mBAINjH,OAAAA,QAAAO,QAEoBP,QAAQuc,WAAWP,IAAS1a,KAA5Ckb,SAAAA,GAEN,MAAO,CACLhB,cACAiB,kBAI8BC,EAJaF,EAKtCE,EACJzT,OAAO,CAAC0T,EAAK/U,KACU,cAAlBA,EAAOP,SAAwBsV,EAAMA,EAAIC,OAAOhV,EAAOlF,QAEpDia,GACN,IACFV,QAAS9d,GAAMA,EAAE4C,QAPtB,IAAkC2b,CAH/B,EACH,CAAC,MAAAnb,GAAAvB,OAAAA,QAAAwB,OAAAD,EAAA,CAAA,EA9Ecsb,GAAwB,SAACC,GAAc,WAAE9c,QAAAO,QAC/B6H,GAAetH,IAAI,CACxCC,KAAM,CACJsH,GAAIyU,EACJ9b,OAAQ,CACN+b,uBACE,yLACF/U,OAAQ,QAEV7F,QAAS,cAEXhB,IAAK,uCACLG,KAAA,UAXIP,KAAEA,IAaR,OAAOA,CAAI,EACb,CAAC,MAAAQ,UAAAvB,QAAAwB,OAAAD,EApBD,CAAA,EAAM6G,GAAiB,IAAI3E,EAAMA,OAAC,CAChCC,KAAMvG,EAAW,YACjBwG,QAAS,eA6FX,SAASyY,IAAevV,QAAEA,EAAOG,aAAEA,EAAYC,aAAEA,EAAYqV,IAAEA,IAC7D,OAAOU,GAAkB,CACvBnW,UACAsB,OAAQ,CACNjH,MAAO,CAAEpD,GAAIwe,EAAItZ,KAAK,OAExBia,KAAMjW,EACNC,gBAEJ,CAEA,SAASoV,IAAgBxV,QAAEA,EAAOG,aAAEA,EAAYC,aAAEA,EAAYqV,IAAEA,IAC9D,OAAOA,EAAIpc,IAAKpC,GACdkf,GAAkB,CAChBnW,UACAoW,KAAO,GAAEjW,KAAgBlJ,IACzBmJ,iBAGN,CAEA,SAASkV,GAAae,GACpB,OAAO,IAAIld,QAAQ,CAACgK,EAAGxI,KACrBA,GACF,EACF,CAuEA,SAASwb,IAAkBnW,QACzBA,EAAOoW,KACPA,EAAIhW,aACJA,EAAYkB,OACZA,EAAS,CAAA,IAET,MAAMgV,EAAS,IAAI1Z,EAAAA,OAAO,CAAEC,KAAMvG,EAAW0J,KACvCuW,EAAQC,EAAUA,WAAC7W,EAAYS,IAErC,OAAOkW,EAAOrc,IAAI,CAChBC,KAAM,CACJC,OAAQ,CACNoc,CAACA,GAAQ,CAAC,OAAQ,2BAEjBjV,GAELhH,IAAK8b,GAET,CAuCA,SAASK,IAAoBR,eAC3BA,EAAc9E,QACdA,IAKA,MAAOpO,EAASO,GAAcD,EAAQA,UAAC,IAChCsR,EAAa+B,GAAkBrT,EAAAA,WAEtCoB,EAAAA,UAAU,KACRqP,KAAkBrZ,KAAMkc,IACtBX,GAAyBC,GACtBxb,KAAK2Z,IACL3Z,KAAK+Z,IACL/Z,KAAKxB,GACLwB,KAAKia,IACLja,KAAK,EAAGka,cAAaiB,sBAtD9B,UAA+CjB,YAC7CA,EAAWiB,iBACXA,EAAgBe,cAChBA,IAEA,OAAOhC,EAAYtb,IAAKuJ,IACtB,MAAM5C,QAAEA,EAAOI,aAAEA,EAAYH,WAAEA,GAAeL,EAC5CgD,EAAW/C,iBAGb,GAAgB,WAAZG,EAIF,OAHA4C,EAAWmN,wBApEjB,SAAgCnN,GAG9B,OAFeA,EAAWpI,KAAK3D,QAAQ,oBAAqB,KAG1D,IAAK,8BACH,MAAO,sBACT,IAAK,mCACH,MAAO,yCACT,IAAK,sCACH,MAAO,6CACT,QACE,YAEN,CAuD2C+f,CAAuBhU,GAC5DA,EAAW+N,UAAYgG,EAAc5a,KAAMxF,GAAgB,WAARA,GAE5CqM,EAIT,MAAM7B,EAAS6U,EAAiB7Z,KAC7B8a,GAAOA,EAAG5f,GAAGmF,YAAc6D,EAAW7D,YAGnC0a,EAAe/V,EACjBA,EAAOvG,MAAQuG,EAAOgW,kBACrB,WAAUP,aAAW7W,EAAYS,OAStC,OAPAwC,EAAWmN,wBApEf,SAA0BnN,EAAYoU,GACpC,MAAMC,EA9CR,SAAuBC,GAIrB,OAF0BA,EAAYrgB,QAAQ,aAAc,KAG1D,IAAK,4BACH,MAAO,QACT,IAAK,8BACH,MAAO,SACT,IAAK,6BACL,IAAK,+BACH,MAAO,cACT,IAAK,+BACL,IAAK,iCACH,MAAO,kBACT,IAAK,iCACH,MAAO,UACT,IAAK,iCACH,MAAO,sCACT,IAAK,mCACH,MAAO,iCACT,IAAK,qCACH,MAAO,wDACT,IAAK,uCACH,MAAO,6DACT,QACE,OAAO,KAEb,CAkBesgB,CAAcvU,EAAWpI,OAEhC4F,aAAEA,GAAiBR,EAAqBgD,EAAW/C,iBAEzD,IAAKoX,EAAM,CAET,MAAMH,EAAe1G,EAAQA,SAAC4G,EAAqB,CACjD9W,OAAQ,IACRsQ,UAAW,MAGb,MAAQ,yCAAwC7Q,EAC9CS,OACI0W,IACR,CAEA,MAAQ,iBAAgBG,KAAQtX,EAC9BS,OACI4W,IACR,CAgDyCI,CACnCxU,EACAkU,GAGFlU,EAAW+N,YAAc5P,EAElB6B,GAEX,CAoBUyU,CAAsC,CACpC1C,cACAgC,gBACAf,sBAGHnb,KAAKic,GACLjc,KAAK,IAAM6I,GAAW,KAC1B,EACA,CAAC2S,IAEJ,MAAMqB,GAAavU,GAAkC,IAAvB4R,EAAYzU,oBAE1C,OACEnJ,MAAAC,cAAAD,MAAAqP,2BACErP,MAAAC,cAACoQ,EAAAA,KACCmQ,aAAe,aAAY3Q,EAAAA,MAAM,sBACjCmC,aAAcnC,QAAM,iBACpBmM,kBAAmB,EACnBjK,UAAWqI,EAAU,GAAK,EAC1BiC,kBAAmBxM,EAAKA,MAAC,iBACzBuJ,gBAAiBvJ,EAAKA,MAAC,+BAEvB7P,MAAAC,cAAC6P,EAAAA,QACCG,CAAAA,MAAOJ,EAAAA,MAAM,2BACbE,MAAO,EACPC,KAAMH,EAAAA,MAAM,qBAEX7D,EACG,uBACAvD,EAAUmV,EAAYzU,OAAQ,yBAGrCoX,eACCvgB,MAAAC,cAACkQ,EAAAA,MACCF,MAAOJ,EAAAA,MAAM,4BACbgH,eAAgBhH,EAAKA,MAAC,kBACvB,0EAGC7D,eACFhM,MAAAC,cAACwgB,EAAAA,QAAO,CACNC,mBAAO1gB,MAAAC,cAAC0gB,EAAOA,QAAA,CAAC3Q,KAAK,OACrBoJ,gBAAiB,GACjBlI,MAAO,iDAGTlR,MAAAC,cAAC2gB,EAAAA,SACChR,CAAAA,QAASC,EAAKA,MAAC,iBACfgH,eAAgBhH,EAAKA,MAAC,iBACtBgR,aAAc,IAEbjD,EAAYtb,IAAKuJ,gBAChB7L,MAAAC,cAAC2Y,GAAmBnS,CAAAA,IAAKoF,EAAW3L,GAAI2L,WAAYA,MAMhE,CC5VA,SAASiV,GAAsBC,GAC7B,MAAQ,aAAYA,EAAGza,kBAAkBya,EAAG7c,sBAAwB,IACtE,CAEA,SAAS8c,GAAUC,GACjB,MAAQ,WAAUA,GACpB,CAcA,SAASC,GACPC,GAEA,OAAOA,EAAQ7e,IAAI,EAAG2F,QAAOnD,wBAC3B9E,MAAAC,cAAC6Q,EAAAA,OAAOK,OAAM,CAAC1K,IAAK3B,EAAOA,MAAOA,GAC/BmD,GAGP,CAEA,SAASmZ,GACPD,GAEA,MAAME,EAAiBC,EAAOA,QAACH,EAAS,SAExC,OADmBxc,OAAO6C,KAAK6Z,GAAgBE,OAC7Bjf,IAAKkf,GACd,SAAPA,EACEN,GAAqCG,EAAeG,iBAEpDxhB,MAAAC,cAAC6Q,EAAMA,OAAC2Q,YAAW,CAAChb,IAAK+a,EAAItQ,MAAOsQ,GACjCN,GAAqCG,EAAeG,KAI7D,CAEA,MAAME,GAAaA,EACjBC,oBACAC,8BACAC,2BAMA,MAAMC,EAAkBH,GAAmBV,QAErCc,EAAoCF,EAAqBvf,IAAKye,IAAE,IACjEA,EACH7gB,GAAI4gB,GAAsBC,MAGtBiB,EAAoBD,EAAkC1a,OACzD0Z,GAAsB,OAAfA,EAAGE,SAGPgB,EAAwBC,EAAAA,OAAOL,EAAsB,WACxDxa,OAAQ0Z,KAASA,EAAGE,SACpB3e,IAAKye,IAAE,CACNoB,MAAOpB,EAAGqB,aACVna,MAAO8Y,EAAGE,QACVnc,MAAOkc,GAAUD,EAAGE,YAGlBoB,EAAsBP,EACxBC,EAAkC1a,OAC/B0Z,GAAOA,EAAGE,UAAYa,GAEzB,GAEJ,SAASQ,GAAsBrR,cAAEA,IAC/B,OAzEJ,SAAgBnM,GACd,GAAIA,EAAMgY,WAAW,WACnB,MAAO,UACEhY,GAAAA,EAAMgY,WAAW,aAC1B,MAAO,YACE,GAAChY,EAGV,MAAU,IAAAiC,MAAO,qBAAoBjC,KAFrC,OACF,IAGF,CA+DYyd,CAAOtR,IACb,IAAK,UACH2Q,EACEC,EAAqB7c,KAClB+b,GAAOC,GAAUD,EAAGE,WAAahQ,IAGtC,MACF,IAAK,YACH2Q,EACEC,EAAqB7c,KAClB+b,GAAOD,GAAsBC,KAAQ9P,IAG1C,MACF,KAAS,KACP2Q,EAA4B,MAGlC,CAEA,SAASY,EAAiBC,GAOxB,OAAOrB,GANqBqB,EAAWngB,IAAKwF,IAAC,CAC3Cqa,MAAOra,EAAEqa,MACTla,MAAOH,EAAEjF,YACTiC,MAAOgD,EAAE5H,MAIb,cAEA,OACEF,MAAAC,cAAC0P,EAAAA,UAAUC,CAAAA,QAASC,EAAAA,MAAM,+BACxB7P,MAAAC,cAAC6Q,EAAAA,OAAM,CACLC,WAAW,mBACX7Q,GAAG,gBACH8Q,SAAUsR,EACVtS,KAAK,KACL,cAAY,oBAEXwS,EAAiBR,GACjBZ,GAAca,IAEhBI,EAAoBlZ,OAAS,gBAC5BnJ,MAAAC,cAAC6Q,EAAAA,QACC4R,aAAcL,EAAoB,GAAGniB,GACrC8Q,SAAUsR,EACVtS,KAAK,MAEJwS,EAAiBH,IAGb,EC1ETM,GAAQA,EACZC,kBACA3c,QACA+K,WACAlM,QACAsC,uBACAyb,mBACAhc,cACAic,mBAWA,MAAMC,EAjCR,SAA2BC,GACzB,MAAOC,EAAgBC,GAAqB5W,EAAQA,SAAC0W,GAUrD,OARAtV,EAAAA,UAAU,KACR,MAAMyV,EAAYH,IAEbI,EAAOA,QAACD,EAAWF,IACtBC,EAAkBC,EACpB,EACC,CAACH,EAAWC,IAERA,CACT,CAqBuBI,CAAkB,IAjDzC,UAA2Bpd,MACzBA,EAAKmB,qBACLA,IAMA,OADkBnB,EAAMqd,WAAa,IACpBjY,OAAO,CAAC0T,EAAKwE,KACxB5e,OAAO+B,UAAUH,eAAeI,KAAKS,EAAsBmc,KAC7DxE,EAAIyE,EAAAA,UAAUD,IAAWnc,EAAqBmc,IAEzCxE,GACN,CAAA,EACL,CAoCI0E,CAAkB,CAAExd,QAAOmB,0BAG7BsG,EAAAA,UAAU,KACJzH,EAAMC,WACR2c,EAAiB,CAAEE,eAAc9c,SACnC,EACC,CAACA,EAAO8c,EAAcF,IAEzB,MAAMa,EACJzd,EAAMa,MAAQD,EAAYb,EAAoBC,KAAW,GAErD0d,EAAuBD,EAAYrc,OACtCuc,IAAQA,EAAGC,sBAGR7X,EAAU/F,EAAMC,WAAa4c,EAAa9c,EAAoBC,iBAuEpE,OACEjG,MAAAC,cAAC0P,EAASA,UAAA,CAACqC,aAAc,EAAGpC,QAAS,iBACnC5P,MAAAC,cAACyQ,EAAKA,MAACC,WAAU,CACfV,MAAOJ,EAAKA,MAAC,2BACbqC,SAAUrC,EAAAA,MAAM,oBAChBe,WAAYf,EAAAA,MAAM,0BAClBgB,SAAU5K,EAAM/F,IAEf+F,EAAMpD,YACNoD,EAAM6d,mBACL9jB,MAAAC,cAAC8jB,EAAYA,aAACC,OAAM,CAACC,SAAW,GAAEhe,EAAM/F,UAAWgU,WAAY,kBAGnElU,MAAAC,cAACoQ,EAAAA,IAAKrE,KAAAA,eAAUhM,MAAAC,cAACikB,GAAS,MAlF9B,WACE,OAAQje,EAAME,MACZ,IAAK,sBACH,OACEnG,MAAAC,cAAC6Q,GACCqT,CAAAA,QAASle,EAAM/F,GACfwjB,YAAaC,EACb3S,SAAUA,EACVlM,MAAOA,EACPjC,YAAaoD,EAAMpD,cAGzB,IAAK,4BACH,OACE7C,MAAAC,cAACmkB,GACCD,CAAAA,QAASle,EAAM/F,GACfwjB,YAAaC,EACb3S,SAAUA,EACVlM,MAAOA,IAGb,IAAK,wBACH,OAAO9E,MAAAC,cAACokB,GAASpe,CAAAA,MAAOA,EAAOnB,MAAOA,EAAOkM,SAAUA,IACzD,IAAK,wBACH,OAAOhR,MAAAC,cAACqkB,GAAQ,CAACre,MAAOA,EAAO+K,SAAUA,EAAUlM,MAAOA,IAE5D,IAAK,yBACH,OAAO9E,MAAAC,cAACskB,IAAUte,MAAOA,EAAO+K,SAAUA,EAAUlM,MAAOA,IAC7D,IAAK,0BACH,OACE9E,MAAAC,cAACukB,GACCL,CAAAA,QAASle,EAAM/F,GACfihB,QAASwC,EACT3S,SAAUA,IAGhB,IAAK,2BACH,OAAOhR,MAAAC,cAACwkB,GAAYxe,CAAAA,MAAOA,EAAO+K,SAAUA,EAAUlM,MAAOA,IAC/D,IAAK,4BACH,OACE9E,MAAAC,cAACykB,GAAY,CACX9B,gBAAiBA,EACjB3c,MAAOA,EACP+K,SAAUA,EACV0S,YAAaA,EACbiB,UAAW7B,EAAa9c,EAAoBC,IAC5C4c,iBAAkBA,EAClB/d,MAAOA,IAGb,IAAK,yBACH,OAAO9E,MAAAC,cAAC2kB,IAAU3e,MAAOA,EAAO+K,SAAUA,EAAUlM,MAAOA,IAC7D,IAAK,4BACH,OACE9E,MAAAC,cAAC4kB,GACC5e,CAAAA,MAAOA,EACPkb,QAASuC,EACT1S,SAAUA,EACVlM,MAAOA,IAGb,IAAK,0BACH,OAAO9E,MAAAC,cAACkQ,EAAAA,KAAK2U,CAAAA,wBAAyB,CAAEC,OAAQ9e,EAAM+e,WACxD,QAEE,OADAC,QAAQC,KAAM,uBAAsBjf,EAAME,SAE9C,KACF,CAekCgf,IAC7Blf,EAAM6d,mBACL9jB,MAAAC,cAAC8jB,EAAYA,aACX7jB,CAAAA,GAAK,GAAE+F,EAAM/F,UACb6R,UAAWlC,EAAAA,MAAM,kCAEjB7P,MAAAC,cAACoQ,EAAAA,IAAG,CAACyU,wBAAyB,CAAEC,OAAQ9e,EAAM6d,SAGzC,EAIThT,GAASA,EACbqT,UACAT,cACA1S,WACAlM,QACAjC,kBAQA,MAAMuiB,EAAsB1B,GAAa1e,KACtCqgB,GAA4B,cAAjBA,EAAOvgB,OAEfuc,EAAiBC,EAAOA,QAACoC,EAAa,SACtC4B,EAAa3gB,OAAO6C,KAAK6Z,GAAgBE,OACzCH,EAAgBA,IACbkE,EAAWhjB,IAAKkf,GACd,SAAPA,GAAwB,cAAPA,EACfN,EAAqCG,EAAeG,iBAEpDxhB,MAAAC,cAACslB,EAAczU,OAAC2Q,YAAW,CAAChb,IAAK+a,EAAItQ,MAAOsQ,GACzCN,EAAqCG,EAAeG,MAMvDN,EACJsE,GAEOA,EAAMljB,IAAKmjB,gBAChBzlB,MAAAC,cAACslB,SAAepU,OAAM,CACpB1K,IAAKgf,EAAK3gB,MACVA,MAAO2gB,EAAK3gB,MAAMO,WAClBgO,SAAUoS,EAAKpS,UAEdoS,EAAK5iB,2BA6BZ,OACE7C,MAAAC,cAACslB,EAAAA,OAAc,CACbrlB,GAAIikB,EACJnT,SA3B8B0U,EAAGzU,oBACnCD,EAAS,CAAEmT,UAASrf,MAAOmM,GAC7B,EA0BIoC,SAAU+N,IAAgBjY,OAAS,EACnC4H,WAZ6B,IAA3BqQ,IAAgBjY,OAAqB,uBAEvCic,GAAqBviB,aAfD8F,KACtB,IAAIgd,EAAU,UAQd,OAPKhd,EAEM,CAAC,IAAK,IAAK,IAAK,IAAK,KAAK9I,SAAS8I,EAAKjD,OAAO,IACxDigB,GAAW,MAAKhd,IAEhBgd,GAAW,KAAIhd,IAJfgd,GAAU,UAMLA,GAOLC,CAAe/iB,GAAaua,eAU5BpN,KAAK,KACLlL,MAAOA,GAASsgB,GAAqBtgB,OAAS,KAC9CgW,UAAU,gBAETsG,IACa,EAIdgD,GAAeA,EACnBD,UACAT,cACA1S,WACAlM,YAOA,MAAM+gB,EAA6BnC,EAAY1e,KAC5CqgB,GAAWA,EAAOvgB,OAAOO,aAAeP,GAErCghB,EAAgBD,GAAgBhjB,aAAe,IAC9CkjB,EAAmBC,GAAwB1Z,EAAQA,SAAC,KACpD2Z,EAAOC,GAAY5Z,EAAAA,SAASwZ,IAC5BK,EAAqBC,GAA0B9Z,EAAQA,UAAC,IACxD+Z,EAAiBC,GAAsBha,EAAQA,UAAC,GAEnDwZ,IAAkBC,IACpBC,EAAqBF,GACrBI,EAASJ,GACTM,GAAuB,IAGzB,IAAIG,EAAkBC,EAAMA,OAACtE,SAAOwB,EAAa,SAAU,SAE3D,GAAIyC,EAAqB,CACvB,MAAMM,EAAiBR,EAAM7I,cAC7BmJ,EAAkBA,EAAgBlf,OAAQge,GACpB,GAAEA,EAAOxiB,eAAewiB,EAAOlD,QAAQ/E,cACzCvd,SAAS4mB,GAE/B,cAMA,OACEzmB,MAAAC,cAACymB,EAAgBC,SAACC,QAAO,CACvBC,eAAa,EACbC,YAAa,CAAE5P,KAAM,CAAElH,KAAM,OAC7BrB,IAAK,CACH,oBAAqB,CACnBoY,OAAQrD,EAAYva,OAAS,EAAI,UAAY,gBAGjD4d,OAAO,UACP1T,SAAiC,IAAvBqQ,EAAYva,OACtB6d,OAAQA,KACNV,GAAmB,GACnBJ,EAASJ,EAAa,EAExB9U,SAAWrN,IACTuiB,EAASviB,EAAEsjB,OAAOniB,OAClBshB,GAAuB,GACvBE,GAAmB,EACrB,EACAY,QACEb,EACI,KACEH,EAAS,IACTE,GAAuB,EACzB,OACAtY,EAENqZ,QAAUxjB,GAA2CA,EAAEsjB,OAAOG,SAC9DzM,SAAW0K,IAjCYvgB,KACzBkM,EAAS,CAAEmT,UAASrf,SAAO,EAiCvBuiB,CAAkBhC,EAAOvgB,OACzBohB,EAASb,EAAOxiB,aAChBujB,GAAuB,GACvBE,GAAmB,IAErBgB,aACAzT,EAAAA,YAAa,IACb0T,YACE7D,EAAYva,OAAS,EAAI,mBAAqB,uBAEhD2R,UAAU,eACV0M,aAAc,CACZC,YAAa,WAEfzT,wBAAYhU,MAAAC,cAACgU,EAAAA,KAAKxQ,CAAAA,KAAK,iBAAiBuM,KAAK,OAC7C0X,yBAAa1nB,MAAAC,cAACgU,EAAAA,KAAI,CAACxQ,KAAK,sBACxBuM,KAAK,KACLlL,MAAOmhB,GAENvC,EAAYva,OAAS,gBACpBnJ,MAAAC,cAAAD,MAAAqP,SAAA,KACGkX,EAAgBpd,OAAS,EACxBod,EAAgBjkB,IAAI,CAAC+iB,EAAoBsC,KACvC,MAAMC,EAAYvC,EAAOvgB,MAAMO,aAAeP,eAC9C,OACE9E,MAAAC,cAACymB,WAAiBhM,KAChB,CAAA,aAAY2K,EAAOxiB,YACnBwQ,SAAUgS,EAAOhS,SACjBsU,MAAOA,EACPlhB,IAAK4e,EAAOvgB,MACZ+O,YAAa,KACbG,wBACEhU,MAAAC,cAACgU,EAAIA,KAAA,CACHC,YAAa,GACbzQ,KAAMmkB,EAAY,gBAAkB,GACpC5X,KAAK,OAGT6X,KAAK,SACLjY,QAASC,EAAKA,MAAC,iBACf/K,MAAO,CACLjC,YAAawiB,EAAOxiB,YACpBiC,MAAOugB,EAAOvgB,MAAMO,0BAGtBrF,MAAAC,cAACkQ,EAAAA,KAAI,CAACkJ,UAAQ,gBACZrZ,MAAAC,cAAC6nB,EAASA,UAAA,CAAC1U,KAAMiS,EAAOxiB,YAAaojB,MAAOA,KAE7CZ,EAAOlD,oBACNniB,MAAAC,cAACyT,EAAKA,MAAA,CACJxC,mBAAOlR,MAAAC,cAAC6nB,EAASA,UAAA,CAAC1U,KAAMiS,EAAOlD,MAAO8D,MAAOA,IAC7CjW,KAAK,KACLkE,WAAW,SAGM,gBAI3BlU,MAAAC,cAAC8nB,EAAIA,KAACrN,KACJ1a,kBAAAA,MAAAC,cAACkQ,EAAAA,KAAI,KAAC,mBAAsB8V,EAAM,OAKlB,EAIxBvB,GAAeA,EACnB9B,kBACA3c,QACA0e,YACAjB,cACAb,mBACA7R,WACAlM,YAUA,MAAMkjB,EAAkBxa,EAAWA,YAChCyY,IACCpD,EAAiB,CAAEE,aAAc,CAAEkD,SAAShgB,SAAO,EAErD,CAAC4c,IAGGoF,EAAkBC,EAAAA,QACtB,IAAMC,EAAQA,SAACH,EAAiB,KAChC,CAACA,IAGGI,EAAS5a,EAAWA,YACvByY,IACMrD,IAEMqD,EAAMpJ,OAAO1T,OAAS,EAC/B8e,EAAgBhC,GAEhBgC,EAAgBI,SAClB,EAEF,CAACJ,IAGGK,EAAqBJ,EAAAA,QACzB,KAAA,CAASrlB,YAAa,SAAUiC,MAAO,SACvC,IAUI+gB,EARiBqC,EAAAA,QAAQ,IACxBtF,EAGIc,EAFA,CAAC4E,GAIT,CAACA,EAAQ5E,IAE0B1e,KAAMqgB,GAAWA,EAAOvgB,QAAUA,GAClEghB,EAAgBD,GAAgBhjB,aAAe,IAC9CojB,EAAOsC,GAAajc,EAAQA,SAACwZ,IAC7BO,EAAiBC,GAAsBha,YAAS,GAEvD,SAAS4Z,EAASphB,GAChByjB,EAAUzjB,GACVsjB,EAAOtjB,GACqB,IAAxBA,EAAM+X,OAAO1T,QACfke,EAAkB,KAEtB,CAEA,MAAMA,EAAqBviB,IACzBkM,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,SAAO,eAGvC,OACE9E,MAAAC,cAACymB,EAAgBC,SAACC,QAAO,CACvBC,eAAa,EACbC,YAAa,CAAE5P,KAAM,CAAElH,KAAM,OAC7B+W,OAAO,UACPC,OAAQA,KACNV,GAAmB,GACnBJ,EAASJ,EACX,EACA9U,SAAWrN,IACTuiB,EAASviB,EAAEsjB,OAAOniB,OAClBwhB,GAAmB,EACrB,EACAY,QACEb,EACI,KACEH,EAAS,GACX,OACApY,EAENqZ,QAAUxjB,GAA0CA,EAAEsjB,OAAOG,SAC7DzM,SAAW0K,IACTgC,EAAkBhC,EAAOvgB,OACzBohB,EAASb,EAAOxiB,aAChByjB,GAAmB,EAAK,EAE1BgB,aACAzT,EAAAA,YAAa,IACb0T,YAAY,SACZzM,UAAU,eACV0M,aAAc,CACZC,YAAa,WAEfzT,WACE6R,GAAkBA,EAAenZ,MAAMqL,oBACrC/X,MAAAC,cAACgc,EAAMA,OAACjM,CAAAA,KAAK,KAAKmM,OAAQ0J,EAAenZ,KAAKqL,sBAE9C/X,MAAAC,cAACgU,EAAIA,KAAA,CAACxQ,KAAK,iBAAiBuM,KAAK,OAGrC0X,yBAAa1nB,MAAAC,cAACgU,EAAIA,KAAA,CAACxQ,KAAK,sBACxBuM,KAAK,KACLlL,MAAOmhB,GAENrD,EACCqD,EAAMpJ,OAAO1T,OAAS,EACpBua,EAAYva,OAAS,EACnBua,EAAYphB,IAAI,CAAC+iB,EAAQsC,iBAErB3nB,MAAAC,cAACymB,EAAgBC,SAACjM,KAAI,CACpB,aAAY2K,EAAOxiB,YACnB8kB,MAAOA,EACPlhB,IAAK4e,EAAOvgB,MACZ+O,YAAa,KACbG,wBACEhU,MAAAC,cAACgc,EAAAA,OAAM,CACL/H,YAAa,GACbiI,OAAQkJ,EAAO3Y,KAAKqL,OACpB/H,KAAK,OAGT6X,KAAK,SACLjY,QAASC,EAAAA,MAAM,iBACf/K,MAAOugB,gBAEPrlB,MAAAC,cAACkQ,EAAIA,KAAA,CAACkJ,UACJrZ,gBAAAA,MAAAC,cAAC6nB,EAASA,UAAC1U,CAAAA,KAAMiS,EAAOxiB,YAAaojB,MAAOA,OAKlDtB,eACF3kB,MAAAC,cAACymB,EAAAA,SAAiBhM,KAChB1a,kBAAAA,MAAAC,cAACkQ,EAAIA,KAAC,KAAA,4BAGRnQ,MAAAC,cAACymB,EAAgBC,SAACjM,KAAI,kBACpB1a,MAAAC,cAACkQ,EAAIA,KAAA,KAAC,4BAIVnQ,MAAAC,cAACymB,EAAAA,SAAiBhM,KAChB1a,kBAAAA,MAAAC,cAACkQ,EAAIA,UAAC,gCAIVnQ,MAAAC,cAACymB,WAAiBhM,KAAI,CAAC5V,MAAOwjB,EAAQX,MAAO,EAAGE,KAAK,uBACnD7nB,MAAAC,cAACkQ,EAAIA,UAAEmY,EAAOzlB,cAGM,EAIxBwhB,GAAWA,EACfpe,QACAnB,QACAkM,2BAYEhR,MAAAC,cAACuoB,EAAgBnE,UACfhR,SAAUpN,EAAMoN,SAChBpL,MAAOhC,EAAMgC,MACbwgB,QAAS3jB,IAAS,EAClBkM,SAV8BrN,IAEhCqN,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,MADhBnB,EAAEsjB,OAAOwB,SACc,IAanCnE,GAAWA,EACfre,QACAnB,QACAkM,2BAWEhR,MAAAC,cAACoQ,EAAGA,IACFrQ,kBAAAA,MAAAC,cAACyoB,EAAAA,SACC5jB,CAAAA,MAAOA,EACPyiB,YAAathB,EAAMshB,YACnBvW,SAToBrN,IAExBqN,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,MADlBnB,EAAEsjB,OAAOniB,OAEvB,EAOMkL,KAAK,QAMPuU,GAAYA,EAChBte,QACAnB,QACAkM,eAMA,MAAM9P,WAAEA,GAAe8M,EAAUA,WAAChN,IAC3B2nB,EAAcC,GAAmBtc,EAAQA,UAAC,GAC3Cuc,EAAc5iB,EAAM6iB,aAAe,sBACnCC,EAAkB,6BAClBC,EAA0B9nB,ER/T7BpB,QAAQ,KAAM,KACdA,QAAQ,KAAM,KACdA,QAAQ,KAAM,KACdA,QAAQ,KAAM,OQ6TVmpB,EAAgBC,GAAqB5c,EAAAA,SAAS/D,EAAAA,QAAOzD,GAAOqkB,UAC7DC,EAAwBnjB,EAAMmjB,wBAAyB,eAoB7D,OACEppB,MAAAC,cAAC0P,EAAAA,UAAUa,CAAAA,KAAK,2BACdxQ,MAAAC,cAACslB,EAAczU,OAAA,CACbE,SArBqBqY,EAAGpY,oBACxBA,IAAkB4X,GAAe5X,IAAkB8X,GACrDH,GAAgB,GAChB5X,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,MAAOmM,KACV,kBAAlBA,GACTD,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,MAAO,OACrC8jB,GAAgB,KAEhBA,GAAgB,GAChB5X,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,MAAO,OACvC,EAYIkL,KAAK,KACL8K,UAAU,6BAEV9a,MAAAC,cAACslB,EAAAA,OAAepU,OAAOrM,CAAAA,MAAO+jB,GAC3BA,IAED5iB,EAAM6iB,0BACN9oB,MAAAC,cAACslB,EAAczU,OAACK,OAAOrM,CAAAA,MAAOikB,GAC3BA,gBAGL/oB,MAAAC,cAACslB,EAAczU,OAACK,OAAOrM,CAAAA,MAAM,iBAAgB,mBAG5CskB,gBACCppB,MAAAC,cAACslB,SAAepU,OAAOrM,CAAAA,MAAM,cAAa,eAK7C6jB,gBACC3oB,MAAAC,cAACoQ,EAAGA,IAAA,kBACFrQ,MAAAC,cAACqpB,EAAiB/E,UAAA,CAChBgF,aAAW,EACXC,YAAaR,EACb9U,WAAY,EACZlD,SAnCkB3I,IAC1B2I,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,MAAOsD,EAAcC,EAAMnH,KACzDgoB,EAAkB7gB,EAAI,EAkCd2H,KAAK,KACLlL,MAAOmkB,KAIJ,EAITzE,GAAaA,EACjBL,UACAhD,UACAnQ,eAMA,MAAOyY,EAAgBC,GAAqBpd,EAAAA,SAAS,CAAA,gBASrD,OACEtM,MAAAC,cAAC0P,EAAAA,UAAS,CAACC,QAAS,GACjBuR,EAAQ7e,IAAKmjB,gBACZzlB,MAAAC,cAACoQ,MAAI5J,CAAAA,IAAKgf,EAAK3gB,oBACb9E,MAAAC,cAACyQ,EAAAA,MAAMC,WAAU,CAACE,SAAW,cAAasT,KAAWsB,EAAK3gB,SACvD2gB,EAAK5iB,aAAe4iB,EAAK3gB,oBAE5B9E,MAAAC,cAACslB,EAAAA,OACCrlB,CAAAA,GAAK,cAAaikB,KAAWsB,EAAK3gB,QAClCkM,SAAUA,EAAGC,mBAhBQ0Y,EAAC1Y,EAAenM,KAC7C,MAAM8kB,EAAoB,IAAKH,GAC/BG,EAAkB9kB,GAASmM,EAC3ByY,EAAkBE,GAClB5Y,EAAS,CAAEmT,UAASrf,MAAO8kB,GAAmB,EAapCD,CAAuB1Y,EAAewU,EAAK3gB,OAE7CkL,KAAK,KACLe,WAAY,6BAEZ/Q,MAAAC,cAACslB,EAAAA,OAAepU,QAAOrM,MAAM,SAAQ,sBACrC9E,MAAAC,cAACslB,EAAAA,OAAepU,QAAOrM,MAAM,WAAU,cAMpC,EAIT2f,GAAcA,EAClBxe,QACA+K,WACAlM,YAMA,MAAM+kB,EAAe5jB,EAAM6jB,UAAY,EAAI7jB,EAAM6jB,SAAW,EACtDC,EACJ9jB,EAAM+jB,UAAY,GAAK/jB,EAAM+jB,UAAY,IAAM/jB,EAAM+jB,SAAW,KAE3DC,EAAYC,GAAiB5d,EAAQA,SAAC6d,OAAOlkB,EAAMyc,eAAiB,GAM3E,OAJAhV,EAAAA,UAAU,KACRsD,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,MAAOmB,EAAMyc,cAAgB,GAAG,EAC7D,CAACzc,iBAGFjG,MAAAC,cAAC0P,EAAAA,UACC3P,kBAAAA,MAAAC,cAACyQ,EAAKA,MAAC0Z,SAAQ,kBACbpqB,MAAAC,cAACoqB,EAAmB5F,YAAA,CAClBzT,SAAWlM,IACT,MAAMwlB,EAAiBH,OAAOrlB,IAAU,EACxColB,EAAcI,GAEdtZ,EAAS,CACPmT,QAASle,EAAM/F,GACf4E,MAAOoI,KAAKqd,IACVrd,KAAKsd,IAAIF,EAAgBT,GACzBE,IAEH,EAEHxC,YAAathB,EAAMshB,YACnBvX,KAAK,KACLlL,MAAOA,EACPylB,IAAKV,EACLW,IAAKT,EACLU,aAAa,KAGhBR,EAAaF,gBACZ/pB,MAAAC,cAAC0W,EAAAA,MAAK,CACJC,KAAK,QACLyF,kBAAmBxM,EAAAA,MAAM,iBACzBuJ,gBAAiBvJ,EAAKA,MAAC,oBACvB6a,QAAQ,eACR3Y,UAAW,kBAEX/R,MAAAC,cAAC0P,EAASA,UAAA,CAACa,KAAK,aAAasB,UAAU,SAASlC,QAAS,kBACvD5P,MAAAC,cAACgU,EAAAA,KAAI,CACHxQ,KAAK,8BACLuM,KAAK,KACLC,MAAM,0BAERjQ,MAAAC,cAACkQ,EAAAA,KAAKH,CAAAA,KAAMH,EAAAA,MAAM,qBAAqB,uBAChBka,EAAa,OAKjC,EAITnF,GAAYA,EAChB3e,QACAnB,QACAkM,2BAWEhR,MAAAC,cAACoQ,EAAAA,IACCrQ,kBAAAA,MAAAC,cAACyQ,EAAKA,MACJV,CAAAA,KAAK,KACLlL,MAAOA,EACP5E,GAAI+F,EAAM/F,GACVqnB,YAAathB,EAAMshB,YACnBvW,SAXoBrN,IAExBqN,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,MADlBnB,EAAEsjB,OAAOniB,YAgBnB+f,GAAeA,EACnB5e,QACAkb,UACAnQ,WACAlM,YAOA,MAAM6lB,EAAuBhnB,IAC3BqN,EAAS,CAAEmT,QAASle,EAAM/F,GAAI4E,MAAOnB,EAAEsjB,OAAOniB,OAChD,eAEA,OACE9E,MAAAC,cAAC0P,EAAAA,UAAS,CAACoC,UAAW,EAAGnC,QAAS,IAC/BuR,EAAQ7e,IAAK+iB,gBACZrlB,MAAAC,cAAC2qB,EAAKA,MACJnC,CAAAA,QAAS3jB,IAAUugB,EAAOvgB,MAC1B2B,IAAK4e,EAAOvgB,MACZmD,MAAOod,EAAOxiB,aAAewiB,EAAOvgB,MACpCkM,SAAU2Z,EACV3a,KAAK,KACLlL,MAAOugB,EAAOvgB,SAGT,EAITof,GAAUA,iBACdlkB,MAAAC,cAAC0P,EAASA,UACRa,CAAAA,KAAK,aACLsB,UAAU,SACVlC,QAASC,EAAKA,MAAC,iBACfwM,kBAAmB,KACnBjD,gBAAiBvJ,EAAAA,MAAM,iBACvBkE,OAAQlE,EAAAA,MAAM,wBACd0D,OAAS,aAAY1D,EAAKA,MAAC,oCAE3B7P,MAAAC,cAAC0gB,EAAOA,QAAA,CAAC3Q,KAAK,oBACdhQ,MAAAC,cAACkQ,EAAIA,KAAC+B,CAAAA,SAAUrC,EAAKA,MAAC,oBAAqBwC,WAAY,MAAM,YCv2B3DwY,GAASA,EACbjI,kBACAzb,mBACA6J,WACA5J,uBACAyb,mBACAhc,cACAic,mBAEApV,EAASA,UAAC,KACR,MAAMod,EAAgB3jB,EAAiBkE,OAAO,CAAC0T,EAAK9Y,KAC9CtB,OAAO+B,UAAUH,eAAeI,KAAKV,EAAO,gBAC9C8Y,EAAI9Y,EAAM/F,IAAM+F,EAAMyc,aACE,cAAfzc,EAAME,OACf4Y,EAAI9Y,EAAM/F,IAAM+F,EAAM6iB,aAAe,wBAGhC/J,GACN,IACH/N,EAAS8Z,IACR,CAAC3jB,EAAkB6J,IAEtB,MAAM+Z,EAAmB7jB,EACvBC,EACAC,GAGI4jB,EAAmCA,EAAG7G,UAASrf,YACnD,MAAMgmB,EAAgB,IAAK1jB,GACrB6jB,EAAa9jB,EAAiBE,OAAQpB,GAAUA,EAAMqd,WAC5D2H,EAAW3oB,IAAK4oB,IACd,GAAIA,EAAU5H,UAAUzjB,SAASskB,GAAU,CACzC,MAAMgH,EAASF,EAAWjmB,KAAMzE,GAC9BA,EAAE+iB,UAAUzjB,SAASqrB,EAAUhrB,KAE7BirB,UACKL,EAAcK,EAAOjrB,WAEvB4qB,EAAcI,EAAUhrB,SAGF4N,IAA3Bod,EAAUxI,mBACsB5U,IAAhCgd,EAAcI,EAAUhrB,MAExB4qB,EAAcI,EAAUhrB,IAAMgrB,EAAUxI,aAE5C,IAGY,cAAV5d,SACKgmB,EAAc3G,GAErB2G,EAAc3G,GAAWrf,EAG3BkM,EAAS,IAAK8Z,GAAe,EAG/B,OAAI3jB,EAAiBgC,oBAEjBnJ,MAAAC,cACG8qB,MAAAA,KAAAA,EAAiBzoB,IAAK2D,gBAEnBjG,MAAAC,cAAC0iB,IACCC,gBAAiBA,EACjB3c,MAAOA,EACPQ,IAAKR,EAAM/F,GACX8Q,SAAUga,EACVlmB,MAAOsC,EAAqBnB,EAAM/F,IAClCkH,qBAAsBA,EACtByb,iBAAkBA,EAClBhc,YAAaA,EACbic,aAAcA,MAQ1B,IAAA,EChBasI,GAAuBA,SAAC5rB,GAAa,IAClD,OAAA4C,QAAAO,QAAO6H,GACJtH,IAAI,CACHC,KAAM,CACJC,OAAQ,CACNioB,oBACE,mHAEJhkB,OAAQ,sBAEV9D,IAAM,mBAAkB/D,4BAEzBkE,KAAK,EAAGP,UAAWA,GACxB,CAAC,MAAAQ,GAAA,OAAAvB,QAAAwB,OAAAD,EAAA,CAAA,EAlCc2nB,GAAe,WAAG,IAC/B,OAAAlpB,QAAAO,QAAO6H,GACJtH,IAA6D,CAC5DC,KAAM,CAAEC,OAAQ,CAAEmoB,aAAc,SAChChoB,IAAK,oBAENG,KAAK,EAAGP,UAAWA,EAAKb,IAAKkpB,GAAMA,EAAE/nB,OAC1C,CAAC,MAAAE,GAAA,OAAAvB,QAAAwB,OAAAD,EAAA,CAAA,EAlBc8nB,GAAc,WAAG,IAC9B,OAAArpB,QAAAO,QAAO4c,GACJrc,IAAoB,CACnBC,KAAM,CACJC,OAAQ,CAAEsoB,OAAQ,SAEpBnoB,IAAK,eAENG,KAAK,EAAGP,UAAWA,EAAKwoB,KAAKrpB,IAAKkpB,GAAMA,EAAE/nB,OAC/C,CAAC,MAAAE,GAAA,OAAAvB,QAAAwB,OAAAD,EAAA,CAAA,EA5BK4b,GAAS,IAAI1Z,EAAAA,OAAO,CAAEC,KAAMvG,EAAW,UAAWwG,QAAS,WAC3DyE,GAAiB,IAAI3E,EAAMA,OAAC,CAChCC,KAAMvG,EAAW,YACjBwG,QAAS,WAEL6lB,GAAkB,CACtBjd,IAAK,CAAEkd,aAAchc,EAAAA,MAAM,yBAC3BwM,kBAAmB,KACnBjD,gBAAiB,KACjBxC,KAAM,SAmGFkV,GAAgBA,EACpBC,qBACAC,iBACAC,aAAY,EACZC,aACArpB,cACAwT,iBACA+D,cAUA,MAAO+R,EAAsBC,GAA2B9f,EAAQA,SAC9D8N,EAAQzQ,OAAO,KAEV0iB,EAA0BC,GAA+BhgB,WAAS,CAAA,IAClEigB,EAAaC,GAAkBlgB,WAAS4f,IACxCtM,EAAe6M,GAAoBngB,WAExC,KACKuV,EAAsB6K,GAA2BpgB,WAEtD,KACKqgB,EAA6BC,GAClCtgB,YAAS,IACJ3E,EAAoBklB,GACzBvgB,EAAQA,YACHlF,EAAsB0lB,GAC3BxgB,EAAAA,SAA+B,CAAE,IAC5BzF,EAAakmB,GAAkBzgB,EAAAA,SACpC,CACF,IACOwW,EAAckK,GAAmB1gB,EAAAA,SAAmC,CAAE,IACtE2gB,EAAYC,GAAiB5gB,EAAAA,UAAS,IACtC/C,EAAO8C,GAAYC,EAAAA,SAIvB,CAAE,IACE6gB,EAAiBC,GAAsB9gB,EAAAA,UAAS,IAChDoQ,EAAe2Q,GAAoB/gB,EAAAA,SACxC,CACF,GACMghB,EAAeC,EAAAA,OAAO,MAEtB3K,EAAkBsF,EAAOA,QAC7B,IAAMtI,EAActd,IAAKkpB,GAAMA,EAAEtrB,IAAIL,SAAS,UAC9C,CAAC+f,IAGG1b,EAAuByD,GAAoBzD,qBAC3CspB,EACwC,WAA5C7lB,GAAoB8lB,eAAetnB,KAE/B0c,EAAmBrV,EAAAA,YACvB,EAAGvH,QAAO8c,mBACRiK,EAAiB9R,QACZA,EACH,CAAClV,EAAoBC,KAAS,KAzGT,UAACzG,IAC5BA,EAAGyG,MACHA,EAAK/B,qBACLA,EAAoB6e,aACpBA,IAMD,IACC,MAAmB,iBAAf9c,EAAME,KAAyB/D,QAAAO,QACF4c,GAAOrc,IAEnC,CACDC,KAAM,CACJC,OAAQ,CAAEgH,OAAQ,eAClB9G,MAAO,CAAEoqB,qBAAsB3K,EAAakD,MAAOxc,OAAQ,WAE7DlG,IAAK,aACLG,eARMP,KAAM+G,IAUd,OAAOA,EAAO5H,IAAKkJ,KACjB3I,YAAa2I,EAAE/H,KACfiJ,KAAM,CAAEqL,OAAQvM,EAAEuM,QAClBjT,MAAO0G,EAAEtL,GAAGmF,aACX,GACEjD,QAAAO,QACkB6H,GAAetH,IAAI,CACxCC,KAAM,IACD4f,EACH7e,uBACAd,OAAQ,CACNuqB,wBAAyB,WAG7BpqB,IAAM,mBAAkB/D,gCAAkCyG,EAAMC,eAChExC,KATI,UAAAP,KAAEA,IAUR,OAAOA,EAAKsB,MAAM,EAEtB,CAAC,MAAAd,GAAAvB,OAAAA,QAAAwB,OAAAD,EAvDc,CAAA,CA0HTiqB,CAAe,CACbpuB,IAAK+sB,EACLroB,uBACA6e,eACA9c,UAECvC,KAAMmqB,IACLd,EAAgB7R,IAAU,IACrBA,EACH,CAAClV,EAAoBC,IAAS4nB,KAEhCb,EAAiB9R,IAAI,IAChBA,EACH,CAAClV,EAAoBC,KAAS,IAElC,GACCzC,MAAO+F,GAAU8C,EAAS,CAAEyhB,oBAAqBvkB,IAAQ,EAE9D,CAACgjB,EAAaroB,IAwBhBwJ,EAASA,UAAC,KACRrB,EAAS,CAAE,GAjLgB,WAAG,IAAA,OAAAjK,QAAAO,QACUP,QAAQC,IAAI,CACpDopB,KACAH,QACA5nB,KAAA,UAHKqqB,EAAaC,IAKpB,OAAOD,EACJ1mB,OAAQ7H,GAAQwuB,EAAanuB,SAASL,IACtC+hB,OACAjf,IAAK9C,IAAiB,CAAEU,GAAIV,EAAI4d,cAAe3Z,KAAMjE,IAAO,EACjE,CAAC,MAAAmE,GAAA,OAAAvB,QAAAwB,OAAAD,EAAA,CAAA,CAwKGsqB,GAAmBvqB,KAAMioB,IACvBc,EAAiBd,GACjB,MAAMuC,EAAmBvC,EAAK3mB,KAAMxF,GAAQA,EAAIU,KAAOgsB,GACnDA,EACAP,EAAK,GAAGzrB,GACZssB,EAAe0B,GACf9C,GAAwB8C,GACrBxqB,KAAMyqB,IACAb,EAAac,UAChB1B,EAAwByB,GACxBvB,GAA+B,GACjC,GAEDppB,MAAO+F,GAAU8C,EAAS,CAAE8hB,YAAa5kB,MAC7C,EACA,CAAC2iB,IAEJxe,EAASA,UAAC,KACRrB,EAAS,CAAE,EAAA,EACV,CAACjF,IAEJ,MAAMinB,EAAoBC,EAAAA,UACxB,eAAgBnC,EACZA,EAAqBoC,WACrBnU,EAAQmU,YAEd,IAAK,MAAM9nB,KAAO4lB,EAChBmC,MAAIH,EAAmB5nB,EAAK4lB,EAAyB5lB,IAEvD,MAAMgoB,EACJ,sBAAuBtC,EACnBA,EAAqBsC,kBACrBrU,EAAQqU,kBAUd,SAASC,IACP,MAAMC,EVrHH,UAA0BhnB,mBAC/BA,EAAkBP,qBAClBA,EAAoBP,YACpBA,IAMA,MAAO,CACLhE,YAAa6E,EAAuB,CAClCb,YAAaA,GAAe,CAAA,EAC5Bc,qBACAP,yBAEF3D,MAU0B4C,EAVCsB,EAWtBvB,EAAyBC,IAAeA,EAAWxD,cAD5D,IAA8BwD,CAR9B,CUoG6Bga,CAAiB,CACxCxZ,cACAc,qBACAP,yBAGF,IAAIvE,EAAc8rB,EAAiBlrB,KAMnC,OAJIkrB,EAAiB9rB,cACnBA,GAAgB,KAAI8rB,EAAiB9rB,gBAGhCA,CACT,CAiDA,SAAS+rB,EAAazrB,GACpB+pB,GAAc,GACd1iB,GACGsI,KAAK,CACJ3P,OACAI,IAAK,iCAENG,KAAK,KACAqoB,GAAoB8C,WAAa1B,GACnC9W,IACA0V,EAAmB8C,UAAU,IAAK1rB,KAElCxD,OAAOC,SAASkvB,QAClB,GAEDtrB,MAAO+F,IACN2jB,GAAc,GACV3jB,EAAMC,OACR6C,EAAS,CAAER,WAAYtC,EAAMC,SAE7BulB,MAAM,iCACR,EAEN,cAEA,OACE/uB,MAAAC,cAAC0P,EAASA,UAAC4F,CAAAA,WAAY,EAAG3F,QAAS,GAChC/M,gBACC7C,MAAAC,cAACoQ,EAAGA,IAAA,kBACFrQ,MAAAC,cAACkQ,QACC4G,MAAO,CACL9G,MAAOJ,EAAAA,MAAM,kBACbqC,SAAUrC,QAAM,oBAChBwC,WAAY,KACZL,aAAcnC,QAAM,mBAGrBhN,EAAa,iBACd7C,MAAAC,cAAC+O,QAAK0K,UAAQ,EAACzK,GAAI+c,GAAgB,gBAMxCziB,EAAMsC,yBACL7L,MAAAC,cAAC0W,EAAKA,MAAKiV,gBACT5rB,MAAAC,cAACkQ,EAAIA,KAAA,KAAC,sJAMVnQ,MAAAC,cAAC0P,EAASA,WAACC,QAAS,gBAClB5P,MAAAC,cAACyQ,EAAKA,MAACC,WACLV,CAAAA,MAAOJ,EAAAA,MAAM,kBACbgB,SAAS,uBACTqB,SAAUrC,EAAKA,MAAC,oBAChBe,WAAYf,EAAAA,MAAM,2BACnB,iCAGD7P,MAAAC,cAAC6Q,SAAM,CACL5Q,GAAG,uBACH8Q,SAAUA,EAAGC,mBAhLnBA,KAEAmb,EAAwBnb,GACxBqb,EAA4B,GAC9B,EA6KU0C,CAAyB/d,GAE3BjB,KAAK,KACLlL,MAAOqnB,GAEN/R,EAAQzQ,OAAOrH,IAAI,CAAC2sB,EAAcC,iBACjClvB,MAAAC,cAAC6Q,EAAAA,OAAOK,QACN1K,IAAM,GAAEwoB,EAAaxrB,QAAQyrB,IAC7BpqB,MAAOmqB,GAENA,EAAapsB,eAKnB4rB,GAAmBtlB,OAAS,gBAC3BnJ,MAAAC,cAAC4qB,IACCjI,gBAAiBA,EACjBzb,iBAAkBsnB,EAClBrnB,qBAAsBilB,EACtBrb,SAAUsb,EACVzlB,YAAa,CAAG,EAChBic,aAAc,CAAA,EACdD,iBAAkBA,IAAM,qBAK9B7iB,MAAAC,cAAC0P,EAAAA,UAAS,CAACC,QAAS,GACjBgQ,EAAczW,OAAS,eACtBnJ,MAAAC,cAACkvB,IACC5C,YAAaA,EACb3M,cAAeA,EACfwP,qBAjOuB5vB,IAC/BgtB,EAAehtB,GACfotB,GAA+B,GAC/BF,EAAwB,IACxBY,EAAac,QAAU5uB,EACvBqtB,EAAsB,MACtBC,EAAwB,CAAA,GACxBzgB,EAAS,CAAE,GACX+e,GAAwB5rB,GACrBkE,KAAKgpB,GACLhpB,KAAK,IAAMkpB,GAA+B,IAC1CppB,MAAO+F,GAAU8C,EAAS,CAAE8hB,YAAa5kB,IAAQ,iBAyN9CvJ,MAAAC,cAAC0P,EAAAA,UAAS,CAACC,QAAS,gBAClB5P,MAAAC,cAACkQ,EAAAA,KACCF,CAAAA,MAAOJ,EAAKA,MAAC,2BACbqC,SAAUrC,EAAAA,MAAM,oBAChBe,WAAYf,QAAM,2BACnB,6CAGD7P,MAAAC,cAAC0P,EAASA,UACRa,CAAAA,KAAK,aACLsB,UAAU,SACVlC,QAASC,QAAM,iBACfwM,kBAAmB,KACnBjD,gBAAiBvJ,EAAAA,MAAM,iBACvBkE,OAAQ,EACRR,OAAS,aAAY1D,EAAKA,MAAC,oCAE3B7P,MAAAC,cAAC0gB,EAAOA,QAAC3Q,CAAAA,KAAK,oBACdhQ,MAAAC,cAACkQ,EAAAA,KAAK+B,CAAAA,SAAUrC,EAAKA,MAAC,oBAAqBwC,WAAY,MAAM,aAMlE9I,EAAM4kB,yBACLnuB,MAAAC,cAAC0W,QAAK/E,EAAA,CAACG,UAAWlC,EAAKA,MAAC,kBAAsB+b,iBAC5C5rB,MAAAC,cAACkQ,OAAI,KAAC,gGAKNwc,eACF3sB,MAAAC,cAACovB,GAA2B,mBAE5BrvB,MAAAC,cAACyhB,GACCC,CAAAA,kBAAmBha,EACnBka,qBAAsBA,EACtBD,4BA/MR0N,IAEAzC,EAAsByC,GACtBjjB,EAAS,CAAE,GACXygB,EAAwB,GAC1B,KA+MKnlB,IACE4B,EAAMukB,iCACL9tB,MAAAC,cAAC0W,QAAUiV,gBACT5rB,MAAAC,cAACkQ,EAAAA,KAAK,KAAA,oHAMRnQ,MAAAC,cAAAD,MAAAqP,SACErP,kBAAAA,MAAAC,cAAC4qB,GACCjI,CAAAA,gBAAiBA,EACjBzb,iBAAkBQ,EAAmBR,kBAAoB,GACzD6J,SAAU8b,EACV1lB,qBAAsBA,EACtBP,YAAaA,EACbgc,iBAAkBA,EAClBC,aAAcA,IAEfiJ,GAAoB9jB,oBACnBjI,MAAAC,cAACokB,EAAQA,UACPhR,SACE4Z,GACAsC,GAAc5nB,EAAoBP,GAEpCa,MAAO8jB,EAAmB9jB,MAC1BwgB,QAAS0E,EACTnc,SAAUA,IAAMoc,GAAoBD,KAGvChB,GAAsBzP,eAAepa,IAAI,CAACktB,EAAON,iBAChDlvB,MAAAC,cAACokB,WAAQ,CACP5d,IAAM,GAAE+oB,EAAM/oB,OAAOyoB,IACrBjnB,MAAOunB,EAAM3sB,YACb4lB,QACG/L,GAAiBA,EAAc8S,EAAM/oB,MACtC+oB,EAAM9M,aAER1R,SAAWrN,IACT0pB,EAAkBnS,IAAI,IACjBA,EACH,CAAE,GAAEsU,EAAM/oB,OAAQ9C,EAAEsjB,OAAOwB,UAC3B,KAIP+E,gBACCxtB,MAAAC,cAAC0W,EAAAA,MAAUiV,gBACT5rB,MAAAC,cAAC0P,EAASA,UAAA,CAACa,KAAK,aAAaZ,QAAS,kBACpC5P,MAAAC,cAACgU,EAAAA,KACCjE,CAAAA,KAAMH,EAAAA,MAAM,uBACZpM,KAAK,8BACLwM,MAAOJ,EAAKA,MAAC,8CAEf7P,MAAAC,cAACkQ,QACC2U,wBAAyB,CACvBC,OAAQpd,EAAmB8lB,eAAegC,YASzDxD,gBACCjsB,MAAAC,yBACG+G,KAAKC,UACJ,CACEpE,YAAa8E,GAAsB+mB,IACnC7nB,cACAc,qBACAP,uBACAinB,qBAEF,KACA,iBAKNruB,MAAAC,cAAC0P,YAAS,CACRmC,UAAU,SACVtB,KAAK,aACLkf,UAAY,aAAY7f,EAAAA,MAAM,sBAC9BY,aAAa,MACbsB,UAAW,EACXiK,kBAAmB,EACnBK,kBAAmB,EACnB9G,WAAY,EACZ3F,QAAS,gBAET5P,MAAAC,cAACmR,SAAM,CACLnB,MAAOJ,EAAAA,MAAM,2BAEb,oBAAgB,EAChBe,WAAYf,EAAKA,MAAC,0BAClByB,QAAS+E,EACTrG,KAAK,KACLkB,MAAM,SACNM,QAAQ,uBAEVxR,MAAAC,cAACmR,EAAMA,QACLiC,SACE4Z,GACAO,GACA+B,GAAc5nB,EAAoBP,GAEpCkK,QAzSR,WACE,GAAI2b,EACF,OAEF,MAAM0C,EAAmB,IAAKvoB,GAE1BO,EAAmBzD,uBACrByrB,EAAiBC,sBACfjoB,EAAmBzD,sBAGvB,MAAMf,EAAO,CACXsH,GAAI2P,EAAQa,SACZ9X,KAAM,CACJ4P,WAAY,CACVlQ,YAAa6rB,IACbjrB,KAAM0oB,EAAqB1oB,KAC3BosB,mBAAoBtD,EACpBuD,gCAAiCnoB,EAAmBrB,gBACpDqpB,mBACAI,mBAAoB1B,EACpB2B,eAAgBtT,GAElB9F,KAAM,2BAGNuW,EACFja,EACGC,KAAK,CACJ8c,iBAAkB,SAClB3U,kBAAmB,sBACnBlI,KAAM,iFACNlC,MAAQ,GAAE6a,EAAmB9jB,WAE9BvE,KAAMsG,IACDA,EAAOlF,MACT8pB,EAAazrB,IAEb+pB,GAAc,GACdE,GAAmB,GACrB,GAGJwB,EAAazrB,EAEjB,EA6PQ6M,KAAK,KACLuB,MAAM,UACNL,MAAOgf,GAAcvoB,EAAoBP,GACzCoK,QAAQ,OACR,cAAY,uBAGP,EAIf,SAAS+d,GACP5nB,EACAP,GAEA,GAAIO,EAAoB,CACtB,MAAMwoB,EAAiBjpB,EACrBS,EAAmBR,iBACnBC,GAGIgpB,EAAiBD,EAAe9oB,OAAQpB,GAAUA,EAAMoqB,UACxDC,EAAeH,EAAe9oB,OAAQpB,GAAUsqB,GAActqB,IAEpE,OACGmqB,EAAeI,MAAOvqB,GACrBwqB,GAAcxqB,EAAOmB,MAEtBkpB,EAAaE,MAAOvqB,GAAUwqB,GAAcxqB,EAAOmB,GAExD,CACE,OACF,CACF,CAEA,SAASmpB,GAActqB,GACrB,MAAsB,WAAfA,EAAME,MAAoC,iBAAfF,EAAME,IAC1C,CAEA,SAASsqB,GACPxqB,EACAmB,GAEA,OAAImpB,GAActqB,GACTmB,EAAqBb,eAAeN,EAAM/F,IAG/CkH,EAAqBb,eAAeN,EAAM/F,KAC1CkH,EAAqBnB,EAAM/F,KAC0B,KAArDkH,EAAqBnB,EAAM/F,IAAImF,WAAWwX,MAGhD,CAmBA,SAASqT,GACPvoB,EACAP,GAEA,MAAMspB,EArBR,SACE/oB,EACAP,GAEA,IAAKO,GAAoBR,iBAAkB,OAE3C,MAAMgpB,EAAiBjpB,EACrBS,EAAmBR,iBACnBC,GAGF,IAAK,MAAMnB,KAASkqB,EAClB,GAAIlqB,EAAMoqB,WAAaI,GAAcxqB,EAAOmB,GAC1C,OAAOnB,EAAMpD,WAEnB,CAMkC8tB,CAC9BhpB,EACAP,GAGF,OAAKO,EAEM+oB,EACD,WACNA,EAAwBhrB,OAAO,GAAGvB,MAAM,YAAc,IAAM,MAC1DusB,EAAwBtT,gBAErB,oBANA,kBAQX,CAEA,MAAM+R,GAAcA,EAClBC,uBACAxP,gBACA2M,8BAWEvsB,MAAAC,cAAC0P,EAASA,UAACC,CAAAA,QAAS,gBAClB5P,MAAAC,cAACyQ,EAAKA,MAACC,WACLV,CAAAA,MAAOJ,QAAM,2BACbgB,SAAS,iBACTqB,SAAUrC,EAAAA,MAAM,oBAChBe,WAAYf,QAAM,2BACnB,6CAGD7P,MAAAC,cAAC6Q,EAAMA,OAAA,CACL8f,WACA1wB,EAAAA,GAAG,iBACH8Q,SAjBe6f,EAAG5f,oBACtBme,EAAqBne,EAAa,EAiB9BjB,KAAK,KACLlL,MAAOynB,GAEN3M,EAActd,IAAK9C,gBAClBQ,MAAAC,cAAC6Q,EAAAA,OAAOK,OAAO1K,CAAAA,IAAKjH,EAAIU,GAAI4E,MAAOtF,EAAIU,IACpCV,EAAIiE,SAQX4rB,GAA8BA,iBAClCrvB,MAAAC,cAAC0P,EAAAA,UACCa,CAAAA,KAAK,aACLsB,UAAU,SACVlC,QAASC,QAAM,iBACfwM,kBAAmB,KACnBjD,gBAAiBvJ,EAAAA,MAAM,iBACvBkE,OAAQlE,QAAM,wBACd0D,OAAS,aAAY1D,EAAKA,MAAC,oCAE3B7P,MAAAC,cAAC0gB,EAAOA,QAAC3Q,CAAAA,KAAK,oBACdhQ,MAAAC,cAACkQ,EAAAA,KAAK+B,CAAAA,SAAUrC,EAAKA,MAAC,oBAAqBwC,WAAY,MAAM,YC5tBjE,SAAS2E,IAAe1F,QACtBA,iBAIA,OACEtR,EAAA,QAAAC,cAACmR,UACC6F,GAAG,SACHrW,OAAQiP,EAAAA,MAAM,uBACdqH,KAAM,CAAEjH,MAAOJ,EAAKA,MAAC,sBAAuBpM,KAAM,aAClD6N,QAASA,EACTtB,KAAM,KACNkB,MAAM,QACNM,QAAQ,SAGd,CAEA,SAASsf,IAAmBtb,SAC1BA,EAAQa,eACRA,EAAcZ,KACdA,EAAIlE,MACJA,iBAOA,OAAO6F,EAAAA,0BACLpX,EAAA,QAAAC,cAACoX,EAAaA,cAAC9F,CAAAA,MAAOA,gBACpBvR,EAAAA,QAAAC,cAACqX,EAAKA,MAAA,CACJ7B,KAAMA,EACNY,eAAgBA,EAChBnH,SAAU,GACV4H,UAAU,+BACVlI,QAASiB,EAAAA,MAAM,iBACf0H,cAAe1H,EAAAA,MAAM,iBACrBkE,OAAQlE,EAAAA,MAAM,wBACdkhB,OAAQ,oBAER/wB,EAAA,QAAAC,cAAC0P,EAAAA,UAAS,CACRa,KAAK,aACLC,aAAa,gBACbqB,UAAU,uBAEV9R,EAAAA,QAAAC,cAAC6P,EAAOA,QACNC,CAAAA,MAAO,EACPE,MAAOJ,EAAKA,MAAC,2BACbe,WAAYf,EAAKA,MAAC,0BAClBqC,SAAUrC,EAAKA,MAAC,qBAChBwC,WAAW,OACZ,kCAGDrS,EAAAA,QAAAC,cAAC+W,GAAe1F,CAAAA,QAAS+E,KAE1Bb,gBAEHxV,EAAA,QAAAC,cAAS,QAAA,KAAA,8EAIXuX,SAAS1N,KAEb,OCxEaknB,GAAQ,CACnBC,aAAAA,WACAC,EAAQnT,SACRA,GC+BIvT,GAAiB,IAAI3E,EAAAA,OAAO,CAChCC,KAAMvG,EAAW,YACjBwG,QAAS,eAGX,SAASwS,IAAOwT,mBACdA,EAAkBnO,YAClBA,EAAWoO,eACXA,EAAcmF,UACdA,EAASjF,WACTA,EAAUrpB,YACVA,EAAWuuB,qBACXA,EAAoBplB,QACpBA,EAAOqlB,mBACPA,EAAkB9f,MAClBA,EAAK6I,QACLA,IAcA,MAAOkX,EAAiBC,GAAsBjlB,EAAAA,UAAS,GACjDklB,EAAWL,IAAcC,EAEzBK,EAAc7T,EAAYvW,OAC7BwE,GAAeA,EAAWsN,QAC3BhQ,OACIuoB,EAAc9T,EAAYvW,OAC7BwE,IAAgBA,EAAWsN,QAC5BhQ,oBAEF,OACEnJ,MAAAC,cAAC0P,EAAAA,UAAS,CACRa,KAAK,aACLsB,UAAU,SACVU,gBACEgf,EAAW3hB,EAAKA,MAAC,4CAAyC/B,EAE5D0S,aACEgR,OACI1jB,EACC,aAAY+B,QAAM,sBAEzB,cAAY,qBACZY,aAAa,gBACbuL,kBAAmB,EACnBhK,aAAcnC,EAAKA,MAAC,iBACpBkC,WAAY,EACZsK,kBAAmBxM,EAAAA,MAAM,iBACzBuJ,gBAAiBvJ,EAAAA,MAAM,iBACvBD,QAASC,EAAAA,MAAM,iBACf8hB,MAAI,EACJZ,OAAQ,GAEPI,IAAcC,eACbpxB,MAAAC,cAAC0P,EAAAA,UACCa,CAAAA,KAAK,aACLsB,UAAU,SACVkK,iBAAkB,EAClBpM,QAAS,gBAET5P,MAAAC,cAACgU,EAAIA,KACHjE,CAAAA,KAAM,EACNC,MAAOJ,EAAKA,MAAC,iCACbpM,KAAK,6CAEPzD,MAAAC,cAAC6P,WACCG,MAAOJ,EAAKA,MAAC,2BACbE,MAAO,EACPC,KAAMH,EAAAA,MAAM,qBACb,kDAKH7P,MAAAC,cAAC6P,EAAOA,QAAA,CACNG,MAAOJ,EAAKA,MAAC,2BACbE,MAAO,EACPC,KAAMH,EAAKA,MAAC,qBAEX7D,EACG,qBACAvD,EAAUgpB,EAAa,qBAC1BC,EAAc,EAAK,KAAIA,YAAwB,IAGnDP,IACEC,eACCpxB,MAAAC,cAAC0P,EAAAA,UAAS,CACRa,KAAK,aACLsB,UAAU,SACVlC,QAASC,QAAM,kBAEd+N,EAAYzU,OAAS,gBACpBnJ,MAAAC,cAACmR,EAAAA,OAAOE,CAAAA,QAAS+f,EAAoB7f,QAAQ,WAAU,kCAIzDxR,MAAAC,cAACmR,EAAMA,OACLG,CAAAA,MAAM,UACNC,QAAQ,OACRF,QAASA,IAAMigB,GAAmB,IACnC,kCAGDvxB,MAAAC,cAAC6wB,GAAkB,CACjBrb,KAAM6b,EACNjb,eAAgBA,IAAMkb,GAAmB,GACzChgB,MAAOA,gBAEPvR,MAAAC,cAAC6rB,GACCjpB,CAAAA,YAAaA,EACbmpB,eAAgBA,EAChBE,WAAYA,EACZ9R,QAASA,EACT/D,eAAgBA,IAAMkb,GAAmB,GACzCxF,mBAAoBA,mBAK1B/rB,MAAAC,cAACoQ,EAAAA,IAAG,kBACFrQ,MAAAC,cAAC0P,YAAUa,CAAAA,KAAK,aAAasB,UAAU,SAASlC,QAAS,gBACvD5P,MAAAC,cAACmR,UACCE,QAAS+f,EACT9f,MAAM,UACNC,QAAQ,WACT,mCAGDxR,MAAAC,cAACmR,EAAAA,OAAM,CACLG,MAAM,UACN8B,UACAwG,EAAAA,QAAS,CACP3I,MAAO,mDAEV,wBAQf,eAEwB,UAAY6a,mBAClCA,EAAkB6F,sBAClBA,EAAqB5F,eACrBA,EAAiB,wEAAuE7R,gBACxFA,EAAeD,uBACfA,EAAsBgS,WACtBA,EAAU2F,yBACVA,EAAwBtgB,MACxBA,EAAK6I,QACLA,EAAO0X,oBACPA,EAAmBC,uBACnBA,EAAyB,gEAA+D1e,SACxFA,GAAW,EAAKgF,eAChBA,EAAiB,gBAoBjB3K,EAASA,UAAC,KACR,IAAK0M,EAAS,OAAO7N,GAAW,IRxNL,SAACzD,GAA2C,IAAA,OAAA1G,QAAAO,QAClD6H,GAAetH,IAAI,CACxCC,KAAM,CACJsH,GAAI3B,EACJ1F,OAAQ,CACN+b,uBACE,sLACF/U,OAAQ,QAEV7F,QAAS,cAEXhB,IAAK,8BACLG,KAXI,UAAAP,KAAEA,IAaR,OAAOA,CAAI,EACb,CAAC,MAAAQ,GAAA,OAAAvB,QAAAwB,OAAAD,EAAA,CAAA,EQ0MGquB,CAAiB5X,EAAQa,UACtBvX,KAAK2Z,IACL3Z,KAAK+Z,IACL/Z,KAAKxB,GACLwB,KAAKic,GACLjc,KAAK,IAAM6I,GAAW,GAC3B,EAAG,CAAC6N,GAASa,WAEb,MAAO2C,EAAa+B,GAAkBrT,EAAQA,SAAC,KACxCN,EAASO,GAAcD,EAAQA,UAAC,IAChCglB,EAAiBC,GAAsBjlB,EAAAA,UAAS,IAEjDpL,WAAEA,EAAUE,mBAAEA,EAAkBD,cAAEA,GAAkB2wB,EAIpDxnB,EAFS,IAAI2nB,gBAAgBtyB,OAAOC,SAASwoB,QAEvBllB,IAAI,iBAG1BgvB,EAAc,IAAK3gB,EAAYyf,MAAO,IAAKA,KAEjDtjB,EAAAA,UAAU,KACR8J,SAAS1N,KAAKqoB,gBAAgB,2BAA4BnmB,EAC5D,EAAG,CAACA,IAEJ,MAAMolB,GAAuBxT,EAAYzU,QACrCyU,EAAYwU,KAAM5G,GAAMA,EAAErS,QAG9B,SAASkZ,EAAanyB,GACpBsK,GACG8nB,OAAO,CACNnvB,KAAM,CAAEsH,GAAI2P,EAAQa,UACpB1X,IAAM,6BAA4BrD,MAEnCwD,KAAK,IACJic,EAAe/B,EAAYvW,OAAQwE,GAAeA,EAAW3L,KAAOA,KAErEsD,MAAO+F,IACN,MAAM6J,EACJ9J,EAAcC,EAAO,WACrB,mFACF2J,EAAkBC,KAAK,CACrBC,OACAlC,MAAO,UACR,EAEP,CAoBA,MAAMqhB,EAAyB,CAC7BtiB,MAAOJ,EAAAA,MAAM,kBACbE,MAAO,EACPC,KAAMH,QAAM,qBACZK,OAAQL,QAAM,yBAGV2iB,EAAsB,CAC1BviB,MAAOJ,EAAKA,MAAC,4BACbwC,WAAY,EACZrC,KAAMH,EAAAA,MAAM,kCAoBd,OACE7P,MAAAC,cAACoX,EAAaA,eAAC9F,MAAO2gB,gBACpBlyB,MAAAC,cAACe,EAAoBgZ,SACnBlV,CAAAA,MAAO,CAAE5D,aAAYC,gBAAeC,uBAEnCgZ,gBACCpa,MAAAC,cAACsY,GAAM,CACLqF,YAAaA,EACboO,eAAgBA,EAChBmF,UAAWjX,IAA2B7G,EACtCrH,QAASA,EACTkgB,WAAYA,EACZrpB,YAAa+uB,EACbrgB,MAAO2gB,EACP9X,QAASA,EACTgX,qBAAsBA,EACtBC,mBAhEV,WACE7mB,GACGsI,KAAK,CACJ3P,KAAM,CACJA,KAAM,CACJ4P,WAAY,CACVtI,GAAI2P,EAAQa,SACZ9B,QAASiY,KAIf7tB,IAAK,uBAENG,KAAK,KACJ/D,OAAOC,SAASkvB,QAAM,EAE5B,EAiDU/C,mBAAoBA,IAGvB/f,eACChM,MAAAC,cAACwgB,EAAOA,QAAA,CACNC,mBAAO1gB,MAAAC,cAAC0gB,UAAQ3Q,CAAAA,KAAK,OACrBoJ,gBAAiB,GACjBlI,MAAO,2BAENkJ,eAGHpa,MAAAC,cAACoQ,EAAAA,IAAG,CAAC,cAAY,uBACduN,GAAazU,OAAS,eACrBnJ,MAAAC,cAAC2gB,WAAShR,CAAAA,QAAS,EAAGiH,eAAgB,EAAGgK,aAAc,IACpD2F,EAAAA,QAAO5I,EAAa,MAAMtb,IAAKkpB,iBAC9BxrB,aAAAC,cAACgY,GAAkB,CACjBxR,IAAK+kB,EAAEtrB,GACP2L,WAAY2f,EACZtT,kBAhDfua,EAgDwDjH,EA/CxDkH,IACC,MAAMC,EACe,mBAAZD,EAAyBA,EAASD,GAAsBC,EAC3DE,EAAiB,IAClBhV,EAAYvW,OAAQwE,GAAeA,EAAW3L,KAAOyyB,EAAQzyB,IAChEyyB,GAGFhT,EAAeiT,KAwCDza,SAAUka,EACV9gB,MAAO2gB,EACP9Z,eAAgBoT,EAAEtrB,KAAOiqB,OAAO7f,GAChC8P,QAAS,CACPzO,OA1DYE,EA0DkB2f,EAzDzCpR,EAAQzQ,OAAO3E,KAAM2G,GAAUA,EAAMlI,OAASoI,EAAWpI,OA0D9CwX,SAAUb,EAAQa,UAEpBd,gBAAiBA,EACjBD,uBAAwBA,EACxB7G,SAAUA,EACVgF,eAAgBA,IAhElC,IAAgCxM,EAK7B4mB,CA6DY,iBAGHzyB,MAAAC,cAAC0P,EAAAA,UACCkjB,CAAAA,OAAQhjB,QAAM,iBACdD,QAASC,QAAM,iBACfiC,UAAU,SACVghB,aAAc,CACZC,GAAI,CACFviB,KAAM,aACNC,aAAc,SACdb,QAASC,EAAKA,MAAC,iCAInB7P,MAAAC,cAACoQ,EAAAA,IAAG,CACF1B,IAAK,CACH,UAAW,CACT/N,OAAQ,OACRD,MAAO,SAGXuO,SAAU,GACV4jB,aAAc,CACZC,GAAI,CACF7jB,SAAU,mBAIdlP,MAAAC,cAACF,EAAgB,oBAEnBC,MAAAC,cAAC0P,EAAAA,WACCmC,UAAU,SACVlC,QAASC,EAAKA,MAAC,iBACfX,SAAU,GACV4jB,aAAc,CACZC,GAAI,CACFjhB,UAAW,QACXrC,UAAW,SAGfA,UAAU,UAETyK,eACCla,MAAAC,cAAAD,MAAAqP,SAAA,kBACErP,MAAAC,cAAC6P,UAAYyiB,EAAwB,kCAGrCvyB,MAAAC,cAAC0P,EAAAA,UACCmC,CAAAA,UAAU,SACVE,aAAcnC,EAAAA,MAAM,iBACpBijB,aAAc,CACZC,GAAI,CACFjhB,UAAW,UAGflC,QAAS,gBAET5P,MAAAC,cAACkQ,EAAAA,KAASqiB,EACPZ,iBAGL5xB,MAAAC,cAAC0P,EAASA,WACRa,KAAK,aACLZ,QAASC,EAAKA,MAAC,+BAEf7P,MAAAC,cAACmR,EAAMA,OACLI,CAAAA,QAAQ,UACRvC,GAAI+c,EACJ/b,MAAQ,GAAEJ,EAAKA,MACb,+CAEH,2BAGD7P,MAAAC,cAACmR,EAAAA,OACC6F,CAAAA,GAAG,SACH1F,MAAM,UACNC,QAAQ,OACRF,QAASA,IAAMigB,GAAmB,IACnC,mCAIHvxB,MAAAC,cAAC6wB,GACCrb,CAAAA,KAAM6b,EACNjb,eAAgBA,IAAMkb,GAAmB,GACzChgB,MAAO2gB,gBAEPlyB,MAAAC,cAAC6rB,GACCI,CAAAA,WAAYA,EACZrpB,YAAa+uB,EACb5F,eAAgBA,EAChB3V,eAAgBA,IAAMkb,GAAmB,GACzCnX,QAASA,EACT2R,mBAAoBA,mBAK1B/rB,MAAAC,cAAAD,MAAAqP,SACErP,kBAAAA,MAAAC,cAAC6P,EAAOA,QAAKyiB,EAAwB,4BACrCvyB,MAAAC,cAACkQ,EAAAA,KAASqiB,EACPT,oBA7Hf/xB,MAAAC,cAAAD,MAAAqP,SAAA,MAsIDwiB,gBACC7xB,MAAAC,cAACyf,GAAmB,CAClBR,eAAgB2S,EAChBzX,QAASA,kBAIfpa,MAAAC,cAAA,QAAA,i1mBAGN"}
|