@aglyn/plugins-workflows 1.0.0-beta.179 → 1.0.0-beta.181
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +12 -11
- package/src/lib/components/automation-trigger-conditions.component.d.ts +43 -0
- package/src/lib/components/automation-trigger-conditions.component.js +189 -0
- package/src/lib/components/automation-trigger-conditions.component.js.map +1 -0
- package/src/lib/components/host-actions-card.component.js +27 -176
- package/src/lib/components/host-actions-card.component.js.map +1 -1
- package/src/lib/components/org-automation-editor.component.d.ts +51 -0
- package/src/lib/components/org-automation-editor.component.js +310 -0
- package/src/lib/components/org-automation-editor.component.js.map +1 -0
- package/src/lib/components/org-automations-card.component.d.ts +28 -0
- package/src/lib/components/org-automations-card.component.js +373 -0
- package/src/lib/components/org-automations-card.component.js.map +1 -0
- package/src/lib/components/org-site-automation-list.component.d.ts +43 -0
- package/src/lib/components/org-site-automation-list.component.js +289 -0
- package/src/lib/components/org-site-automation-list.component.js.map +1 -0
- package/src/lib/components/site-org-automations-panel.component.d.ts +22 -0
- package/src/lib/components/site-org-automations-panel.component.js +201 -0
- package/src/lib/components/site-org-automations-panel.component.js.map +1 -0
- package/src/lib/components/use-org-automation-step-pickers.d.ts +20 -0
- package/src/lib/components/use-org-automation-step-pickers.js +108 -0
- package/src/lib/components/use-org-automation-step-pickers.js.map +1 -0
- package/src/lib/components/use-org-automations-api.d.ts +16 -0
- package/src/lib/components/use-org-automations-api.js +55 -0
- package/src/lib/components/use-org-automations-api.js.map +1 -0
- package/src/lib/components/workflows-console-page.js +63 -1
- package/src/lib/components/workflows-console-page.js.map +1 -1
- package/src/lib/components/workflows-console-sections.d.ts +19 -1
- package/src/lib/components/workflows-console-sections.js +37 -2
- package/src/lib/components/workflows-console-sections.js.map +1 -1
- package/src/lib/components/workflows-org-mount.d.ts +52 -0
- package/src/lib/components/workflows-org-mount.js +49 -0
- package/src/lib/components/workflows-org-mount.js.map +1 -0
- package/src/lib/engine/flow-enrollments.d.ts +26 -10
- package/src/lib/engine/flow-enrollments.js +14 -7
- package/src/lib/engine/flow-enrollments.js.map +1 -1
- package/src/lib/engine/run-event-actions.d.ts +57 -4
- package/src/lib/engine/run-event-actions.js +119 -19
- package/src/lib/engine/run-event-actions.js.map +1 -1
- package/src/lib/engine/run-org-automations.d.ts +75 -0
- package/src/lib/engine/run-org-automations.js +154 -0
- package/src/lib/engine/run-org-automations.js.map +1 -0
- package/src/lib/model/org-automations.d.ts +232 -0
- package/src/lib/model/org-automations.js +423 -0
- package/src/lib/model/org-automations.js.map +1 -0
- package/src/lib/plugin.js +26 -1
- package/src/lib/plugin.js.map +1 -1
- package/src/lib/server/org-automations-routes.d.ts +88 -0
- package/src/lib/server/org-automations-routes.js +474 -0
- package/src/lib/server/org-automations-routes.js.map +1 -0
- package/src/lib/server-console.d.ts +2 -1
- package/src/lib/server-console.js +12 -2
- package/src/lib/server-console.js.map +1 -1
|
@@ -0,0 +1,289 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2026 Aglyn LLC
|
|
4
|
+
*
|
|
5
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
6
|
+
* you may not use this file except in compliance with the License.
|
|
7
|
+
* You may obtain a copy of the License at
|
|
8
|
+
*
|
|
9
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
10
|
+
*
|
|
11
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
12
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
13
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
14
|
+
* See the License for the specific language governing permissions and
|
|
15
|
+
* limitations under the License.
|
|
16
|
+
*/ 'use client';
|
|
17
|
+
import { _ as _extends } from "@swc/helpers/_/_extends";
|
|
18
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
19
|
+
import { hostEventLabel, pluginDocsHelp } from "@aglyn/aglyn";
|
|
20
|
+
import { AppLink, CardDisplay } from "@aglyn/shared-ui-jsx";
|
|
21
|
+
import { ScrollTable } from "@aglyn/shared-ui-jsx/components/scroll-table.component";
|
|
22
|
+
import { useFirestore, useFirestoreCollection } from "@aglyn/tenant-feature-instance";
|
|
23
|
+
/*
|
|
24
|
+
* The MODULE, not the barrel, for the two pure helpers — the cards' specs
|
|
25
|
+
* mock `@aglyn/tenant-feature-instance` wholesale, and a query builder
|
|
26
|
+
* imported through that barrel disappears under the mock.
|
|
27
|
+
*/ import { ceilingedWindow, collectionCeiling } from "@aglyn/tenant-feature-instance/hooks/host-collection-queries";
|
|
28
|
+
import { Alert, Button, Menu, MenuItem, Stack, TableBody, TableCell, TableHead, TableRow, Typography } from "@mui/material";
|
|
29
|
+
import { collection } from "firebase/firestore";
|
|
30
|
+
import { useState } from "react";
|
|
31
|
+
import { orgSiteAutomationPath } from "./workflows-org-mount.js";
|
|
32
|
+
/**
|
|
33
|
+
* How many sites a list opens with their rows read. The rest wait behind
|
|
34
|
+
* "Show more" — and, since each site's rows are read by the row group that
|
|
35
|
+
* shows them, are not read until then either.
|
|
36
|
+
*/ export const ORG_SITE_LIST_OPEN_SITES = 5;
|
|
37
|
+
/**
|
|
38
|
+
* The most sites one list will read, however many the organization has —
|
|
39
|
+
* the platform's per-scan site bound. Past it the list says so and each
|
|
40
|
+
* site's own hub is the way in.
|
|
41
|
+
*/ export const ORG_SITE_LIST_MAX_SITES = 25;
|
|
42
|
+
/**
|
|
43
|
+
* Rows read per site. A ceiling with a probe row, not a page: the org list is
|
|
44
|
+
* an index of where things are, and each site's own hub holds the full,
|
|
45
|
+
* editable list the row links to.
|
|
46
|
+
*/ export const ORG_SITE_LIST_ROWS = 10;
|
|
47
|
+
/** A trigger bound to one element, which makes an `actions` row an interaction. */ const LEAF_SELECTOR = /^\[data-aglyn="leaf:.+"\]$/;
|
|
48
|
+
const COPY = {
|
|
49
|
+
workflows: {
|
|
50
|
+
header: 'Workflows on every site',
|
|
51
|
+
noun: 'workflow',
|
|
52
|
+
plural: 'workflows',
|
|
53
|
+
intro: 'Every site’s workflows, side by side. A workflow calls its own site’s ' + 'functions and variables, so it is built and edited in that site’s ' + 'Automation.'
|
|
54
|
+
},
|
|
55
|
+
actions: {
|
|
56
|
+
header: 'Actions on every site',
|
|
57
|
+
noun: 'action',
|
|
58
|
+
plural: 'actions',
|
|
59
|
+
intro: 'Every site’s own actions, side by side. To run one automation on ' + 'several sites, make it an org automation instead.'
|
|
60
|
+
},
|
|
61
|
+
webhooks: {
|
|
62
|
+
header: 'Webhooks on every site',
|
|
63
|
+
noun: 'webhook',
|
|
64
|
+
plural: 'webhooks',
|
|
65
|
+
intro: 'Every site’s webhooks, side by side. A webhook holds its site’s ' + 'address and secret, so it is managed in that site’s Automation.'
|
|
66
|
+
}
|
|
67
|
+
};
|
|
68
|
+
/**
|
|
69
|
+
* EVERY SITE'S WORKFLOWS, ACTIONS OR WEBHOOKS, on the org hub (AGL-3302).
|
|
70
|
+
*
|
|
71
|
+
* Read-only and bounded: one ceilinged read per open site, the first
|
|
72
|
+
* {@link ORG_SITE_LIST_OPEN_SITES} sites on arrival and up to
|
|
73
|
+
* {@link ORG_SITE_LIST_MAX_SITES} when asked, each row naming its site and
|
|
74
|
+
* linking into that site's own Automation hub, where the thing is edited.
|
|
75
|
+
* "Add" asks which site and goes there.
|
|
76
|
+
*
|
|
77
|
+
* `canRead` gates the webhooks list: a webhook holds its site's secret and
|
|
78
|
+
* the rules admit only a site's admins and editors, so a reader who is
|
|
79
|
+
* neither is told so rather than handed listeners that would be refused.
|
|
80
|
+
*/ export function OrgSiteAutomationList(props) {
|
|
81
|
+
const { mount, kind, canRead } = props;
|
|
82
|
+
const copy = COPY[kind];
|
|
83
|
+
const [opened, setOpened] = useState(false);
|
|
84
|
+
const [addAnchor, setAddAnchor] = useState(null);
|
|
85
|
+
const reachable = mount.hosts.slice(0, ORG_SITE_LIST_MAX_SITES);
|
|
86
|
+
const shown = opened ? reachable : reachable.slice(0, ORG_SITE_LIST_OPEN_SITES);
|
|
87
|
+
const folded = reachable.length - shown.length;
|
|
88
|
+
const linkable = mount.hosts.filter((host)=>orgSiteAutomationPath(mount, host.id, kind));
|
|
89
|
+
return /*#__PURE__*/ _jsxs(CardDisplay, {
|
|
90
|
+
header: copy.header,
|
|
91
|
+
help: pluginDocsHelp('orgAutomations', {
|
|
92
|
+
anchor: '#every-sites-own-automations'
|
|
93
|
+
}),
|
|
94
|
+
contentGutterX: true,
|
|
95
|
+
contentGutterY: true,
|
|
96
|
+
children: [
|
|
97
|
+
/*#__PURE__*/ _jsxs(Stack, {
|
|
98
|
+
spacing: 1.5,
|
|
99
|
+
children: [
|
|
100
|
+
/*#__PURE__*/ _jsx(Typography, {
|
|
101
|
+
variant: "body2",
|
|
102
|
+
color: "text.secondary",
|
|
103
|
+
children: copy.intro
|
|
104
|
+
}),
|
|
105
|
+
!canRead ? /*#__PURE__*/ _jsx(Alert, {
|
|
106
|
+
severity: "info",
|
|
107
|
+
children: `Each site’s ${copy.plural} are listed for its admins and editors.`
|
|
108
|
+
}) : !mount.hostsReady ? /*#__PURE__*/ _jsx(Typography, {
|
|
109
|
+
variant: "caption",
|
|
110
|
+
color: "text.secondary",
|
|
111
|
+
children: '…'
|
|
112
|
+
}) : !mount.hosts.length ? /*#__PURE__*/ _jsx(Typography, {
|
|
113
|
+
variant: "body2",
|
|
114
|
+
color: "text.secondary",
|
|
115
|
+
children: 'This organization has no sites yet.'
|
|
116
|
+
}) : /*#__PURE__*/ _jsxs(_Fragment, {
|
|
117
|
+
children: [
|
|
118
|
+
/*#__PURE__*/ _jsxs(ScrollTable, {
|
|
119
|
+
size: "small",
|
|
120
|
+
"aria-label": copy.header,
|
|
121
|
+
children: [
|
|
122
|
+
/*#__PURE__*/ _jsx(TableHead, {
|
|
123
|
+
children: /*#__PURE__*/ _jsxs(TableRow, {
|
|
124
|
+
children: [
|
|
125
|
+
/*#__PURE__*/ _jsx(TableCell, {
|
|
126
|
+
children: 'Name'
|
|
127
|
+
}),
|
|
128
|
+
/*#__PURE__*/ _jsx(TableCell, {
|
|
129
|
+
children: 'Site'
|
|
130
|
+
}),
|
|
131
|
+
/*#__PURE__*/ _jsx(TableCell, {
|
|
132
|
+
children: kind === 'webhooks' ? 'Direction' : 'Trigger'
|
|
133
|
+
}),
|
|
134
|
+
/*#__PURE__*/ _jsx(TableCell, {
|
|
135
|
+
children: 'Status'
|
|
136
|
+
})
|
|
137
|
+
]
|
|
138
|
+
})
|
|
139
|
+
}),
|
|
140
|
+
/*#__PURE__*/ _jsx(TableBody, {
|
|
141
|
+
children: shown.map((host)=>/*#__PURE__*/ _jsx(SiteRows, {
|
|
142
|
+
mount: mount,
|
|
143
|
+
host: host,
|
|
144
|
+
kind: kind
|
|
145
|
+
}, host.id))
|
|
146
|
+
})
|
|
147
|
+
]
|
|
148
|
+
}),
|
|
149
|
+
folded > 0 ? /*#__PURE__*/ _jsx(Button, {
|
|
150
|
+
size: "small",
|
|
151
|
+
variant: "text",
|
|
152
|
+
onClick: ()=>setOpened(true),
|
|
153
|
+
sx: {
|
|
154
|
+
alignSelf: 'flex-start'
|
|
155
|
+
},
|
|
156
|
+
children: `Show ${folded} more ${folded === 1 ? 'site' : 'sites'}`
|
|
157
|
+
}) : null,
|
|
158
|
+
mount.hosts.length > ORG_SITE_LIST_MAX_SITES ? /*#__PURE__*/ _jsx(Alert, {
|
|
159
|
+
severity: "info",
|
|
160
|
+
children: `Listing the first ${ORG_SITE_LIST_MAX_SITES} sites. Open a ` + `site’s own Automation for the ${copy.plural} of the rest.`
|
|
161
|
+
}) : null
|
|
162
|
+
]
|
|
163
|
+
}),
|
|
164
|
+
linkable.length ? /*#__PURE__*/ _jsx(Stack, {
|
|
165
|
+
direction: "row",
|
|
166
|
+
spacing: 1,
|
|
167
|
+
sx: {
|
|
168
|
+
alignSelf: 'flex-start'
|
|
169
|
+
},
|
|
170
|
+
children: /*#__PURE__*/ _jsx(Button, {
|
|
171
|
+
size: "small",
|
|
172
|
+
color: "primary",
|
|
173
|
+
"aria-haspopup": "menu",
|
|
174
|
+
onClick: (event)=>setAddAnchor(event.currentTarget),
|
|
175
|
+
children: `Add ${copy.noun} on a site`
|
|
176
|
+
})
|
|
177
|
+
}) : null
|
|
178
|
+
]
|
|
179
|
+
}),
|
|
180
|
+
/*#__PURE__*/ _jsx(Menu, {
|
|
181
|
+
anchorEl: addAnchor,
|
|
182
|
+
open: Boolean(addAnchor),
|
|
183
|
+
onClose: ()=>setAddAnchor(null),
|
|
184
|
+
children: linkable.map((host)=>{
|
|
185
|
+
var _orgSiteAutomationPath;
|
|
186
|
+
return /*#__PURE__*/ _jsx(MenuItem, _extends({
|
|
187
|
+
component: AppLink
|
|
188
|
+
}, {
|
|
189
|
+
componentVariant: 'naked'
|
|
190
|
+
}, {
|
|
191
|
+
href: (_orgSiteAutomationPath = orgSiteAutomationPath(mount, host.id, kind)) != null ? _orgSiteAutomationPath : '',
|
|
192
|
+
onClick: ()=>setAddAnchor(null),
|
|
193
|
+
children: host.name || host.subdomain || host.id
|
|
194
|
+
}), host.id);
|
|
195
|
+
})
|
|
196
|
+
})
|
|
197
|
+
]
|
|
198
|
+
});
|
|
199
|
+
}
|
|
200
|
+
OrgSiteAutomationList.displayName = 'OrgSiteAutomationList';
|
|
201
|
+
/** How a row's trigger or direction reads. */ function rowTrigger(kind, row) {
|
|
202
|
+
var _row_trigger;
|
|
203
|
+
if (kind === 'webhooks') {
|
|
204
|
+
return (row == null ? void 0 : row.direction) === 'inbound' ? 'Inbound' : 'Outbound';
|
|
205
|
+
}
|
|
206
|
+
const event = row == null ? void 0 : (_row_trigger = row.trigger) == null ? void 0 : _row_trigger.event;
|
|
207
|
+
if (!event) return kind === 'workflows' ? 'Run by other automations' : '—';
|
|
208
|
+
return hostEventLabel(event);
|
|
209
|
+
}
|
|
210
|
+
/** How a row's status reads. */ function rowStatus(kind, row) {
|
|
211
|
+
if (kind === 'workflows') return 'Ready';
|
|
212
|
+
return (row == null ? void 0 : row.enabled) === false ? 'Off' : 'On';
|
|
213
|
+
}
|
|
214
|
+
/**
|
|
215
|
+
* One site's rows: its own ceilinged read, drawn as table rows naming the
|
|
216
|
+
* site. A site with none draws nothing; one past the ceiling says so in a row
|
|
217
|
+
* that links to where the rest are.
|
|
218
|
+
*/ function SiteRows(props) {
|
|
219
|
+
const { mount, host, kind } = props;
|
|
220
|
+
const firestore = useFirestore();
|
|
221
|
+
const { data } = useFirestoreCollection(()=>collectionCeiling(collection(firestore, 'hosts', host.id, kind), ORG_SITE_LIST_ROWS), [
|
|
222
|
+
firestore,
|
|
223
|
+
host.id,
|
|
224
|
+
kind
|
|
225
|
+
], {
|
|
226
|
+
idField: '$id'
|
|
227
|
+
});
|
|
228
|
+
const { rows, truncated } = ceilingedWindow(data, ORG_SITE_LIST_ROWS);
|
|
229
|
+
const live = (rows != null ? rows : []).filter((row)=>{
|
|
230
|
+
var _ref;
|
|
231
|
+
var _row_trigger;
|
|
232
|
+
return !row.deletedAt && // An element interaction belongs to its page, not to the site's
|
|
233
|
+
// automation list — the site's own Actions card counts rather than
|
|
234
|
+
// lists them, and so does this.
|
|
235
|
+
!(kind === 'actions' && LEAF_SELECTOR.test(String((_ref = row == null ? void 0 : (_row_trigger = row.trigger) == null ? void 0 : _row_trigger.selector) != null ? _ref : '')));
|
|
236
|
+
});
|
|
237
|
+
const siteName = host.name || host.subdomain || host.id;
|
|
238
|
+
const href = orgSiteAutomationPath(mount, host.id, kind);
|
|
239
|
+
const site = href ? /*#__PURE__*/ _jsx(AppLink, {
|
|
240
|
+
href: href,
|
|
241
|
+
underline: "hover",
|
|
242
|
+
children: siteName
|
|
243
|
+
}) : siteName;
|
|
244
|
+
return /*#__PURE__*/ _jsxs(_Fragment, {
|
|
245
|
+
children: [
|
|
246
|
+
live.map((row)=>/*#__PURE__*/ _jsxs(TableRow, {
|
|
247
|
+
children: [
|
|
248
|
+
/*#__PURE__*/ _jsx(TableCell, {
|
|
249
|
+
children: href ? /*#__PURE__*/ _jsx(AppLink, {
|
|
250
|
+
href: href,
|
|
251
|
+
underline: "hover",
|
|
252
|
+
children: String(row.name || row.$id)
|
|
253
|
+
}) : String(row.name || row.$id)
|
|
254
|
+
}),
|
|
255
|
+
/*#__PURE__*/ _jsx(TableCell, {
|
|
256
|
+
children: site
|
|
257
|
+
}),
|
|
258
|
+
/*#__PURE__*/ _jsx(TableCell, {
|
|
259
|
+
children: rowTrigger(kind, row)
|
|
260
|
+
}),
|
|
261
|
+
/*#__PURE__*/ _jsx(TableCell, {
|
|
262
|
+
children: rowStatus(kind, row)
|
|
263
|
+
})
|
|
264
|
+
]
|
|
265
|
+
}, `${host.id}/${row.$id}`)),
|
|
266
|
+
truncated ? /*#__PURE__*/ _jsx(TableRow, {
|
|
267
|
+
children: /*#__PURE__*/ _jsx(TableCell, {
|
|
268
|
+
colSpan: 4,
|
|
269
|
+
children: /*#__PURE__*/ _jsxs(Typography, {
|
|
270
|
+
variant: "caption",
|
|
271
|
+
color: "text.secondary",
|
|
272
|
+
children: [
|
|
273
|
+
`${siteName} has more than ${ORG_SITE_LIST_ROWS} — `,
|
|
274
|
+
href ? /*#__PURE__*/ _jsx(AppLink, {
|
|
275
|
+
href: href,
|
|
276
|
+
underline: "hover",
|
|
277
|
+
children: 'open the site to see them all'
|
|
278
|
+
}) : 'open the site to see them all'
|
|
279
|
+
]
|
|
280
|
+
})
|
|
281
|
+
})
|
|
282
|
+
}) : null
|
|
283
|
+
]
|
|
284
|
+
});
|
|
285
|
+
}
|
|
286
|
+
SiteRows.displayName = 'SiteRows';
|
|
287
|
+
export default OrgSiteAutomationList;
|
|
288
|
+
|
|
289
|
+
//# sourceMappingURL=org-site-automation-list.component.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../../../../../libs/plugins/workflows/src/lib/components/org-site-automation-list.component.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 type { ConsolePluginOrgHost } from '@aglyn/aglyn'\nimport { hostEventLabel, pluginDocsHelp } from '@aglyn/aglyn'\nimport { AppLink, CardDisplay } from '@aglyn/shared-ui-jsx'\nimport { ScrollTable } from '@aglyn/shared-ui-jsx/components/scroll-table.component'\nimport {\n useFirestore,\n useFirestoreCollection,\n} from '@aglyn/tenant-feature-instance'\n/*\n * The MODULE, not the barrel, for the two pure helpers — the cards' specs\n * mock `@aglyn/tenant-feature-instance` wholesale, and a query builder\n * imported through that barrel disappears under the mock.\n */\nimport {\n ceilingedWindow,\n collectionCeiling,\n} from '@aglyn/tenant-feature-instance/hooks/host-collection-queries'\nimport {\n Alert,\n Button,\n Menu,\n MenuItem,\n Stack,\n TableBody,\n TableCell,\n TableHead,\n TableRow,\n Typography,\n} from '@mui/material'\nimport { collection } from 'firebase/firestore'\nimport { useState } from 'react'\nimport {\n orgSiteAutomationPath,\n type WorkflowsOrgMount,\n} from './workflows-org-mount'\n\n/** The three site collections the org hub lists across its sites. */\nexport type OrgSiteAutomationKind = 'workflows' | 'actions' | 'webhooks'\n\n/**\n * How many sites a list opens with their rows read. The rest wait behind\n * \"Show more\" — and, since each site's rows are read by the row group that\n * shows them, are not read until then either.\n */\nexport const ORG_SITE_LIST_OPEN_SITES = 5\n\n/**\n * The most sites one list will read, however many the organization has —\n * the platform's per-scan site bound. Past it the list says so and each\n * site's own hub is the way in.\n */\nexport const ORG_SITE_LIST_MAX_SITES = 25\n\n/**\n * Rows read per site. A ceiling with a probe row, not a page: the org list is\n * an index of where things are, and each site's own hub holds the full,\n * editable list the row links to.\n */\nexport const ORG_SITE_LIST_ROWS = 10\n\n/** A trigger bound to one element, which makes an `actions` row an interaction. */\nconst LEAF_SELECTOR = /^\\[data-aglyn=\"leaf:.+\"\\]$/\n\nconst COPY: Record<\n OrgSiteAutomationKind,\n { header: string; noun: string; plural: string; intro: string }\n> = {\n workflows: {\n header: 'Workflows on every site',\n noun: 'workflow',\n plural: 'workflows',\n intro:\n 'Every site’s workflows, side by side. A workflow calls its own site’s ' +\n 'functions and variables, so it is built and edited in that site’s ' +\n 'Automation.',\n },\n actions: {\n header: 'Actions on every site',\n noun: 'action',\n plural: 'actions',\n intro:\n 'Every site’s own actions, side by side. To run one automation on ' +\n 'several sites, make it an org automation instead.',\n },\n webhooks: {\n header: 'Webhooks on every site',\n noun: 'webhook',\n plural: 'webhooks',\n intro:\n 'Every site’s webhooks, side by side. A webhook holds its site’s ' +\n 'address and secret, so it is managed in that site’s Automation.',\n },\n}\n\n/**\n * EVERY SITE'S WORKFLOWS, ACTIONS OR WEBHOOKS, on the org hub (AGL-3302).\n *\n * Read-only and bounded: one ceilinged read per open site, the first\n * {@link ORG_SITE_LIST_OPEN_SITES} sites on arrival and up to\n * {@link ORG_SITE_LIST_MAX_SITES} when asked, each row naming its site and\n * linking into that site's own Automation hub, where the thing is edited.\n * \"Add\" asks which site and goes there.\n *\n * `canRead` gates the webhooks list: a webhook holds its site's secret and\n * the rules admit only a site's admins and editors, so a reader who is\n * neither is told so rather than handed listeners that would be refused.\n */\nexport function OrgSiteAutomationList(props: {\n mount: WorkflowsOrgMount\n kind: OrgSiteAutomationKind\n canRead: boolean\n}) {\n const { mount, kind, canRead } = props\n const copy = COPY[kind]\n const [opened, setOpened] = useState(false)\n const [addAnchor, setAddAnchor] = useState<HTMLElement | null>(null)\n const reachable = mount.hosts.slice(0, ORG_SITE_LIST_MAX_SITES)\n const shown = opened\n ? reachable\n : reachable.slice(0, ORG_SITE_LIST_OPEN_SITES)\n const folded = reachable.length - shown.length\n const linkable = mount.hosts.filter((host) =>\n orgSiteAutomationPath(mount, host.id, kind),\n )\n return (\n <CardDisplay\n header={copy.header}\n help={pluginDocsHelp('orgAutomations', {\n anchor: '#every-sites-own-automations',\n })}\n contentGutterX\n contentGutterY\n >\n <Stack spacing={1.5}>\n <Typography variant=\"body2\" color=\"text.secondary\">\n {copy.intro}\n </Typography>\n {!canRead ? (\n <Alert severity=\"info\">\n {`Each site’s ${copy.plural} are listed for its admins and editors.`}\n </Alert>\n ) : !mount.hostsReady ? (\n <Typography variant=\"caption\" color=\"text.secondary\">\n {'…'}\n </Typography>\n ) : !mount.hosts.length ? (\n <Typography variant=\"body2\" color=\"text.secondary\">\n {'This organization has no sites yet.'}\n </Typography>\n ) : (\n <>\n <ScrollTable size=\"small\" aria-label={copy.header}>\n <TableHead>\n <TableRow>\n <TableCell>{'Name'}</TableCell>\n <TableCell>{'Site'}</TableCell>\n <TableCell>\n {kind === 'webhooks' ? 'Direction' : 'Trigger'}\n </TableCell>\n <TableCell>{'Status'}</TableCell>\n </TableRow>\n </TableHead>\n <TableBody>\n {shown.map((host) => (\n <SiteRows key={host.id} mount={mount} host={host} kind={kind} />\n ))}\n </TableBody>\n </ScrollTable>\n {folded > 0 ? (\n <Button\n size=\"small\"\n variant=\"text\"\n onClick={() => setOpened(true)}\n sx={{ alignSelf: 'flex-start' }}\n >\n {`Show ${folded} more ${folded === 1 ? 'site' : 'sites'}`}\n </Button>\n ) : null}\n {mount.hosts.length > ORG_SITE_LIST_MAX_SITES ? (\n <Alert severity=\"info\">\n {`Listing the first ${ORG_SITE_LIST_MAX_SITES} sites. Open a ` +\n `site’s own Automation for the ${copy.plural} of the rest.`}\n </Alert>\n ) : null}\n </>\n )}\n {linkable.length ? (\n <Stack direction=\"row\" spacing={1} sx={{ alignSelf: 'flex-start' }}>\n <Button\n size=\"small\"\n color=\"primary\"\n aria-haspopup=\"menu\"\n onClick={(event) => setAddAnchor(event.currentTarget)}\n >\n {`Add ${copy.noun} on a site`}\n </Button>\n </Stack>\n ) : null}\n </Stack>\n <Menu\n anchorEl={addAnchor}\n open={Boolean(addAnchor)}\n onClose={() => setAddAnchor(null)}\n >\n {linkable.map((host) => (\n <MenuItem\n key={host.id}\n component={AppLink as any}\n {...({ componentVariant: 'naked' } as any)}\n href={orgSiteAutomationPath(mount, host.id, kind) ?? ''}\n onClick={() => setAddAnchor(null)}\n >\n {host.name || host.subdomain || host.id}\n </MenuItem>\n ))}\n </Menu>\n </CardDisplay>\n )\n}\nOrgSiteAutomationList.displayName = 'OrgSiteAutomationList'\n\n/** How a row's trigger or direction reads. */\nfunction rowTrigger(kind: OrgSiteAutomationKind, row: any): string {\n if (kind === 'webhooks') {\n return row?.direction === 'inbound' ? 'Inbound' : 'Outbound'\n }\n const event = row?.trigger?.event\n if (!event) return kind === 'workflows' ? 'Run by other automations' : '—'\n return hostEventLabel(event)\n}\n\n/** How a row's status reads. */\nfunction rowStatus(kind: OrgSiteAutomationKind, row: any): string {\n if (kind === 'workflows') return 'Ready'\n return row?.enabled === false ? 'Off' : 'On'\n}\n\n/**\n * One site's rows: its own ceilinged read, drawn as table rows naming the\n * site. A site with none draws nothing; one past the ceiling says so in a row\n * that links to where the rest are.\n */\nfunction SiteRows(props: {\n mount: WorkflowsOrgMount\n host: ConsolePluginOrgHost\n kind: OrgSiteAutomationKind\n}) {\n const { mount, host, kind } = props\n const firestore = useFirestore()\n const { data } = useFirestoreCollection<any>(\n () =>\n collectionCeiling(\n collection(firestore, 'hosts', host.id, kind),\n ORG_SITE_LIST_ROWS,\n ),\n [firestore, host.id, kind],\n { idField: '$id' },\n )\n const { rows, truncated } = ceilingedWindow<any>(data, ORG_SITE_LIST_ROWS)\n const live = (rows ?? []).filter(\n (row: any) =>\n !row.deletedAt &&\n // An element interaction belongs to its page, not to the site's\n // automation list — the site's own Actions card counts rather than\n // lists them, and so does this.\n !(kind === 'actions' && LEAF_SELECTOR.test(String(row?.trigger?.selector ?? ''))),\n )\n const siteName = host.name || host.subdomain || host.id\n const href = orgSiteAutomationPath(mount, host.id, kind)\n const site = href ? (\n <AppLink href={href} underline=\"hover\">\n {siteName}\n </AppLink>\n ) : (\n siteName\n )\n return (\n <>\n {live.map((row: any) => (\n <TableRow key={`${host.id}/${row.$id}`}>\n <TableCell>\n {href ? (\n <AppLink href={href} underline=\"hover\">\n {String(row.name || row.$id)}\n </AppLink>\n ) : (\n String(row.name || row.$id)\n )}\n </TableCell>\n <TableCell>{site}</TableCell>\n <TableCell>{rowTrigger(kind, row)}</TableCell>\n <TableCell>{rowStatus(kind, row)}</TableCell>\n </TableRow>\n ))}\n {truncated ? (\n <TableRow>\n <TableCell colSpan={4}>\n <Typography variant=\"caption\" color=\"text.secondary\">\n {`${siteName} has more than ${ORG_SITE_LIST_ROWS} — `}\n {href ? (\n <AppLink href={href} underline=\"hover\">\n {'open the site to see them all'}\n </AppLink>\n ) : (\n 'open the site to see them all'\n )}\n </Typography>\n </TableCell>\n </TableRow>\n ) : null}\n </>\n )\n}\nSiteRows.displayName = 'SiteRows'\n\nexport default OrgSiteAutomationList\n"],"names":["hostEventLabel","pluginDocsHelp","AppLink","CardDisplay","ScrollTable","useFirestore","useFirestoreCollection","ceilingedWindow","collectionCeiling","Alert","Button","Menu","MenuItem","Stack","TableBody","TableCell","TableHead","TableRow","Typography","collection","useState","orgSiteAutomationPath","ORG_SITE_LIST_OPEN_SITES","ORG_SITE_LIST_MAX_SITES","ORG_SITE_LIST_ROWS","LEAF_SELECTOR","COPY","workflows","header","noun","plural","intro","actions","webhooks","OrgSiteAutomationList","props","mount","kind","canRead","copy","opened","setOpened","addAnchor","setAddAnchor","reachable","hosts","slice","shown","folded","length","linkable","filter","host","id","help","anchor","contentGutterX","contentGutterY","spacing","variant","color","severity","hostsReady","size","aria-label","map","SiteRows","onClick","sx","alignSelf","direction","aria-haspopup","event","currentTarget","anchorEl","open","Boolean","onClose","component","componentVariant","href","name","subdomain","displayName","rowTrigger","row","trigger","rowStatus","enabled","firestore","data","idField","rows","truncated","live","deletedAt","test","String","selector","siteName","site","underline","$id","colSpan"],"mappings":"AAAA;;;;;;;;;;;;;;;CAeC,GACD;;;AAGA,SAASA,cAAc,EAAEC,cAAc,QAAQ,eAAc;AAC7D,SAASC,OAAO,EAAEC,WAAW,QAAQ,uBAAsB;AAC3D,SAASC,WAAW,QAAQ,yDAAwD;AACpF,SACEC,YAAY,EACZC,sBAAsB,QACjB,iCAAgC;AACvC;;;;CAIC,GACD,SACEC,eAAe,EACfC,iBAAiB,QACZ,+DAA8D;AACrE,SACEC,KAAK,EACLC,MAAM,EACNC,IAAI,EACJC,QAAQ,EACRC,KAAK,EACLC,SAAS,EACTC,SAAS,EACTC,SAAS,EACTC,QAAQ,EACRC,UAAU,QACL,gBAAe;AACtB,SAASC,UAAU,QAAQ,qBAAoB;AAC/C,SAASC,QAAQ,QAAQ,QAAO;AAChC,SACEC,qBAAqB,QAEhB,2BAAuB;AAK9B;;;;CAIC,GACD,OAAO,MAAMC,2BAA2B,EAAC;AAEzC;;;;CAIC,GACD,OAAO,MAAMC,0BAA0B,GAAE;AAEzC;;;;CAIC,GACD,OAAO,MAAMC,qBAAqB,GAAE;AAEpC,iFAAiF,GACjF,MAAMC,gBAAgB;AAEtB,MAAMC,OAGF;IACFC,WAAW;QACTC,QAAQ;QACRC,MAAM;QACNC,QAAQ;QACRC,OACE,2EACA,uEACA;IACJ;IACAC,SAAS;QACPJ,QAAQ;QACRC,MAAM;QACNC,QAAQ;QACRC,OACE,sEACA;IACJ;IACAE,UAAU;QACRL,QAAQ;QACRC,MAAM;QACNC,QAAQ;QACRC,OACE,qEACA;IACJ;AACF;AAEA;;;;;;;;;;;;CAYC,GACD,OAAO,SAASG,sBAAsBC,KAIrC;IACC,MAAM,EAAEC,KAAK,EAAEC,IAAI,EAAEC,OAAO,EAAE,GAAGH;IACjC,MAAMI,OAAOb,IAAI,CAACW,KAAK;IACvB,MAAM,CAACG,QAAQC,UAAU,GAAGrB,SAAS;IACrC,MAAM,CAACsB,WAAWC,aAAa,GAAGvB,SAA6B;IAC/D,MAAMwB,YAAYR,MAAMS,KAAK,CAACC,KAAK,CAAC,GAAGvB;IACvC,MAAMwB,QAAQP,SACVI,YACAA,UAAUE,KAAK,CAAC,GAAGxB;IACvB,MAAM0B,SAASJ,UAAUK,MAAM,GAAGF,MAAME,MAAM;IAC9C,MAAMC,WAAWd,MAAMS,KAAK,CAACM,MAAM,CAAC,CAACC,OACnC/B,sBAAsBe,OAAOgB,KAAKC,EAAE,EAAEhB;IAExC,qBACE,MAAClC;QACCyB,QAAQW,KAAKX,MAAM;QACnB0B,MAAMrD,eAAe,kBAAkB;YACrCsD,QAAQ;QACV;QACAC,cAAc;QACdC,cAAc;;0BAEd,MAAC5C;gBAAM6C,SAAS;;kCACd,KAACxC;wBAAWyC,SAAQ;wBAAQC,OAAM;kCAC/BrB,KAAKR,KAAK;;oBAEZ,CAACO,wBACA,KAAC7B;wBAAMoD,UAAS;kCACb,CAAC,YAAY,EAAEtB,KAAKT,MAAM,CAAC,uCAAuC,CAAC;yBAEpE,CAACM,MAAM0B,UAAU,iBACnB,KAAC5C;wBAAWyC,SAAQ;wBAAUC,OAAM;kCACjC;yBAED,CAACxB,MAAMS,KAAK,CAACI,MAAM,iBACrB,KAAC/B;wBAAWyC,SAAQ;wBAAQC,OAAM;kCAC/B;uCAGH;;0CACE,MAACxD;gCAAY2D,MAAK;gCAAQC,cAAYzB,KAAKX,MAAM;;kDAC/C,KAACZ;kDACC,cAAA,MAACC;;8DACC,KAACF;8DAAW;;8DACZ,KAACA;8DAAW;;8DACZ,KAACA;8DACEsB,SAAS,aAAa,cAAc;;8DAEvC,KAACtB;8DAAW;;;;;kDAGhB,KAACD;kDACEiC,MAAMkB,GAAG,CAAC,CAACb,qBACV,KAACc;gDAAuB9B,OAAOA;gDAAOgB,MAAMA;gDAAMf,MAAMA;+CAAzCe,KAAKC,EAAE;;;;4BAI3BL,SAAS,kBACR,KAACtC;gCACCqD,MAAK;gCACLJ,SAAQ;gCACRQ,SAAS,IAAM1B,UAAU;gCACzB2B,IAAI;oCAAEC,WAAW;gCAAa;0CAE7B,CAAC,KAAK,EAAErB,OAAO,MAAM,EAAEA,WAAW,IAAI,SAAS,SAAS;iCAEzD;4BACHZ,MAAMS,KAAK,CAACI,MAAM,GAAG1B,wCACpB,KAACd;gCAAMoD,UAAS;0CACb,CAAC,kBAAkB,EAAEtC,wBAAwB,eAAe,CAAC,GAC5D,CAAC,8BAA8B,EAAEgB,KAAKT,MAAM,CAAC,aAAa,CAAC;iCAE7D;;;oBAGPoB,SAASD,MAAM,iBACd,KAACpC;wBAAMyD,WAAU;wBAAMZ,SAAS;wBAAGU,IAAI;4BAAEC,WAAW;wBAAa;kCAC/D,cAAA,KAAC3D;4BACCqD,MAAK;4BACLH,OAAM;4BACNW,iBAAc;4BACdJ,SAAS,CAACK,QAAU7B,aAAa6B,MAAMC,aAAa;sCAEnD,CAAC,IAAI,EAAElC,KAAKV,IAAI,CAAC,UAAU,CAAC;;yBAG/B;;;0BAEN,KAAClB;gBACC+D,UAAUhC;gBACViC,MAAMC,QAAQlC;gBACdmC,SAAS,IAAMlC,aAAa;0BAE3BO,SAASe,GAAG,CAAC,CAACb;wBAKL/B;yCAJR,KAACT;wBAECkE,WAAW5E;uBACN;wBAAE6E,kBAAkB;oBAAQ;wBACjCC,IAAI,GAAE3D,yBAAAA,sBAAsBe,OAAOgB,KAAKC,EAAE,EAAEhB,iBAAtChB,yBAA+C;wBACrD8C,SAAS,IAAMxB,aAAa;kCAE3BS,KAAK6B,IAAI,IAAI7B,KAAK8B,SAAS,IAAI9B,KAAKC,EAAE;wBANlCD,KAAKC,EAAE;;;;;AAYxB;AACAnB,sBAAsBiD,WAAW,GAAG;AAEpC,4CAA4C,GAC5C,SAASC,WAAW/C,IAA2B,EAAEgD,GAAQ;QAIzCA;IAHd,IAAIhD,SAAS,YAAY;QACvB,OAAOgD,CAAAA,uBAAAA,IAAKf,SAAS,MAAK,YAAY,YAAY;IACpD;IACA,MAAME,QAAQa,wBAAAA,eAAAA,IAAKC,OAAO,qBAAZD,aAAcb,KAAK;IACjC,IAAI,CAACA,OAAO,OAAOnC,SAAS,cAAc,6BAA6B;IACvE,OAAOrC,eAAewE;AACxB;AAEA,8BAA8B,GAC9B,SAASe,UAAUlD,IAA2B,EAAEgD,GAAQ;IACtD,IAAIhD,SAAS,aAAa,OAAO;IACjC,OAAOgD,CAAAA,uBAAAA,IAAKG,OAAO,MAAK,QAAQ,QAAQ;AAC1C;AAEA;;;;CAIC,GACD,SAAStB,SAAS/B,KAIjB;IACC,MAAM,EAAEC,KAAK,EAAEgB,IAAI,EAAEf,IAAI,EAAE,GAAGF;IAC9B,MAAMsD,YAAYpF;IAClB,MAAM,EAAEqF,IAAI,EAAE,GAAGpF,uBACf,IACEE,kBACEW,WAAWsE,WAAW,SAASrC,KAAKC,EAAE,EAAEhB,OACxCb,qBAEJ;QAACiE;QAAWrC,KAAKC,EAAE;QAAEhB;KAAK,EAC1B;QAAEsD,SAAS;IAAM;IAEnB,MAAM,EAAEC,IAAI,EAAEC,SAAS,EAAE,GAAGtF,gBAAqBmF,MAAMlE;IACvD,MAAMsE,OAAO,CAACF,eAAAA,OAAQ,EAAE,EAAEzC,MAAM,CAC9B,CAACkC;;YAKmDA;eAJlD,CAACA,IAAIU,SAAS,IACd,gEAAgE;QAChE,mEAAmE;QACnE,gCAAgC;QAChC,CAAE1D,CAAAA,SAAS,aAAaZ,cAAcuE,IAAI,CAACC,eAAOZ,wBAAAA,eAAAA,IAAKC,OAAO,qBAAZD,aAAca,QAAQ,mBAAI,IAAG;;IAEnF,MAAMC,WAAW/C,KAAK6B,IAAI,IAAI7B,KAAK8B,SAAS,IAAI9B,KAAKC,EAAE;IACvD,MAAM2B,OAAO3D,sBAAsBe,OAAOgB,KAAKC,EAAE,EAAEhB;IACnD,MAAM+D,OAAOpB,qBACX,KAAC9E;QAAQ8E,MAAMA;QAAMqB,WAAU;kBAC5BF;SAGHA;IAEF,qBACE;;YACGL,KAAK7B,GAAG,CAAC,CAACoB,oBACT,MAACpE;;sCACC,KAACF;sCACEiE,qBACC,KAAC9E;gCAAQ8E,MAAMA;gCAAMqB,WAAU;0CAC5BJ,OAAOZ,IAAIJ,IAAI,IAAII,IAAIiB,GAAG;iCAG7BL,OAAOZ,IAAIJ,IAAI,IAAII,IAAIiB,GAAG;;sCAG9B,KAACvF;sCAAWqF;;sCACZ,KAACrF;sCAAWqE,WAAW/C,MAAMgD;;sCAC7B,KAACtE;sCAAWwE,UAAUlD,MAAMgD;;;mBAZf,GAAGjC,KAAKC,EAAE,CAAC,CAAC,EAAEgC,IAAIiB,GAAG,EAAE;YAevCT,0BACC,KAAC5E;0BACC,cAAA,KAACF;oBAAUwF,SAAS;8BAClB,cAAA,MAACrF;wBAAWyC,SAAQ;wBAAUC,OAAM;;4BACjC,GAAGuC,SAAS,eAAe,EAAE3E,mBAAmB,GAAG,CAAC;4BACpDwD,qBACC,KAAC9E;gCAAQ8E,MAAMA;gCAAMqB,WAAU;0CAC5B;iCAGH;;;;iBAKN;;;AAGV;AACAnC,SAASiB,WAAW,GAAG;AAEvB,eAAejD,sBAAqB"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* THE ORGANIZATION'S AUTOMATIONS THAT RUN ON THIS SITE (AGL-3302), on the
|
|
3
|
+
* site's own Actions section: read-only, with the one control that belongs
|
|
4
|
+
* to the site — pausing an automation here, and resuming it.
|
|
5
|
+
*
|
|
6
|
+
* Read with the site's own scope tokens, so the listener is provable for a
|
|
7
|
+
* collaborator scoped to this site as well as for an org-wide member, and
|
|
8
|
+
* only the live ones placed here come back. Editing is the organization's,
|
|
9
|
+
* on its own hub; a pause is the site's, through `automations/pause`, which
|
|
10
|
+
* admits the site's admins and editors and refuses anyone else with its own
|
|
11
|
+
* words.
|
|
12
|
+
*
|
|
13
|
+
* Renders nothing while there is nothing: a site the organization runs no
|
|
14
|
+
* automation on has no panel to explain.
|
|
15
|
+
*/
|
|
16
|
+
export declare function SiteOrgAutomationsPanel(props: {
|
|
17
|
+
hostId: string;
|
|
18
|
+
}): import("react").JSX.Element;
|
|
19
|
+
export declare namespace SiteOrgAutomationsPanel {
|
|
20
|
+
var displayName: string;
|
|
21
|
+
}
|
|
22
|
+
export default SiteOrgAutomationsPanel;
|
|
@@ -0,0 +1,201 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license
|
|
3
|
+
* Copyright 2026 Aglyn LLC
|
|
4
|
+
*
|
|
5
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
6
|
+
* you may not use this file except in compliance with the License.
|
|
7
|
+
* You may obtain a copy of the License at
|
|
8
|
+
*
|
|
9
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
|
10
|
+
*
|
|
11
|
+
* Unless required by applicable law or agreed to in writing, software
|
|
12
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
13
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
14
|
+
* See the License for the specific language governing permissions and
|
|
15
|
+
* limitations under the License.
|
|
16
|
+
*/ 'use client';
|
|
17
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
18
|
+
import { HOST_ACTION_STEP_LABELS, hostEventLabel, pluginDocsHelp, scopeTokensForHost } from "@aglyn/aglyn";
|
|
19
|
+
import { CardDisplay } from "@aglyn/shared-ui-jsx";
|
|
20
|
+
import { useSnackbar } from "@aglyn/shared-ui-snackstack";
|
|
21
|
+
import { useFirestore, useFirestoreCollection, useOrgDataScope } from "@aglyn/tenant-feature-instance";
|
|
22
|
+
import { Button, Chip, Dialog, DialogActions, DialogContent, DialogTitle, Stack, Typography } from "@mui/material";
|
|
23
|
+
import { collection, limit, query, where } from "firebase/firestore";
|
|
24
|
+
import { useCallback, useMemo, useState } from "react";
|
|
25
|
+
import { ORG_AUTOMATIONS_COLLECTION, ORG_AUTOMATIONS_MAX, orgAutomationPausedHostIds } from "../model/org-automations.js";
|
|
26
|
+
import HostRunHistoryCard from "./host-run-history-card.component.js";
|
|
27
|
+
import { useOrgAutomationsApi } from "./use-org-automations-api.js";
|
|
28
|
+
/**
|
|
29
|
+
* THE ORGANIZATION'S AUTOMATIONS THAT RUN ON THIS SITE (AGL-3302), on the
|
|
30
|
+
* site's own Actions section: read-only, with the one control that belongs
|
|
31
|
+
* to the site — pausing an automation here, and resuming it.
|
|
32
|
+
*
|
|
33
|
+
* Read with the site's own scope tokens, so the listener is provable for a
|
|
34
|
+
* collaborator scoped to this site as well as for an org-wide member, and
|
|
35
|
+
* only the live ones placed here come back. Editing is the organization's,
|
|
36
|
+
* on its own hub; a pause is the site's, through `automations/pause`, which
|
|
37
|
+
* admits the site's admins and editors and refuses anyone else with its own
|
|
38
|
+
* words.
|
|
39
|
+
*
|
|
40
|
+
* Renders nothing while there is nothing: a site the organization runs no
|
|
41
|
+
* automation on has no panel to explain.
|
|
42
|
+
*/ export function SiteOrgAutomationsPanel(props) {
|
|
43
|
+
var _ref, _runsFor_name;
|
|
44
|
+
const { hostId } = props;
|
|
45
|
+
const firestore = useFirestore();
|
|
46
|
+
const api = useOrgAutomationsApi();
|
|
47
|
+
const { enqueueSnackbar } = useSnackbar();
|
|
48
|
+
const { scope } = useOrgDataScope({
|
|
49
|
+
hostId
|
|
50
|
+
});
|
|
51
|
+
const tokens = useMemo(()=>scopeTokensForHost(hostId), [
|
|
52
|
+
hostId
|
|
53
|
+
]);
|
|
54
|
+
const { data: rows } = useFirestoreCollection(()=>scope ? query(collection(firestore, scope[0], scope[1], ORG_AUTOMATIONS_COLLECTION), where('deletedAt', '==', null), where('visibleTo', 'array-contains-any', tokens), limit(ORG_AUTOMATIONS_MAX + 1)) : null, [
|
|
55
|
+
firestore,
|
|
56
|
+
scope,
|
|
57
|
+
tokens
|
|
58
|
+
], {
|
|
59
|
+
idField: '$id'
|
|
60
|
+
});
|
|
61
|
+
const automations = useMemo(()=>[
|
|
62
|
+
...rows != null ? rows : []
|
|
63
|
+
].sort((a, b)=>{
|
|
64
|
+
var _a_name, _b_name;
|
|
65
|
+
return String((_a_name = a.name) != null ? _a_name : '').localeCompare(String((_b_name = b.name) != null ? _b_name : ''));
|
|
66
|
+
}), [
|
|
67
|
+
rows
|
|
68
|
+
]);
|
|
69
|
+
const [busy, setBusy] = useState(null);
|
|
70
|
+
const [runsFor, setRunsFor] = useState(null);
|
|
71
|
+
const setPaused = useCallback(async (row, paused)=>{
|
|
72
|
+
setBusy(row.$id);
|
|
73
|
+
try {
|
|
74
|
+
await api('pause', {
|
|
75
|
+
hostId,
|
|
76
|
+
automationId: row.$id,
|
|
77
|
+
paused
|
|
78
|
+
});
|
|
79
|
+
enqueueSnackbar(paused ? `“${row.name}” is paused on this site` : `“${row.name}” runs on this site again`, {
|
|
80
|
+
variant: 'success',
|
|
81
|
+
persist: false
|
|
82
|
+
});
|
|
83
|
+
} catch (error) {
|
|
84
|
+
enqueueSnackbar((error == null ? void 0 : error.message) || 'The request could not be completed', {
|
|
85
|
+
variant: 'warning',
|
|
86
|
+
persist: false
|
|
87
|
+
});
|
|
88
|
+
} finally{
|
|
89
|
+
setBusy(null);
|
|
90
|
+
}
|
|
91
|
+
}, [
|
|
92
|
+
api,
|
|
93
|
+
hostId,
|
|
94
|
+
enqueueSnackbar
|
|
95
|
+
]);
|
|
96
|
+
if (!automations.length) return null;
|
|
97
|
+
return /*#__PURE__*/ _jsxs(CardDisplay, {
|
|
98
|
+
header: 'Org automations on this site',
|
|
99
|
+
help: pluginDocsHelp('orgAutomations', {
|
|
100
|
+
anchor: '#pause-it-on-one-site'
|
|
101
|
+
}),
|
|
102
|
+
contentGutterX: true,
|
|
103
|
+
contentGutterY: true,
|
|
104
|
+
children: [
|
|
105
|
+
/*#__PURE__*/ _jsxs(Stack, {
|
|
106
|
+
spacing: 1,
|
|
107
|
+
children: [
|
|
108
|
+
/*#__PURE__*/ _jsx(Typography, {
|
|
109
|
+
variant: "body2",
|
|
110
|
+
color: "text.secondary",
|
|
111
|
+
children: 'Your organization runs these on this site beside the site’s own ' + 'actions. Each run sends from this site and counts on its action ' + 'runs. Pausing one stops it here — and anyone waiting inside it ' + 'here — and leaves every other site alone.'
|
|
112
|
+
}),
|
|
113
|
+
automations.map((row)=>{
|
|
114
|
+
var _row_steps;
|
|
115
|
+
var _row_trigger;
|
|
116
|
+
const paused = orgAutomationPausedHostIds(row).includes(hostId);
|
|
117
|
+
const off = row.enabled === false;
|
|
118
|
+
return /*#__PURE__*/ _jsxs(Stack, {
|
|
119
|
+
direction: "row",
|
|
120
|
+
spacing: 1,
|
|
121
|
+
sx: {
|
|
122
|
+
alignItems: 'center'
|
|
123
|
+
},
|
|
124
|
+
children: [
|
|
125
|
+
/*#__PURE__*/ _jsxs(Stack, {
|
|
126
|
+
sx: {
|
|
127
|
+
flex: 1,
|
|
128
|
+
minWidth: 0
|
|
129
|
+
},
|
|
130
|
+
children: [
|
|
131
|
+
/*#__PURE__*/ _jsx(Typography, {
|
|
132
|
+
variant: "body2",
|
|
133
|
+
noWrap: true,
|
|
134
|
+
children: row.name
|
|
135
|
+
}),
|
|
136
|
+
/*#__PURE__*/ _jsx(Typography, {
|
|
137
|
+
variant: "caption",
|
|
138
|
+
color: "text.secondary",
|
|
139
|
+
noWrap: true,
|
|
140
|
+
children: `on ${hostEventLabel((_row_trigger = row.trigger) == null ? void 0 : _row_trigger.event)} · ${((_row_steps = row.steps) != null ? _row_steps : []).map((step)=>{
|
|
141
|
+
var _HOST_ACTION_STEP_LABELS_step_type;
|
|
142
|
+
return (_HOST_ACTION_STEP_LABELS_step_type = HOST_ACTION_STEP_LABELS[step.type]) != null ? _HOST_ACTION_STEP_LABELS_step_type : step.type;
|
|
143
|
+
}).join(' → ')}`
|
|
144
|
+
})
|
|
145
|
+
]
|
|
146
|
+
}),
|
|
147
|
+
/*#__PURE__*/ _jsx(Chip, {
|
|
148
|
+
size: "small",
|
|
149
|
+
variant: "outlined",
|
|
150
|
+
color: off ? 'default' : paused ? 'warning' : 'success',
|
|
151
|
+
label: off ? 'Switched off' : paused ? 'Paused here' : 'Runs here'
|
|
152
|
+
}),
|
|
153
|
+
/*#__PURE__*/ _jsx(Button, {
|
|
154
|
+
size: "small",
|
|
155
|
+
disabled: busy === row.$id,
|
|
156
|
+
onClick: ()=>void setPaused(row, !paused),
|
|
157
|
+
children: paused ? 'Resume here' : 'Pause here'
|
|
158
|
+
}),
|
|
159
|
+
/*#__PURE__*/ _jsx(Button, {
|
|
160
|
+
size: "small",
|
|
161
|
+
onClick: ()=>setRunsFor(row),
|
|
162
|
+
children: 'Runs'
|
|
163
|
+
})
|
|
164
|
+
]
|
|
165
|
+
}, row.$id);
|
|
166
|
+
})
|
|
167
|
+
]
|
|
168
|
+
}),
|
|
169
|
+
/*#__PURE__*/ _jsxs(Dialog, {
|
|
170
|
+
open: Boolean(runsFor),
|
|
171
|
+
onClose: ()=>setRunsFor(null),
|
|
172
|
+
maxWidth: "sm",
|
|
173
|
+
fullWidth: true,
|
|
174
|
+
children: [
|
|
175
|
+
/*#__PURE__*/ _jsx(DialogTitle, {
|
|
176
|
+
children: `Runs — ${(_ref = runsFor == null ? void 0 : runsFor.name) != null ? _ref : ''}`
|
|
177
|
+
}),
|
|
178
|
+
/*#__PURE__*/ _jsx(DialogContent, {
|
|
179
|
+
children: runsFor ? /*#__PURE__*/ _jsx(HostRunHistoryCard, {
|
|
180
|
+
hostId: hostId,
|
|
181
|
+
targetId: runsFor.$id,
|
|
182
|
+
targetName: (_runsFor_name = runsFor.name) != null ? _runsFor_name : '',
|
|
183
|
+
header: "Recent runs on this site"
|
|
184
|
+
}) : null
|
|
185
|
+
}),
|
|
186
|
+
/*#__PURE__*/ _jsx(DialogActions, {
|
|
187
|
+
children: /*#__PURE__*/ _jsx(Button, {
|
|
188
|
+
color: "inherit",
|
|
189
|
+
onClick: ()=>setRunsFor(null),
|
|
190
|
+
children: 'Close'
|
|
191
|
+
})
|
|
192
|
+
})
|
|
193
|
+
]
|
|
194
|
+
})
|
|
195
|
+
]
|
|
196
|
+
});
|
|
197
|
+
}
|
|
198
|
+
SiteOrgAutomationsPanel.displayName = 'SiteOrgAutomationsPanel';
|
|
199
|
+
export default SiteOrgAutomationsPanel;
|
|
200
|
+
|
|
201
|
+
//# sourceMappingURL=site-org-automations-panel.component.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../../../../../libs/plugins/workflows/src/lib/components/site-org-automations-panel.component.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 HOST_ACTION_STEP_LABELS,\n type HostActionStepType,\n hostEventLabel,\n pluginDocsHelp,\n scopeTokensForHost,\n} from '@aglyn/aglyn'\nimport { CardDisplay } from '@aglyn/shared-ui-jsx'\nimport { useSnackbar } from '@aglyn/shared-ui-snackstack'\nimport {\n useFirestore,\n useFirestoreCollection,\n useOrgDataScope,\n} from '@aglyn/tenant-feature-instance'\nimport {\n Button,\n Chip,\n Dialog,\n DialogActions,\n DialogContent,\n DialogTitle,\n Stack,\n Typography,\n} from '@mui/material'\nimport { collection, limit, query, where } from 'firebase/firestore'\nimport { useCallback, useMemo, useState } from 'react'\nimport {\n ORG_AUTOMATIONS_COLLECTION,\n ORG_AUTOMATIONS_MAX,\n orgAutomationPausedHostIds,\n type OrgAutomationRow,\n} from '../model/org-automations'\nimport HostRunHistoryCard from './host-run-history-card.component'\nimport { useOrgAutomationsApi } from './use-org-automations-api'\n\n/**\n * THE ORGANIZATION'S AUTOMATIONS THAT RUN ON THIS SITE (AGL-3302), on the\n * site's own Actions section: read-only, with the one control that belongs\n * to the site — pausing an automation here, and resuming it.\n *\n * Read with the site's own scope tokens, so the listener is provable for a\n * collaborator scoped to this site as well as for an org-wide member, and\n * only the live ones placed here come back. Editing is the organization's,\n * on its own hub; a pause is the site's, through `automations/pause`, which\n * admits the site's admins and editors and refuses anyone else with its own\n * words.\n *\n * Renders nothing while there is nothing: a site the organization runs no\n * automation on has no panel to explain.\n */\nexport function SiteOrgAutomationsPanel(props: { hostId: string }) {\n const { hostId } = props\n const firestore = useFirestore()\n const api = useOrgAutomationsApi()\n const { enqueueSnackbar } = useSnackbar()\n const { scope } = useOrgDataScope({ hostId })\n const tokens = useMemo(() => scopeTokensForHost(hostId), [hostId])\n const { data: rows } = useFirestoreCollection<OrgAutomationRow>(\n () =>\n scope\n ? query(\n collection(firestore, scope[0], scope[1], ORG_AUTOMATIONS_COLLECTION),\n where('deletedAt', '==', null),\n where('visibleTo', 'array-contains-any', tokens),\n limit(ORG_AUTOMATIONS_MAX + 1),\n )\n : null,\n [firestore, scope, tokens],\n { idField: '$id' },\n )\n const automations = useMemo(\n () =>\n [...(rows ?? [])].sort((a, b) =>\n String(a.name ?? '').localeCompare(String(b.name ?? '')),\n ),\n [rows],\n )\n const [busy, setBusy] = useState<string | null>(null)\n const [runsFor, setRunsFor] = useState<OrgAutomationRow | null>(null)\n\n const setPaused = useCallback(\n async (row: OrgAutomationRow, paused: boolean) => {\n setBusy(row.$id)\n try {\n await api('pause', { hostId, automationId: row.$id, paused })\n enqueueSnackbar(\n paused\n ? `“${row.name}” is paused on this site`\n : `“${row.name}” runs on this site again`,\n { variant: 'success', persist: false },\n )\n } catch (error) {\n enqueueSnackbar(\n (error as Error)?.message || 'The request could not be completed',\n { variant: 'warning', persist: false },\n )\n } finally {\n setBusy(null)\n }\n },\n [api, hostId, enqueueSnackbar],\n )\n\n if (!automations.length) return null\n return (\n <CardDisplay\n header={'Org automations on this site'}\n help={pluginDocsHelp('orgAutomations', { anchor: '#pause-it-on-one-site' })}\n contentGutterX\n contentGutterY\n >\n <Stack spacing={1}>\n <Typography variant=\"body2\" color=\"text.secondary\">\n {'Your organization runs these on this site beside the site’s own ' +\n 'actions. Each run sends from this site and counts on its action ' +\n 'runs. Pausing one stops it here — and anyone waiting inside it ' +\n 'here — and leaves every other site alone.'}\n </Typography>\n {automations.map((row) => {\n const paused = orgAutomationPausedHostIds(row).includes(hostId)\n const off = row.enabled === false\n return (\n <Stack\n key={row.$id}\n direction=\"row\"\n spacing={1}\n sx={{ alignItems: 'center' }}\n >\n <Stack sx={{ flex: 1, minWidth: 0 }}>\n <Typography variant=\"body2\" noWrap>\n {row.name}\n </Typography>\n <Typography variant=\"caption\" color=\"text.secondary\" noWrap>\n {`on ${hostEventLabel(row.trigger?.event)} · ${(row.steps ?? [])\n .map(\n (step) =>\n HOST_ACTION_STEP_LABELS[step.type as HostActionStepType] ??\n step.type,\n )\n .join(' → ')}`}\n </Typography>\n </Stack>\n <Chip\n size=\"small\"\n variant=\"outlined\"\n color={off ? 'default' : paused ? 'warning' : 'success'}\n label={off ? 'Switched off' : paused ? 'Paused here' : 'Runs here'}\n />\n <Button\n size=\"small\"\n disabled={busy === row.$id}\n onClick={() => void setPaused(row, !paused)}\n >\n {paused ? 'Resume here' : 'Pause here'}\n </Button>\n <Button size=\"small\" onClick={() => setRunsFor(row)}>\n {'Runs'}\n </Button>\n </Stack>\n )\n })}\n </Stack>\n <Dialog\n open={Boolean(runsFor)}\n onClose={() => setRunsFor(null)}\n maxWidth=\"sm\"\n fullWidth\n >\n <DialogTitle>{`Runs — ${runsFor?.name ?? ''}`}</DialogTitle>\n <DialogContent>\n {runsFor ? (\n <HostRunHistoryCard\n hostId={hostId}\n targetId={runsFor.$id}\n targetName={runsFor.name ?? ''}\n header=\"Recent runs on this site\"\n />\n ) : null}\n </DialogContent>\n <DialogActions>\n <Button color=\"inherit\" onClick={() => setRunsFor(null)}>\n {'Close'}\n </Button>\n </DialogActions>\n </Dialog>\n </CardDisplay>\n )\n}\nSiteOrgAutomationsPanel.displayName = 'SiteOrgAutomationsPanel'\n\nexport default SiteOrgAutomationsPanel\n"],"names":["HOST_ACTION_STEP_LABELS","hostEventLabel","pluginDocsHelp","scopeTokensForHost","CardDisplay","useSnackbar","useFirestore","useFirestoreCollection","useOrgDataScope","Button","Chip","Dialog","DialogActions","DialogContent","DialogTitle","Stack","Typography","collection","limit","query","where","useCallback","useMemo","useState","ORG_AUTOMATIONS_COLLECTION","ORG_AUTOMATIONS_MAX","orgAutomationPausedHostIds","HostRunHistoryCard","useOrgAutomationsApi","SiteOrgAutomationsPanel","props","runsFor","hostId","firestore","api","enqueueSnackbar","scope","tokens","data","rows","idField","automations","sort","a","b","String","name","localeCompare","busy","setBusy","setRunsFor","setPaused","row","paused","$id","automationId","variant","persist","error","message","length","header","help","anchor","contentGutterX","contentGutterY","spacing","color","map","includes","off","enabled","direction","sx","alignItems","flex","minWidth","noWrap","trigger","event","steps","step","type","join","size","label","disabled","onClick","open","Boolean","onClose","maxWidth","fullWidth","targetId","targetName","displayName"],"mappings":"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"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { type AutomationStepPickerData } from './use-automation-step-pickers';
|
|
2
|
+
/**
|
|
3
|
+
* WHAT AN ORG AUTOMATION'S STEPS CAN BE POINTED AT (AGL-3302).
|
|
4
|
+
*
|
|
5
|
+
* The site editor's pickers read one site's records; an org automation runs
|
|
6
|
+
* on every site it is placed on, so its pickers read the ORGANIZATION's —
|
|
7
|
+
* the lists, the datasets and the campaign containers — and offer only what
|
|
8
|
+
* every one of those sites can use. A dataset or a campaign shared with some
|
|
9
|
+
* of the org's sites and not the others would resolve on one site and fail
|
|
10
|
+
* the step on the next, so a record is offered only when its own sharing
|
|
11
|
+
* covers the automation's placement (`scopeCovers`). A list belongs to the
|
|
12
|
+
* whole organization and is always offered.
|
|
13
|
+
*
|
|
14
|
+
* The site-only pickers — workflows, overlays, webhooks — are empty: no step
|
|
15
|
+
* an org automation may hold points at one.
|
|
16
|
+
*
|
|
17
|
+
* Read on the same latch and at the same ceiling as the site editor's, and
|
|
18
|
+
* paid only by an author who opens the editor.
|
|
19
|
+
*/
|
|
20
|
+
export declare function useOrgAutomationStepPickers(orgId: string, editorOpened: boolean, placement: readonly string[]): AutomationStepPickerData;
|