@aglyn/plugins-outreach 1.0.0-beta.274 → 1.0.0-beta.277

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (61) hide show
  1. package/README.md +7 -2
  2. package/package.json +14 -14
  3. package/src/lib/components/enrollment-actions.d.ts +11 -4
  4. package/src/lib/components/enrollment-actions.js +16 -0
  5. package/src/lib/components/enrollment-actions.js.map +1 -1
  6. package/src/lib/components/enrollment-detail.js +40 -13
  7. package/src/lib/components/enrollment-detail.js.map +1 -1
  8. package/src/lib/components/mailbox-card.js +13 -2
  9. package/src/lib/components/mailbox-card.js.map +1 -1
  10. package/src/lib/components/record-reply-button.d.ts +52 -0
  11. package/src/lib/components/record-reply-button.js +92 -0
  12. package/src/lib/components/record-reply-button.js.map +1 -0
  13. package/src/lib/components/reply-dialog.d.ts +67 -0
  14. package/src/lib/components/reply-dialog.js +353 -0
  15. package/src/lib/components/reply-dialog.js.map +1 -0
  16. package/src/lib/components/use-outreach-api.d.ts +5 -1
  17. package/src/lib/components/use-outreach-api.js +10 -0
  18. package/src/lib/components/use-outreach-api.js.map +1 -1
  19. package/src/lib/constants/api-routes.d.ts +8 -0
  20. package/src/lib/constants/api-routes.js +6 -0
  21. package/src/lib/constants/api-routes.js.map +1 -1
  22. package/src/lib/engine/index.d.ts +1 -0
  23. package/src/lib/engine/index.js +1 -0
  24. package/src/lib/engine/index.js.map +1 -1
  25. package/src/lib/engine/manual-reply.d.ts +122 -0
  26. package/src/lib/engine/manual-reply.js +311 -0
  27. package/src/lib/engine/manual-reply.js.map +1 -0
  28. package/src/lib/model/enrollment-history.d.ts +2 -0
  29. package/src/lib/model/enrollment-history.js +10 -5
  30. package/src/lib/model/enrollment-history.js.map +1 -1
  31. package/src/lib/model/enrollment-timeline.d.ts +3 -1
  32. package/src/lib/model/enrollment-timeline.js +90 -9
  33. package/src/lib/model/enrollment-timeline.js.map +1 -1
  34. package/src/lib/model/outreach-api.d.ts +68 -2
  35. package/src/lib/model/outreach-api.js.map +1 -1
  36. package/src/lib/model/outreach.types.d.ts +91 -3
  37. package/src/lib/model/outreach.types.js +6 -0
  38. package/src/lib/model/outreach.types.js.map +1 -1
  39. package/src/lib/model/stored-records.d.ts +7 -1
  40. package/src/lib/model/stored-records.js +37 -1
  41. package/src/lib/model/stored-records.js.map +1 -1
  42. package/src/lib/plugin.d.ts +4 -0
  43. package/src/lib/plugin.js +17 -0
  44. package/src/lib/plugin.js.map +1 -1
  45. package/src/lib/routes/register-routes.d.ts +7 -0
  46. package/src/lib/routes/register-routes.js +26 -0
  47. package/src/lib/routes/register-routes.js.map +1 -1
  48. package/src/lib/routes/reply-routes.d.ts +92 -0
  49. package/src/lib/routes/reply-routes.js +644 -0
  50. package/src/lib/routes/reply-routes.js.map +1 -0
  51. package/src/lib/runtime/click-events.d.ts +13 -0
  52. package/src/lib/runtime/click-events.js +19 -6
  53. package/src/lib/runtime/click-events.js.map +1 -1
  54. package/src/lib/runtime/click-link.d.ts +8 -0
  55. package/src/lib/runtime/click-link.js +7 -0
  56. package/src/lib/runtime/click-link.js.map +1 -1
  57. package/src/lib/runtime/sync-job.js +14 -0
  58. package/src/lib/runtime/sync-job.js.map +1 -1
  59. package/src/lib/transport/send-message.d.ts +11 -0
  60. package/src/lib/transport/send-message.js +22 -0
  61. package/src/lib/transport/send-message.js.map +1 -1
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../../../../libs/plugins/outreach/src/lib/components/enrollment-detail.tsx"],"sourcesContent":["/**\n * @license\n * Copyright 2026 Aglyn LLC\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n'use client'\n\nimport {\n type ConsolePluginOrgMount,\n PageHeaderRecord,\n pluginDocsHelp,\n} from '@aglyn/aglyn'\nimport { pluginRecordHref } from '@aglyn/aglyn/plugin-manager/plugin-record-routes'\nimport {\n mdiAccountCancelOutline,\n mdiAccountOutline,\n mdiAccountPlusOutline,\n mdiAlertCircleOutline,\n mdiCheckCircleOutline,\n mdiChevronDown,\n mdiChevronUp,\n mdiClipboardCheckOutline,\n mdiContentCopy,\n mdiCursorDefaultClickOutline,\n mdiEmailAlertOutline,\n mdiEmailOffOutline,\n mdiEmailOpenOutline,\n mdiEmailOutline,\n mdiHandBackLeftOutline,\n mdiPauseCircleOutline,\n mdiPencilOutline,\n mdiPlayCircleOutline,\n mdiReply,\n mdiShieldSearch,\n mdiSkipNext,\n mdiStopCircleOutline,\n} from '@aglyn/shared-data-mdi'\nimport { AppLink, CardDisplay, MdiIcon } from '@aglyn/shared-ui-jsx'\nimport EmptyStateComponent from '@aglyn/shared-ui-jsx/components/empty-state.component'\nimport RowActionsMenu from '@aglyn/shared-ui-jsx/components/row-actions-menu.component'\nimport { useSnackbar } from '@aglyn/shared-ui-snackstack'\nimport { useOrgContainerOptions, useOrgMemberOptions } from '@aglyn/tenant-feature-instance'\nimport {\n Alert,\n Box,\n Button,\n Card,\n Chip,\n Collapse,\n Divider,\n IconButton,\n Link,\n List,\n ListItem,\n ListItemIcon,\n ListItemText,\n Stack,\n Tooltip,\n Typography,\n} from '@mui/material'\nimport { type ReactNode, useCallback, useMemo, useState } from 'react'\nimport { OUTREACH_MAIL_GATEWAY_LABELS } from '../engine/mail-gateway'\nimport { outreachNextSendState } from '../engine/next-send'\nimport { outreachClickSummary } from '../model/enrollment-engagement'\nimport {\n outreachEnrollmentFigures,\n outreachEnrollmentTimeline,\n outreachStepName,\n type OutreachTimelineEntry,\n type OutreachTimelineKind,\n type OutreachTimelineTone,\n} from '../model/enrollment-timeline'\nimport {\n OUTREACH_ATTESTATION_KINDS,\n OUTREACH_ATTESTATION_LABELS,\n type OutreachEnrollment,\n type OutreachMailbox,\n type OutreachSequence,\n} from '../model/outreach.types'\nimport {\n OUTREACH_ENROLLMENT_ACTION_LABELS,\n outreachEnrollmentActionsFor,\n type OutreachEnrollmentRowAction,\n useOutreachEnrollmentActions,\n} from './enrollment-actions'\nimport { outreachCurrentStepLabel, outreachStepIsCurated, outreachStopLabel } from './enrollments-table'\nimport {\n formatOutreachTime,\n OutreachEnrollmentStatusChip,\n OutreachLoading,\n OutreachLoadProblem,\n} from './outreach-ui'\nimport { outreachNextSendDetail, outreachNextSendLabel, useOutreachNowMs } from './next-send'\nimport { OutreachFigure } from './sequence-report-card'\nimport { useOutreachApi } from './use-outreach-api'\nimport { useOutreachSequence } from './use-outreach-data'\nimport type { OutreachEnrollmentGatewayResponse } from '../model/outreach-api'\nimport {\n useOutreachEnrollment,\n useOutreachEnrollmentGateway,\n useOutreachEnrollmentHistory,\n} from './use-outreach-enrollment'\nimport type { OutreachMailboxesResult } from './use-outreach-mailboxes'\n\n/*==========================================\n * ONE PERSON IN ONE SEQUENCE (AGL-3332):\n * `/[orgSlug]/outreach/sequences/{sequenceId}/enrollments/{enrollmentId}`.\n *\n * A row of the Enrollments tab opens it, and its URL is the person's: a\n * comment or a message can link straight to them.\n *\n * Laid out the way every record page in the console is (the CRM's\n * `CrmRecordHeader` grammar): the page heading names the person; the first\n * card says what the record is, with the way back and the actions in its\n * HEADER — the one that changes things as a button, the rest and the\n * destructive ones behind the menu — and the facts that identify it as\n * chips. Under the chips, five numbers.\n *\n * Then ONE timeline, newest first, which is the page: every send, click,\n * reply, bounce, stop, hold and resume, from `model/enrollment-timeline.ts`.\n * Everything else stored on the enrollment is under Details, closed until\n * asked for — nothing is left out, and nothing is in the way.\n *=========================================*/\n\nexport interface OutreachEnrollmentDetailProps {\n orgId: string\n /** The org the hub is mounted under: its slug and sites, for the CRM record's address. */\n orgMount?: ConsolePluginOrgMount\n /** `/[orgSlug]/outreach/sequences`. */\n sectionPath: string\n sequenceId: string\n enrollmentId: string\n mailboxes: OutreachMailboxesResult\n}\n\n/**\n * Where the CRM record the person is lives — the site's own CRM when the site\n * is known, else the organization's — at the address the plugin that keeps\n * leads and contacts publishes, or `null` where none does.\n */\nexport function outreachCrmRecordHref(\n kind: 'lead' | 'contact',\n id: string | null | undefined,\n hostId: string,\n orgMount: Pick<ConsolePluginOrgMount, 'orgSlug' | 'hosts'> | undefined,\n): string | null {\n if (!id || !orgMount?.orgSlug) return null\n const host = orgMount.hosts.find((entry) => entry.id === hostId)?.subdomain ?? null\n return pluginRecordHref(kind, { orgSlug: orgMount.orgSlug, host }, id)\n}\n\n/**\n * Whether a mailbox's threads open in Gmail. A Microsoft 365 mailbox's\n * conversation has no address of its own in Outlook (AGL-3489), so its\n * thread is shown without a link.\n */\nexport const outreachThreadOpensInGmail = (mailbox: { provider?: string } | null | undefined): boolean =>\n mailbox?.provider !== 'microsoft'\n\n/** A Gmail thread, opened in the mailbox's own account. */\nexport function outreachGmailThreadUrl(threadId: string, mailboxEmail: string | null | undefined): string {\n const account = mailboxEmail ? `?authuser=${encodeURIComponent(mailboxEmail)}` : ''\n return `https://mail.google.com/mail/${account}#all/${encodeURIComponent(threadId)}`\n}\n\nconst KIND_ICONS: Record<OutreachTimelineKind, { path: string }> = {\n enrolled: mdiAccountPlusOutline,\n skipped: mdiSkipNext,\n curated: mdiPencilOutline,\n sent: mdiEmailOutline,\n task: mdiClipboardCheckOutline,\n click: mdiCursorDefaultClickOutline,\n scanner: mdiShieldSearch,\n 'earlier-clicks': mdiCursorDefaultClickOutline,\n open: mdiEmailOpenOutline,\n 'machine-open': mdiShieldSearch,\n paused: mdiPauseCircleOutline,\n resumed: mdiPlayCircleOutline,\n stopped: mdiStopCircleOutline,\n 'do-not-contact': mdiAccountCancelOutline,\n replied: mdiReply,\n bounced: mdiEmailAlertOutline,\n 'opted-out': mdiEmailOffOutline,\n held: mdiHandBackLeftOutline,\n released: mdiPlayCircleOutline,\n failed: mdiAlertCircleOutline,\n finished: mdiCheckCircleOutline,\n}\n\nconst TONE_COLORS: Record<OutreachTimelineTone, string> = {\n default: 'text.secondary',\n success: 'success.main',\n info: 'info.main',\n warning: 'warning.main',\n error: 'error.main',\n}\n\n/** A destination, whole, opening in a new tab. */\nfunction Destination(props: { url: string; label?: string }) {\n return (\n <Typography variant=\"body2\" component=\"span\" sx={{ display: 'block', wordBreak: 'break-all' }}>\n {props.label ? `${props.label}: ` : null}\n <Link href={props.url} target=\"_blank\" rel=\"noopener noreferrer\" underline=\"hover\">\n {props.url}\n </Link>\n </Typography>\n )\n}\n\n/** One line of the timeline. */\nfunction TimelineRow(props: {\n entry: OutreachTimelineEntry\n timeZone: string | null\n mailboxEmail: string | null\n /** False for a mailbox whose threads do not open in Gmail. */\n threadsOpenInGmail?: boolean\n divider: boolean\n}) {\n const { entry } = props\n return (\n <ListItem alignItems=\"flex-start\" divider={props.divider} disableGutters data-kind={entry.kind}>\n <ListItemIcon sx={{ minWidth: 36, mt: 0.75, color: TONE_COLORS[entry.tone] }}>\n <MdiIcon path={KIND_ICONS[entry.kind].path} fontSize=\"small\" />\n </ListItemIcon>\n <ListItemText\n disableTypography\n primary={\n <Stack\n direction={{ xs: 'column', sm: 'row' }}\n spacing={{ xs: 0, sm: 1 }}\n sx={{ justifyContent: 'space-between', alignItems: { sm: 'baseline' } }}\n >\n <Typography variant=\"body2\" sx={{ fontWeight: 500 }}>\n {entry.title}\n </Typography>\n <Typography variant=\"caption\" color=\"text.secondary\" sx={{ whiteSpace: 'nowrap' }}>\n {formatOutreachTime(entry.atMs, props.timeZone)}\n </Typography>\n </Stack>\n }\n secondary={\n <Stack spacing={0.25} sx={{ mt: 0.25 }}>\n {entry.url ? <Destination url={entry.url} label={entry.urlLabel} /> : null}\n {entry.detail ? (\n <Typography variant=\"body2\" sx={{ whiteSpace: 'pre-wrap', wordBreak: 'break-word' }}>\n {entry.detail}\n </Typography>\n ) : null}\n {entry.facts.length || (entry.gmailThreadId && props.threadsOpenInGmail !== false) ? (\n <Typography variant=\"caption\" color=\"text.secondary\" component=\"div\">\n {entry.facts.join(' · ')}\n {entry.gmailThreadId && props.threadsOpenInGmail !== false ? (\n <>\n {entry.facts.length ? ' · ' : null}\n <Link\n href={outreachGmailThreadUrl(entry.gmailThreadId, props.mailboxEmail)}\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n underline=\"hover\"\n >\n Open thread in Gmail\n </Link>\n </>\n ) : null}\n </Typography>\n ) : null}\n </Stack>\n }\n />\n </ListItem>\n )\n}\n\n/** One fact of the Details list. */\nfunction Fact(props: { label: string; children: ReactNode }) {\n return (\n <>\n <Typography component=\"dt\" variant=\"body2\" color=\"text.secondary\">\n {props.label}\n </Typography>\n <Box component=\"dd\" sx={{ m: 0, minWidth: 0, typography: 'body2', wordBreak: 'break-word' }}>\n {props.children}\n </Box>\n </>\n )\n}\n\n/** What mail from the sequence's sending domain met at the person's domain, in a line. */\nfunction gatewaySentence(answer: OutreachEnrollmentGatewayResponse, timeZone: string | null): string {\n const { intel, standing } = answer\n if (!intel) return 'Could not be looked up'\n if (intel.status === 'no_mx' || intel.status === 'null_mx') {\n return `${answer.domain ?? 'The domain'} takes no mail · looked up ${formatOutreachTime(intel.resolvedAtMs, timeZone)}`\n }\n const from = answer.sendingDomain ? ` from ${answer.sendingDomain}` : ''\n const parts = [\n OUTREACH_MAIL_GATEWAY_LABELS[intel.gateway],\n intel.mx.length ? `MX ${intel.mx.join(', ')}` : 'no MX; delivered to its address record',\n standing\n ? `${standing.delivered30} delivered, ${standing.blocked30} refused${from} in the last 30 days`\n : null,\n `looked up ${formatOutreachTime(intel.resolvedAtMs, timeZone)}`,\n ]\n return parts.filter(Boolean).join(' · ')\n}\n\n/**\n * Everything else the enrollment holds, all of it, behind one toggle.\n */\nfunction EnrollmentDetails(props: {\n enrollment: OutreachEnrollment\n sequence: OutreachSequence\n mailbox: OutreachMailbox | null\n gateway: OutreachEnrollmentGatewayResponse | null\n /** What the Mail gateway line says while there is no answer to show. */\n gatewayUnread: string\n campaignName: (id: string) => string\n memberName: (uid: string) => string\n orgMount?: ConsolePluginOrgMount\n timeZone: string | null\n}) {\n const { enrollment, sequence, memberName, timeZone } = props\n const { enqueueSnackbar } = useSnackbar()\n const time = (ms: number | null | undefined) => formatOutreachTime(ms, timeZone)\n const leadHref = outreachCrmRecordHref('lead', enrollment.leadId, enrollment.hostId, props.orgMount)\n const contactHref = outreachCrmRecordHref('contact', enrollment.contactId, enrollment.hostId, props.orgMount)\n const clicks = outreachClickSummary(enrollment.engagement)\n const overrides = Object.entries(enrollment.stepOverrides ?? {}).sort(\n ([a], [b]) => Number(a) - Number(b),\n )\n const attested = OUTREACH_ATTESTATION_KINDS.filter((kind) => enrollment.attestations?.[kind])\n const threads = enrollment.gmailThreadIds.length\n ? enrollment.gmailThreadIds\n : enrollment.gmailThreadId\n ? [enrollment.gmailThreadId]\n : []\n const copyId = () => {\n void navigator.clipboard\n ?.writeText(enrollment.id)\n .then(() => enqueueSnackbar('Enrollment id copied.', { variant: 'success' }))\n .catch(() => enqueueSnackbar('The id could not be copied.', { variant: 'error' }))\n }\n const link = (href: string | null, label: string) =>\n href ? (\n <Link {...({ component: AppLink, componentVariant: 'naked' } as object)} href={href} underline=\"hover\">\n {label}\n </Link>\n ) : (\n label\n )\n\n return (\n <Box\n component=\"dl\"\n sx={{\n m: 0,\n display: 'grid',\n gridTemplateColumns: { xs: '1fr', sm: 'minmax(160px, 220px) 1fr' },\n columnGap: 2,\n rowGap: 1.25,\n }}\n >\n <Fact label=\"Personal line\">\n {enrollment.personalLine ? (\n <Typography variant=\"body2\" sx={{ whiteSpace: 'pre-wrap' }}>\n {enrollment.personalLine}\n </Typography>\n ) : (\n '—'\n )}\n </Fact>\n <Fact label=\"Enrolled as\">\n {enrollment.target === 'lead' ? (\n link(leadHref, 'Lead')\n ) : enrollment.leadId ? (\n <>\n {link(contactHref, 'Contact')}\n {', converted from a '}\n {link(leadHref, 'lead')}\n </>\n ) : (\n link(contactHref, 'Contact')\n )}\n </Fact>\n <Fact label=\"Enrolled\">\n {`${time(enrollment.createdAtMs)}${enrollment.enrolledByUid ? ` by ${memberName(enrollment.enrolledByUid)}` : ''}`}\n </Fact>\n <Fact label=\"Cold contact\">\n {enrollment.cold\n ? 'Yes — no inbound capture behind them, so the member confirmed the address before enrolling'\n : 'No'}\n </Fact>\n <Fact label=\"Attestations\">\n {attested.length ? (\n <Stack component=\"ul\" spacing={0.25} sx={{ m: 0, pl: 2.5 }}>\n {attested.map((kind) => {\n const entry = enrollment.attestations?.[kind]\n return (\n <li key={kind}>\n {`${OUTREACH_ATTESTATION_LABELS[kind]} — ${memberName(entry?.uid ?? '')}, ${time(entry?.atMs)}`}\n </li>\n )\n })}\n </Stack>\n ) : (\n '—'\n )}\n </Fact>\n <Fact label=\"Mailbox\">\n {props.mailbox\n ? `${props.mailbox.sendAs || props.mailbox.email}${props.mailbox.sendAs && props.mailbox.sendAs !== props.mailbox.email ? ` (${props.mailbox.email})` : ''}`\n : enrollment.mailboxId\n ? 'No longer connected'\n : '—'}\n </Fact>\n <Fact label=\"Campaigns\">\n {enrollment.campaignIds?.length\n ? enrollment.campaignIds.map(props.campaignName).join(', ')\n : '—'}\n </Fact>\n <Fact label=\"Mail gateway\">\n {props.gateway ? gatewaySentence(props.gateway, timeZone) : props.gatewayUnread}\n </Fact>\n <Fact label=\"Gateway hold\">\n {enrollment.gatewayHold\n ? [\n OUTREACH_MAIL_GATEWAY_LABELS[enrollment.gatewayHold.gateway],\n enrollment.gatewayHold.heldAtMs ? `held ${time(enrollment.gatewayHold.heldAtMs)}` : 'never held',\n enrollment.gatewayHold.releasedAtMs\n ? `released ${time(enrollment.gatewayHold.releasedAtMs)}${enrollment.gatewayHold.releasedByUid ? ` by ${memberName(enrollment.gatewayHold.releasedByUid)}` : ''}`\n : 'not released',\n ].join(' · ')\n : '—'}\n {enrollment.gatewayDeliveredSteps\n ? ` (${enrollment.gatewayDeliveredSteps} of their emails counted as delivered on the gateway ledger)`\n : null}\n </Fact>\n <Fact label=\"Clicks\">\n {clicks.clicks || clicks.machineClicks\n ? [\n `${clicks.clicks} by the person`,\n `${clicks.machineClicks} by scanners, not counted`,\n `${clicks.clicks - clicks.unloggedClicks + clicks.machineClicks - clicks.unloggedMachineClicks} listed one by one`,\n enrollment.engagement?.firstClickAtMs ? `first ${time(enrollment.engagement.firstClickAtMs)}` : null,\n enrollment.engagement?.lastClickAtMs ? `last ${time(enrollment.engagement.lastClickAtMs)}` : null,\n ]\n .filter(Boolean)\n .join(' · ')\n : '—'}\n {clicks.followed.length ? (\n <Box sx={{ mt: 0.5 }}>\n {clicks.followed.map((url) => (\n <Destination key={url} url={url} />\n ))}\n </Box>\n ) : null}\n </Fact>\n <Fact label=\"Curated steps\">\n {overrides.length ? (\n <Stack spacing={1.5}>\n {overrides.map(([key, override]) => (\n <Box key={key}>\n <Typography variant=\"body2\" sx={{ fontWeight: 500 }}>\n {outreachStepName(sequence.steps, Number(key))}\n </Typography>\n <Typography variant=\"caption\" color=\"text.secondary\" component=\"div\">\n {[\n override.source === 'ai' ? (override.edited ? 'AI draft, edited' : 'AI draft') : 'Written by a member',\n override.draftedByUid ? `confirmed by ${memberName(override.draftedByUid)}` : null,\n override.draftedAtMs ? time(override.draftedAtMs) : null,\n override.model ? `model ${override.model}` : null,\n ]\n .filter(Boolean)\n .join(' · ')}\n </Typography>\n {override.subject !== undefined ? (\n <Typography variant=\"body2\">{`Subject: ${override.subject}`}</Typography>\n ) : null}\n {override.body !== undefined ? (\n <Typography\n variant=\"body2\"\n sx={{ whiteSpace: 'pre-wrap', mt: 0.5, pl: 1.5, borderLeft: 2, borderColor: 'divider' }}\n >\n {override.body}\n </Typography>\n ) : null}\n {override.prompt ? (\n <Typography variant=\"caption\" color=\"text.secondary\" component=\"div\" sx={{ whiteSpace: 'pre-wrap', mt: 0.5 }}>\n {`Prompt: ${override.prompt}`}\n </Typography>\n ) : null}\n </Box>\n ))}\n </Stack>\n ) : (\n '—'\n )}\n </Fact>\n <Fact label={outreachThreadOpensInGmail(props.mailbox) ? 'Gmail threads' : 'Threads'}>\n {threads.length ? (\n <Stack spacing={0.25}>\n {threads.map((thread) => (\n <span key={thread}>\n {outreachThreadOpensInGmail(props.mailbox) ? (\n <Link\n href={outreachGmailThreadUrl(thread, props.mailbox?.email)}\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n underline=\"hover\"\n >\n {thread}\n </Link>\n ) : (\n <Box component=\"span\" sx={{ wordBreak: 'break-all' }}>\n {thread}\n </Box>\n )}\n {thread === enrollment.gmailThreadId ? ' (current)' : null}\n </span>\n ))}\n {enrollment.threadSubject ? (\n <Typography variant=\"caption\" color=\"text.secondary\">{`Started as “${enrollment.threadSubject}”`}</Typography>\n ) : null}\n {enrollment.messageIds.length ? (\n <Typography variant=\"caption\" color=\"text.secondary\" sx={{ wordBreak: 'break-all' }}>\n {`Message-IDs in the current thread: ${enrollment.messageIds.join(' ')}`}\n </Typography>\n ) : null}\n </Stack>\n ) : (\n '—'\n )}\n </Fact>\n <Fact label=\"Stop\">\n {enrollment.stopReason\n ? `${outreachStopLabel(enrollment)} · ${time(enrollment.stoppedAtMs)}${enrollment.stoppedByUid ? ` · by ${memberName(enrollment.stoppedByUid)}` : ''}`\n : '—'}\n </Fact>\n <Fact label=\"Created · updated\">{`${time(enrollment.createdAtMs)} · ${time(enrollment.updatedAtMs)}`}</Fact>\n <Fact label=\"Enrollment id\">\n <Stack direction=\"row\" spacing={0.5} sx={{ alignItems: 'center' }}>\n <Typography variant=\"body2\" sx={{ fontFamily: 'monospace', wordBreak: 'break-all' }}>\n {enrollment.id}\n </Typography>\n <Tooltip title=\"Copy the id\">\n <IconButton size=\"small\" aria-label=\"Copy the enrollment id\" onClick={copyId}>\n <MdiIcon path={mdiContentCopy.path} fontSize=\"small\" />\n </IconButton>\n </Tooltip>\n </Stack>\n </Fact>\n </Box>\n )\n}\n\nexport function OutreachEnrollmentDetail(props: OutreachEnrollmentDetailProps) {\n const { orgId, sectionPath, sequenceId, enrollmentId, orgMount } = props\n const api = useOutreachApi(orgId)\n const loadedSequence = useOutreachSequence(orgId, sequenceId)\n const loaded = useOutreachEnrollment(orgId, enrollmentId)\n const history = useOutreachEnrollmentHistory(orgId, enrollmentId)\n const gateway = useOutreachEnrollmentGateway(api, enrollmentId)\n const roster = useOrgMemberOptions(orgId, { enabled: true })\n const [detailsOpen, setDetailsOpen] = useState(false)\n const nowMs = useOutreachNowMs()\n const enrollment = loaded.data\n const sequence = loadedSequence.data\n const campaigns = useOrgContainerOptions('campaign', orgId, {\n enabled: detailsOpen && Boolean(enrollment?.campaignIds?.length),\n })\n const steps = useMemo(() => sequence?.steps ?? [], [sequence])\n const actions = useOutreachEnrollmentActions({ api, steps })\n\n const memberName = useCallback(\n (uid: string) => roster.options.find((option) => option.uid === uid)?.label ?? 'a member',\n [roster.options],\n )\n const campaignName = useCallback(\n (id: string) => campaigns.options.find((option) => option.value === id)?.label ?? id,\n [campaigns.options],\n )\n\n const enrollmentsPath = `${sectionPath}/${sequenceId}/enrollments`\n const mailbox =\n props.mailboxes.mailboxes.find((entry) => entry.id === (enrollment?.mailboxId || sequence?.mailboxId)) ?? null\n const timeZone = mailbox?.timezone ?? null\n const time = (ms: number | null | undefined) => formatOutreachTime(ms, timeZone)\n const timeline = useMemo(\n () =>\n enrollment\n ? outreachEnrollmentTimeline({\n enrollment,\n steps,\n history: history.status === 'ready' ? history.data : null,\n memberName,\n formatTime: (ms) => formatOutreachTime(ms, timeZone),\n gateway: gateway.data?.intel?.gateway ?? null,\n })\n : [],\n [enrollment, steps, history, memberName, timeZone, gateway.data],\n )\n\n const back = (\n <Button\n // A real link, as the CRM record header's is: it opens in a new tab when asked.\n {...({ component: AppLink, componentVariant: 'naked', nativeButton: false } as object)}\n href={enrollmentsPath}\n size=\"small\"\n color=\"primary\"\n >\n Back to enrollments\n </Button>\n )\n\n if (loaded.status === 'loading' || loadedSequence.status === 'loading') {\n return <OutreachLoading label=\"Loading this person…\" />\n }\n if (loaded.status === 'error' || loaded.status === 'refused') {\n return <OutreachLoadProblem status={loaded.status} what=\"enrollment\" />\n }\n if (loadedSequence.status === 'error' || loadedSequence.status === 'refused') {\n return <OutreachLoadProblem status={loadedSequence.status} what=\"sequence\" />\n }\n // An id from another sequence reads as not here: the URL names both.\n if (!enrollment || !sequence || enrollment.sequenceId !== sequenceId) {\n return (\n <Card variant=\"outlined\">\n <EmptyStateComponent\n label=\"This person isn’t in this sequence\"\n description=\"They may have been removed from the workspace, or the link names a different sequence.\"\n action={back}\n />\n </Card>\n )\n }\n\n const name = enrollment.contactName || enrollment.email\n const kind = enrollment.target === 'lead' ? 'lead' : 'contact'\n const recordHref = outreachCrmRecordHref(\n kind,\n kind === 'lead' ? enrollment.leadId : enrollment.contactId,\n enrollment.hostId,\n orgMount,\n )\n const figures = outreachEnrollmentFigures(enrollment)\n const trackClicks = sequence.settings.trackClicks || sequence.stats?.clickTracked === true\n // Opens are shown for a sequence that counts them or once did (AGL-3395),\n // and for a person with any recorded, whatever the sequence says now.\n const countOpens =\n sequence.settings.countOpens ||\n sequence.stats?.openTracked === true ||\n figures.opens > 0 ||\n figures.machineOpens > 0\n const open = enrollment.status === 'active' || enrollment.status === 'paused'\n const held = enrollment.status === 'paused' && enrollment.stopReason === 'gateway_blocked_here'\n\n /*\n * The one act that moves the person forward is the button: resuming a\n * paused one, else curating the next email. Everything else is in the\n * menu, the destructive acts included, as on every record page.\n */\n const available = outreachEnrollmentActionsFor(enrollment, steps)\n const primary: OutreachEnrollmentRowAction | null = available.includes('resume')\n ? 'resume'\n : available.includes('curate')\n ? 'curate'\n : null\n const menu = actions.menuItems(enrollment, (action) => action !== primary)\n const dash = (value: number) => (value ? value.toLocaleString() : '—')\n const notTracked = !trackClicks && !figures.clicks && !figures.scannerClicks ? 'Not tracked' : undefined\n const thread = enrollment.gmailThreadId ?? enrollment.gmailThreadIds.at(-1) ?? null\n const nextSend = outreachNextSendState({\n enrollment,\n sequence,\n mailbox: props.mailboxes.status === 'ready' ? mailbox : undefined,\n nowMs,\n })\n const nothingYet =\n enrollment.status === 'active' && enrollment.nextDueAtMs\n ? nextSend.kind === 'queued'\n ? `Nothing yet — step ${enrollment.stepIndex + 1} is due and queued to send.`\n : `Nothing yet — step ${enrollment.stepIndex + 1} sends ${time(enrollment.nextDueAtMs)}.`\n : 'Nothing yet.'\n\n return (\n <Stack spacing={2}>\n {/* The page heading and the trail name the person; the card says what they are in. */}\n <PageHeaderRecord title={name} />\n <CardDisplay\n header=\"Enrollment\"\n subheader={\n <>\n {enrollment.contactName ? `${enrollment.email} · ` : ''}\n {`In ${sequence.name || 'Untitled'}`}\n </>\n }\n help={pluginDocsHelp('sequences', { anchor: '#person-history' })}\n contentGutterX\n contentGutterY\n HeaderProps={{\n action: (\n <Stack useFlexGap direction=\"row\" spacing={1} sx={{ alignItems: 'center', flexWrap: 'wrap', rowGap: 1 }}>\n {back}\n {primary ? (\n <Button\n variant=\"outlined\"\n size=\"small\"\n disabled={actions.busy === enrollment.id}\n onClick={() => actions.choose(enrollment, primary)}\n >\n {held ? 'Resume and send' : OUTREACH_ENROLLMENT_ACTION_LABELS[primary]}\n </Button>\n ) : null}\n {menu.length ? <RowActionsMenu label={name} items={menu} /> : null}\n </Stack>\n ),\n }}\n >\n <Stack spacing={2}>\n <Stack useFlexGap direction=\"row\" spacing={1} sx={{ alignItems: 'center', flexWrap: 'wrap', rowGap: 1 }}>\n <Tooltip\n describeChild\n title={recordHref ? `Open the ${kind} in the CRM` : `The ${kind}’s record can’t be linked`}\n >\n <Chip\n size=\"small\"\n variant=\"outlined\"\n color={recordHref ? 'primary' : 'default'}\n icon={<MdiIcon path={mdiAccountOutline.path} fontSize=\"small\" />}\n label={kind === 'lead' ? 'Lead' : 'Contact'}\n {...(recordHref\n ? ({ component: AppLink, href: recordHref, clickable: true, componentVariant: 'naked' } as object)\n : {})}\n />\n </Tooltip>\n <OutreachEnrollmentStatusChip status={enrollment.status} />\n <Chip size=\"small\" variant=\"outlined\" label={outreachCurrentStepLabel(enrollment, steps)} />\n {outreachStepIsCurated(enrollment) ? (\n <Chip size=\"small\" variant=\"outlined\" color=\"success\" label=\"Curated\" />\n ) : null}\n {open && enrollment.nextDueAtMs ? (\n nextSend.kind === 'queued' ? (\n <Tooltip describeChild title={outreachNextSendDetail(nextSend, timeZone)}>\n <Chip\n size=\"small\"\n variant=\"outlined\"\n color={\n nextSend.reason === 'mailbox_not_sending' || nextSend.reason === 'sequence_not_active'\n ? 'warning'\n : 'default'\n }\n label={`Next send ${outreachNextSendLabel(nextSend, timeZone)}`}\n />\n </Tooltip>\n ) : (\n <Chip size=\"small\" variant=\"outlined\" label={`Next send ${time(enrollment.nextDueAtMs)}`} />\n )\n ) : null}\n </Stack>\n {held ? (\n <Alert severity=\"warning\">\n {enrollment.stopDetail ||\n 'Their mail gateway refused this sender, so the next email is held. Resume to send it anyway.'}\n </Alert>\n ) : null}\n {figures.anything ? (\n <Stack useFlexGap direction=\"row\" spacing={3} sx={{ flexWrap: 'wrap', rowGap: 2 }} role=\"group\" aria-label=\"In numbers\">\n <OutreachFigure label=\"Emails sent\" value={dash(figures.emailsSent)} />\n {countOpens ? (\n <OutreachFigure\n label=\"Opens\"\n value={dash(figures.opens)}\n hint={figures.machineOpens ? `${figures.machineOpens.toLocaleString()} by machines, not counted` : undefined}\n />\n ) : null}\n <OutreachFigure label=\"Clicks\" value={dash(figures.clicks)} hint={notTracked} />\n <OutreachFigure\n label=\"Links followed\"\n value={\n figures.linksFollowed.count\n ? `${figures.linksFollowed.count}${figures.linksFollowed.atLeast ? '+' : ''}`\n : '—'\n }\n hint={\n notTracked ??\n (figures.linksFollowed.atLeast && figures.linksFollowed.count\n ? 'Earlier clicks kept the last link only'\n : undefined)\n }\n />\n <OutreachFigure label=\"Scanner clicks\" value={dash(figures.scannerClicks)} hint={notTracked ?? 'Not counted'} />\n <OutreachFigure label=\"Replies\" value={dash(figures.replies)} />\n </Stack>\n ) : (\n <Typography variant=\"body2\" color=\"text.secondary\">\n {nothingYet}\n </Typography>\n )}\n </Stack>\n </CardDisplay>\n\n <CardDisplay\n header=\"Activity\"\n subheader=\"Newest first\"\n help={pluginDocsHelp('sequences', { anchor: '#person-activity' })}\n contentGutterX\n contentGutterY\n HeaderProps={\n thread && outreachThreadOpensInGmail(mailbox)\n ? {\n action: (\n <Button\n size=\"small\"\n href={outreachGmailThreadUrl(thread, mailbox?.email)}\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n >\n Open thread in Gmail\n </Button>\n ),\n }\n : undefined\n }\n >\n <Stack spacing={1}>\n {history.status === 'loading' ? <OutreachLoading label=\"Loading their history…\" /> : null}\n {history.status === 'error' || history.status === 'refused' ? (\n <OutreachLoadProblem\n status={history.status}\n what=\"list of their clicks\"\n // Only the one-by-one list is missing: the totals, the sends and\n // every stop above come from the enrollment, which was read.\n message={\n history.status === 'refused'\n ? 'Their clicks can’t be listed one by one here; the numbers above still count them.'\n : 'Their clicks couldn’t be listed one by one. Reload the page to try again.'\n }\n />\n ) : null}\n <List disablePadding aria-label=\"Activity\">\n {timeline.map((entry, index) => (\n <TimelineRow\n key={entry.key}\n entry={entry}\n timeZone={timeZone}\n mailboxEmail={mailbox?.email ?? null}\n threadsOpenInGmail={outreachThreadOpensInGmail(mailbox)}\n divider={index < timeline.length - 1}\n />\n ))}\n </List>\n </Stack>\n </CardDisplay>\n\n <CardDisplay\n header=\"Details\"\n help={pluginDocsHelp('sequences', { anchor: '#person-details' })}\n contentGutterX\n HeaderProps={{\n action: (\n <Button\n size=\"small\"\n aria-expanded={detailsOpen}\n aria-controls=\"outreach-enrollment-details\"\n endIcon={<MdiIcon path={(detailsOpen ? mdiChevronUp : mdiChevronDown).path} fontSize=\"small\" />}\n onClick={() => setDetailsOpen((was) => !was)}\n >\n {detailsOpen ? 'Hide' : 'Show'}\n </Button>\n ),\n }}\n >\n <Collapse in={detailsOpen} unmountOnExit>\n <Box id=\"outreach-enrollment-details\" sx={{ pb: 2 }}>\n <Divider sx={{ mb: 2 }} />\n <EnrollmentDetails\n enrollment={enrollment}\n sequence={sequence}\n mailbox={mailbox}\n gateway={gateway.status === 'ready' ? gateway.data : null}\n gatewayUnread={\n gateway.status === 'loading'\n ? 'Looking it up…'\n : gateway.status === 'refused'\n ? 'Your role cannot look it up'\n : 'Could not be looked up'\n }\n campaignName={campaignName}\n memberName={memberName}\n orgMount={orgMount}\n timeZone={timeZone}\n />\n </Box>\n </Collapse>\n </CardDisplay>\n\n {actions.dialogs}\n </Stack>\n )\n}\nOutreachEnrollmentDetail.displayName = 'OutreachEnrollmentDetail'\n\nexport default OutreachEnrollmentDetail\n"],"names":["PageHeaderRecord","pluginDocsHelp","pluginRecordHref","mdiAccountCancelOutline","mdiAccountOutline","mdiAccountPlusOutline","mdiAlertCircleOutline","mdiCheckCircleOutline","mdiChevronDown","mdiChevronUp","mdiClipboardCheckOutline","mdiContentCopy","mdiCursorDefaultClickOutline","mdiEmailAlertOutline","mdiEmailOffOutline","mdiEmailOpenOutline","mdiEmailOutline","mdiHandBackLeftOutline","mdiPauseCircleOutline","mdiPencilOutline","mdiPlayCircleOutline","mdiReply","mdiShieldSearch","mdiSkipNext","mdiStopCircleOutline","AppLink","CardDisplay","MdiIcon","EmptyStateComponent","RowActionsMenu","useSnackbar","useOrgContainerOptions","useOrgMemberOptions","Alert","Box","Button","Card","Chip","Collapse","Divider","IconButton","Link","List","ListItem","ListItemIcon","ListItemText","Stack","Tooltip","Typography","useCallback","useMemo","useState","OUTREACH_MAIL_GATEWAY_LABELS","outreachNextSendState","outreachClickSummary","outreachEnrollmentFigures","outreachEnrollmentTimeline","outreachStepName","OUTREACH_ATTESTATION_KINDS","OUTREACH_ATTESTATION_LABELS","OUTREACH_ENROLLMENT_ACTION_LABELS","outreachEnrollmentActionsFor","useOutreachEnrollmentActions","outreachCurrentStepLabel","outreachStepIsCurated","outreachStopLabel","formatOutreachTime","OutreachEnrollmentStatusChip","OutreachLoading","OutreachLoadProblem","outreachNextSendDetail","outreachNextSendLabel","useOutreachNowMs","OutreachFigure","useOutreachApi","useOutreachSequence","useOutreachEnrollment","useOutreachEnrollmentGateway","useOutreachEnrollmentHistory","outreachCrmRecordHref","kind","id","hostId","orgMount","orgSlug","host","hosts","find","entry","subdomain","outreachThreadOpensInGmail","mailbox","provider","outreachGmailThreadUrl","threadId","mailboxEmail","account","encodeURIComponent","KIND_ICONS","enrolled","skipped","curated","sent","task","click","scanner","open","paused","resumed","stopped","replied","bounced","held","released","failed","finished","TONE_COLORS","default","success","info","warning","error","Destination","props","variant","component","sx","display","wordBreak","label","href","url","target","rel","underline","TimelineRow","alignItems","divider","disableGutters","data-kind","minWidth","mt","color","tone","path","fontSize","disableTypography","primary","direction","xs","sm","spacing","justifyContent","fontWeight","title","whiteSpace","atMs","timeZone","secondary","urlLabel","detail","facts","length","gmailThreadId","threadsOpenInGmail","join","Fact","m","typography","children","gatewaySentence","answer","intel","standing","status","domain","resolvedAtMs","from","sendingDomain","parts","gateway","mx","delivered30","blocked30","filter","Boolean","EnrollmentDetails","enrollment","sequence","memberName","enqueueSnackbar","time","ms","leadHref","leadId","contactHref","contactId","clicks","engagement","overrides","Object","entries","stepOverrides","sort","a","b","Number","attested","attestations","threads","gmailThreadIds","copyId","navigator","clipboard","writeText","then","catch","link","componentVariant","gridTemplateColumns","columnGap","rowGap","personalLine","createdAtMs","enrolledByUid","cold","pl","map","li","uid","sendAs","email","mailboxId","campaignIds","campaignName","gatewayUnread","gatewayHold","heldAtMs","releasedAtMs","releasedByUid","gatewayDeliveredSteps","machineClicks","unloggedClicks","unloggedMachineClicks","firstClickAtMs","lastClickAtMs","followed","key","override","steps","source","edited","draftedByUid","draftedAtMs","model","subject","undefined","body","borderLeft","borderColor","prompt","thread","span","threadSubject","messageIds","stopReason","stoppedAtMs","stoppedByUid","updatedAtMs","fontFamily","size","aria-label","onClick","OutreachEnrollmentDetail","orgId","sectionPath","sequenceId","enrollmentId","api","loadedSequence","loaded","history","roster","enabled","detailsOpen","setDetailsOpen","nowMs","data","campaigns","actions","options","option","value","enrollmentsPath","mailboxes","timezone","timeline","formatTime","back","nativeButton","what","description","action","name","contactName","recordHref","figures","trackClicks","settings","stats","clickTracked","countOpens","openTracked","opens","machineOpens","available","includes","menu","menuItems","dash","toLocaleString","notTracked","scannerClicks","at","nextSend","nothingYet","nextDueAtMs","stepIndex","header","subheader","help","anchor","contentGutterX","contentGutterY","HeaderProps","useFlexGap","flexWrap","disabled","busy","choose","items","describeChild","icon","clickable","reason","severity","stopDetail","anything","role","emailsSent","hint","linksFollowed","count","atLeast","replies","message","disablePadding","index","aria-expanded","aria-controls","endIcon","was","in","unmountOnExit","pb","mb","dialogs","displayName"],"mappings":"AAAA;;;;;;;;;;;;;;;CAeC,GACD;;;AAEA,SAEEA,gBAAgB,EAChBC,cAAc,QACT,eAAc;AACrB,SAASC,gBAAgB,QAAQ,mDAAkD;AACnF,SACEC,uBAAuB,EACvBC,iBAAiB,EACjBC,qBAAqB,EACrBC,qBAAqB,EACrBC,qBAAqB,EACrBC,cAAc,EACdC,YAAY,EACZC,wBAAwB,EACxBC,cAAc,EACdC,4BAA4B,EAC5BC,oBAAoB,EACpBC,kBAAkB,EAClBC,mBAAmB,EACnBC,eAAe,EACfC,sBAAsB,EACtBC,qBAAqB,EACrBC,gBAAgB,EAChBC,oBAAoB,EACpBC,QAAQ,EACRC,eAAe,EACfC,WAAW,EACXC,oBAAoB,QACf,yBAAwB;AAC/B,SAASC,OAAO,EAAEC,WAAW,EAAEC,OAAO,QAAQ,uBAAsB;AACpE,OAAOC,yBAAyB,wDAAuD;AACvF,OAAOC,oBAAoB,6DAA4D;AACvF,SAASC,WAAW,QAAQ,8BAA6B;AACzD,SAASC,sBAAsB,EAAEC,mBAAmB,QAAQ,iCAAgC;AAC5F,SACEC,KAAK,EACLC,GAAG,EACHC,MAAM,EACNC,IAAI,EACJC,IAAI,EACJC,QAAQ,EACRC,OAAO,EACPC,UAAU,EACVC,IAAI,EACJC,IAAI,EACJC,QAAQ,EACRC,YAAY,EACZC,YAAY,EACZC,KAAK,EACLC,OAAO,EACPC,UAAU,QACL,gBAAe;AACtB,SAAyBC,WAAW,EAAEC,OAAO,EAAEC,QAAQ,QAAQ,QAAO;AACtE,SAASC,4BAA4B,QAAQ,4BAAwB;AACrE,SAASC,qBAAqB,QAAQ,yBAAqB;AAC3D,SAASC,oBAAoB,QAAQ,oCAAgC;AACrE,SACEC,yBAAyB,EACzBC,0BAA0B,EAC1BC,gBAAgB,QAIX,kCAA8B;AACrC,SACEC,0BAA0B,EAC1BC,2BAA2B,QAItB,6BAAyB;AAChC,SACEC,iCAAiC,EACjCC,4BAA4B,EAE5BC,4BAA4B,QACvB,0BAAsB;AAC7B,SAASC,wBAAwB,EAAEC,qBAAqB,EAAEC,iBAAiB,QAAQ,yBAAqB;AACxG,SACEC,kBAAkB,EAClBC,4BAA4B,EAC5BC,eAAe,EACfC,mBAAmB,QACd,mBAAe;AACtB,SAASC,sBAAsB,EAAEC,qBAAqB,EAAEC,gBAAgB,QAAQ,iBAAa;AAC7F,SAASC,cAAc,QAAQ,4BAAwB;AACvD,SAASC,cAAc,QAAQ,wBAAoB;AACnD,SAASC,mBAAmB,QAAQ,yBAAqB;AAEzD,SACEC,qBAAqB,EACrBC,4BAA4B,EAC5BC,4BAA4B,QACvB,+BAA2B;AAkClC;;;;CAIC,GACD,OAAO,SAASC,sBACdC,IAAwB,EACxBC,EAA6B,EAC7BC,MAAc,EACdC,QAAsE;;QAGzDA;IADb,IAAI,CAACF,MAAM,EAACE,4BAAAA,SAAUC,OAAO,GAAE,OAAO;IACtC,MAAMC,gBAAOF,uBAAAA,SAASG,KAAK,CAACC,IAAI,CAAC,CAACC,QAAUA,MAAMP,EAAE,KAAKC,4BAA5CC,qBAAqDM,SAAS,mBAAI;IAC/E,OAAOvF,iBAAiB8E,MAAM;QAAEI,SAASD,SAASC,OAAO;QAAEC;IAAK,GAAGJ;AACrE;AAEA;;;;CAIC,GACD,OAAO,MAAMS,6BAA6B,CAACC,UACzCA,CAAAA,2BAAAA,QAASC,QAAQ,MAAK,YAAW;AAEnC,yDAAyD,GACzD,OAAO,SAASC,uBAAuBC,QAAgB,EAAEC,YAAuC;IAC9F,MAAMC,UAAUD,eAAe,CAAC,UAAU,EAAEE,mBAAmBF,eAAe,GAAG;IACjF,OAAO,CAAC,6BAA6B,EAAEC,QAAQ,KAAK,EAAEC,mBAAmBH,WAAW;AACtF;AAEA,MAAMI,aAA6D;IACjEC,UAAU9F;IACV+F,SAAS7E;IACT8E,SAASlF;IACTmF,MAAMtF;IACNuF,MAAM7F;IACN8F,OAAO5F;IACP6F,SAASnF;IACT,kBAAkBV;IAClB8F,MAAM3F;IACN,gBAAgBO;IAChBqF,QAAQzF;IACR0F,SAASxF;IACTyF,SAASrF;IACT,kBAAkBrB;IAClB2G,SAASzF;IACT0F,SAASlG;IACT,aAAaC;IACbkG,MAAM/F;IACNgG,UAAU7F;IACV8F,QAAQ5G;IACR6G,UAAU5G;AACZ;AAEA,MAAM6G,cAAoD;IACxDC,SAAS;IACTC,SAAS;IACTC,MAAM;IACNC,SAAS;IACTC,OAAO;AACT;AAEA,gDAAgD,GAChD,SAASC,YAAYC,KAAsC;IACzD,qBACE,MAAC3E;QAAW4E,SAAQ;QAAQC,WAAU;QAAOC,IAAI;YAAEC,SAAS;YAASC,WAAW;QAAY;;YACzFL,MAAMM,KAAK,GAAG,GAAGN,MAAMM,KAAK,CAAC,EAAE,CAAC,GAAG;0BACpC,KAACxF;gBAAKyF,MAAMP,MAAMQ,GAAG;gBAAEC,QAAO;gBAASC,KAAI;gBAAsBC,WAAU;0BACxEX,MAAMQ,GAAG;;;;AAIlB;AAEA,8BAA8B,GAC9B,SAASI,YAAYZ,KAOpB;IACC,MAAM,EAAEnC,KAAK,EAAE,GAAGmC;IAClB,qBACE,MAAChF;QAAS6F,YAAW;QAAaC,SAASd,MAAMc,OAAO;QAAEC,cAAc;QAACC,aAAWnD,MAAMR,IAAI;;0BAC5F,KAACpC;gBAAakF,IAAI;oBAAEc,UAAU;oBAAIC,IAAI;oBAAMC,OAAO1B,WAAW,CAAC5B,MAAMuD,IAAI,CAAC;gBAAC;0BACzE,cAAA,KAACpH;oBAAQqH,MAAM9C,UAAU,CAACV,MAAMR,IAAI,CAAC,CAACgE,IAAI;oBAAEC,UAAS;;;0BAEvD,KAACpG;gBACCqG,iBAAiB;gBACjBC,uBACE,MAACrG;oBACCsG,WAAW;wBAAEC,IAAI;wBAAUC,IAAI;oBAAM;oBACrCC,SAAS;wBAAEF,IAAI;wBAAGC,IAAI;oBAAE;oBACxBxB,IAAI;wBAAE0B,gBAAgB;wBAAiBhB,YAAY;4BAAEc,IAAI;wBAAW;oBAAE;;sCAEtE,KAACtG;4BAAW4E,SAAQ;4BAAQE,IAAI;gCAAE2B,YAAY;4BAAI;sCAC/CjE,MAAMkE,KAAK;;sCAEd,KAAC1G;4BAAW4E,SAAQ;4BAAUkB,OAAM;4BAAiBhB,IAAI;gCAAE6B,YAAY;4BAAS;sCAC7EzF,mBAAmBsB,MAAMoE,IAAI,EAAEjC,MAAMkC,QAAQ;;;;gBAIpDC,yBACE,MAAChH;oBAAMyG,SAAS;oBAAMzB,IAAI;wBAAEe,IAAI;oBAAK;;wBAClCrD,MAAM2C,GAAG,iBAAG,KAACT;4BAAYS,KAAK3C,MAAM2C,GAAG;4BAAEF,OAAOzC,MAAMuE,QAAQ;6BAAO;wBACrEvE,MAAMwE,MAAM,iBACX,KAAChH;4BAAW4E,SAAQ;4BAAQE,IAAI;gCAAE6B,YAAY;gCAAY3B,WAAW;4BAAa;sCAC/ExC,MAAMwE,MAAM;6BAEb;wBACHxE,MAAMyE,KAAK,CAACC,MAAM,IAAK1E,MAAM2E,aAAa,IAAIxC,MAAMyC,kBAAkB,KAAK,sBAC1E,MAACpH;4BAAW4E,SAAQ;4BAAUkB,OAAM;4BAAiBjB,WAAU;;gCAC5DrC,MAAMyE,KAAK,CAACI,IAAI,CAAC;gCACjB7E,MAAM2E,aAAa,IAAIxC,MAAMyC,kBAAkB,KAAK,sBACnD;;wCACG5E,MAAMyE,KAAK,CAACC,MAAM,GAAG,QAAQ;sDAC9B,KAACzH;4CACCyF,MAAMrC,uBAAuBL,MAAM2E,aAAa,EAAExC,MAAM5B,YAAY;4CACpEqC,QAAO;4CACPC,KAAI;4CACJC,WAAU;sDACX;;;qCAID;;6BAEJ;;;;;;AAMhB;AAEA,kCAAkC,GAClC,SAASgC,KAAK3C,KAA6C;IACzD,qBACE;;0BACE,KAAC3E;gBAAW6E,WAAU;gBAAKD,SAAQ;gBAAQkB,OAAM;0BAC9CnB,MAAMM,KAAK;;0BAEd,KAAC/F;gBAAI2F,WAAU;gBAAKC,IAAI;oBAAEyC,GAAG;oBAAG3B,UAAU;oBAAG4B,YAAY;oBAASxC,WAAW;gBAAa;0BACvFL,MAAM8C,QAAQ;;;;AAIvB;AAEA,wFAAwF,GACxF,SAASC,gBAAgBC,MAAyC,EAAEd,QAAuB;IACzF,MAAM,EAAEe,KAAK,EAAEC,QAAQ,EAAE,GAAGF;IAC5B,IAAI,CAACC,OAAO,OAAO;IACnB,IAAIA,MAAME,MAAM,KAAK,WAAWF,MAAME,MAAM,KAAK,WAAW;YAChDH;QAAV,OAAO,IAAGA,iBAAAA,OAAOI,MAAM,YAAbJ,iBAAiB,aAAa,2BAA2B,EAAEzG,mBAAmB0G,MAAMI,YAAY,EAAEnB,WAAW;IACzH;IACA,MAAMoB,OAAON,OAAOO,aAAa,GAAG,CAAC,MAAM,EAAEP,OAAOO,aAAa,EAAE,GAAG;IACtE,MAAMC,QAAQ;QACZ/H,4BAA4B,CAACwH,MAAMQ,OAAO,CAAC;QAC3CR,MAAMS,EAAE,CAACnB,MAAM,GAAG,CAAC,GAAG,EAAEU,MAAMS,EAAE,CAAChB,IAAI,CAAC,OAAO,GAAG;QAChDQ,WACI,GAAGA,SAASS,WAAW,CAAC,YAAY,EAAET,SAASU,SAAS,CAAC,QAAQ,EAAEN,KAAK,oBAAoB,CAAC,GAC7F;QACJ,CAAC,UAAU,EAAE/G,mBAAmB0G,MAAMI,YAAY,EAAEnB,WAAW;KAChE;IACD,OAAOsB,MAAMK,MAAM,CAACC,SAASpB,IAAI,CAAC;AACpC;AAEA;;CAEC,GACD,SAASqB,kBAAkB/D,KAW1B;QAOkCgE;QAyF1BA,yBA2BKA,wBACAA;IA3HZ,MAAM,EAAEA,UAAU,EAAEC,QAAQ,EAAEC,UAAU,EAAEhC,QAAQ,EAAE,GAAGlC;IACvD,MAAM,EAAEmE,eAAe,EAAE,GAAGhK;IAC5B,MAAMiK,OAAO,CAACC,KAAkC9H,mBAAmB8H,IAAInC;IACvE,MAAMoC,WAAWlH,sBAAsB,QAAQ4G,WAAWO,MAAM,EAAEP,WAAWzG,MAAM,EAAEyC,MAAMxC,QAAQ;IACnG,MAAMgH,cAAcpH,sBAAsB,WAAW4G,WAAWS,SAAS,EAAET,WAAWzG,MAAM,EAAEyC,MAAMxC,QAAQ;IAC5G,MAAMkH,SAAS/I,qBAAqBqI,WAAWW,UAAU;IACzD,MAAMC,YAAYC,OAAOC,OAAO,EAACd,4BAAAA,WAAWe,aAAa,YAAxBf,4BAA4B,CAAC,GAAGgB,IAAI,CACnE,CAAC,CAACC,EAAE,EAAE,CAACC,EAAE,GAAKC,OAAOF,KAAKE,OAAOD;IAEnC,MAAME,WAAWrJ,2BAA2B8H,MAAM,CAAC,CAACxG;YAAS2G;gBAAAA,2BAAAA,WAAWqB,YAAY,qBAAvBrB,wBAAyB,CAAC3G,KAAK;;IAC5F,MAAMiI,UAAUtB,WAAWuB,cAAc,CAAChD,MAAM,GAC5CyB,WAAWuB,cAAc,GACzBvB,WAAWxB,aAAa,GACtB;QAACwB,WAAWxB,aAAa;KAAC,GAC1B,EAAE;IACR,MAAMgD,SAAS;YACRC;QAAL,OAAKA,uBAAAA,UAAUC,SAAS,qBAAnBD,qBACDE,SAAS,CAAC3B,WAAW1G,EAAE,EACxBsI,IAAI,CAAC,IAAMzB,gBAAgB,yBAAyB;gBAAElE,SAAS;YAAU,IACzE4F,KAAK,CAAC,IAAM1B,gBAAgB,+BAA+B;gBAAElE,SAAS;YAAQ;IACnF;IACA,MAAM6F,OAAO,CAACvF,MAAqBD,QACjCC,qBACE,KAACzF,mBAAU;YAAEoF,WAAWpG;YAASiM,kBAAkB;QAAQ;YAAcxF,MAAMA;YAAMI,WAAU;sBAC5FL;cAGHA;IAGJ,qBACE,MAAC/F;QACC2F,WAAU;QACVC,IAAI;YACFyC,GAAG;YACHxC,SAAS;YACT4F,qBAAqB;gBAAEtE,IAAI;gBAAOC,IAAI;YAA2B;YACjEsE,WAAW;YACXC,QAAQ;QACV;;0BAEA,KAACvD;gBAAKrC,OAAM;0BACT0D,WAAWmC,YAAY,iBACtB,KAAC9K;oBAAW4E,SAAQ;oBAAQE,IAAI;wBAAE6B,YAAY;oBAAW;8BACtDgC,WAAWmC,YAAY;qBAG1B;;0BAGJ,KAACxD;gBAAKrC,OAAM;0BACT0D,WAAWvD,MAAM,KAAK,SACrBqF,KAAKxB,UAAU,UACbN,WAAWO,MAAM,iBACnB;;wBACGuB,KAAKtB,aAAa;wBAClB;wBACAsB,KAAKxB,UAAU;;qBAGlBwB,KAAKtB,aAAa;;0BAGtB,KAAC7B;gBAAKrC,OAAM;0BACT,GAAG8D,KAAKJ,WAAWoC,WAAW,IAAIpC,WAAWqC,aAAa,GAAG,CAAC,IAAI,EAAEnC,WAAWF,WAAWqC,aAAa,GAAG,GAAG,IAAI;;0BAEpH,KAAC1D;gBAAKrC,OAAM;0BACT0D,WAAWsC,IAAI,GACZ,+FACA;;0BAEN,KAAC3D;gBAAKrC,OAAM;0BACT8E,SAAS7C,MAAM,iBACd,KAACpH;oBAAM+E,WAAU;oBAAK0B,SAAS;oBAAMzB,IAAI;wBAAEyC,GAAG;wBAAG2D,IAAI;oBAAI;8BACtDnB,SAASoB,GAAG,CAAC,CAACnJ;;4BACC2G;wBAAd,MAAMnG,SAAQmG,2BAAAA,WAAWqB,YAAY,qBAAvBrB,wBAAyB,CAAC3G,KAAK;wBAC7C,qBACE,KAACoJ;sCACE,GAAGzK,2BAA2B,CAACqB,KAAK,CAAC,GAAG,EAAE6G,mBAAWrG,yBAAAA,MAAO6I,GAAG,mBAAI,IAAI,EAAE,EAAEtC,KAAKvG,yBAAAA,MAAOoE,IAAI,GAAG;2BADxF5E;oBAIb;qBAGF;;0BAGJ,KAACsF;gBAAKrC,OAAM;0BACTN,MAAMhC,OAAO,GACV,GAAGgC,MAAMhC,OAAO,CAAC2I,MAAM,IAAI3G,MAAMhC,OAAO,CAAC4I,KAAK,GAAG5G,MAAMhC,OAAO,CAAC2I,MAAM,IAAI3G,MAAMhC,OAAO,CAAC2I,MAAM,KAAK3G,MAAMhC,OAAO,CAAC4I,KAAK,GAAG,CAAC,EAAE,EAAE5G,MAAMhC,OAAO,CAAC4I,KAAK,CAAC,CAAC,CAAC,GAAG,IAAI,GAC1J5C,WAAW6C,SAAS,GAClB,wBACA;;0BAER,KAAClE;gBAAKrC,OAAM;0BACT0D,EAAAA,0BAAAA,WAAW8C,WAAW,qBAAtB9C,wBAAwBzB,MAAM,IAC3ByB,WAAW8C,WAAW,CAACN,GAAG,CAACxG,MAAM+G,YAAY,EAAErE,IAAI,CAAC,QACpD;;0BAEN,KAACC;gBAAKrC,OAAM;0BACTN,MAAMyD,OAAO,GAAGV,gBAAgB/C,MAAMyD,OAAO,EAAEvB,YAAYlC,MAAMgH,aAAa;;0BAEjF,MAACrE;gBAAKrC,OAAM;;oBACT0D,WAAWiD,WAAW,GACnB;wBACExL,4BAA4B,CAACuI,WAAWiD,WAAW,CAACxD,OAAO,CAAC;wBAC5DO,WAAWiD,WAAW,CAACC,QAAQ,GAAG,CAAC,KAAK,EAAE9C,KAAKJ,WAAWiD,WAAW,CAACC,QAAQ,GAAG,GAAG;wBACpFlD,WAAWiD,WAAW,CAACE,YAAY,GAC/B,CAAC,SAAS,EAAE/C,KAAKJ,WAAWiD,WAAW,CAACE,YAAY,IAAInD,WAAWiD,WAAW,CAACG,aAAa,GAAG,CAAC,IAAI,EAAElD,WAAWF,WAAWiD,WAAW,CAACG,aAAa,GAAG,GAAG,IAAI,GAC/J;qBACL,CAAC1E,IAAI,CAAC,SACP;oBACHsB,WAAWqD,qBAAqB,GAC7B,CAAC,EAAE,EAAErD,WAAWqD,qBAAqB,CAAC,4DAA4D,CAAC,GACnG;;;0BAEN,MAAC1E;gBAAKrC,OAAM;;oBACToE,OAAOA,MAAM,IAAIA,OAAO4C,aAAa,GAClC;wBACE,GAAG5C,OAAOA,MAAM,CAAC,cAAc,CAAC;wBAChC,GAAGA,OAAO4C,aAAa,CAAC,yBAAyB,CAAC;wBAClD,GAAG5C,OAAOA,MAAM,GAAGA,OAAO6C,cAAc,GAAG7C,OAAO4C,aAAa,GAAG5C,OAAO8C,qBAAqB,CAAC,kBAAkB,CAAC;wBAClHxD,EAAAA,yBAAAA,WAAWW,UAAU,qBAArBX,uBAAuByD,cAAc,IAAG,CAAC,MAAM,EAAErD,KAAKJ,WAAWW,UAAU,CAAC8C,cAAc,GAAG,GAAG;wBAChGzD,EAAAA,0BAAAA,WAAWW,UAAU,qBAArBX,wBAAuB0D,aAAa,IAAG,CAAC,KAAK,EAAEtD,KAAKJ,WAAWW,UAAU,CAAC+C,aAAa,GAAG,GAAG;qBAC9F,CACE7D,MAAM,CAACC,SACPpB,IAAI,CAAC,SACR;oBACHgC,OAAOiD,QAAQ,CAACpF,MAAM,iBACrB,KAAChI;wBAAI4F,IAAI;4BAAEe,IAAI;wBAAI;kCAChBwD,OAAOiD,QAAQ,CAACnB,GAAG,CAAC,CAAChG,oBACpB,KAACT;gCAAsBS,KAAKA;+BAAVA;yBAGpB;;;0BAEN,KAACmC;gBAAKrC,OAAM;0BACTsE,UAAUrC,MAAM,iBACf,KAACpH;oBAAMyG,SAAS;8BACbgD,UAAU4B,GAAG,CAAC,CAAC,CAACoB,KAAKC,SAAS,iBAC7B,MAACtN;;8CACC,KAACc;oCAAW4E,SAAQ;oCAAQE,IAAI;wCAAE2B,YAAY;oCAAI;8CAC/ChG,iBAAiBmI,SAAS6D,KAAK,EAAE3C,OAAOyC;;8CAE3C,KAACvM;oCAAW4E,SAAQ;oCAAUkB,OAAM;oCAAiBjB,WAAU;8CAC5D;wCACC2H,SAASE,MAAM,KAAK,OAAQF,SAASG,MAAM,GAAG,qBAAqB,aAAc;wCACjFH,SAASI,YAAY,GAAG,CAAC,aAAa,EAAE/D,WAAW2D,SAASI,YAAY,GAAG,GAAG;wCAC9EJ,SAASK,WAAW,GAAG9D,KAAKyD,SAASK,WAAW,IAAI;wCACpDL,SAASM,KAAK,GAAG,CAAC,MAAM,EAAEN,SAASM,KAAK,EAAE,GAAG;qCAC9C,CACEtE,MAAM,CAACC,SACPpB,IAAI,CAAC;;gCAETmF,SAASO,OAAO,KAAKC,0BACpB,KAAChN;oCAAW4E,SAAQ;8CAAS,CAAC,SAAS,EAAE4H,SAASO,OAAO,EAAE;qCACzD;gCACHP,SAASS,IAAI,KAAKD,0BACjB,KAAChN;oCACC4E,SAAQ;oCACRE,IAAI;wCAAE6B,YAAY;wCAAYd,IAAI;wCAAKqF,IAAI;wCAAKgC,YAAY;wCAAGC,aAAa;oCAAU;8CAErFX,SAASS,IAAI;qCAEd;gCACHT,SAASY,MAAM,iBACd,KAACpN;oCAAW4E,SAAQ;oCAAUkB,OAAM;oCAAiBjB,WAAU;oCAAMC,IAAI;wCAAE6B,YAAY;wCAAYd,IAAI;oCAAI;8CACxG,CAAC,QAAQ,EAAE2G,SAASY,MAAM,EAAE;qCAE7B;;2BA7BIb;qBAkCd;;0BAGJ,KAACjF;gBAAKrC,OAAOvC,2BAA2BiC,MAAMhC,OAAO,IAAI,kBAAkB;0BACxEsH,QAAQ/C,MAAM,iBACb,MAACpH;oBAAMyG,SAAS;;wBACb0D,QAAQkB,GAAG,CAAC,CAACkC;gCAI+B1I;iDAH3C,MAAC2I;;oCACE5K,2BAA2BiC,MAAMhC,OAAO,kBACvC,KAAClD;wCACCyF,MAAMrC,uBAAuBwK,SAAQ1I,iBAAAA,MAAMhC,OAAO,qBAAbgC,eAAe4G,KAAK;wCACzDnG,QAAO;wCACPC,KAAI;wCACJC,WAAU;kDAET+H;uDAGH,KAACnO;wCAAI2F,WAAU;wCAAOC,IAAI;4CAAEE,WAAW;wCAAY;kDAChDqI;;oCAGJA,WAAW1E,WAAWxB,aAAa,GAAG,eAAe;;+BAf7CkG;;wBAkBZ1E,WAAW4E,aAAa,iBACvB,KAACvN;4BAAW4E,SAAQ;4BAAUkB,OAAM;sCAAkB,CAAC,YAAY,EAAE6C,WAAW4E,aAAa,CAAC,CAAC,CAAC;6BAC9F;wBACH5E,WAAW6E,UAAU,CAACtG,MAAM,iBAC3B,KAAClH;4BAAW4E,SAAQ;4BAAUkB,OAAM;4BAAiBhB,IAAI;gCAAEE,WAAW;4BAAY;sCAC/E,CAAC,mCAAmC,EAAE2D,WAAW6E,UAAU,CAACnG,IAAI,CAAC,MAAM;6BAExE;;qBAGN;;0BAGJ,KAACC;gBAAKrC,OAAM;0BACT0D,WAAW8E,UAAU,GAClB,GAAGxM,kBAAkB0H,YAAY,GAAG,EAAEI,KAAKJ,WAAW+E,WAAW,IAAI/E,WAAWgF,YAAY,GAAG,CAAC,MAAM,EAAE9E,WAAWF,WAAWgF,YAAY,GAAG,GAAG,IAAI,GACpJ;;0BAEN,KAACrG;gBAAKrC,OAAM;0BAAqB,GAAG8D,KAAKJ,WAAWoC,WAAW,EAAE,GAAG,EAAEhC,KAAKJ,WAAWiF,WAAW,GAAG;;0BACpG,KAACtG;gBAAKrC,OAAM;0BACV,cAAA,MAACnF;oBAAMsG,WAAU;oBAAMG,SAAS;oBAAKzB,IAAI;wBAAEU,YAAY;oBAAS;;sCAC9D,KAACxF;4BAAW4E,SAAQ;4BAAQE,IAAI;gCAAE+I,YAAY;gCAAa7I,WAAW;4BAAY;sCAC/E2D,WAAW1G,EAAE;;sCAEhB,KAAClC;4BAAQ2G,OAAM;sCACb,cAAA,KAAClH;gCAAWsO,MAAK;gCAAQC,cAAW;gCAAyBC,SAAS7D;0CACpE,cAAA,KAACxL;oCAAQqH,MAAMrI,eAAeqI,IAAI;oCAAEC,UAAS;;;;;;;;;AAO3D;AAEA,OAAO,SAASgI,yBAAyBtJ,KAAoC;QA6BzEA,uCAsFagE,OAAAA;QAtGmBA,yBA6EmBC,iBAKnDA;IA9FF,MAAM,EAAEsF,KAAK,EAAEC,WAAW,EAAEC,UAAU,EAAEC,YAAY,EAAElM,QAAQ,EAAE,GAAGwC;IACnE,MAAM2J,MAAM5M,eAAewM;IAC3B,MAAMK,iBAAiB5M,oBAAoBuM,OAAOE;IAClD,MAAMI,SAAS5M,sBAAsBsM,OAAOG;IAC5C,MAAMI,UAAU3M,6BAA6BoM,OAAOG;IACpD,MAAMjG,UAAUvG,6BAA6ByM,KAAKD;IAClD,MAAMK,SAAS1P,oBAAoBkP,OAAO;QAAES,SAAS;IAAK;IAC1D,MAAM,CAACC,aAAaC,eAAe,GAAG1O,SAAS;IAC/C,MAAM2O,QAAQtN;IACd,MAAMmH,aAAa6F,OAAOO,IAAI;IAC9B,MAAMnG,WAAW2F,eAAeQ,IAAI;IACpC,MAAMC,YAAYjQ,uBAAuB,YAAYmP,OAAO;QAC1DS,SAASC,eAAenG,QAAQE,+BAAAA,0BAAAA,WAAY8C,WAAW,qBAAvB9C,wBAAyBzB,MAAM;IACjE;IACA,MAAMuF,QAAQvM,QAAQ;;uBAAM0I,4BAAAA,SAAU6D,KAAK,mBAAI,EAAE;OAAE;QAAC7D;KAAS;IAC7D,MAAMqG,UAAUnO,6BAA6B;QAAEwN;QAAK7B;IAAM;IAE1D,MAAM5D,aAAa5I,YACjB,CAACoL;;YAAgBqD;wBAAAA,uBAAAA,OAAOQ,OAAO,CAAC3M,IAAI,CAAC,CAAC4M,SAAWA,OAAO9D,GAAG,KAAKA,yBAA/CqD,qBAAqDzJ,KAAK,mBAAI;OAC/E;QAACyJ,OAAOQ,OAAO;KAAC;IAElB,MAAMxD,eAAezL,YACnB,CAACgC;;YAAe+M;wBAAAA,0BAAAA,UAAUE,OAAO,CAAC3M,IAAI,CAAC,CAAC4M,SAAWA,OAAOC,KAAK,KAAKnN,wBAApD+M,wBAAyD/J,KAAK,mBAAIhD;OAClF;QAAC+M,UAAUE,OAAO;KAAC;IAGrB,MAAMG,kBAAkB,GAAGlB,YAAY,CAAC,EAAEC,WAAW,YAAY,CAAC;IAClE,MAAMzL,WACJgC,kCAAAA,MAAM2K,SAAS,CAACA,SAAS,CAAC/M,IAAI,CAAC,CAACC,QAAUA,MAAMP,EAAE,KAAM0G,CAAAA,CAAAA,8BAAAA,WAAY6C,SAAS,MAAI5C,4BAAAA,SAAU4C,SAAS,CAAD,cAAnG7G,kCAA0G;IAC5G,MAAMkC,mBAAWlE,2BAAAA,QAAS4M,QAAQ,mBAAI;IACtC,MAAMxG,OAAO,CAACC,KAAkC9H,mBAAmB8H,IAAInC;IACvE,MAAM2I,WAAWtP,QACf;;YAQiBkI,qBAAAA;eAPfO,aACInI,2BAA2B;YACzBmI;YACA8D;YACAgC,SAASA,QAAQ3G,MAAM,KAAK,UAAU2G,QAAQM,IAAI,GAAG;YACrDlG;YACA4G,YAAY,CAACzG,KAAO9H,mBAAmB8H,IAAInC;YAC3CuB,OAAO,WAAEA,gBAAAA,QAAQ2G,IAAI,sBAAZ3G,sBAAAA,cAAcR,KAAK,qBAAnBQ,oBAAqBA,OAAO,mBAAI;QAC3C,KACA,EAAE;OACR;QAACO;QAAY8D;QAAOgC;QAAS5F;QAAYhC;QAAUuB,QAAQ2G,IAAI;KAAC;IAGlE,MAAMW,qBACJ,KAACvQ,qBAEM;QAAE0F,WAAWpG;QAASiM,kBAAkB;QAASiF,cAAc;IAAM;QAC1EzK,MAAMmK;QACNvB,MAAK;QACLhI,OAAM;kBACP;;IAKH,IAAI0I,OAAO1G,MAAM,KAAK,aAAayG,eAAezG,MAAM,KAAK,WAAW;QACtE,qBAAO,KAAC1G;YAAgB6D,OAAM;;IAChC;IACA,IAAIuJ,OAAO1G,MAAM,KAAK,WAAW0G,OAAO1G,MAAM,KAAK,WAAW;QAC5D,qBAAO,KAACzG;YAAoByG,QAAQ0G,OAAO1G,MAAM;YAAE8H,MAAK;;IAC1D;IACA,IAAIrB,eAAezG,MAAM,KAAK,WAAWyG,eAAezG,MAAM,KAAK,WAAW;QAC5E,qBAAO,KAACzG;YAAoByG,QAAQyG,eAAezG,MAAM;YAAE8H,MAAK;;IAClE;IACA,qEAAqE;IACrE,IAAI,CAACjH,cAAc,CAACC,YAAYD,WAAWyF,UAAU,KAAKA,YAAY;QACpE,qBACE,KAAChP;YAAKwF,SAAQ;sBACZ,cAAA,KAAChG;gBACCqG,OAAM;gBACN4K,aAAY;gBACZC,QAAQJ;;;IAIhB;IAEA,MAAMK,OAAOpH,WAAWqH,WAAW,IAAIrH,WAAW4C,KAAK;IACvD,MAAMvJ,OAAO2G,WAAWvD,MAAM,KAAK,SAAS,SAAS;IACrD,MAAM6K,aAAalO,sBACjBC,MACAA,SAAS,SAAS2G,WAAWO,MAAM,GAAGP,WAAWS,SAAS,EAC1DT,WAAWzG,MAAM,EACjBC;IAEF,MAAM+N,UAAU3P,0BAA0BoI;IAC1C,MAAMwH,cAAcvH,SAASwH,QAAQ,CAACD,WAAW,IAAIvH,EAAAA,kBAAAA,SAASyH,KAAK,qBAAdzH,gBAAgB0H,YAAY,MAAK;IACtF,0EAA0E;IAC1E,sEAAsE;IACtE,MAAMC,aACJ3H,SAASwH,QAAQ,CAACG,UAAU,IAC5B3H,EAAAA,mBAAAA,SAASyH,KAAK,qBAAdzH,iBAAgB4H,WAAW,MAAK,QAChCN,QAAQO,KAAK,GAAG,KAChBP,QAAQQ,YAAY,GAAG;IACzB,MAAMhN,OAAOiF,WAAWb,MAAM,KAAK,YAAYa,WAAWb,MAAM,KAAK;IACrE,MAAM9D,OAAO2E,WAAWb,MAAM,KAAK,YAAYa,WAAW8E,UAAU,KAAK;IAEzE;;;;GAIC,GACD,MAAMkD,YAAY9P,6BAA6B8H,YAAY8D;IAC3D,MAAMtG,UAA8CwK,UAAUC,QAAQ,CAAC,YACnE,WACAD,UAAUC,QAAQ,CAAC,YACjB,WACA;IACN,MAAMC,OAAO5B,QAAQ6B,SAAS,CAACnI,YAAY,CAACmH,SAAWA,WAAW3J;IAClE,MAAM4K,OAAO,CAAC3B,QAAmBA,QAAQA,MAAM4B,cAAc,KAAK;IAClE,MAAMC,aAAa,CAACd,eAAe,CAACD,QAAQ7G,MAAM,IAAI,CAAC6G,QAAQgB,aAAa,GAAG,gBAAgBlE;IAC/F,MAAMK,UAAS1E,SAAAA,4BAAAA,WAAWxB,aAAa,YAAxBwB,4BAA4BA,WAAWuB,cAAc,CAACiH,EAAE,CAAC,CAAC,cAA1DxI,QAAgE;IAC/E,MAAMyI,WAAW/Q,sBAAsB;QACrCsI;QACAC;QACAjG,SAASgC,MAAM2K,SAAS,CAACxH,MAAM,KAAK,UAAUnF,UAAUqK;QACxD8B;IACF;IACA,MAAMuC,aACJ1I,WAAWb,MAAM,KAAK,YAAYa,WAAW2I,WAAW,GACpDF,SAASpP,IAAI,KAAK,WAChB,CAAC,mBAAmB,EAAE2G,WAAW4I,SAAS,GAAG,EAAE,2BAA2B,CAAC,GAC3E,CAAC,mBAAmB,EAAE5I,WAAW4I,SAAS,GAAG,EAAE,OAAO,EAAExI,KAAKJ,WAAW2I,WAAW,EAAE,CAAC,CAAC,GACzF;IAEN,qBACE,MAACxR;QAAMyG,SAAS;;0BAEd,KAACvJ;gBAAiB0J,OAAOqJ;;0BACzB,KAACrR;gBACC8S,QAAO;gBACPC,yBACE;;wBACG9I,WAAWqH,WAAW,GAAG,GAAGrH,WAAW4C,KAAK,CAAC,GAAG,CAAC,GAAG;wBACpD,CAAC,GAAG,EAAE3C,SAASmH,IAAI,IAAI,YAAY;;;gBAGxC2B,MAAMzU,eAAe,aAAa;oBAAE0U,QAAQ;gBAAkB;gBAC9DC,cAAc;gBACdC,cAAc;gBACdC,aAAa;oBACXhC,sBACE,MAAChQ;wBAAMiS,UAAU;wBAAC3L,WAAU;wBAAMG,SAAS;wBAAGzB,IAAI;4BAAEU,YAAY;4BAAUwM,UAAU;4BAAQnH,QAAQ;wBAAE;;4BACnG6E;4BACAvJ,wBACC,KAAChH;gCACCyF,SAAQ;gCACRkJ,MAAK;gCACLmE,UAAUhD,QAAQiD,IAAI,KAAKvJ,WAAW1G,EAAE;gCACxC+L,SAAS,IAAMiB,QAAQkD,MAAM,CAACxJ,YAAYxC;0CAEzCnC,OAAO,oBAAoBpD,iCAAiC,CAACuF,QAAQ;iCAEtE;4BACH0K,KAAK3J,MAAM,iBAAG,KAACrI;gCAAeoG,OAAO8K;gCAAMqC,OAAOvB;iCAAW;;;gBAGpE;0BAEA,cAAA,MAAC/Q;oBAAMyG,SAAS;;sCACd,MAACzG;4BAAMiS,UAAU;4BAAC3L,WAAU;4BAAMG,SAAS;4BAAGzB,IAAI;gCAAEU,YAAY;gCAAUwM,UAAU;gCAAQnH,QAAQ;4BAAE;;8CACpG,KAAC9K;oCACCsS,aAAa;oCACb3L,OAAOuJ,aAAa,CAAC,SAAS,EAAEjO,KAAK,WAAW,CAAC,GAAG,CAAC,IAAI,EAAEA,KAAK,yBAAyB,CAAC;8CAE1F,cAAA,KAAC3C;wCACCyO,MAAK;wCACLlJ,SAAQ;wCACRkB,OAAOmK,aAAa,YAAY;wCAChCqC,oBAAM,KAAC3T;4CAAQqH,MAAM5I,kBAAkB4I,IAAI;4CAAEC,UAAS;;wCACtDhB,OAAOjD,SAAS,SAAS,SAAS;uCAC7BiO,aACA;wCAAEpL,WAAWpG;wCAASyG,MAAM+K;wCAAYsC,WAAW;wCAAM7H,kBAAkB;oCAAQ,IACpF,CAAC;;8CAGT,KAACvJ;oCAA6B2G,QAAQa,WAAWb,MAAM;;8CACvD,KAACzI;oCAAKyO,MAAK;oCAAQlJ,SAAQ;oCAAWK,OAAOlE,yBAAyB4H,YAAY8D;;gCACjFzL,sBAAsB2H,4BACrB,KAACtJ;oCAAKyO,MAAK;oCAAQlJ,SAAQ;oCAAWkB,OAAM;oCAAUb,OAAM;qCAC1D;gCACHvB,QAAQiF,WAAW2I,WAAW,GAC7BF,SAASpP,IAAI,KAAK,yBAChB,KAACjC;oCAAQsS,aAAa;oCAAC3L,OAAOpF,uBAAuB8P,UAAUvK;8CAC7D,cAAA,KAACxH;wCACCyO,MAAK;wCACLlJ,SAAQ;wCACRkB,OACEsL,SAASoB,MAAM,KAAK,yBAAyBpB,SAASoB,MAAM,KAAK,wBAC7D,YACA;wCAENvN,OAAO,CAAC,UAAU,EAAE1D,sBAAsB6P,UAAUvK,WAAW;;mDAInE,KAACxH;oCAAKyO,MAAK;oCAAQlJ,SAAQ;oCAAWK,OAAO,CAAC,UAAU,EAAE8D,KAAKJ,WAAW2I,WAAW,GAAG;qCAExF;;;wBAELtN,qBACC,KAAC/E;4BAAMwT,UAAS;sCACb9J,WAAW+J,UAAU,IACpB;6BAEF;wBACHxC,QAAQyC,QAAQ,iBACf,MAAC7S;4BAAMiS,UAAU;4BAAC3L,WAAU;4BAAMG,SAAS;4BAAGzB,IAAI;gCAAEkN,UAAU;gCAAQnH,QAAQ;4BAAE;4BAAG+H,MAAK;4BAAQ7E,cAAW;;8CACzG,KAACtM;oCAAewD,OAAM;oCAAcmK,OAAO2B,KAAKb,QAAQ2C,UAAU;;gCACjEtC,2BACC,KAAC9O;oCACCwD,OAAM;oCACNmK,OAAO2B,KAAKb,QAAQO,KAAK;oCACzBqC,MAAM5C,QAAQQ,YAAY,GAAG,GAAGR,QAAQQ,YAAY,CAACM,cAAc,GAAG,yBAAyB,CAAC,GAAGhE;qCAEnG;8CACJ,KAACvL;oCAAewD,OAAM;oCAASmK,OAAO2B,KAAKb,QAAQ7G,MAAM;oCAAGyJ,MAAM7B;;8CAClE,KAACxP;oCACCwD,OAAM;oCACNmK,OACEc,QAAQ6C,aAAa,CAACC,KAAK,GACvB,GAAG9C,QAAQ6C,aAAa,CAACC,KAAK,GAAG9C,QAAQ6C,aAAa,CAACE,OAAO,GAAG,MAAM,IAAI,GAC3E;oCAENH,IAAI,EACF7B,qBAAAA,aACCf,QAAQ6C,aAAa,CAACE,OAAO,IAAI/C,QAAQ6C,aAAa,CAACC,KAAK,GACzD,2CACAhG;;8CAGR,KAACvL;oCAAewD,OAAM;oCAAiBmK,OAAO2B,KAAKb,QAAQgB,aAAa;oCAAG4B,IAAI,EAAE7B,qBAAAA,aAAc;;8CAC/F,KAACxP;oCAAewD,OAAM;oCAAUmK,OAAO2B,KAAKb,QAAQgD,OAAO;;;2CAG7D,KAAClT;4BAAW4E,SAAQ;4BAAQkB,OAAM;sCAC/BuL;;;;;0BAMT,KAAC3S;gBACC8S,QAAO;gBACPC,WAAU;gBACVC,MAAMzU,eAAe,aAAa;oBAAE0U,QAAQ;gBAAmB;gBAC/DC,cAAc;gBACdC,cAAc;gBACdC,aACEzE,UAAU3K,2BAA2BC,WACjC;oBACEmN,sBACE,KAAC3Q;wBACC2O,MAAK;wBACL5I,MAAMrC,uBAAuBwK,QAAQ1K,2BAAAA,QAAS4I,KAAK;wBACnDnG,QAAO;wBACPC,KAAI;kCACL;;gBAIL,IACA2H;0BAGN,cAAA,MAAClN;oBAAMyG,SAAS;;wBACbkI,QAAQ3G,MAAM,KAAK,0BAAY,KAAC1G;4BAAgB6D,OAAM;6BAA8B;wBACpFwJ,QAAQ3G,MAAM,KAAK,WAAW2G,QAAQ3G,MAAM,KAAK,0BAChD,KAACzG;4BACCyG,QAAQ2G,QAAQ3G,MAAM;4BACtB8H,MAAK;4BACL,iEAAiE;4BACjE,6DAA6D;4BAC7DuD,SACE1E,QAAQ3G,MAAM,KAAK,YACf,sFACA;6BAGN;sCACJ,KAACpI;4BAAK0T,cAAc;4BAACrF,cAAW;sCAC7ByB,SAASrE,GAAG,CAAC,CAAC3I,OAAO6Q;;qDACpB,KAAC9N;oCAEC/C,OAAOA;oCACPqE,UAAUA;oCACV9D,YAAY,UAAEJ,2BAAAA,QAAS4I,KAAK,mBAAI;oCAChCnE,oBAAoB1E,2BAA2BC;oCAC/C8C,SAAS4N,QAAQ7D,SAAStI,MAAM,GAAG;mCAL9B1E,MAAM+J,GAAG;;;;;;0BAYxB,KAAC7N;gBACC8S,QAAO;gBACPE,MAAMzU,eAAe,aAAa;oBAAE0U,QAAQ;gBAAkB;gBAC9DC,cAAc;gBACdE,aAAa;oBACXhC,sBACE,KAAC3Q;wBACC2O,MAAK;wBACLwF,iBAAe1E;wBACf2E,iBAAc;wBACdC,uBAAS,KAAC7U;4BAAQqH,MAAM,AAAC4I,CAAAA,cAAcnR,eAAeD,cAAa,EAAGwI,IAAI;4BAAEC,UAAS;;wBACrF+H,SAAS,IAAMa,eAAe,CAAC4E,MAAQ,CAACA;kCAEvC7E,cAAc,SAAS;;gBAG9B;0BAEA,cAAA,KAACtP;oBAASoU,IAAI9E;oBAAa+E,aAAa;8BACtC,cAAA,MAACzU;wBAAI+C,IAAG;wBAA8B6C,IAAI;4BAAE8O,IAAI;wBAAE;;0CAChD,KAACrU;gCAAQuF,IAAI;oCAAE+O,IAAI;gCAAE;;0CACrB,KAACnL;gCACCC,YAAYA;gCACZC,UAAUA;gCACVjG,SAASA;gCACTyF,SAASA,QAAQN,MAAM,KAAK,UAAUM,QAAQ2G,IAAI,GAAG;gCACrDpD,eACEvD,QAAQN,MAAM,KAAK,YACf,mBACAM,QAAQN,MAAM,KAAK,YACjB,gCACA;gCAER4D,cAAcA;gCACd7C,YAAYA;gCACZ1G,UAAUA;gCACV0E,UAAUA;;;;;;YAMjBoI,QAAQ6E,OAAO;;;AAGtB;AACA7F,yBAAyB8F,WAAW,GAAG;AAEvC,eAAe9F,yBAAwB"}
1
+ {"version":3,"sources":["../../../../../../../libs/plugins/outreach/src/lib/components/enrollment-detail.tsx"],"sourcesContent":["/**\n * @license\n * Copyright 2026 Aglyn LLC\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n'use client'\n\nimport {\n type ConsolePluginOrgMount,\n PageHeaderRecord,\n pluginDocsHelp,\n} from '@aglyn/aglyn'\nimport { pluginRecordHref } from '@aglyn/aglyn/plugin-manager/plugin-record-routes'\nimport {\n mdiAccountCancelOutline,\n mdiAccountOutline,\n mdiAccountPlusOutline,\n mdiAlertCircleOutline,\n mdiCheckCircleOutline,\n mdiChevronDown,\n mdiChevronUp,\n mdiClipboardCheckOutline,\n mdiContentCopy,\n mdiCursorDefaultClickOutline,\n mdiEmailAlertOutline,\n mdiEmailOffOutline,\n mdiEmailOpenOutline,\n mdiEmailOutline,\n mdiHandBackLeftOutline,\n mdiPauseCircleOutline,\n mdiPencilOutline,\n mdiMessageReplyTextOutline,\n mdiPlayCircleOutline,\n mdiReply,\n mdiReplyOutline,\n mdiShieldSearch,\n mdiSkipNext,\n mdiStopCircleOutline,\n} from '@aglyn/shared-data-mdi'\nimport { AppLink, CardDisplay, MdiIcon } from '@aglyn/shared-ui-jsx'\nimport EmptyStateComponent from '@aglyn/shared-ui-jsx/components/empty-state.component'\nimport RowActionsMenu from '@aglyn/shared-ui-jsx/components/row-actions-menu.component'\nimport { useSnackbar } from '@aglyn/shared-ui-snackstack'\nimport { useOrgContainerOptions, useOrgMemberOptions } from '@aglyn/tenant-feature-instance'\nimport {\n Alert,\n Box,\n Button,\n Card,\n Chip,\n Collapse,\n Divider,\n IconButton,\n Link,\n List,\n ListItem,\n ListItemIcon,\n ListItemText,\n Stack,\n Tooltip,\n Typography,\n} from '@mui/material'\nimport { type ReactNode, useCallback, useEffect, useMemo, useRef, useState } from 'react'\nimport { OUTREACH_MAIL_GATEWAY_LABELS } from '../engine/mail-gateway'\nimport { outreachEnrollmentHasInbound } from '../engine/manual-reply'\nimport { outreachNextSendState } from '../engine/next-send'\nimport { outreachClickSummary } from '../model/enrollment-engagement'\nimport {\n outreachEnrollmentFigures,\n outreachEnrollmentTimeline,\n outreachStepName,\n type OutreachTimelineEntry,\n type OutreachTimelineKind,\n type OutreachTimelineTone,\n} from '../model/enrollment-timeline'\nimport {\n OUTREACH_ATTESTATION_KINDS,\n OUTREACH_ATTESTATION_LABELS,\n type OutreachEnrollment,\n type OutreachMailbox,\n type OutreachSequence,\n} from '../model/outreach.types'\nimport {\n OUTREACH_ENROLLMENT_ACTION_LABELS,\n outreachEnrollmentActionsFor,\n type OutreachEnrollmentRowAction,\n useOutreachEnrollmentActions,\n} from './enrollment-actions'\nimport { outreachCurrentStepLabel, outreachStepIsCurated, outreachStopLabel } from './enrollments-table'\nimport {\n formatOutreachTime,\n OutreachEnrollmentStatusChip,\n OutreachLoading,\n OutreachLoadProblem,\n} from './outreach-ui'\nimport { outreachNextSendDetail, outreachNextSendLabel, useOutreachNowMs } from './next-send'\nimport { OutreachFigure } from './sequence-report-card'\nimport { useOutreachApi } from './use-outreach-api'\nimport { useOutreachSequence } from './use-outreach-data'\nimport type { OutreachEnrollmentGatewayResponse } from '../model/outreach-api'\nimport {\n useOutreachEnrollment,\n useOutreachEnrollmentGateway,\n useOutreachEnrollmentHistory,\n} from './use-outreach-enrollment'\nimport type { OutreachMailboxesResult } from './use-outreach-mailboxes'\n\n/*==========================================\n * ONE PERSON IN ONE SEQUENCE (AGL-3332):\n * `/[orgSlug]/outreach/sequences/{sequenceId}/enrollments/{enrollmentId}`.\n *\n * A row of the Enrollments tab opens it, and its URL is the person's: a\n * comment or a message can link straight to them.\n *\n * Laid out the way every record page in the console is (the CRM's\n * `CrmRecordHeader` grammar): the page heading names the person; the first\n * card says what the record is, with the way back and the actions in its\n * HEADER — the one that changes things as a button, the rest and the\n * destructive ones behind the menu — and the facts that identify it as\n * chips. Under the chips, five numbers.\n *\n * Then ONE timeline, newest first, which is the page: every send, click,\n * reply, bounce, stop, hold and resume, from `model/enrollment-timeline.ts`.\n * Everything else stored on the enrollment is under Details, closed until\n * asked for — nothing is left out, and nothing is in the way.\n *=========================================*/\n\nexport interface OutreachEnrollmentDetailProps {\n orgId: string\n /** The org the hub is mounted under: its slug and sites, for the CRM record's address. */\n orgMount?: ConsolePluginOrgMount\n /** `/[orgSlug]/outreach/sequences`. */\n sectionPath: string\n sequenceId: string\n enrollmentId: string\n mailboxes: OutreachMailboxesResult\n}\n\n/**\n * Where the CRM record the person is lives — the site's own CRM when the site\n * is known, else the organization's — at the address the plugin that keeps\n * leads and contacts publishes, or `null` where none does.\n */\nexport function outreachCrmRecordHref(\n kind: 'lead' | 'contact',\n id: string | null | undefined,\n hostId: string,\n orgMount: Pick<ConsolePluginOrgMount, 'orgSlug' | 'hosts'> | undefined,\n): string | null {\n if (!id || !orgMount?.orgSlug) return null\n const host = orgMount.hosts.find((entry) => entry.id === hostId)?.subdomain ?? null\n return pluginRecordHref(kind, { orgSlug: orgMount.orgSlug, host }, id)\n}\n\n/**\n * Whether a mailbox's threads open in Gmail. A Microsoft 365 mailbox's\n * conversation has no address of its own in Outlook (AGL-3489), so its\n * thread is shown without a link.\n */\nexport const outreachThreadOpensInGmail = (mailbox: { provider?: string } | null | undefined): boolean =>\n mailbox?.provider !== 'microsoft'\n\n/** A Gmail thread, opened in the mailbox's own account. */\nexport function outreachGmailThreadUrl(threadId: string, mailboxEmail: string | null | undefined): string {\n const account = mailboxEmail ? `?authuser=${encodeURIComponent(mailboxEmail)}` : ''\n return `https://mail.google.com/mail/${account}#all/${encodeURIComponent(threadId)}`\n}\n\nconst KIND_ICONS: Record<OutreachTimelineKind, { path: string }> = {\n enrolled: mdiAccountPlusOutline,\n skipped: mdiSkipNext,\n curated: mdiPencilOutline,\n sent: mdiEmailOutline,\n task: mdiClipboardCheckOutline,\n click: mdiCursorDefaultClickOutline,\n scanner: mdiShieldSearch,\n 'earlier-clicks': mdiCursorDefaultClickOutline,\n open: mdiEmailOpenOutline,\n 'machine-open': mdiShieldSearch,\n paused: mdiPauseCircleOutline,\n resumed: mdiPlayCircleOutline,\n stopped: mdiStopCircleOutline,\n 'do-not-contact': mdiAccountCancelOutline,\n replied: mdiReply,\n 'auto-reply': mdiReplyOutline,\n answered: mdiMessageReplyTextOutline,\n bounced: mdiEmailAlertOutline,\n 'opted-out': mdiEmailOffOutline,\n held: mdiHandBackLeftOutline,\n released: mdiPlayCircleOutline,\n failed: mdiAlertCircleOutline,\n finished: mdiCheckCircleOutline,\n}\n\nconst TONE_COLORS: Record<OutreachTimelineTone, string> = {\n default: 'text.secondary',\n success: 'success.main',\n info: 'info.main',\n warning: 'warning.main',\n error: 'error.main',\n}\n\n/** A destination, whole, opening in a new tab. */\nfunction Destination(props: { url: string; label?: string }) {\n return (\n <Typography variant=\"body2\" component=\"span\" sx={{ display: 'block', wordBreak: 'break-all' }}>\n {props.label ? `${props.label}: ` : null}\n <Link href={props.url} target=\"_blank\" rel=\"noopener noreferrer\" underline=\"hover\">\n {props.url}\n </Link>\n </Typography>\n )\n}\n\n/** One line of the timeline. */\nfunction TimelineRow(props: {\n entry: OutreachTimelineEntry\n timeZone: string | null\n mailboxEmail: string | null\n /** False for a mailbox whose threads do not open in Gmail. */\n threadsOpenInGmail?: boolean\n divider: boolean\n}) {\n const { entry } = props\n return (\n <ListItem alignItems=\"flex-start\" divider={props.divider} disableGutters data-kind={entry.kind}>\n <ListItemIcon sx={{ minWidth: 36, mt: 0.75, color: TONE_COLORS[entry.tone] }}>\n <MdiIcon path={KIND_ICONS[entry.kind].path} fontSize=\"small\" />\n </ListItemIcon>\n <ListItemText\n disableTypography\n primary={\n <Stack\n direction={{ xs: 'column', sm: 'row' }}\n spacing={{ xs: 0, sm: 1 }}\n sx={{ justifyContent: 'space-between', alignItems: { sm: 'baseline' } }}\n >\n <Typography variant=\"body2\" sx={{ fontWeight: 500 }}>\n {entry.title}\n </Typography>\n <Typography variant=\"caption\" color=\"text.secondary\" sx={{ whiteSpace: 'nowrap' }}>\n {formatOutreachTime(entry.atMs, props.timeZone)}\n </Typography>\n </Stack>\n }\n secondary={\n <Stack spacing={0.25} sx={{ mt: 0.25 }}>\n {entry.url ? <Destination url={entry.url} label={entry.urlLabel} /> : null}\n {entry.detail ? (\n <Typography variant=\"body2\" sx={{ whiteSpace: 'pre-wrap', wordBreak: 'break-word' }}>\n {entry.detail}\n </Typography>\n ) : null}\n {entry.facts.length || (entry.gmailThreadId && props.threadsOpenInGmail !== false) ? (\n <Typography variant=\"caption\" color=\"text.secondary\" component=\"div\">\n {entry.facts.join(' · ')}\n {entry.gmailThreadId && props.threadsOpenInGmail !== false ? (\n <>\n {entry.facts.length ? ' · ' : null}\n <Link\n href={outreachGmailThreadUrl(entry.gmailThreadId, props.mailboxEmail)}\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n underline=\"hover\"\n >\n Open thread in Gmail\n </Link>\n </>\n ) : null}\n </Typography>\n ) : null}\n </Stack>\n }\n />\n </ListItem>\n )\n}\n\n/** One fact of the Details list. */\nfunction Fact(props: { label: string; children: ReactNode }) {\n return (\n <>\n <Typography component=\"dt\" variant=\"body2\" color=\"text.secondary\">\n {props.label}\n </Typography>\n <Box component=\"dd\" sx={{ m: 0, minWidth: 0, typography: 'body2', wordBreak: 'break-word' }}>\n {props.children}\n </Box>\n </>\n )\n}\n\n/** What mail from the sequence's sending domain met at the person's domain, in a line. */\nfunction gatewaySentence(answer: OutreachEnrollmentGatewayResponse, timeZone: string | null): string {\n const { intel, standing } = answer\n if (!intel) return 'Could not be looked up'\n if (intel.status === 'no_mx' || intel.status === 'null_mx') {\n return `${answer.domain ?? 'The domain'} takes no mail · looked up ${formatOutreachTime(intel.resolvedAtMs, timeZone)}`\n }\n const from = answer.sendingDomain ? ` from ${answer.sendingDomain}` : ''\n const parts = [\n OUTREACH_MAIL_GATEWAY_LABELS[intel.gateway],\n intel.mx.length ? `MX ${intel.mx.join(', ')}` : 'no MX; delivered to its address record',\n standing\n ? `${standing.delivered30} delivered, ${standing.blocked30} refused${from} in the last 30 days`\n : null,\n `looked up ${formatOutreachTime(intel.resolvedAtMs, timeZone)}`,\n ]\n return parts.filter(Boolean).join(' · ')\n}\n\n/**\n * Everything else the enrollment holds, all of it, behind one toggle.\n */\nfunction EnrollmentDetails(props: {\n enrollment: OutreachEnrollment\n sequence: OutreachSequence\n mailbox: OutreachMailbox | null\n gateway: OutreachEnrollmentGatewayResponse | null\n /** What the Mail gateway line says while there is no answer to show. */\n gatewayUnread: string\n campaignName: (id: string) => string\n memberName: (uid: string) => string\n orgMount?: ConsolePluginOrgMount\n timeZone: string | null\n}) {\n const { enrollment, sequence, memberName, timeZone } = props\n const { enqueueSnackbar } = useSnackbar()\n const time = (ms: number | null | undefined) => formatOutreachTime(ms, timeZone)\n const leadHref = outreachCrmRecordHref('lead', enrollment.leadId, enrollment.hostId, props.orgMount)\n const contactHref = outreachCrmRecordHref('contact', enrollment.contactId, enrollment.hostId, props.orgMount)\n const clicks = outreachClickSummary(enrollment.engagement)\n const overrides = Object.entries(enrollment.stepOverrides ?? {}).sort(\n ([a], [b]) => Number(a) - Number(b),\n )\n const attested = OUTREACH_ATTESTATION_KINDS.filter((kind) => enrollment.attestations?.[kind])\n const threads = enrollment.gmailThreadIds.length\n ? enrollment.gmailThreadIds\n : enrollment.gmailThreadId\n ? [enrollment.gmailThreadId]\n : []\n const copyId = () => {\n void navigator.clipboard\n ?.writeText(enrollment.id)\n .then(() => enqueueSnackbar('Enrollment id copied.', { variant: 'success' }))\n .catch(() => enqueueSnackbar('The id could not be copied.', { variant: 'error' }))\n }\n const link = (href: string | null, label: string) =>\n href ? (\n <Link {...({ component: AppLink, componentVariant: 'naked' } as object)} href={href} underline=\"hover\">\n {label}\n </Link>\n ) : (\n label\n )\n\n return (\n <Box\n component=\"dl\"\n sx={{\n m: 0,\n display: 'grid',\n gridTemplateColumns: { xs: '1fr', sm: 'minmax(160px, 220px) 1fr' },\n columnGap: 2,\n rowGap: 1.25,\n }}\n >\n <Fact label=\"Personal line\">\n {enrollment.personalLine ? (\n <Typography variant=\"body2\" sx={{ whiteSpace: 'pre-wrap' }}>\n {enrollment.personalLine}\n </Typography>\n ) : (\n '—'\n )}\n </Fact>\n <Fact label=\"Enrolled as\">\n {enrollment.target === 'lead' ? (\n link(leadHref, 'Lead')\n ) : enrollment.leadId ? (\n <>\n {link(contactHref, 'Contact')}\n {', converted from a '}\n {link(leadHref, 'lead')}\n </>\n ) : (\n link(contactHref, 'Contact')\n )}\n </Fact>\n <Fact label=\"Enrolled\">\n {`${time(enrollment.createdAtMs)}${enrollment.enrolledByUid ? ` by ${memberName(enrollment.enrolledByUid)}` : ''}`}\n </Fact>\n <Fact label=\"Cold contact\">\n {enrollment.cold\n ? 'Yes — no inbound capture behind them, so the member confirmed the address before enrolling'\n : 'No'}\n </Fact>\n <Fact label=\"Attestations\">\n {attested.length ? (\n <Stack component=\"ul\" spacing={0.25} sx={{ m: 0, pl: 2.5 }}>\n {attested.map((kind) => {\n const entry = enrollment.attestations?.[kind]\n return (\n <li key={kind}>\n {`${OUTREACH_ATTESTATION_LABELS[kind]} — ${memberName(entry?.uid ?? '')}, ${time(entry?.atMs)}`}\n </li>\n )\n })}\n </Stack>\n ) : (\n '—'\n )}\n </Fact>\n <Fact label=\"Mailbox\">\n {props.mailbox\n ? `${props.mailbox.sendAs || props.mailbox.email}${props.mailbox.sendAs && props.mailbox.sendAs !== props.mailbox.email ? ` (${props.mailbox.email})` : ''}`\n : enrollment.mailboxId\n ? 'No longer connected'\n : '—'}\n </Fact>\n <Fact label=\"Campaigns\">\n {enrollment.campaignIds?.length\n ? enrollment.campaignIds.map(props.campaignName).join(', ')\n : '—'}\n </Fact>\n <Fact label=\"Mail gateway\">\n {props.gateway ? gatewaySentence(props.gateway, timeZone) : props.gatewayUnread}\n </Fact>\n <Fact label=\"Gateway hold\">\n {enrollment.gatewayHold\n ? [\n OUTREACH_MAIL_GATEWAY_LABELS[enrollment.gatewayHold.gateway],\n enrollment.gatewayHold.heldAtMs ? `held ${time(enrollment.gatewayHold.heldAtMs)}` : 'never held',\n enrollment.gatewayHold.releasedAtMs\n ? `released ${time(enrollment.gatewayHold.releasedAtMs)}${enrollment.gatewayHold.releasedByUid ? ` by ${memberName(enrollment.gatewayHold.releasedByUid)}` : ''}`\n : 'not released',\n ].join(' · ')\n : '—'}\n {enrollment.gatewayDeliveredSteps\n ? ` (${enrollment.gatewayDeliveredSteps} of their emails counted as delivered on the gateway ledger)`\n : null}\n </Fact>\n <Fact label=\"Clicks\">\n {clicks.clicks || clicks.machineClicks\n ? [\n `${clicks.clicks} by the person`,\n `${clicks.machineClicks} by scanners, not counted`,\n `${clicks.clicks - clicks.unloggedClicks + clicks.machineClicks - clicks.unloggedMachineClicks} listed one by one`,\n enrollment.engagement?.firstClickAtMs ? `first ${time(enrollment.engagement.firstClickAtMs)}` : null,\n enrollment.engagement?.lastClickAtMs ? `last ${time(enrollment.engagement.lastClickAtMs)}` : null,\n ]\n .filter(Boolean)\n .join(' · ')\n : '—'}\n {clicks.followed.length ? (\n <Box sx={{ mt: 0.5 }}>\n {clicks.followed.map((url) => (\n <Destination key={url} url={url} />\n ))}\n </Box>\n ) : null}\n </Fact>\n <Fact label=\"Curated steps\">\n {overrides.length ? (\n <Stack spacing={1.5}>\n {overrides.map(([key, override]) => (\n <Box key={key}>\n <Typography variant=\"body2\" sx={{ fontWeight: 500 }}>\n {outreachStepName(sequence.steps, Number(key))}\n </Typography>\n <Typography variant=\"caption\" color=\"text.secondary\" component=\"div\">\n {[\n override.source === 'ai' ? (override.edited ? 'AI draft, edited' : 'AI draft') : 'Written by a member',\n override.draftedByUid ? `confirmed by ${memberName(override.draftedByUid)}` : null,\n override.draftedAtMs ? time(override.draftedAtMs) : null,\n override.model ? `model ${override.model}` : null,\n ]\n .filter(Boolean)\n .join(' · ')}\n </Typography>\n {override.subject !== undefined ? (\n <Typography variant=\"body2\">{`Subject: ${override.subject}`}</Typography>\n ) : null}\n {override.body !== undefined ? (\n <Typography\n variant=\"body2\"\n sx={{ whiteSpace: 'pre-wrap', mt: 0.5, pl: 1.5, borderLeft: 2, borderColor: 'divider' }}\n >\n {override.body}\n </Typography>\n ) : null}\n {override.prompt ? (\n <Typography variant=\"caption\" color=\"text.secondary\" component=\"div\" sx={{ whiteSpace: 'pre-wrap', mt: 0.5 }}>\n {`Prompt: ${override.prompt}`}\n </Typography>\n ) : null}\n </Box>\n ))}\n </Stack>\n ) : (\n '—'\n )}\n </Fact>\n <Fact label={outreachThreadOpensInGmail(props.mailbox) ? 'Gmail threads' : 'Threads'}>\n {threads.length ? (\n <Stack spacing={0.25}>\n {threads.map((thread) => (\n <span key={thread}>\n {outreachThreadOpensInGmail(props.mailbox) ? (\n <Link\n href={outreachGmailThreadUrl(thread, props.mailbox?.email)}\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n underline=\"hover\"\n >\n {thread}\n </Link>\n ) : (\n <Box component=\"span\" sx={{ wordBreak: 'break-all' }}>\n {thread}\n </Box>\n )}\n {thread === enrollment.gmailThreadId ? ' (current)' : null}\n </span>\n ))}\n {enrollment.threadSubject ? (\n <Typography variant=\"caption\" color=\"text.secondary\">{`Started as “${enrollment.threadSubject}”`}</Typography>\n ) : null}\n {enrollment.messageIds.length ? (\n <Typography variant=\"caption\" color=\"text.secondary\" sx={{ wordBreak: 'break-all' }}>\n {`Message-IDs in the current thread: ${enrollment.messageIds.join(' ')}`}\n </Typography>\n ) : null}\n </Stack>\n ) : (\n '—'\n )}\n </Fact>\n <Fact label=\"Stop\">\n {enrollment.stopReason\n ? `${outreachStopLabel(enrollment)} · ${time(enrollment.stoppedAtMs)}${enrollment.stoppedByUid ? ` · by ${memberName(enrollment.stoppedByUid)}` : ''}`\n : '—'}\n </Fact>\n <Fact label=\"Created · updated\">{`${time(enrollment.createdAtMs)} · ${time(enrollment.updatedAtMs)}`}</Fact>\n <Fact label=\"Enrollment id\">\n <Stack direction=\"row\" spacing={0.5} sx={{ alignItems: 'center' }}>\n <Typography variant=\"body2\" sx={{ fontFamily: 'monospace', wordBreak: 'break-all' }}>\n {enrollment.id}\n </Typography>\n <Tooltip title=\"Copy the id\">\n <IconButton size=\"small\" aria-label=\"Copy the enrollment id\" onClick={copyId}>\n <MdiIcon path={mdiContentCopy.path} fontSize=\"small\" />\n </IconButton>\n </Tooltip>\n </Stack>\n </Fact>\n </Box>\n )\n}\n\nexport function OutreachEnrollmentDetail(props: OutreachEnrollmentDetailProps) {\n const { orgId, sectionPath, sequenceId, enrollmentId, orgMount } = props\n const api = useOutreachApi(orgId)\n const loadedSequence = useOutreachSequence(orgId, sequenceId)\n const loaded = useOutreachEnrollment(orgId, enrollmentId)\n const history = useOutreachEnrollmentHistory(orgId, enrollmentId)\n const gateway = useOutreachEnrollmentGateway(api, enrollmentId)\n const roster = useOrgMemberOptions(orgId, { enabled: true })\n const [detailsOpen, setDetailsOpen] = useState(false)\n const nowMs = useOutreachNowMs()\n const enrollment = loaded.data\n const sequence = loadedSequence.data\n const campaigns = useOrgContainerOptions('campaign', orgId, {\n enabled: detailsOpen && Boolean(enrollment?.campaignIds?.length),\n })\n const steps = useMemo(() => sequence?.steps ?? [], [sequence])\n\n const memberName = useCallback(\n (uid: string) => roster.options.find((option) => option.uid === uid)?.label ?? 'a member',\n [roster.options],\n )\n const campaignName = useCallback(\n (id: string) => campaigns.options.find((option) => option.value === id)?.label ?? id,\n [campaigns.options],\n )\n\n const enrollmentsPath = `${sectionPath}/${sequenceId}/enrollments`\n const mailbox =\n props.mailboxes.mailboxes.find((entry) => entry.id === (enrollment?.mailboxId || sequence?.mailboxId)) ?? null\n const timeZone = mailbox?.timezone ?? null\n const actions = useOutreachEnrollmentActions({ api, steps, timeZone })\n const time = (ms: number | null | undefined) => formatOutreachTime(ms, timeZone)\n const timeline = useMemo(\n () =>\n enrollment\n ? outreachEnrollmentTimeline({\n enrollment,\n steps,\n history: history.status === 'ready' ? history.data : null,\n memberName,\n formatTime: (ms) => formatOutreachTime(ms, timeZone),\n gateway: gateway.data?.intel?.gateway ?? null,\n })\n : [],\n [enrollment, steps, history, memberName, timeZone, gateway.data],\n )\n\n /*\n * A reply synced before replies were kept is on the enrollment only as an\n * id (AGL-4020). Once per page, the thread route reads it from the mailbox\n * and keeps it; the enrollment's listener then shows it in the timeline.\n * A member who may not read that mailbox is answered with nothing new.\n */\n const backfilled = useRef<string | null>(null)\n const unreadReply =\n enrollment !== null && outreachEnrollmentHasInbound(enrollment) && !enrollment.inboundMessages?.length\n useEffect(() => {\n if (!unreadReply || !enrollmentId || backfilled.current === enrollmentId) return\n backfilled.current = enrollmentId\n api.readEnrollmentThread(enrollmentId).catch((error: unknown) => {\n console.warn('[outreach] their reply could not be read from the mailbox', error)\n })\n }, [api, enrollmentId, unreadReply])\n\n const back = (\n <Button\n // A real link, as the CRM record header's is: it opens in a new tab when asked.\n {...({ component: AppLink, componentVariant: 'naked', nativeButton: false } as object)}\n href={enrollmentsPath}\n size=\"small\"\n color=\"primary\"\n >\n Back to enrollments\n </Button>\n )\n\n if (loaded.status === 'loading' || loadedSequence.status === 'loading') {\n return <OutreachLoading label=\"Loading this person…\" />\n }\n if (loaded.status === 'error' || loaded.status === 'refused') {\n return <OutreachLoadProblem status={loaded.status} what=\"enrollment\" />\n }\n if (loadedSequence.status === 'error' || loadedSequence.status === 'refused') {\n return <OutreachLoadProblem status={loadedSequence.status} what=\"sequence\" />\n }\n // An id from another sequence reads as not here: the URL names both.\n if (!enrollment || !sequence || enrollment.sequenceId !== sequenceId) {\n return (\n <Card variant=\"outlined\">\n <EmptyStateComponent\n label=\"This person isn’t in this sequence\"\n description=\"They may have been removed from the workspace, or the link names a different sequence.\"\n action={back}\n />\n </Card>\n )\n }\n\n const name = enrollment.contactName || enrollment.email\n const kind = enrollment.target === 'lead' ? 'lead' : 'contact'\n const recordHref = outreachCrmRecordHref(\n kind,\n kind === 'lead' ? enrollment.leadId : enrollment.contactId,\n enrollment.hostId,\n orgMount,\n )\n const figures = outreachEnrollmentFigures(enrollment)\n const trackClicks = sequence.settings.trackClicks || sequence.stats?.clickTracked === true\n // Opens are shown for a sequence that counts them or once did (AGL-3395),\n // and for a person with any recorded, whatever the sequence says now.\n const countOpens =\n sequence.settings.countOpens ||\n sequence.stats?.openTracked === true ||\n figures.opens > 0 ||\n figures.machineOpens > 0\n const open = enrollment.status === 'active' || enrollment.status === 'paused'\n const held = enrollment.status === 'paused' && enrollment.stopReason === 'gateway_blocked_here'\n\n /*\n * The one act that moves the person forward is the button: answering a\n * person who wrote back (AGL-4020), else resuming a paused one, else\n * curating the next email. Everything else is in the menu, the\n * destructive acts included, as on every record page.\n */\n const available = outreachEnrollmentActionsFor(enrollment, steps)\n const primary: OutreachEnrollmentRowAction | null = available.includes('reply')\n ? 'reply'\n : available.includes('resume')\n ? 'resume'\n : available.includes('curate')\n ? 'curate'\n : null\n const menu = actions.menuItems(enrollment, (action) => action !== primary)\n const dash = (value: number) => (value ? value.toLocaleString() : '—')\n const notTracked = !trackClicks && !figures.clicks && !figures.scannerClicks ? 'Not tracked' : undefined\n const thread = enrollment.gmailThreadId ?? enrollment.gmailThreadIds.at(-1) ?? null\n const nextSend = outreachNextSendState({\n enrollment,\n sequence,\n mailbox: props.mailboxes.status === 'ready' ? mailbox : undefined,\n nowMs,\n })\n const nothingYet =\n enrollment.status === 'active' && enrollment.nextDueAtMs\n ? nextSend.kind === 'queued'\n ? `Nothing yet — step ${enrollment.stepIndex + 1} is due and queued to send.`\n : `Nothing yet — step ${enrollment.stepIndex + 1} sends ${time(enrollment.nextDueAtMs)}.`\n : 'Nothing yet.'\n\n return (\n <Stack spacing={2}>\n {/* The page heading and the trail name the person; the card says what they are in. */}\n <PageHeaderRecord title={name} />\n <CardDisplay\n header=\"Enrollment\"\n subheader={\n <>\n {enrollment.contactName ? `${enrollment.email} · ` : ''}\n {`In ${sequence.name || 'Untitled'}`}\n </>\n }\n help={pluginDocsHelp('sequences', { anchor: '#person-history' })}\n contentGutterX\n contentGutterY\n HeaderProps={{\n action: (\n <Stack useFlexGap direction=\"row\" spacing={1} sx={{ alignItems: 'center', flexWrap: 'wrap', rowGap: 1 }}>\n {back}\n {primary ? (\n <Button\n variant=\"outlined\"\n size=\"small\"\n disabled={actions.busy === enrollment.id}\n onClick={() => actions.choose(enrollment, primary)}\n >\n {held && primary === 'resume' ? 'Resume and send' : OUTREACH_ENROLLMENT_ACTION_LABELS[primary]}\n </Button>\n ) : null}\n {menu.length ? <RowActionsMenu label={name} items={menu} /> : null}\n </Stack>\n ),\n }}\n >\n <Stack spacing={2}>\n <Stack useFlexGap direction=\"row\" spacing={1} sx={{ alignItems: 'center', flexWrap: 'wrap', rowGap: 1 }}>\n <Tooltip\n describeChild\n title={recordHref ? `Open the ${kind} in the CRM` : `The ${kind}’s record can’t be linked`}\n >\n <Chip\n size=\"small\"\n variant=\"outlined\"\n color={recordHref ? 'primary' : 'default'}\n icon={<MdiIcon path={mdiAccountOutline.path} fontSize=\"small\" />}\n label={kind === 'lead' ? 'Lead' : 'Contact'}\n {...(recordHref\n ? ({ component: AppLink, href: recordHref, clickable: true, componentVariant: 'naked' } as object)\n : {})}\n />\n </Tooltip>\n <OutreachEnrollmentStatusChip status={enrollment.status} />\n <Chip size=\"small\" variant=\"outlined\" label={outreachCurrentStepLabel(enrollment, steps)} />\n {outreachStepIsCurated(enrollment) ? (\n <Chip size=\"small\" variant=\"outlined\" color=\"success\" label=\"Curated\" />\n ) : null}\n {open && enrollment.nextDueAtMs ? (\n nextSend.kind === 'queued' ? (\n <Tooltip describeChild title={outreachNextSendDetail(nextSend, timeZone)}>\n <Chip\n size=\"small\"\n variant=\"outlined\"\n color={\n nextSend.reason === 'mailbox_not_sending' || nextSend.reason === 'sequence_not_active'\n ? 'warning'\n : 'default'\n }\n label={`Next send ${outreachNextSendLabel(nextSend, timeZone)}`}\n />\n </Tooltip>\n ) : (\n <Chip size=\"small\" variant=\"outlined\" label={`Next send ${time(enrollment.nextDueAtMs)}`} />\n )\n ) : null}\n </Stack>\n {held ? (\n <Alert severity=\"warning\">\n {enrollment.stopDetail ||\n 'Their mail gateway refused this sender, so the next email is held. Resume to send it anyway.'}\n </Alert>\n ) : null}\n {figures.anything ? (\n <Stack useFlexGap direction=\"row\" spacing={3} sx={{ flexWrap: 'wrap', rowGap: 2 }} role=\"group\" aria-label=\"In numbers\">\n <OutreachFigure label=\"Emails sent\" value={dash(figures.emailsSent)} />\n {countOpens ? (\n <OutreachFigure\n label=\"Opens\"\n value={dash(figures.opens)}\n hint={figures.machineOpens ? `${figures.machineOpens.toLocaleString()} by machines, not counted` : undefined}\n />\n ) : null}\n <OutreachFigure label=\"Clicks\" value={dash(figures.clicks)} hint={notTracked} />\n <OutreachFigure\n label=\"Links followed\"\n value={\n figures.linksFollowed.count\n ? `${figures.linksFollowed.count}${figures.linksFollowed.atLeast ? '+' : ''}`\n : '—'\n }\n hint={\n notTracked ??\n (figures.linksFollowed.atLeast && figures.linksFollowed.count\n ? 'Earlier clicks kept the last link only'\n : undefined)\n }\n />\n <OutreachFigure label=\"Scanner clicks\" value={dash(figures.scannerClicks)} hint={notTracked ?? 'Not counted'} />\n <OutreachFigure label=\"Replies\" value={dash(figures.replies)} />\n {figures.answers ? <OutreachFigure label=\"Answers sent\" value={dash(figures.answers)} /> : null}\n </Stack>\n ) : (\n <Typography variant=\"body2\" color=\"text.secondary\">\n {nothingYet}\n </Typography>\n )}\n </Stack>\n </CardDisplay>\n\n <CardDisplay\n header=\"Activity\"\n subheader=\"Newest first\"\n help={pluginDocsHelp('sequences', { anchor: '#person-activity' })}\n contentGutterX\n contentGutterY\n HeaderProps={\n thread && outreachThreadOpensInGmail(mailbox)\n ? {\n action: (\n <Button\n size=\"small\"\n href={outreachGmailThreadUrl(thread, mailbox?.email)}\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n >\n Open thread in Gmail\n </Button>\n ),\n }\n : undefined\n }\n >\n <Stack spacing={1}>\n {history.status === 'loading' ? <OutreachLoading label=\"Loading their history…\" /> : null}\n {history.status === 'error' || history.status === 'refused' ? (\n <OutreachLoadProblem\n status={history.status}\n what=\"list of their clicks\"\n // Only the one-by-one list is missing: the totals, the sends and\n // every stop above come from the enrollment, which was read.\n message={\n history.status === 'refused'\n ? 'Their clicks can’t be listed one by one here; the numbers above still count them.'\n : 'Their clicks couldn’t be listed one by one. Reload the page to try again.'\n }\n />\n ) : null}\n <List disablePadding aria-label=\"Activity\">\n {timeline.map((entry, index) => (\n <TimelineRow\n key={entry.key}\n entry={entry}\n timeZone={timeZone}\n mailboxEmail={mailbox?.email ?? null}\n threadsOpenInGmail={outreachThreadOpensInGmail(mailbox)}\n divider={index < timeline.length - 1}\n />\n ))}\n </List>\n </Stack>\n </CardDisplay>\n\n <CardDisplay\n header=\"Details\"\n help={pluginDocsHelp('sequences', { anchor: '#person-details' })}\n contentGutterX\n HeaderProps={{\n action: (\n <Button\n size=\"small\"\n aria-expanded={detailsOpen}\n aria-controls=\"outreach-enrollment-details\"\n endIcon={<MdiIcon path={(detailsOpen ? mdiChevronUp : mdiChevronDown).path} fontSize=\"small\" />}\n onClick={() => setDetailsOpen((was) => !was)}\n >\n {detailsOpen ? 'Hide' : 'Show'}\n </Button>\n ),\n }}\n >\n <Collapse in={detailsOpen} unmountOnExit>\n <Box id=\"outreach-enrollment-details\" sx={{ pb: 2 }}>\n <Divider sx={{ mb: 2 }} />\n <EnrollmentDetails\n enrollment={enrollment}\n sequence={sequence}\n mailbox={mailbox}\n gateway={gateway.status === 'ready' ? gateway.data : null}\n gatewayUnread={\n gateway.status === 'loading'\n ? 'Looking it up…'\n : gateway.status === 'refused'\n ? 'Your role cannot look it up'\n : 'Could not be looked up'\n }\n campaignName={campaignName}\n memberName={memberName}\n orgMount={orgMount}\n timeZone={timeZone}\n />\n </Box>\n </Collapse>\n </CardDisplay>\n\n {actions.dialogs}\n </Stack>\n )\n}\nOutreachEnrollmentDetail.displayName = 'OutreachEnrollmentDetail'\n\nexport default OutreachEnrollmentDetail\n"],"names":["PageHeaderRecord","pluginDocsHelp","pluginRecordHref","mdiAccountCancelOutline","mdiAccountOutline","mdiAccountPlusOutline","mdiAlertCircleOutline","mdiCheckCircleOutline","mdiChevronDown","mdiChevronUp","mdiClipboardCheckOutline","mdiContentCopy","mdiCursorDefaultClickOutline","mdiEmailAlertOutline","mdiEmailOffOutline","mdiEmailOpenOutline","mdiEmailOutline","mdiHandBackLeftOutline","mdiPauseCircleOutline","mdiPencilOutline","mdiMessageReplyTextOutline","mdiPlayCircleOutline","mdiReply","mdiReplyOutline","mdiShieldSearch","mdiSkipNext","mdiStopCircleOutline","AppLink","CardDisplay","MdiIcon","EmptyStateComponent","RowActionsMenu","useSnackbar","useOrgContainerOptions","useOrgMemberOptions","Alert","Box","Button","Card","Chip","Collapse","Divider","IconButton","Link","List","ListItem","ListItemIcon","ListItemText","Stack","Tooltip","Typography","useCallback","useEffect","useMemo","useRef","useState","OUTREACH_MAIL_GATEWAY_LABELS","outreachEnrollmentHasInbound","outreachNextSendState","outreachClickSummary","outreachEnrollmentFigures","outreachEnrollmentTimeline","outreachStepName","OUTREACH_ATTESTATION_KINDS","OUTREACH_ATTESTATION_LABELS","OUTREACH_ENROLLMENT_ACTION_LABELS","outreachEnrollmentActionsFor","useOutreachEnrollmentActions","outreachCurrentStepLabel","outreachStepIsCurated","outreachStopLabel","formatOutreachTime","OutreachEnrollmentStatusChip","OutreachLoading","OutreachLoadProblem","outreachNextSendDetail","outreachNextSendLabel","useOutreachNowMs","OutreachFigure","useOutreachApi","useOutreachSequence","useOutreachEnrollment","useOutreachEnrollmentGateway","useOutreachEnrollmentHistory","outreachCrmRecordHref","kind","id","hostId","orgMount","orgSlug","host","hosts","find","entry","subdomain","outreachThreadOpensInGmail","mailbox","provider","outreachGmailThreadUrl","threadId","mailboxEmail","account","encodeURIComponent","KIND_ICONS","enrolled","skipped","curated","sent","task","click","scanner","open","paused","resumed","stopped","replied","answered","bounced","held","released","failed","finished","TONE_COLORS","default","success","info","warning","error","Destination","props","variant","component","sx","display","wordBreak","label","href","url","target","rel","underline","TimelineRow","alignItems","divider","disableGutters","data-kind","minWidth","mt","color","tone","path","fontSize","disableTypography","primary","direction","xs","sm","spacing","justifyContent","fontWeight","title","whiteSpace","atMs","timeZone","secondary","urlLabel","detail","facts","length","gmailThreadId","threadsOpenInGmail","join","Fact","m","typography","children","gatewaySentence","answer","intel","standing","status","domain","resolvedAtMs","from","sendingDomain","parts","gateway","mx","delivered30","blocked30","filter","Boolean","EnrollmentDetails","enrollment","sequence","memberName","enqueueSnackbar","time","ms","leadHref","leadId","contactHref","contactId","clicks","engagement","overrides","Object","entries","stepOverrides","sort","a","b","Number","attested","attestations","threads","gmailThreadIds","copyId","navigator","clipboard","writeText","then","catch","link","componentVariant","gridTemplateColumns","columnGap","rowGap","personalLine","createdAtMs","enrolledByUid","cold","pl","map","li","uid","sendAs","email","mailboxId","campaignIds","campaignName","gatewayUnread","gatewayHold","heldAtMs","releasedAtMs","releasedByUid","gatewayDeliveredSteps","machineClicks","unloggedClicks","unloggedMachineClicks","firstClickAtMs","lastClickAtMs","followed","key","override","steps","source","edited","draftedByUid","draftedAtMs","model","subject","undefined","body","borderLeft","borderColor","prompt","thread","span","threadSubject","messageIds","stopReason","stoppedAtMs","stoppedByUid","updatedAtMs","fontFamily","size","aria-label","onClick","OutreachEnrollmentDetail","orgId","sectionPath","sequenceId","enrollmentId","api","loadedSequence","loaded","history","roster","enabled","detailsOpen","setDetailsOpen","nowMs","data","campaigns","options","option","value","enrollmentsPath","mailboxes","timezone","actions","timeline","formatTime","backfilled","unreadReply","inboundMessages","current","readEnrollmentThread","console","warn","back","nativeButton","what","description","action","name","contactName","recordHref","figures","trackClicks","settings","stats","clickTracked","countOpens","openTracked","opens","machineOpens","available","includes","menu","menuItems","dash","toLocaleString","notTracked","scannerClicks","at","nextSend","nothingYet","nextDueAtMs","stepIndex","header","subheader","help","anchor","contentGutterX","contentGutterY","HeaderProps","useFlexGap","flexWrap","disabled","busy","choose","items","describeChild","icon","clickable","reason","severity","stopDetail","anything","role","emailsSent","hint","linksFollowed","count","atLeast","replies","answers","message","disablePadding","index","aria-expanded","aria-controls","endIcon","was","in","unmountOnExit","pb","mb","dialogs","displayName"],"mappings":"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"}
@@ -111,7 +111,7 @@ const draftOf = (mailbox)=>{
111
111
  * because both act in that member's own Google or Microsoft account.
112
112
  */ export function MailboxCard(props) {
113
113
  var _mailbox_rampStartedAtMs, _OUTREACH_MAILBOX_STATUS_LABELS_mailbox_status, _STATUS_COLOR_mailbox_status;
114
- var _mailbox_health_daily_outreachLocalDay, _mailbox_health_daily, _mailbox_health, _mailbox_sendAsOptions;
114
+ var _mailbox_health_daily, _mailbox_health, _mailbox_sendAsOptions;
115
115
  const { mailbox, isMine, canManage, api, onReconnect, reconnecting = false, nowMs = Date.now() } = props;
116
116
  const { enqueueSnackbar } = useSnackbar();
117
117
  const { confirm } = useConfirmationContext();
@@ -181,7 +181,11 @@ const draftOf = (mailbox)=>{
181
181
  const health = summarizeMailboxHealth(mailbox.health, mailbox.timezone, nowMs);
182
182
  // Tests of a sequence step sent today (AGL-3325): counted beside the
183
183
  // sends, never among them, so the cap and the seven-day sum stay honest.
184
- const testsToday = Math.max(0, Number((_mailbox_health = mailbox.health) == null ? void 0 : (_mailbox_health_daily = _mailbox_health.daily) == null ? void 0 : (_mailbox_health_daily_outreachLocalDay = _mailbox_health_daily[outreachLocalDay(nowMs, mailbox.timezone)]) == null ? void 0 : _mailbox_health_daily_outreachLocalDay.tests) || 0);
184
+ const today = (_mailbox_health = mailbox.health) == null ? void 0 : (_mailbox_health_daily = _mailbox_health.daily) == null ? void 0 : _mailbox_health_daily[outreachLocalDay(nowMs, mailbox.timezone)];
185
+ const testsToday = Math.max(0, Number(today == null ? void 0 : today.tests) || 0);
186
+ // Answers members sent people who wrote back (AGL-4020): counted apart
187
+ // like the tests, so they never spend the cap or pause the mailbox.
188
+ const answersToday = Math.max(0, Number(today == null ? void 0 : today.manualReplies) || 0);
185
189
  const needsReconnect = mailbox.status === 'reconnect_required' || mailbox.status === 'disconnected';
186
190
  const capCheck = validateDailyCap(draft.dailyCap === '' ? Number.NaN : Number(draft.dailyCap));
187
191
  const windowCheck = validateSendWindow(draft.window);
@@ -386,6 +390,13 @@ const draftOf = (mailbox)=>{
386
390
  "aria-label": "Tests today",
387
391
  children: `Tests today: ${testsToday}`
388
392
  }),
393
+ answersToday ? /*#__PURE__*/ _jsx(Typography, {
394
+ variant: "caption",
395
+ color: "text.secondary",
396
+ component: "p",
397
+ "aria-label": "Answers today",
398
+ children: `Answers to replies today: ${answersToday}, not counted against the daily cap`
399
+ }) : null,
389
400
  /*#__PURE__*/ _jsx(Typography, {
390
401
  variant: "caption",
391
402
  color: "text.secondary",
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../../../../libs/plugins/outreach/src/lib/components/mailbox-card.tsx"],"sourcesContent":["/**\n * @license\n * Copyright 2026 Aglyn LLC\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n'use client'\n\nimport { pluginDocsHelp } from '@aglyn/aglyn'\nimport { CardDisplay, useConfirmationContext } from '@aglyn/shared-ui-jsx'\nimport { useSnackbar } from '@aglyn/shared-ui-snackstack'\nimport SenderReadinessPanel from '@aglyn/tenant-feature-instance/components/sender-readiness-panel'\nimport {\n Alert,\n Autocomplete,\n Box,\n Button,\n Chip,\n FormControlLabel,\n FormHelperText,\n MenuItem,\n Stack,\n Switch,\n TextField,\n ToggleButton,\n ToggleButtonGroup,\n Typography,\n} from '@mui/material'\nimport { useEffect, useMemo, useRef, useState } from 'react'\nimport {\n formatMinuteOfDay,\n isValidTimezone,\n OUTREACH_DEFAULT_WINDOW,\n OUTREACH_MAILBOX_STATUS_LABELS,\n OUTREACH_MAX_DAILY_CAP,\n OUTREACH_RAMP_STEPS,\n OUTREACH_WEEKDAY_LABELS,\n outreachEffectiveDailyCap,\n outreachLocalDay,\n summarizeMailboxHealth,\n validateDailyCap,\n validateDisplayName,\n validateSendWindow,\n} from '../mailboxes/mailbox-settings'\nimport type { OutreachMailboxReadinessResponse } from '../mailboxes/mailbox-api'\nimport type {\n OutreachMailbox,\n OutreachMailboxStatus,\n OutreachSendWindow,\n} from '../model/outreach.types'\nimport { outreachPacingNote } from './next-send'\nimport type { OutreachMailboxApi } from './use-outreach-mailbox-api'\n\nexport interface MailboxCardProps {\n mailbox: OutreachMailbox\n /** The viewer is the member who connected it. */\n isMine: boolean\n /** The viewer may change, pause and disconnect it: its member, or an org owner or admin. */\n canManage: boolean\n api: OutreachMailboxApi\n /** Starts a new connect with the mailbox's provider, for a mailbox that needs reconnecting. */\n onReconnect(): void\n /** True while that connect is on its way to the provider. */\n reconnecting?: boolean\n /** The clock the health window and today's limit are read on. */\n nowMs?: number\n}\n\n/**\n * What the card says about a mailbox that paused ITSELF (AGL-2981): the\n * engine's own sentence, when it paused, and — after a complaint — the day\n * resuming stops being premature. Nothing sends from it until a member\n * resumes it.\n */\nexport function autoPauseSentence(mailbox: Pick<OutreachMailbox, 'autoPause' | 'timezone'>): string {\n const pause = mailbox.autoPause\n if (!pause) return ''\n const day = (atMs: number) => {\n try {\n return new Intl.DateTimeFormat('en-US', { dateStyle: 'medium', timeZone: mailbox.timezone }).format(atMs)\n } catch {\n return new Intl.DateTimeFormat('en-US', { dateStyle: 'medium', timeZone: 'UTC' }).format(atMs)\n }\n }\n const until = typeof pause.untilMs === 'number' ? ` Wait until ${day(pause.untilMs)} before resuming it.` : ''\n return `Sequences paused this mailbox on ${day(pause.atMs)}. ${pause.message}${until} Nothing sends from it until it is resumed.`\n}\n\n/** Accessible names of the card's actions, spelled once for the specs. */\nexport const MAILBOX_ACTION_LABELS = {\n save: 'Save settings',\n pause: 'Pause',\n resume: 'Resume',\n test: 'Send a test to myself',\n testElsewhere: 'Send a test',\n testAddress: 'Test address',\n warmUp: 'Warm up gradually',\n disconnect: 'Disconnect',\n reconnect: 'Reconnect',\n recheckReadiness: 'Check DNS again',\n} as const\n\nconst WEEKDAY_NAMES = ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday']\n\nconst STATUS_COLOR: Record<OutreachMailboxStatus, 'success' | 'default' | 'warning' | 'error'> = {\n connected: 'success',\n paused: 'default',\n reconnect_required: 'warning',\n disconnected: 'error',\n}\n\n/** Every half hour of the day, and midnight at its end. */\nconst MINUTE_OPTIONS = Array.from({ length: 49 }, (_, index) => index * 30)\n\n/** The zones this runtime knows, the mailbox's own included whatever it is. */\nfunction timezoneOptions(current: string): string[] {\n const supported = (Intl as { supportedValuesOf?: (key: string) => string[] }).supportedValuesOf?.('timeZone') ?? []\n const zones = supported.length ? supported : ['UTC']\n return zones.includes(current) ? zones : [current, ...zones]\n}\n\n/** The ramp, as the cap's helper text reads it. */\nconst RAMP_SENTENCE = `Warm-up: ${OUTREACH_RAMP_STEPS.map((step, index) =>\n `week ${step.week}${index === OUTREACH_RAMP_STEPS.length - 1 ? '+' : ''}: ${step.limit}`,\n).join(' · ')} a day, never above the cap.`\n\ninterface Draft {\n sendAs: string\n displayName: string\n dailyCap: string\n window: OutreachSendWindow\n timezone: string\n /** Whether the warm-up ramp applies — `rampStartedAtMs` as a switch. */\n warmUp: boolean\n}\n\nconst draftOf = (mailbox: OutreachMailbox): Draft => ({\n sendAs: mailbox.sendAs ?? mailbox.email,\n displayName: mailbox.displayName ?? '',\n dailyCap: String(mailbox.dailyCap ?? ''),\n window: mailbox.window ?? OUTREACH_DEFAULT_WINDOW,\n timezone: mailbox.timezone ?? 'UTC',\n warmUp: typeof mailbox.rampStartedAtMs === 'number',\n})\n\n/**\n * One connected mailbox (AGL-2978): its account and status, its last seven\n * days, its settings, and pause, test and disconnect.\n *\n * Every control is offered only where the route will allow it: the settings\n * form and pause and disconnect to the member who connected the mailbox or an\n * org owner or admin, and the test and the reconnect to its member alone,\n * because both act in that member's own Google or Microsoft account.\n */\nexport function MailboxCard(props: MailboxCardProps) {\n const { mailbox, isMine, canManage, api, onReconnect, reconnecting = false, nowMs = Date.now() } = props\n const { enqueueSnackbar } = useSnackbar()\n const { confirm } = useConfirmationContext()\n const microsoft = mailbox.provider === 'microsoft'\n const providerName = microsoft ? 'Microsoft' : 'Google'\n const [draft, setDraft] = useState<Draft>(() => draftOf(mailbox))\n const [saving, setSaving] = useState(false)\n const [saveError, setSaveError] = useState<string | null>(null)\n const [busy, setBusy] = useState<'status' | 'test' | 'disconnect' | null>(null)\n // Where a test goes when not to the member themself (AGL-3228): a test to\n // one's own address never leaves the provider and shows no authentication result.\n const [testAddress, setTestAddress] = useState('')\n\n /*\n * SPF, DKIM and DMARC for the address this mailbox sends as (AGL-3328),\n * read by the server and remembered there briefly. Re-read when the\n * send-as address changes; a failed read shows nothing rather than a\n * verdict nobody made.\n */\n const sendAsAddress = mailbox.sendAs || mailbox.email\n const [readiness, setReadiness] = useState<OutreachMailboxReadinessResponse | null>(null)\n const [readinessBusy, setReadinessBusy] = useState(false)\n useEffect(() => {\n let active = true\n api\n .readiness(mailbox.id)\n .then((answer) => {\n if (active) setReadiness(answer)\n })\n .catch(() => {\n if (active) setReadiness(null)\n })\n return () => {\n active = false\n }\n }, [api, mailbox.id, sendAsAddress])\n const recheckReadiness = async () => {\n setReadinessBusy(true)\n try {\n setReadiness(await api.readiness(mailbox.id, true))\n } catch (error) {\n enqueueSnackbar((error as Error).message, { variant: 'error', allowDuplicate: true })\n } finally {\n setReadinessBusy(false)\n }\n }\n\n // A save here, a change made from another tab, or a reconnect rewrites the\n // stored settings; the form follows them, unless the member has unsaved\n // edits of their own, which are never thrown away.\n const stored = useMemo(() => draftOf(mailbox), [mailbox])\n const storedKey = JSON.stringify(stored)\n const seededFrom = useRef(storedKey)\n const dirty = JSON.stringify(draft) !== storedKey\n useEffect(() => {\n if (seededFrom.current === storedKey) return\n const previous = seededFrom.current\n seededFrom.current = storedKey\n setDraft((current) => (JSON.stringify(current) === previous ? stored : current))\n }, [storedKey, stored])\n\n const health = summarizeMailboxHealth(mailbox.health, mailbox.timezone, nowMs)\n // Tests of a sequence step sent today (AGL-3325): counted beside the\n // sends, never among them, so the cap and the seven-day sum stay honest.\n const testsToday = Math.max(\n 0,\n Number(mailbox.health?.daily?.[outreachLocalDay(nowMs, mailbox.timezone)]?.tests) || 0,\n )\n const needsReconnect = mailbox.status === 'reconnect_required' || mailbox.status === 'disconnected'\n const capCheck = validateDailyCap(draft.dailyCap === '' ? Number.NaN : Number(draft.dailyCap))\n const windowCheck = validateSendWindow(draft.window)\n const nameCheck = validateDisplayName(draft.displayName)\n const timezoneValid = isValidTimezone(draft.timezone)\n const invalid =\n typeof capCheck !== 'number' || !('days' in windowCheck) || typeof nameCheck !== 'string' || !timezoneValid\n const todayLimit = outreachEffectiveDailyCap(\n {\n dailyCap: typeof capCheck === 'number' ? capCheck : mailbox.dailyCap,\n // A ramp switched on in the draft reads as starting today.\n rampStartedAtMs: draft.warmUp ? (mailbox.rampStartedAtMs ?? nowMs) : null,\n timezone: timezoneValid ? draft.timezone : mailbox.timezone,\n },\n nowMs,\n )\n\n const save = async () => {\n setSaving(true)\n setSaveError(null)\n try {\n await api.saveSettings({\n mailboxId: mailbox.id,\n ...(draft.sendAs !== stored.sendAs ? { sendAs: draft.sendAs } : {}),\n ...(draft.displayName !== stored.displayName ? { displayName: draft.displayName } : {}),\n ...(draft.dailyCap !== stored.dailyCap ? { dailyCap: Number(draft.dailyCap) } : {}),\n ...(JSON.stringify(draft.window) !== JSON.stringify(stored.window) ? { window: draft.window } : {}),\n ...(draft.timezone !== stored.timezone ? { timezone: draft.timezone } : {}),\n ...(draft.warmUp !== stored.warmUp ? { warmUp: draft.warmUp } : {}),\n })\n enqueueSnackbar('Mailbox settings saved', { variant: 'success' })\n } catch (error) {\n setSaveError((error as Error).message)\n } finally {\n setSaving(false)\n }\n }\n\n const togglePaused = async () => {\n const paused = mailbox.status !== 'paused'\n setBusy('status')\n try {\n await api.setPaused(mailbox.id, paused)\n enqueueSnackbar(paused ? 'Mailbox paused' : 'Mailbox resumed', { variant: 'success' })\n } catch (error) {\n enqueueSnackbar((error as Error).message, { variant: 'error', allowDuplicate: true })\n } finally {\n setBusy(null)\n }\n }\n\n const sendTest = async () => {\n setBusy('test')\n try {\n const to = testAddress.trim()\n const sent = await api.sendTest(mailbox.id, to || undefined)\n enqueueSnackbar(\n to\n ? `Test sent to ${sent.sentTo}. Its original source shows whether the sender authenticated.`\n : `Test sent to ${sent.sentTo}. Check your inbox.`,\n { variant: 'success' },\n )\n } catch (error) {\n enqueueSnackbar((error as Error).message, { variant: 'error', allowDuplicate: true })\n } finally {\n setBusy(null)\n }\n }\n\n const disconnect = async () => {\n const confirmed = await confirm({\n title: 'Disconnect this mailbox?',\n description:\n (microsoft\n ? 'Disconnecting deletes the access stored for this mailbox. '\n : 'Disconnecting deletes the access stored for this mailbox and asks Google to revoke it. ') +\n 'Nothing is sent from it again unless it is connected again.',\n confirmationText: MAILBOX_ACTION_LABELS.disconnect,\n confirmationButtonProps: { color: 'error' },\n })\n .then(() => true)\n .catch(() => false)\n if (!confirmed) return\n setBusy('disconnect')\n try {\n const { revocation } = await api.disconnect(mailbox.id)\n if (revocation === 'failed') {\n enqueueSnackbar(\n 'Mailbox disconnected, but Google could not confirm the access was revoked. ' +\n 'Remove it from the Google Account’s third-party connections to be sure.',\n { variant: 'warning', persist: true },\n )\n } else if (revocation === 'unsupported') {\n enqueueSnackbar(\n 'Mailbox disconnected. To end the access at Microsoft too, remove the app at myapps.microsoft.com.',\n { variant: 'success' },\n )\n } else if (revocation === 'kept-for-other-mailbox') {\n enqueueSnackbar(\n 'Mailbox disconnected. Google access stays in place for another connected mailbox on the same account.',\n { variant: 'success' },\n )\n } else {\n enqueueSnackbar('Mailbox disconnected', { variant: 'success' })\n }\n } catch (error) {\n enqueueSnackbar((error as Error).message, { variant: 'error', allowDuplicate: true })\n setBusy(null)\n }\n }\n\n const sendAsLabel = (email: string) => {\n const option = mailbox.sendAsOptions?.find((entry) => entry.email === email)\n return option?.displayName ? `${option.displayName} <${option.email}>` : email\n }\n\n return (\n <CardDisplay\n header={mailbox.email}\n subheader={isMine ? 'Your mailbox' : 'A teammate’s mailbox'}\n help={pluginDocsHelp('sequences', { anchor: '#mailbox-actions' })}\n contentGutterX\n contentGutterY\n HeaderProps={{\n action: (\n <Chip\n size=\"small\"\n label={OUTREACH_MAILBOX_STATUS_LABELS[mailbox.status] ?? mailbox.status}\n color={STATUS_COLOR[mailbox.status] ?? 'default'}\n />\n ),\n }}\n >\n <Stack spacing={2}>\n {needsReconnect ? (\n <Alert\n severity=\"warning\"\n action={\n isMine ? (\n <Button color=\"inherit\" size=\"small\" disabled={reconnecting} onClick={onReconnect}>\n {MAILBOX_ACTION_LABELS.reconnect}\n </Button>\n ) : undefined\n }\n >\n {`${\n mailbox.status === 'disconnected'\n ? 'This mailbox was disconnected.'\n : `${providerName} stopped accepting this mailbox’s connection.`\n } ${\n isMine\n ? 'Nothing sends from it until you connect it again.'\n : 'Only the member who connected it can reconnect it.'\n }`}\n </Alert>\n ) : null}\n {mailbox.status === 'paused' && mailbox.autoPause ? (\n <Alert severity=\"error\" role=\"alert\">\n {autoPauseSentence(mailbox)}\n </Alert>\n ) : null}\n\n <Box>\n <Typography variant=\"subtitle2\">Last 7 days</Typography>\n {health.hasSent ? null : (\n <Typography variant=\"body2\" color=\"text.secondary\">\n No sends yet\n </Typography>\n )}\n <Stack direction=\"row\" spacing={3} sx={{ mt: 0.5 }}>\n {[\n ['Sent', health.sent],\n ['Bounces', health.bounces],\n ['Replies', health.replies],\n ].map(([label, value]) => (\n <Box key={label as string} aria-label={`${label} in the last 7 days`}>\n <Typography variant=\"h6\" component=\"p\">\n {value}\n </Typography>\n <Typography variant=\"caption\" color=\"text.secondary\">\n {label}\n </Typography>\n </Box>\n ))}\n </Stack>\n <Typography variant=\"caption\" color=\"text.secondary\" aria-label=\"Tests today\">\n {`Tests today: ${testsToday}`}\n </Typography>\n <Typography variant=\"caption\" color=\"text.secondary\" component=\"p\" aria-label=\"Pacing\">\n {outreachPacingNote(mailbox, nowMs)}\n </Typography>\n </Box>\n\n {readiness?.readiness ? (\n <Stack spacing={1}>\n <SenderReadinessPanel readiness={readiness.readiness} />\n <Box>\n <Button size=\"small\" disabled={readinessBusy} onClick={() => void recheckReadiness()}>\n {MAILBOX_ACTION_LABELS.recheckReadiness}\n </Button>\n </Box>\n </Stack>\n ) : readiness ? (\n <Typography variant=\"caption\" color=\"text.secondary\">\n {`${providerName} authenticates mail from ${readiness.sendAs.slice(readiness.sendAs.lastIndexOf('@') + 1)} ` +\n 'itself, so there are no records to publish for this address.'}\n </Typography>\n ) : null}\n\n {canManage ? (\n <Stack spacing={2} component=\"form\" onSubmit={(event) => event.preventDefault()}>\n <TextField\n select\n size=\"small\"\n label=\"Send as\"\n value={draft.sendAs}\n onChange={(event) => setDraft({ ...draft, sendAs: event.target.value })}\n helperText=\"Addresses Gmail has verified for this account.\"\n >\n {(mailbox.sendAsOptions?.length ? mailbox.sendAsOptions : [{ email: mailbox.sendAs }]).map((option) => (\n <MenuItem key={option.email} value={option.email}>\n {sendAsLabel(option.email)}\n </MenuItem>\n ))}\n </TextField>\n <TextField\n size=\"small\"\n label=\"Display name\"\n value={draft.displayName}\n onChange={(event) => setDraft({ ...draft, displayName: event.target.value })}\n error={typeof nameCheck !== 'string'}\n helperText={typeof nameCheck !== 'string' ? nameCheck.message : 'The name recipients see beside the address.'}\n />\n <TextField\n size=\"small\"\n type=\"number\"\n label=\"Daily cap\"\n value={draft.dailyCap}\n onChange={(event) => setDraft({ ...draft, dailyCap: event.target.value })}\n error={typeof capCheck !== 'number'}\n slotProps={{ htmlInput: { min: 1, max: OUTREACH_MAX_DAILY_CAP, step: 1 } }}\n helperText={\n typeof capCheck !== 'number'\n ? capCheck.message\n : draft.warmUp\n ? `${RAMP_SENTENCE} Today’s limit: ${todayLimit}.`\n : `No warm-up: today’s limit is the cap, ${todayLimit}.`\n }\n />\n <FormControlLabel\n control={\n <Switch\n checked={draft.warmUp}\n onChange={(event) => setDraft({ ...draft, warmUp: event.target.checked })}\n />\n }\n label={MAILBOX_ACTION_LABELS.warmUp}\n />\n <FormHelperText sx={{ mt: -1 }}>\n {'For a mailbox that is new or has not sent much. One that has sent mail for years already has ' +\n 'its reputation and can start at its cap.'}\n </FormHelperText>\n <Box>\n <Typography variant=\"subtitle2\" gutterBottom>\n Sending window\n </Typography>\n <ToggleButtonGroup\n size=\"small\"\n aria-label=\"Sending days\"\n value={draft.window.days}\n onChange={(_event, days: number[]) =>\n setDraft({ ...draft, window: { ...draft.window, days: [...days].sort((a, b) => a - b) } })\n }\n >\n {OUTREACH_WEEKDAY_LABELS.map((label, day) => (\n <ToggleButton key={label} value={day} aria-label={WEEKDAY_NAMES[day]}>\n {label}\n </ToggleButton>\n ))}\n </ToggleButtonGroup>\n <Stack direction={{ xs: 'column', sm: 'row' }} spacing={2} sx={{ mt: 2 }}>\n <TextField\n select\n size=\"small\"\n label=\"From\"\n value={draft.window.startMinute}\n onChange={(event) =>\n setDraft({ ...draft, window: { ...draft.window, startMinute: Number(event.target.value) } })\n }\n >\n {MINUTE_OPTIONS.slice(0, -1).map((minute) => (\n <MenuItem key={minute} value={minute}>\n {formatMinuteOfDay(minute)}\n </MenuItem>\n ))}\n </TextField>\n <TextField\n select\n size=\"small\"\n label=\"Until\"\n value={draft.window.endMinute}\n onChange={(event) =>\n setDraft({ ...draft, window: { ...draft.window, endMinute: Number(event.target.value) } })\n }\n >\n {MINUTE_OPTIONS.slice(1).map((minute) => (\n <MenuItem key={minute} value={minute}>\n {formatMinuteOfDay(minute)}\n </MenuItem>\n ))}\n </TextField>\n <Autocomplete\n size=\"small\"\n disableClearable\n options={timezoneOptions(mailbox.timezone)}\n value={draft.timezone}\n onChange={(_event, timezone) => setDraft({ ...draft, timezone: timezone ?? draft.timezone })}\n sx={{ minWidth: 240 }}\n renderInput={(params) => <TextField {...params} label=\"Timezone\" />}\n />\n </Stack>\n {'days' in windowCheck ? null : <FormHelperText error>{windowCheck.message}</FormHelperText>}\n </Box>\n {saveError ? <FormHelperText error>{saveError}</FormHelperText> : null}\n <Box>\n <Button variant=\"contained\" disabled={!dirty || invalid || saving} onClick={() => void save()}>\n {MAILBOX_ACTION_LABELS.save}\n </Button>\n </Box>\n </Stack>\n ) : (\n <Typography variant=\"body2\" color=\"text.secondary\">\n {`Sends as ${sendAsLabel(stored.sendAs)}, at most ${stored.dailyCap} a day, ` +\n `${stored.window.days.map((day) => OUTREACH_WEEKDAY_LABELS[day]).join(', ')} ` +\n `${formatMinuteOfDay(stored.window.startMinute)}–${formatMinuteOfDay(stored.window.endMinute)} ` +\n `(${stored.timezone}).`}\n </Typography>\n )}\n\n {isMine && !needsReconnect ? (\n <TextField\n label={MAILBOX_ACTION_LABELS.testAddress}\n value={testAddress}\n onChange={(event) => setTestAddress(event.target.value)}\n disabled={busy !== null}\n size=\"small\"\n type=\"email\"\n helperText={\n 'Leave empty to send the test to yourself. A test to an outside mailbox you can ' +\n 'read is the only one whose original source shows the sender authentication results.'\n }\n fullWidth\n />\n ) : null}\n\n {canManage || isMine ? (\n <Stack direction=\"row\" spacing={1} useFlexGap sx={{ flexWrap: 'wrap' }}>\n {canManage && !needsReconnect ? (\n <Button variant=\"outlined\" disabled={busy !== null} onClick={() => void togglePaused()}>\n {mailbox.status === 'paused' ? MAILBOX_ACTION_LABELS.resume : MAILBOX_ACTION_LABELS.pause}\n </Button>\n ) : null}\n {isMine && !needsReconnect ? (\n <Button variant=\"outlined\" disabled={busy !== null} onClick={() => void sendTest()}>\n {testAddress.trim() ? MAILBOX_ACTION_LABELS.testElsewhere : MAILBOX_ACTION_LABELS.test}\n </Button>\n ) : null}\n {canManage ? (\n <Button color=\"error\" disabled={busy !== null} onClick={() => void disconnect()}>\n {MAILBOX_ACTION_LABELS.disconnect}\n </Button>\n ) : null}\n </Stack>\n ) : null}\n </Stack>\n </CardDisplay>\n )\n}\nMailboxCard.displayName = 'MailboxCard'\n\nexport default MailboxCard\n"],"names":["pluginDocsHelp","CardDisplay","useConfirmationContext","useSnackbar","SenderReadinessPanel","Alert","Autocomplete","Box","Button","Chip","FormControlLabel","FormHelperText","MenuItem","Stack","Switch","TextField","ToggleButton","ToggleButtonGroup","Typography","useEffect","useMemo","useRef","useState","formatMinuteOfDay","isValidTimezone","OUTREACH_DEFAULT_WINDOW","OUTREACH_MAILBOX_STATUS_LABELS","OUTREACH_MAX_DAILY_CAP","OUTREACH_RAMP_STEPS","OUTREACH_WEEKDAY_LABELS","outreachEffectiveDailyCap","outreachLocalDay","summarizeMailboxHealth","validateDailyCap","validateDisplayName","validateSendWindow","outreachPacingNote","autoPauseSentence","mailbox","pause","autoPause","day","atMs","Intl","DateTimeFormat","dateStyle","timeZone","timezone","format","until","untilMs","message","MAILBOX_ACTION_LABELS","save","resume","test","testElsewhere","testAddress","warmUp","disconnect","reconnect","recheckReadiness","WEEKDAY_NAMES","STATUS_COLOR","connected","paused","reconnect_required","disconnected","MINUTE_OPTIONS","Array","from","length","_","index","timezoneOptions","current","supported","supportedValuesOf","zones","includes","RAMP_SENTENCE","map","step","week","limit","join","draftOf","sendAs","email","displayName","dailyCap","String","window","rampStartedAtMs","MailboxCard","props","isMine","canManage","api","onReconnect","reconnecting","nowMs","Date","now","enqueueSnackbar","confirm","microsoft","provider","providerName","draft","setDraft","saving","setSaving","saveError","setSaveError","busy","setBusy","setTestAddress","sendAsAddress","readiness","setReadiness","readinessBusy","setReadinessBusy","active","id","then","answer","catch","error","variant","allowDuplicate","stored","storedKey","JSON","stringify","seededFrom","dirty","previous","health","testsToday","Math","max","Number","daily","tests","needsReconnect","status","capCheck","NaN","windowCheck","nameCheck","timezoneValid","invalid","todayLimit","saveSettings","mailboxId","togglePaused","setPaused","sendTest","to","trim","sent","undefined","sentTo","confirmed","title","description","confirmationText","confirmationButtonProps","color","revocation","persist","sendAsLabel","option","sendAsOptions","find","entry","header","subheader","help","anchor","contentGutterX","contentGutterY","HeaderProps","action","size","label","spacing","severity","disabled","onClick","role","hasSent","direction","sx","mt","bounces","replies","value","aria-label","component","slice","lastIndexOf","onSubmit","event","preventDefault","select","onChange","target","helperText","type","slotProps","htmlInput","min","control","checked","gutterBottom","days","_event","sort","a","b","xs","sm","startMinute","minute","endMinute","disableClearable","options","minWidth","renderInput","params","fullWidth","useFlexGap","flexWrap"],"mappings":"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"}
1
+ {"version":3,"sources":["../../../../../../../libs/plugins/outreach/src/lib/components/mailbox-card.tsx"],"sourcesContent":["/**\n * @license\n * Copyright 2026 Aglyn LLC\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n'use client'\n\nimport { pluginDocsHelp } from '@aglyn/aglyn'\nimport { CardDisplay, useConfirmationContext } from '@aglyn/shared-ui-jsx'\nimport { useSnackbar } from '@aglyn/shared-ui-snackstack'\nimport SenderReadinessPanel from '@aglyn/tenant-feature-instance/components/sender-readiness-panel'\nimport {\n Alert,\n Autocomplete,\n Box,\n Button,\n Chip,\n FormControlLabel,\n FormHelperText,\n MenuItem,\n Stack,\n Switch,\n TextField,\n ToggleButton,\n ToggleButtonGroup,\n Typography,\n} from '@mui/material'\nimport { useEffect, useMemo, useRef, useState } from 'react'\nimport {\n formatMinuteOfDay,\n isValidTimezone,\n OUTREACH_DEFAULT_WINDOW,\n OUTREACH_MAILBOX_STATUS_LABELS,\n OUTREACH_MAX_DAILY_CAP,\n OUTREACH_RAMP_STEPS,\n OUTREACH_WEEKDAY_LABELS,\n outreachEffectiveDailyCap,\n outreachLocalDay,\n summarizeMailboxHealth,\n validateDailyCap,\n validateDisplayName,\n validateSendWindow,\n} from '../mailboxes/mailbox-settings'\nimport type { OutreachMailboxReadinessResponse } from '../mailboxes/mailbox-api'\nimport type {\n OutreachMailbox,\n OutreachMailboxStatus,\n OutreachSendWindow,\n} from '../model/outreach.types'\nimport { outreachPacingNote } from './next-send'\nimport type { OutreachMailboxApi } from './use-outreach-mailbox-api'\n\nexport interface MailboxCardProps {\n mailbox: OutreachMailbox\n /** The viewer is the member who connected it. */\n isMine: boolean\n /** The viewer may change, pause and disconnect it: its member, or an org owner or admin. */\n canManage: boolean\n api: OutreachMailboxApi\n /** Starts a new connect with the mailbox's provider, for a mailbox that needs reconnecting. */\n onReconnect(): void\n /** True while that connect is on its way to the provider. */\n reconnecting?: boolean\n /** The clock the health window and today's limit are read on. */\n nowMs?: number\n}\n\n/**\n * What the card says about a mailbox that paused ITSELF (AGL-2981): the\n * engine's own sentence, when it paused, and — after a complaint — the day\n * resuming stops being premature. Nothing sends from it until a member\n * resumes it.\n */\nexport function autoPauseSentence(mailbox: Pick<OutreachMailbox, 'autoPause' | 'timezone'>): string {\n const pause = mailbox.autoPause\n if (!pause) return ''\n const day = (atMs: number) => {\n try {\n return new Intl.DateTimeFormat('en-US', { dateStyle: 'medium', timeZone: mailbox.timezone }).format(atMs)\n } catch {\n return new Intl.DateTimeFormat('en-US', { dateStyle: 'medium', timeZone: 'UTC' }).format(atMs)\n }\n }\n const until = typeof pause.untilMs === 'number' ? ` Wait until ${day(pause.untilMs)} before resuming it.` : ''\n return `Sequences paused this mailbox on ${day(pause.atMs)}. ${pause.message}${until} Nothing sends from it until it is resumed.`\n}\n\n/** Accessible names of the card's actions, spelled once for the specs. */\nexport const MAILBOX_ACTION_LABELS = {\n save: 'Save settings',\n pause: 'Pause',\n resume: 'Resume',\n test: 'Send a test to myself',\n testElsewhere: 'Send a test',\n testAddress: 'Test address',\n warmUp: 'Warm up gradually',\n disconnect: 'Disconnect',\n reconnect: 'Reconnect',\n recheckReadiness: 'Check DNS again',\n} as const\n\nconst WEEKDAY_NAMES = ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday']\n\nconst STATUS_COLOR: Record<OutreachMailboxStatus, 'success' | 'default' | 'warning' | 'error'> = {\n connected: 'success',\n paused: 'default',\n reconnect_required: 'warning',\n disconnected: 'error',\n}\n\n/** Every half hour of the day, and midnight at its end. */\nconst MINUTE_OPTIONS = Array.from({ length: 49 }, (_, index) => index * 30)\n\n/** The zones this runtime knows, the mailbox's own included whatever it is. */\nfunction timezoneOptions(current: string): string[] {\n const supported = (Intl as { supportedValuesOf?: (key: string) => string[] }).supportedValuesOf?.('timeZone') ?? []\n const zones = supported.length ? supported : ['UTC']\n return zones.includes(current) ? zones : [current, ...zones]\n}\n\n/** The ramp, as the cap's helper text reads it. */\nconst RAMP_SENTENCE = `Warm-up: ${OUTREACH_RAMP_STEPS.map((step, index) =>\n `week ${step.week}${index === OUTREACH_RAMP_STEPS.length - 1 ? '+' : ''}: ${step.limit}`,\n).join(' · ')} a day, never above the cap.`\n\ninterface Draft {\n sendAs: string\n displayName: string\n dailyCap: string\n window: OutreachSendWindow\n timezone: string\n /** Whether the warm-up ramp applies — `rampStartedAtMs` as a switch. */\n warmUp: boolean\n}\n\nconst draftOf = (mailbox: OutreachMailbox): Draft => ({\n sendAs: mailbox.sendAs ?? mailbox.email,\n displayName: mailbox.displayName ?? '',\n dailyCap: String(mailbox.dailyCap ?? ''),\n window: mailbox.window ?? OUTREACH_DEFAULT_WINDOW,\n timezone: mailbox.timezone ?? 'UTC',\n warmUp: typeof mailbox.rampStartedAtMs === 'number',\n})\n\n/**\n * One connected mailbox (AGL-2978): its account and status, its last seven\n * days, its settings, and pause, test and disconnect.\n *\n * Every control is offered only where the route will allow it: the settings\n * form and pause and disconnect to the member who connected the mailbox or an\n * org owner or admin, and the test and the reconnect to its member alone,\n * because both act in that member's own Google or Microsoft account.\n */\nexport function MailboxCard(props: MailboxCardProps) {\n const { mailbox, isMine, canManage, api, onReconnect, reconnecting = false, nowMs = Date.now() } = props\n const { enqueueSnackbar } = useSnackbar()\n const { confirm } = useConfirmationContext()\n const microsoft = mailbox.provider === 'microsoft'\n const providerName = microsoft ? 'Microsoft' : 'Google'\n const [draft, setDraft] = useState<Draft>(() => draftOf(mailbox))\n const [saving, setSaving] = useState(false)\n const [saveError, setSaveError] = useState<string | null>(null)\n const [busy, setBusy] = useState<'status' | 'test' | 'disconnect' | null>(null)\n // Where a test goes when not to the member themself (AGL-3228): a test to\n // one's own address never leaves the provider and shows no authentication result.\n const [testAddress, setTestAddress] = useState('')\n\n /*\n * SPF, DKIM and DMARC for the address this mailbox sends as (AGL-3328),\n * read by the server and remembered there briefly. Re-read when the\n * send-as address changes; a failed read shows nothing rather than a\n * verdict nobody made.\n */\n const sendAsAddress = mailbox.sendAs || mailbox.email\n const [readiness, setReadiness] = useState<OutreachMailboxReadinessResponse | null>(null)\n const [readinessBusy, setReadinessBusy] = useState(false)\n useEffect(() => {\n let active = true\n api\n .readiness(mailbox.id)\n .then((answer) => {\n if (active) setReadiness(answer)\n })\n .catch(() => {\n if (active) setReadiness(null)\n })\n return () => {\n active = false\n }\n }, [api, mailbox.id, sendAsAddress])\n const recheckReadiness = async () => {\n setReadinessBusy(true)\n try {\n setReadiness(await api.readiness(mailbox.id, true))\n } catch (error) {\n enqueueSnackbar((error as Error).message, { variant: 'error', allowDuplicate: true })\n } finally {\n setReadinessBusy(false)\n }\n }\n\n // A save here, a change made from another tab, or a reconnect rewrites the\n // stored settings; the form follows them, unless the member has unsaved\n // edits of their own, which are never thrown away.\n const stored = useMemo(() => draftOf(mailbox), [mailbox])\n const storedKey = JSON.stringify(stored)\n const seededFrom = useRef(storedKey)\n const dirty = JSON.stringify(draft) !== storedKey\n useEffect(() => {\n if (seededFrom.current === storedKey) return\n const previous = seededFrom.current\n seededFrom.current = storedKey\n setDraft((current) => (JSON.stringify(current) === previous ? stored : current))\n }, [storedKey, stored])\n\n const health = summarizeMailboxHealth(mailbox.health, mailbox.timezone, nowMs)\n // Tests of a sequence step sent today (AGL-3325): counted beside the\n // sends, never among them, so the cap and the seven-day sum stay honest.\n const today = mailbox.health?.daily?.[outreachLocalDay(nowMs, mailbox.timezone)]\n const testsToday = Math.max(0, Number(today?.tests) || 0)\n // Answers members sent people who wrote back (AGL-4020): counted apart\n // like the tests, so they never spend the cap or pause the mailbox.\n const answersToday = Math.max(0, Number(today?.manualReplies) || 0)\n const needsReconnect = mailbox.status === 'reconnect_required' || mailbox.status === 'disconnected'\n const capCheck = validateDailyCap(draft.dailyCap === '' ? Number.NaN : Number(draft.dailyCap))\n const windowCheck = validateSendWindow(draft.window)\n const nameCheck = validateDisplayName(draft.displayName)\n const timezoneValid = isValidTimezone(draft.timezone)\n const invalid =\n typeof capCheck !== 'number' || !('days' in windowCheck) || typeof nameCheck !== 'string' || !timezoneValid\n const todayLimit = outreachEffectiveDailyCap(\n {\n dailyCap: typeof capCheck === 'number' ? capCheck : mailbox.dailyCap,\n // A ramp switched on in the draft reads as starting today.\n rampStartedAtMs: draft.warmUp ? (mailbox.rampStartedAtMs ?? nowMs) : null,\n timezone: timezoneValid ? draft.timezone : mailbox.timezone,\n },\n nowMs,\n )\n\n const save = async () => {\n setSaving(true)\n setSaveError(null)\n try {\n await api.saveSettings({\n mailboxId: mailbox.id,\n ...(draft.sendAs !== stored.sendAs ? { sendAs: draft.sendAs } : {}),\n ...(draft.displayName !== stored.displayName ? { displayName: draft.displayName } : {}),\n ...(draft.dailyCap !== stored.dailyCap ? { dailyCap: Number(draft.dailyCap) } : {}),\n ...(JSON.stringify(draft.window) !== JSON.stringify(stored.window) ? { window: draft.window } : {}),\n ...(draft.timezone !== stored.timezone ? { timezone: draft.timezone } : {}),\n ...(draft.warmUp !== stored.warmUp ? { warmUp: draft.warmUp } : {}),\n })\n enqueueSnackbar('Mailbox settings saved', { variant: 'success' })\n } catch (error) {\n setSaveError((error as Error).message)\n } finally {\n setSaving(false)\n }\n }\n\n const togglePaused = async () => {\n const paused = mailbox.status !== 'paused'\n setBusy('status')\n try {\n await api.setPaused(mailbox.id, paused)\n enqueueSnackbar(paused ? 'Mailbox paused' : 'Mailbox resumed', { variant: 'success' })\n } catch (error) {\n enqueueSnackbar((error as Error).message, { variant: 'error', allowDuplicate: true })\n } finally {\n setBusy(null)\n }\n }\n\n const sendTest = async () => {\n setBusy('test')\n try {\n const to = testAddress.trim()\n const sent = await api.sendTest(mailbox.id, to || undefined)\n enqueueSnackbar(\n to\n ? `Test sent to ${sent.sentTo}. Its original source shows whether the sender authenticated.`\n : `Test sent to ${sent.sentTo}. Check your inbox.`,\n { variant: 'success' },\n )\n } catch (error) {\n enqueueSnackbar((error as Error).message, { variant: 'error', allowDuplicate: true })\n } finally {\n setBusy(null)\n }\n }\n\n const disconnect = async () => {\n const confirmed = await confirm({\n title: 'Disconnect this mailbox?',\n description:\n (microsoft\n ? 'Disconnecting deletes the access stored for this mailbox. '\n : 'Disconnecting deletes the access stored for this mailbox and asks Google to revoke it. ') +\n 'Nothing is sent from it again unless it is connected again.',\n confirmationText: MAILBOX_ACTION_LABELS.disconnect,\n confirmationButtonProps: { color: 'error' },\n })\n .then(() => true)\n .catch(() => false)\n if (!confirmed) return\n setBusy('disconnect')\n try {\n const { revocation } = await api.disconnect(mailbox.id)\n if (revocation === 'failed') {\n enqueueSnackbar(\n 'Mailbox disconnected, but Google could not confirm the access was revoked. ' +\n 'Remove it from the Google Account’s third-party connections to be sure.',\n { variant: 'warning', persist: true },\n )\n } else if (revocation === 'unsupported') {\n enqueueSnackbar(\n 'Mailbox disconnected. To end the access at Microsoft too, remove the app at myapps.microsoft.com.',\n { variant: 'success' },\n )\n } else if (revocation === 'kept-for-other-mailbox') {\n enqueueSnackbar(\n 'Mailbox disconnected. Google access stays in place for another connected mailbox on the same account.',\n { variant: 'success' },\n )\n } else {\n enqueueSnackbar('Mailbox disconnected', { variant: 'success' })\n }\n } catch (error) {\n enqueueSnackbar((error as Error).message, { variant: 'error', allowDuplicate: true })\n setBusy(null)\n }\n }\n\n const sendAsLabel = (email: string) => {\n const option = mailbox.sendAsOptions?.find((entry) => entry.email === email)\n return option?.displayName ? `${option.displayName} <${option.email}>` : email\n }\n\n return (\n <CardDisplay\n header={mailbox.email}\n subheader={isMine ? 'Your mailbox' : 'A teammate’s mailbox'}\n help={pluginDocsHelp('sequences', { anchor: '#mailbox-actions' })}\n contentGutterX\n contentGutterY\n HeaderProps={{\n action: (\n <Chip\n size=\"small\"\n label={OUTREACH_MAILBOX_STATUS_LABELS[mailbox.status] ?? mailbox.status}\n color={STATUS_COLOR[mailbox.status] ?? 'default'}\n />\n ),\n }}\n >\n <Stack spacing={2}>\n {needsReconnect ? (\n <Alert\n severity=\"warning\"\n action={\n isMine ? (\n <Button color=\"inherit\" size=\"small\" disabled={reconnecting} onClick={onReconnect}>\n {MAILBOX_ACTION_LABELS.reconnect}\n </Button>\n ) : undefined\n }\n >\n {`${\n mailbox.status === 'disconnected'\n ? 'This mailbox was disconnected.'\n : `${providerName} stopped accepting this mailbox’s connection.`\n } ${\n isMine\n ? 'Nothing sends from it until you connect it again.'\n : 'Only the member who connected it can reconnect it.'\n }`}\n </Alert>\n ) : null}\n {mailbox.status === 'paused' && mailbox.autoPause ? (\n <Alert severity=\"error\" role=\"alert\">\n {autoPauseSentence(mailbox)}\n </Alert>\n ) : null}\n\n <Box>\n <Typography variant=\"subtitle2\">Last 7 days</Typography>\n {health.hasSent ? null : (\n <Typography variant=\"body2\" color=\"text.secondary\">\n No sends yet\n </Typography>\n )}\n <Stack direction=\"row\" spacing={3} sx={{ mt: 0.5 }}>\n {[\n ['Sent', health.sent],\n ['Bounces', health.bounces],\n ['Replies', health.replies],\n ].map(([label, value]) => (\n <Box key={label as string} aria-label={`${label} in the last 7 days`}>\n <Typography variant=\"h6\" component=\"p\">\n {value}\n </Typography>\n <Typography variant=\"caption\" color=\"text.secondary\">\n {label}\n </Typography>\n </Box>\n ))}\n </Stack>\n <Typography variant=\"caption\" color=\"text.secondary\" aria-label=\"Tests today\">\n {`Tests today: ${testsToday}`}\n </Typography>\n {answersToday ? (\n <Typography variant=\"caption\" color=\"text.secondary\" component=\"p\" aria-label=\"Answers today\">\n {`Answers to replies today: ${answersToday}, not counted against the daily cap`}\n </Typography>\n ) : null}\n <Typography variant=\"caption\" color=\"text.secondary\" component=\"p\" aria-label=\"Pacing\">\n {outreachPacingNote(mailbox, nowMs)}\n </Typography>\n </Box>\n\n {readiness?.readiness ? (\n <Stack spacing={1}>\n <SenderReadinessPanel readiness={readiness.readiness} />\n <Box>\n <Button size=\"small\" disabled={readinessBusy} onClick={() => void recheckReadiness()}>\n {MAILBOX_ACTION_LABELS.recheckReadiness}\n </Button>\n </Box>\n </Stack>\n ) : readiness ? (\n <Typography variant=\"caption\" color=\"text.secondary\">\n {`${providerName} authenticates mail from ${readiness.sendAs.slice(readiness.sendAs.lastIndexOf('@') + 1)} ` +\n 'itself, so there are no records to publish for this address.'}\n </Typography>\n ) : null}\n\n {canManage ? (\n <Stack spacing={2} component=\"form\" onSubmit={(event) => event.preventDefault()}>\n <TextField\n select\n size=\"small\"\n label=\"Send as\"\n value={draft.sendAs}\n onChange={(event) => setDraft({ ...draft, sendAs: event.target.value })}\n helperText=\"Addresses Gmail has verified for this account.\"\n >\n {(mailbox.sendAsOptions?.length ? mailbox.sendAsOptions : [{ email: mailbox.sendAs }]).map((option) => (\n <MenuItem key={option.email} value={option.email}>\n {sendAsLabel(option.email)}\n </MenuItem>\n ))}\n </TextField>\n <TextField\n size=\"small\"\n label=\"Display name\"\n value={draft.displayName}\n onChange={(event) => setDraft({ ...draft, displayName: event.target.value })}\n error={typeof nameCheck !== 'string'}\n helperText={typeof nameCheck !== 'string' ? nameCheck.message : 'The name recipients see beside the address.'}\n />\n <TextField\n size=\"small\"\n type=\"number\"\n label=\"Daily cap\"\n value={draft.dailyCap}\n onChange={(event) => setDraft({ ...draft, dailyCap: event.target.value })}\n error={typeof capCheck !== 'number'}\n slotProps={{ htmlInput: { min: 1, max: OUTREACH_MAX_DAILY_CAP, step: 1 } }}\n helperText={\n typeof capCheck !== 'number'\n ? capCheck.message\n : draft.warmUp\n ? `${RAMP_SENTENCE} Today’s limit: ${todayLimit}.`\n : `No warm-up: today’s limit is the cap, ${todayLimit}.`\n }\n />\n <FormControlLabel\n control={\n <Switch\n checked={draft.warmUp}\n onChange={(event) => setDraft({ ...draft, warmUp: event.target.checked })}\n />\n }\n label={MAILBOX_ACTION_LABELS.warmUp}\n />\n <FormHelperText sx={{ mt: -1 }}>\n {'For a mailbox that is new or has not sent much. One that has sent mail for years already has ' +\n 'its reputation and can start at its cap.'}\n </FormHelperText>\n <Box>\n <Typography variant=\"subtitle2\" gutterBottom>\n Sending window\n </Typography>\n <ToggleButtonGroup\n size=\"small\"\n aria-label=\"Sending days\"\n value={draft.window.days}\n onChange={(_event, days: number[]) =>\n setDraft({ ...draft, window: { ...draft.window, days: [...days].sort((a, b) => a - b) } })\n }\n >\n {OUTREACH_WEEKDAY_LABELS.map((label, day) => (\n <ToggleButton key={label} value={day} aria-label={WEEKDAY_NAMES[day]}>\n {label}\n </ToggleButton>\n ))}\n </ToggleButtonGroup>\n <Stack direction={{ xs: 'column', sm: 'row' }} spacing={2} sx={{ mt: 2 }}>\n <TextField\n select\n size=\"small\"\n label=\"From\"\n value={draft.window.startMinute}\n onChange={(event) =>\n setDraft({ ...draft, window: { ...draft.window, startMinute: Number(event.target.value) } })\n }\n >\n {MINUTE_OPTIONS.slice(0, -1).map((minute) => (\n <MenuItem key={minute} value={minute}>\n {formatMinuteOfDay(minute)}\n </MenuItem>\n ))}\n </TextField>\n <TextField\n select\n size=\"small\"\n label=\"Until\"\n value={draft.window.endMinute}\n onChange={(event) =>\n setDraft({ ...draft, window: { ...draft.window, endMinute: Number(event.target.value) } })\n }\n >\n {MINUTE_OPTIONS.slice(1).map((minute) => (\n <MenuItem key={minute} value={minute}>\n {formatMinuteOfDay(minute)}\n </MenuItem>\n ))}\n </TextField>\n <Autocomplete\n size=\"small\"\n disableClearable\n options={timezoneOptions(mailbox.timezone)}\n value={draft.timezone}\n onChange={(_event, timezone) => setDraft({ ...draft, timezone: timezone ?? draft.timezone })}\n sx={{ minWidth: 240 }}\n renderInput={(params) => <TextField {...params} label=\"Timezone\" />}\n />\n </Stack>\n {'days' in windowCheck ? null : <FormHelperText error>{windowCheck.message}</FormHelperText>}\n </Box>\n {saveError ? <FormHelperText error>{saveError}</FormHelperText> : null}\n <Box>\n <Button variant=\"contained\" disabled={!dirty || invalid || saving} onClick={() => void save()}>\n {MAILBOX_ACTION_LABELS.save}\n </Button>\n </Box>\n </Stack>\n ) : (\n <Typography variant=\"body2\" color=\"text.secondary\">\n {`Sends as ${sendAsLabel(stored.sendAs)}, at most ${stored.dailyCap} a day, ` +\n `${stored.window.days.map((day) => OUTREACH_WEEKDAY_LABELS[day]).join(', ')} ` +\n `${formatMinuteOfDay(stored.window.startMinute)}–${formatMinuteOfDay(stored.window.endMinute)} ` +\n `(${stored.timezone}).`}\n </Typography>\n )}\n\n {isMine && !needsReconnect ? (\n <TextField\n label={MAILBOX_ACTION_LABELS.testAddress}\n value={testAddress}\n onChange={(event) => setTestAddress(event.target.value)}\n disabled={busy !== null}\n size=\"small\"\n type=\"email\"\n helperText={\n 'Leave empty to send the test to yourself. A test to an outside mailbox you can ' +\n 'read is the only one whose original source shows the sender authentication results.'\n }\n fullWidth\n />\n ) : null}\n\n {canManage || isMine ? (\n <Stack direction=\"row\" spacing={1} useFlexGap sx={{ flexWrap: 'wrap' }}>\n {canManage && !needsReconnect ? (\n <Button variant=\"outlined\" disabled={busy !== null} onClick={() => void togglePaused()}>\n {mailbox.status === 'paused' ? MAILBOX_ACTION_LABELS.resume : MAILBOX_ACTION_LABELS.pause}\n </Button>\n ) : null}\n {isMine && !needsReconnect ? (\n <Button variant=\"outlined\" disabled={busy !== null} onClick={() => void sendTest()}>\n {testAddress.trim() ? MAILBOX_ACTION_LABELS.testElsewhere : MAILBOX_ACTION_LABELS.test}\n </Button>\n ) : null}\n {canManage ? (\n <Button color=\"error\" disabled={busy !== null} onClick={() => void disconnect()}>\n {MAILBOX_ACTION_LABELS.disconnect}\n </Button>\n ) : null}\n </Stack>\n ) : null}\n </Stack>\n </CardDisplay>\n )\n}\nMailboxCard.displayName = 'MailboxCard'\n\nexport default MailboxCard\n"],"names":["pluginDocsHelp","CardDisplay","useConfirmationContext","useSnackbar","SenderReadinessPanel","Alert","Autocomplete","Box","Button","Chip","FormControlLabel","FormHelperText","MenuItem","Stack","Switch","TextField","ToggleButton","ToggleButtonGroup","Typography","useEffect","useMemo","useRef","useState","formatMinuteOfDay","isValidTimezone","OUTREACH_DEFAULT_WINDOW","OUTREACH_MAILBOX_STATUS_LABELS","OUTREACH_MAX_DAILY_CAP","OUTREACH_RAMP_STEPS","OUTREACH_WEEKDAY_LABELS","outreachEffectiveDailyCap","outreachLocalDay","summarizeMailboxHealth","validateDailyCap","validateDisplayName","validateSendWindow","outreachPacingNote","autoPauseSentence","mailbox","pause","autoPause","day","atMs","Intl","DateTimeFormat","dateStyle","timeZone","timezone","format","until","untilMs","message","MAILBOX_ACTION_LABELS","save","resume","test","testElsewhere","testAddress","warmUp","disconnect","reconnect","recheckReadiness","WEEKDAY_NAMES","STATUS_COLOR","connected","paused","reconnect_required","disconnected","MINUTE_OPTIONS","Array","from","length","_","index","timezoneOptions","current","supported","supportedValuesOf","zones","includes","RAMP_SENTENCE","map","step","week","limit","join","draftOf","sendAs","email","displayName","dailyCap","String","window","rampStartedAtMs","MailboxCard","props","isMine","canManage","api","onReconnect","reconnecting","nowMs","Date","now","enqueueSnackbar","confirm","microsoft","provider","providerName","draft","setDraft","saving","setSaving","saveError","setSaveError","busy","setBusy","setTestAddress","sendAsAddress","readiness","setReadiness","readinessBusy","setReadinessBusy","active","id","then","answer","catch","error","variant","allowDuplicate","stored","storedKey","JSON","stringify","seededFrom","dirty","previous","health","today","daily","testsToday","Math","max","Number","tests","answersToday","manualReplies","needsReconnect","status","capCheck","NaN","windowCheck","nameCheck","timezoneValid","invalid","todayLimit","saveSettings","mailboxId","togglePaused","setPaused","sendTest","to","trim","sent","undefined","sentTo","confirmed","title","description","confirmationText","confirmationButtonProps","color","revocation","persist","sendAsLabel","option","sendAsOptions","find","entry","header","subheader","help","anchor","contentGutterX","contentGutterY","HeaderProps","action","size","label","spacing","severity","disabled","onClick","role","hasSent","direction","sx","mt","bounces","replies","value","aria-label","component","slice","lastIndexOf","onSubmit","event","preventDefault","select","onChange","target","helperText","type","slotProps","htmlInput","min","control","checked","gutterBottom","days","_event","sort","a","b","xs","sm","startMinute","minute","endMinute","disableClearable","options","minWidth","renderInput","params","fullWidth","useFlexGap","flexWrap"],"mappings":"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"}