agentix-cli 0.16.0 → 0.18.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agent-RDVGL2TW.js +2 -0
- package/dist/audit-Z47AQFFD.js +3 -0
- package/dist/audit-Z47AQFFD.js.map +1 -0
- package/dist/board-dashboard-KX2CNOSY.js +7282 -0
- package/dist/board-dashboard-KX2CNOSY.js.map +1 -0
- package/dist/chunk-34NG7UDX.js +11 -0
- package/dist/chunk-34NG7UDX.js.map +1 -0
- package/dist/{chunk-6MKAXEE5.js → chunk-4ITQP3XL.js} +2 -2
- package/dist/{chunk-6MKAXEE5.js.map → chunk-4ITQP3XL.js.map} +1 -1
- package/dist/chunk-53NRX2NA.js +2 -0
- package/dist/chunk-53NRX2NA.js.map +1 -0
- package/dist/chunk-6PPIFDOQ.js +1742 -0
- package/dist/chunk-6PPIFDOQ.js.map +1 -0
- package/dist/chunk-AFRHKA7B.js +2 -0
- package/dist/chunk-AFRHKA7B.js.map +1 -0
- package/dist/chunk-ASSJ4Z6Z.js +164 -0
- package/dist/chunk-ASSJ4Z6Z.js.map +1 -0
- package/dist/chunk-BLUXL6HR.js +854 -0
- package/dist/chunk-BLUXL6HR.js.map +1 -0
- package/dist/chunk-BTAEYL3P.js +72 -0
- package/dist/chunk-BTAEYL3P.js.map +1 -0
- package/dist/chunk-CDNWCYF7.js +2 -0
- package/dist/chunk-CDNWCYF7.js.map +1 -0
- package/dist/chunk-DJEZ2HVU.js +5 -0
- package/dist/chunk-DJEZ2HVU.js.map +1 -0
- package/dist/{chunk-FLOGK2U7.js → chunk-DSCMCVTV.js} +3 -3
- package/dist/chunk-DSCMCVTV.js.map +1 -0
- package/dist/chunk-EW27SCCC.js +2 -0
- package/dist/chunk-EW27SCCC.js.map +1 -0
- package/dist/chunk-HPDHNIA3.js +2 -0
- package/dist/chunk-IM376SD6.js +13 -0
- package/dist/chunk-IM376SD6.js.map +1 -0
- package/dist/chunk-J4WKMKTP.js +5 -0
- package/dist/{chunk-YI2T5QYB.js.map → chunk-J4WKMKTP.js.map} +1 -1
- package/dist/chunk-JGXE2YNV.js +46 -0
- package/dist/chunk-JGXE2YNV.js.map +1 -0
- package/dist/chunk-JXEPJ3YD.js +118 -0
- package/dist/chunk-JXEPJ3YD.js.map +1 -0
- package/dist/chunk-LY7JGDV7.js +6 -0
- package/dist/chunk-LY7JGDV7.js.map +1 -0
- package/dist/chunk-N67JZAXU.js +2 -0
- package/dist/chunk-N67JZAXU.js.map +1 -0
- package/dist/chunk-SR3X25TN.js +3 -0
- package/dist/chunk-SR3X25TN.js.map +1 -0
- package/dist/{chunk-7MBTMCKY.js → chunk-TRQSP67X.js} +2 -2
- package/dist/chunk-U364GNQX.js +719 -0
- package/dist/chunk-U364GNQX.js.map +1 -0
- package/dist/chunk-VJUTQAPJ.js +2 -0
- package/dist/chunk-VJUTQAPJ.js.map +1 -0
- package/dist/{chunk-HI24KAEY.js → chunk-WJXU5F4Z.js} +3 -4
- package/dist/{chunk-HI24KAEY.js.map → chunk-WJXU5F4Z.js.map} +1 -1
- package/dist/{chunk-QZP65I2H.js → chunk-ZE2YFX4K.js} +2 -2
- package/dist/cli.js +1 -320
- package/dist/cli.js.map +1 -1
- package/dist/{compaction-JBZZ7I7Y.js → compaction-S5H6DTOR.js} +6 -6
- package/dist/compaction-S5H6DTOR.js.map +1 -0
- package/dist/config-UOHEG4BW.js +2 -0
- package/dist/config-mutator-KSEBWKJH.js +2 -0
- package/dist/context-planner-2RGHJHSO.js +17 -0
- package/dist/context-planner-2RGHJHSO.js.map +1 -0
- package/dist/debug-TGAP7E7W.js +2 -0
- package/dist/discover-OATU7SHI.js +4 -0
- package/dist/discover-OATU7SHI.js.map +1 -0
- package/dist/editor-chat-FUBQLMAQ.js +137 -0
- package/dist/editor-chat-FUBQLMAQ.js.map +1 -0
- package/dist/heal-YP7QI7D3.js +2 -0
- package/dist/inbox-O5UB3YQN.js +315 -0
- package/dist/inbox-O5UB3YQN.js.map +1 -0
- package/dist/index.d.ts +3390 -1814
- package/dist/index.js +23 -53
- package/dist/index.js.map +1 -1
- package/dist/ingest-whatsapp-C3O5UPBX.js +6 -0
- package/dist/ingest-whatsapp-C3O5UPBX.js.map +1 -0
- package/dist/loader-BGWA7IRY.js +2 -0
- package/dist/loader-LBHKSXBK.js +2 -0
- package/dist/memory-extract-KKPKAOPH.js +2 -0
- package/dist/processes-7W27G3J3.js +256 -0
- package/dist/processes-7W27G3J3.js.map +1 -0
- package/dist/program-2MDELQLX.js +2 -0
- package/dist/providers-WCQSKTNP.js +2 -0
- package/dist/query-FZAL7AQD.js +2 -0
- package/dist/recipes-LZ56TA3X.js +2 -0
- package/dist/registry-ONJSILH4.js +2 -0
- package/dist/scheduler-XRM2RJIV.js +2 -0
- package/dist/slack-D27BE37Q.js +3 -0
- package/dist/slack-D27BE37Q.js.map +1 -0
- package/dist/store-4UCO56K2.js +2 -0
- package/dist/store-4UCO56K2.js.map +1 -0
- package/dist/{subagent-2SJHSSJS.js → subagent-EPOT3QDM.js} +2 -2
- package/dist/task-store-3NUWLYRY.js +2 -0
- package/dist/task-store-3NUWLYRY.js.map +1 -0
- package/dist/telegram-UWV67KWG.js +3 -0
- package/dist/telegram-UWV67KWG.js.map +1 -0
- package/dist/timers-QB4KYNAE.js +2 -0
- package/dist/timers-QB4KYNAE.js.map +1 -0
- package/dist/types-ECMEC5BZ.js +2 -0
- package/dist/types-ECMEC5BZ.js.map +1 -0
- package/dist/types-TTB6DJUE.js +2 -0
- package/dist/types-TTB6DJUE.js.map +1 -0
- package/dist/usage-dashboard-FQGPPABD.js +803 -0
- package/dist/usage-dashboard-FQGPPABD.js.map +1 -0
- package/dist/web/workflow-editor.global.js +1450 -0
- package/dist/web/workflow-editor.global.js.map +1 -0
- package/dist/whatsapp-KJ2NRKKQ.js +3 -0
- package/dist/whatsapp-KJ2NRKKQ.js.map +1 -0
- package/dist/{whatsapp-state-6D6FHHD2.js → whatsapp-state-3ZVQ6MQD.js} +2 -2
- package/dist/{wiki-UDPYFJBL.js → wiki-OUYKM7MB.js} +2 -2
- package/dist/wiki-OUYKM7MB.js.map +1 -0
- package/dist/workspace-setup-6GDBEORT.js +2 -0
- package/dist/workspace-setup-6GDBEORT.js.map +1 -0
- package/package.json +19 -2
- package/dist/agent-BCDPSPKU.js +0 -2
- package/dist/board-dashboard-LA7WW56M.js +0 -5668
- package/dist/board-dashboard-LA7WW56M.js.map +0 -1
- package/dist/chunk-6U2XOQHU.js +0 -7
- package/dist/chunk-6U2XOQHU.js.map +0 -1
- package/dist/chunk-7FJQGD6U.js +0 -6
- package/dist/chunk-7FJQGD6U.js.map +0 -1
- package/dist/chunk-ABDP7TDL.js +0 -71
- package/dist/chunk-ABDP7TDL.js.map +0 -1
- package/dist/chunk-CXY2RYNI.js +0 -11
- package/dist/chunk-CXY2RYNI.js.map +0 -1
- package/dist/chunk-FIOB3MEX.js +0 -2
- package/dist/chunk-FLOGK2U7.js.map +0 -1
- package/dist/chunk-HVC6FJNP.js +0 -108
- package/dist/chunk-HVC6FJNP.js.map +0 -1
- package/dist/chunk-K7BE4E35.js +0 -138
- package/dist/chunk-K7BE4E35.js.map +0 -1
- package/dist/chunk-KXJSLLSQ.js +0 -199
- package/dist/chunk-KXJSLLSQ.js.map +0 -1
- package/dist/chunk-KXZMYLHQ.js +0 -46
- package/dist/chunk-KXZMYLHQ.js.map +0 -1
- package/dist/chunk-M7HKBG3V.js +0 -2
- package/dist/chunk-M7HKBG3V.js.map +0 -1
- package/dist/chunk-MCJUAE6V.js +0 -6
- package/dist/chunk-MCJUAE6V.js.map +0 -1
- package/dist/chunk-RB7265LO.js +0 -12
- package/dist/chunk-RB7265LO.js.map +0 -1
- package/dist/chunk-YI2T5QYB.js +0 -5
- package/dist/compaction-JBZZ7I7Y.js.map +0 -1
- package/dist/config-LN6JEHMF.js +0 -2
- package/dist/config-mutator-24TH7PHM.js +0 -2
- package/dist/debug-3MEUO2P2.js +0 -2
- package/dist/heal-WKY5I4KB.js +0 -2
- package/dist/loader-PTCXLJEX.js +0 -2
- package/dist/memory-extract-AD7KMRPC.js +0 -2
- package/dist/providers-VUIWO3ZK.js +0 -2
- package/dist/query-PKGYE5HR.js +0 -2
- package/dist/registry-ASC2QS5K.js +0 -2
- package/dist/scheduler-A3TQOCKT.js +0 -2
- package/dist/types-OIFU3KSQ.js +0 -2
- package/dist/usage-dashboard-QX3CF6KK.js +0 -404
- package/dist/usage-dashboard-QX3CF6KK.js.map +0 -1
- package/dist/workspace-setup-ZWTT42XT.js +0 -2
- /package/dist/{agent-BCDPSPKU.js.map → agent-RDVGL2TW.js.map} +0 -0
- /package/dist/{chunk-FIOB3MEX.js.map → chunk-HPDHNIA3.js.map} +0 -0
- /package/dist/{chunk-7MBTMCKY.js.map → chunk-TRQSP67X.js.map} +0 -0
- /package/dist/{chunk-QZP65I2H.js.map → chunk-ZE2YFX4K.js.map} +0 -0
- /package/dist/{config-LN6JEHMF.js.map → config-UOHEG4BW.js.map} +0 -0
- /package/dist/{config-mutator-24TH7PHM.js.map → config-mutator-KSEBWKJH.js.map} +0 -0
- /package/dist/{debug-3MEUO2P2.js.map → debug-TGAP7E7W.js.map} +0 -0
- /package/dist/{heal-WKY5I4KB.js.map → heal-YP7QI7D3.js.map} +0 -0
- /package/dist/{loader-PTCXLJEX.js.map → loader-BGWA7IRY.js.map} +0 -0
- /package/dist/{memory-extract-AD7KMRPC.js.map → loader-LBHKSXBK.js.map} +0 -0
- /package/dist/{providers-VUIWO3ZK.js.map → memory-extract-KKPKAOPH.js.map} +0 -0
- /package/dist/{query-PKGYE5HR.js.map → program-2MDELQLX.js.map} +0 -0
- /package/dist/{registry-ASC2QS5K.js.map → providers-WCQSKTNP.js.map} +0 -0
- /package/dist/{scheduler-A3TQOCKT.js.map → query-FZAL7AQD.js.map} +0 -0
- /package/dist/{types-OIFU3KSQ.js.map → recipes-LZ56TA3X.js.map} +0 -0
- /package/dist/{wiki-UDPYFJBL.js.map → registry-ONJSILH4.js.map} +0 -0
- /package/dist/{workspace-setup-ZWTT42XT.js.map → scheduler-XRM2RJIV.js.map} +0 -0
- /package/dist/{subagent-2SJHSSJS.js.map → subagent-EPOT3QDM.js.map} +0 -0
- /package/dist/{whatsapp-state-6D6FHHD2.js.map → whatsapp-state-3ZVQ6MQD.js.map} +0 -0
|
@@ -0,0 +1,315 @@
|
|
|
1
|
+
import{a,b as t}from"./chunk-6PPIFDOQ.js";import"./chunk-HPDHNIA3.js";function s(e={}){let o=`<div class="ax-inbox__root" data-actor="${t(e.actor??"")}">
|
|
2
|
+
<aside class="ax-inbox__list">
|
|
3
|
+
<header>
|
|
4
|
+
<h2>Inbox</h2>
|
|
5
|
+
<button id="inbox-refresh" class="ax-inbox__icon" title="Refresh (r)">\u21BB</button>
|
|
6
|
+
</header>
|
|
7
|
+
<div class="ax-inbox__actor">
|
|
8
|
+
<label>Actor <input id="inbox-actor" type="text" placeholder="actor:<id>" value="${t(e.actor??"")}" autocomplete="off" /></label>
|
|
9
|
+
</div>
|
|
10
|
+
<ul id="inbox-tasks" class="ax-inbox__cards" aria-live="polite"></ul>
|
|
11
|
+
<div id="inbox-empty" class="ax-inbox__empty" hidden>
|
|
12
|
+
<p>No open tasks.</p>
|
|
13
|
+
<p class="hint">Set the actor filter to see tasks assigned to you, or leave blank for all tasks in the system.</p>
|
|
14
|
+
</div>
|
|
15
|
+
</aside>
|
|
16
|
+
|
|
17
|
+
<section class="ax-inbox__detail">
|
|
18
|
+
<header id="inbox-detail-head">
|
|
19
|
+
<span class="hint">Select a task to open its form.</span>
|
|
20
|
+
</header>
|
|
21
|
+
<div id="inbox-detail-body" class="ax-inbox__detail-body"></div>
|
|
22
|
+
</section>
|
|
23
|
+
</div>
|
|
24
|
+
|
|
25
|
+
<div id="inbox-toast" class="ax-inbox__toast" hidden></div>`;return a({title:"AgentX \xB7 Inbox",activeTab:"workflows",subtitle:"Inbox",peers:e.peers,currentPeerId:e.currentPeerId,body:o,css:n,scripts:`<script>${i}</script>`})}var n=`
|
|
26
|
+
.ax-inbox__root {
|
|
27
|
+
display: grid;
|
|
28
|
+
grid-template-columns: 340px 1fr;
|
|
29
|
+
height: calc(100vh - var(--ax-topbar-h, 48px));
|
|
30
|
+
background: var(--ax-bg);
|
|
31
|
+
}
|
|
32
|
+
.ax-inbox__list {
|
|
33
|
+
border-right: 1px solid var(--ax-border);
|
|
34
|
+
display: flex;
|
|
35
|
+
flex-direction: column;
|
|
36
|
+
min-height: 0;
|
|
37
|
+
}
|
|
38
|
+
.ax-inbox__list > header {
|
|
39
|
+
display: flex;
|
|
40
|
+
justify-content: space-between;
|
|
41
|
+
align-items: center;
|
|
42
|
+
padding: 12px 14px;
|
|
43
|
+
border-bottom: 1px solid var(--ax-border);
|
|
44
|
+
}
|
|
45
|
+
.ax-inbox__list > header h2 { margin: 0; font-size: 14px; font-weight: 600; }
|
|
46
|
+
.ax-inbox__actor {
|
|
47
|
+
padding: 10px 14px;
|
|
48
|
+
border-bottom: 1px solid var(--ax-border);
|
|
49
|
+
}
|
|
50
|
+
.ax-inbox__actor label { display: flex; flex-direction: column; gap: 4px; font-size: 12px; color: var(--ax-muted); }
|
|
51
|
+
.ax-inbox__actor input {
|
|
52
|
+
font: inherit;
|
|
53
|
+
padding: 6px 8px;
|
|
54
|
+
border: 1px solid var(--ax-border);
|
|
55
|
+
border-radius: 6px;
|
|
56
|
+
background: var(--ax-bg);
|
|
57
|
+
color: var(--ax-fg);
|
|
58
|
+
}
|
|
59
|
+
.ax-inbox__cards { list-style: none; margin: 0; padding: 6px; overflow-y: auto; flex: 1; }
|
|
60
|
+
.ax-inbox__card {
|
|
61
|
+
padding: 10px 12px;
|
|
62
|
+
border-radius: 6px;
|
|
63
|
+
margin-bottom: 4px;
|
|
64
|
+
cursor: pointer;
|
|
65
|
+
border: 1px solid transparent;
|
|
66
|
+
}
|
|
67
|
+
.ax-inbox__card:hover { background: var(--ax-surface-2, rgba(127,127,127,0.08)); }
|
|
68
|
+
.ax-inbox__card.is-active { background: var(--ax-surface-2); border-color: var(--ax-border); }
|
|
69
|
+
.ax-inbox__card-title { font-weight: 600; font-size: 13px; margin-bottom: 2px; }
|
|
70
|
+
.ax-inbox__card-meta { font-size: 11px; color: var(--ax-muted); }
|
|
71
|
+
.ax-inbox__card-due { font-size: 11px; color: #d48a00; margin-top: 4px; }
|
|
72
|
+
.ax-inbox__empty { padding: 20px; color: var(--ax-muted); text-align: center; font-size: 13px; }
|
|
73
|
+
.ax-inbox__detail { display: flex; flex-direction: column; min-height: 0; }
|
|
74
|
+
.ax-inbox__detail > header { padding: 14px 18px; border-bottom: 1px solid var(--ax-border); }
|
|
75
|
+
.ax-inbox__detail-body { overflow-y: auto; padding: 18px; flex: 1; }
|
|
76
|
+
.ax-inbox__form { max-width: 560px; display: grid; gap: 14px; }
|
|
77
|
+
.ax-inbox__field { display: flex; flex-direction: column; gap: 4px; }
|
|
78
|
+
.ax-inbox__field label { font-size: 12px; color: var(--ax-muted); font-weight: 600; }
|
|
79
|
+
.ax-inbox__field input, .ax-inbox__field textarea, .ax-inbox__field select {
|
|
80
|
+
font: inherit;
|
|
81
|
+
padding: 8px 10px;
|
|
82
|
+
border: 1px solid var(--ax-border);
|
|
83
|
+
border-radius: 6px;
|
|
84
|
+
background: var(--ax-bg);
|
|
85
|
+
color: var(--ax-fg);
|
|
86
|
+
}
|
|
87
|
+
.ax-inbox__field textarea { min-height: 100px; resize: vertical; }
|
|
88
|
+
.ax-inbox__field-hint { font-size: 11px; color: var(--ax-muted); }
|
|
89
|
+
.ax-inbox__field-error { font-size: 11px; color: #c0392b; }
|
|
90
|
+
.ax-inbox__actions { display: flex; gap: 8px; margin-top: 8px; }
|
|
91
|
+
.ax-inbox__actions button {
|
|
92
|
+
font: inherit;
|
|
93
|
+
padding: 8px 14px;
|
|
94
|
+
border: 1px solid var(--ax-border);
|
|
95
|
+
border-radius: 6px;
|
|
96
|
+
cursor: pointer;
|
|
97
|
+
background: var(--ax-surface-2);
|
|
98
|
+
color: var(--ax-fg);
|
|
99
|
+
}
|
|
100
|
+
.ax-inbox__actions button.is-primary {
|
|
101
|
+
background: #2ecc71; color: white; border-color: #27ae60;
|
|
102
|
+
}
|
|
103
|
+
.ax-inbox__actions button:disabled { opacity: 0.5; cursor: not-allowed; }
|
|
104
|
+
.ax-inbox__icon {
|
|
105
|
+
background: none; border: 1px solid transparent; color: var(--ax-fg); cursor: pointer;
|
|
106
|
+
font-size: 14px; padding: 4px 8px; border-radius: 4px;
|
|
107
|
+
}
|
|
108
|
+
.ax-inbox__icon:hover { background: var(--ax-surface-2); }
|
|
109
|
+
.ax-inbox__toast {
|
|
110
|
+
position: fixed; bottom: 16px; right: 16px; padding: 10px 14px;
|
|
111
|
+
background: var(--ax-fg); color: var(--ax-bg); border-radius: 6px;
|
|
112
|
+
font-size: 13px; z-index: 100;
|
|
113
|
+
}
|
|
114
|
+
`,i=`
|
|
115
|
+
(function(){
|
|
116
|
+
const $ = (sel) => document.querySelector(sel);
|
|
117
|
+
const state = { tasks: [], selected: null, actor: document.querySelector('.ax-inbox__root').dataset.actor || '' };
|
|
118
|
+
const toast = (msg) => {
|
|
119
|
+
const el = $('#inbox-toast');
|
|
120
|
+
el.textContent = msg;
|
|
121
|
+
el.hidden = false;
|
|
122
|
+
setTimeout(() => { el.hidden = true; }, 2500);
|
|
123
|
+
};
|
|
124
|
+
|
|
125
|
+
async function fetchTasks() {
|
|
126
|
+
const qs = state.actor ? ('?actor=' + encodeURIComponent(state.actor)) : '';
|
|
127
|
+
try {
|
|
128
|
+
const r = await fetch('/api/workflows/tasks' + qs, { credentials: 'same-origin' });
|
|
129
|
+
if (!r.ok) { toast('fetch failed: ' + r.status); return; }
|
|
130
|
+
const data = await r.json();
|
|
131
|
+
state.tasks = Array.isArray(data.tasks) ? data.tasks : [];
|
|
132
|
+
renderList();
|
|
133
|
+
if (state.selected && !state.tasks.find(t => t.id === state.selected)) {
|
|
134
|
+
state.selected = null;
|
|
135
|
+
renderDetail();
|
|
136
|
+
}
|
|
137
|
+
} catch (e) { toast('fetch error: ' + e.message); }
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
function renderList() {
|
|
141
|
+
const ul = $('#inbox-tasks');
|
|
142
|
+
const empty = $('#inbox-empty');
|
|
143
|
+
ul.innerHTML = '';
|
|
144
|
+
if (!state.tasks.length) { empty.hidden = false; return; }
|
|
145
|
+
empty.hidden = true;
|
|
146
|
+
for (const t of state.tasks) {
|
|
147
|
+
const li = document.createElement('li');
|
|
148
|
+
li.className = 'ax-inbox__card' + (t.id === state.selected ? ' is-active' : '');
|
|
149
|
+
li.innerHTML =
|
|
150
|
+
'<div class="ax-inbox__card-title">' + escHtml(t.title) + '</div>' +
|
|
151
|
+
'<div class="ax-inbox__card-meta">' + escHtml(t.assignee) + ' \xB7 ' + escHtml(t.workflowId) + '</div>' +
|
|
152
|
+
(t.dueAt ? ('<div class="ax-inbox__card-due">due ' + new Date(t.dueAt).toLocaleString() + '</div>') : '');
|
|
153
|
+
li.addEventListener('click', () => { state.selected = t.id; renderList(); renderDetail(); });
|
|
154
|
+
ul.appendChild(li);
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
function renderDetail() {
|
|
159
|
+
const head = $('#inbox-detail-head');
|
|
160
|
+
const body = $('#inbox-detail-body');
|
|
161
|
+
const t = state.tasks.find(x => x.id === state.selected);
|
|
162
|
+
if (!t) {
|
|
163
|
+
head.innerHTML = '<span class="hint">Select a task to open its form.</span>';
|
|
164
|
+
body.innerHTML = '';
|
|
165
|
+
return;
|
|
166
|
+
}
|
|
167
|
+
head.innerHTML = '<h2 style="margin:0;font-size:15px">' + escHtml(t.title) + '</h2>' +
|
|
168
|
+
(t.description ? '<p class="hint" style="margin:6px 0 0">' + escHtml(t.description) + '</p>' : '');
|
|
169
|
+
const form = document.createElement('form');
|
|
170
|
+
form.className = 'ax-inbox__form';
|
|
171
|
+
form.addEventListener('submit', (e) => { e.preventDefault(); submit(t, 'primary'); });
|
|
172
|
+
for (const field of (t.form.fields || [])) {
|
|
173
|
+
form.appendChild(renderField(field));
|
|
174
|
+
}
|
|
175
|
+
const actions = document.createElement('div');
|
|
176
|
+
actions.className = 'ax-inbox__actions';
|
|
177
|
+
const primary = document.createElement('button');
|
|
178
|
+
primary.type = 'submit';
|
|
179
|
+
primary.className = 'is-primary';
|
|
180
|
+
primary.textContent = t.form.submitLabel || 'Submit';
|
|
181
|
+
actions.appendChild(primary);
|
|
182
|
+
if (t.form.secondaryAction) {
|
|
183
|
+
const secondary = document.createElement('button');
|
|
184
|
+
secondary.type = 'button';
|
|
185
|
+
secondary.textContent = t.form.secondaryAction.label;
|
|
186
|
+
secondary.addEventListener('click', () => submit(t, 'secondary'));
|
|
187
|
+
actions.appendChild(secondary);
|
|
188
|
+
}
|
|
189
|
+
form.appendChild(actions);
|
|
190
|
+
body.innerHTML = '';
|
|
191
|
+
body.appendChild(form);
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
function renderField(field) {
|
|
195
|
+
const wrap = document.createElement('div');
|
|
196
|
+
wrap.className = 'ax-inbox__field';
|
|
197
|
+
const label = document.createElement('label');
|
|
198
|
+
label.textContent = field.label + (field.required ? ' *' : '');
|
|
199
|
+
wrap.appendChild(label);
|
|
200
|
+
let input;
|
|
201
|
+
switch (field.type) {
|
|
202
|
+
case 'long-text':
|
|
203
|
+
input = document.createElement('textarea');
|
|
204
|
+
break;
|
|
205
|
+
case 'number':
|
|
206
|
+
input = document.createElement('input'); input.type = 'number';
|
|
207
|
+
break;
|
|
208
|
+
case 'boolean':
|
|
209
|
+
input = document.createElement('select');
|
|
210
|
+
for (const v of ['', 'yes', 'no']) {
|
|
211
|
+
const o = document.createElement('option'); o.value = v; o.textContent = v || '\u2014';
|
|
212
|
+
input.appendChild(o);
|
|
213
|
+
}
|
|
214
|
+
break;
|
|
215
|
+
case 'date':
|
|
216
|
+
input = document.createElement('input'); input.type = 'date';
|
|
217
|
+
break;
|
|
218
|
+
case 'select':
|
|
219
|
+
input = document.createElement('select');
|
|
220
|
+
if (!field.required) { const o = document.createElement('option'); o.value = ''; o.textContent = '\u2014'; input.appendChild(o); }
|
|
221
|
+
for (const opt of (field.options || [])) {
|
|
222
|
+
const o = document.createElement('option'); o.value = opt; o.textContent = opt;
|
|
223
|
+
input.appendChild(o);
|
|
224
|
+
}
|
|
225
|
+
break;
|
|
226
|
+
case 'multi-select':
|
|
227
|
+
input = document.createElement('select'); input.multiple = true; input.size = Math.min(6, (field.options||[]).length || 3);
|
|
228
|
+
for (const opt of (field.options || [])) {
|
|
229
|
+
const o = document.createElement('option'); o.value = opt; o.textContent = opt;
|
|
230
|
+
input.appendChild(o);
|
|
231
|
+
}
|
|
232
|
+
break;
|
|
233
|
+
case 'file':
|
|
234
|
+
input = document.createElement('input'); input.type = 'text'; input.placeholder = 'URL or path';
|
|
235
|
+
break;
|
|
236
|
+
default:
|
|
237
|
+
input = document.createElement('input'); input.type = 'text';
|
|
238
|
+
}
|
|
239
|
+
input.name = field.key;
|
|
240
|
+
if (field.defaultValue !== undefined && field.type !== 'multi-select') input.value = String(field.defaultValue);
|
|
241
|
+
wrap.appendChild(input);
|
|
242
|
+
if (field.hint) {
|
|
243
|
+
const hint = document.createElement('div');
|
|
244
|
+
hint.className = 'ax-inbox__field-hint';
|
|
245
|
+
hint.textContent = field.hint;
|
|
246
|
+
wrap.appendChild(hint);
|
|
247
|
+
}
|
|
248
|
+
const err = document.createElement('div');
|
|
249
|
+
err.className = 'ax-inbox__field-error';
|
|
250
|
+
err.dataset.for = field.key;
|
|
251
|
+
wrap.appendChild(err);
|
|
252
|
+
return wrap;
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
async function submit(task, action) {
|
|
256
|
+
const form = $('.ax-inbox__form');
|
|
257
|
+
if (!form) return;
|
|
258
|
+
const values = {};
|
|
259
|
+
for (const field of (task.form.fields || [])) {
|
|
260
|
+
const el = form.querySelector('[name="' + field.key + '"]');
|
|
261
|
+
if (!el) continue;
|
|
262
|
+
if (field.type === 'multi-select') {
|
|
263
|
+
values[field.key] = Array.from(el.selectedOptions).map(o => o.value);
|
|
264
|
+
} else if (field.type === 'boolean') {
|
|
265
|
+
values[field.key] = el.value;
|
|
266
|
+
} else {
|
|
267
|
+
values[field.key] = el.value;
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
form.querySelectorAll('.ax-inbox__field-error').forEach(e => { e.textContent = ''; });
|
|
271
|
+
try {
|
|
272
|
+
const r = await fetch('/api/workflows/tasks/' + encodeURIComponent(task.id) + '/submit', {
|
|
273
|
+
method: 'POST',
|
|
274
|
+
credentials: 'same-origin',
|
|
275
|
+
headers: { 'Content-Type': 'application/json' },
|
|
276
|
+
body: JSON.stringify({ submittedBy: state.actor || 'anonymous', submission: { action, values } }),
|
|
277
|
+
});
|
|
278
|
+
const data = await r.json().catch(() => ({}));
|
|
279
|
+
if (!r.ok) {
|
|
280
|
+
if (data.fieldErrors && Array.isArray(data.fieldErrors)) {
|
|
281
|
+
for (const fe of data.fieldErrors) {
|
|
282
|
+
const node = form.querySelector('[data-for="' + fe.field + '"]');
|
|
283
|
+
if (node) node.textContent = fe.message;
|
|
284
|
+
}
|
|
285
|
+
toast('form has errors');
|
|
286
|
+
} else {
|
|
287
|
+
toast(data.error || 'submit failed');
|
|
288
|
+
}
|
|
289
|
+
return;
|
|
290
|
+
}
|
|
291
|
+
toast('submitted');
|
|
292
|
+
state.selected = null;
|
|
293
|
+
fetchTasks();
|
|
294
|
+
} catch (e) { toast('submit error: ' + e.message); }
|
|
295
|
+
}
|
|
296
|
+
|
|
297
|
+
function escHtml(s) {
|
|
298
|
+
return String(s).replace(/[&<>"']/g, c => ({'&':'&','<':'<','>':'>','"':'"',"'":'''})[c]);
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
$('#inbox-actor').addEventListener('change', (e) => {
|
|
302
|
+
state.actor = e.target.value.trim();
|
|
303
|
+
state.selected = null;
|
|
304
|
+
const url = new URL(window.location.href);
|
|
305
|
+
if (state.actor) url.searchParams.set('actor', state.actor); else url.searchParams.delete('actor');
|
|
306
|
+
history.replaceState({}, '', url.toString());
|
|
307
|
+
fetchTasks();
|
|
308
|
+
});
|
|
309
|
+
$('#inbox-refresh').addEventListener('click', fetchTasks);
|
|
310
|
+
|
|
311
|
+
fetchTasks();
|
|
312
|
+
setInterval(fetchTasks, 10000);
|
|
313
|
+
})();
|
|
314
|
+
`;export{s as renderInboxPage};
|
|
315
|
+
//# sourceMappingURL=inbox-O5UB3YQN.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/daemon/ui/pages/inbox.ts"],"sourcesContent":["import { renderShell, esc, type TopbarPeer } from \"..\"\n\n// --- Inbox page ---\n//\n// Per-actor (or global) list of open user-tasks with an inline form\n// renderer. Reads /api/workflows/tasks; submits via\n// POST /api/workflows/tasks/:id/submit.\n//\n// Scope is intentionally tight for Phase 1:\n// - text / long-text / number / boolean / select / multi-select / date\n// - primary + optional secondary action buttons\n// - required-field validation is server-side; the UI just relays errors\n//\n// No channel-adapter coupling here — the form UI is the same whether the\n// renderer ran on Telegram or not.\n\nexport interface InboxPageOpts {\n peers?: TopbarPeer[]\n currentPeerId?: string\n /** Optional actor id to pre-filter. When unset, the page shows a prompt\n * asking the user to pick their actor id. */\n actor?: string\n}\n\nexport function renderInboxPage(opts: InboxPageOpts = {}): string {\n const body = `<div class=\"ax-inbox__root\" data-actor=\"${esc(opts.actor ?? \"\")}\">\n <aside class=\"ax-inbox__list\">\n <header>\n <h2>Inbox</h2>\n <button id=\"inbox-refresh\" class=\"ax-inbox__icon\" title=\"Refresh (r)\">↻</button>\n </header>\n <div class=\"ax-inbox__actor\">\n <label>Actor <input id=\"inbox-actor\" type=\"text\" placeholder=\"actor:<id>\" value=\"${esc(opts.actor ?? \"\")}\" autocomplete=\"off\" /></label>\n </div>\n <ul id=\"inbox-tasks\" class=\"ax-inbox__cards\" aria-live=\"polite\"></ul>\n <div id=\"inbox-empty\" class=\"ax-inbox__empty\" hidden>\n <p>No open tasks.</p>\n <p class=\"hint\">Set the actor filter to see tasks assigned to you, or leave blank for all tasks in the system.</p>\n </div>\n </aside>\n\n <section class=\"ax-inbox__detail\">\n <header id=\"inbox-detail-head\">\n <span class=\"hint\">Select a task to open its form.</span>\n </header>\n <div id=\"inbox-detail-body\" class=\"ax-inbox__detail-body\"></div>\n </section>\n</div>\n\n<div id=\"inbox-toast\" class=\"ax-inbox__toast\" hidden></div>`\n\n return renderShell({\n title: \"AgentX · Inbox\",\n activeTab: \"workflows\",\n subtitle: \"Inbox\",\n peers: opts.peers,\n currentPeerId: opts.currentPeerId,\n body,\n css: INBOX_PAGE_CSS,\n scripts: `<script>${INBOX_PAGE_SCRIPT}</script>`,\n })\n}\n\nconst INBOX_PAGE_CSS = `\n.ax-inbox__root {\n display: grid;\n grid-template-columns: 340px 1fr;\n height: calc(100vh - var(--ax-topbar-h, 48px));\n background: var(--ax-bg);\n}\n.ax-inbox__list {\n border-right: 1px solid var(--ax-border);\n display: flex;\n flex-direction: column;\n min-height: 0;\n}\n.ax-inbox__list > header {\n display: flex;\n justify-content: space-between;\n align-items: center;\n padding: 12px 14px;\n border-bottom: 1px solid var(--ax-border);\n}\n.ax-inbox__list > header h2 { margin: 0; font-size: 14px; font-weight: 600; }\n.ax-inbox__actor {\n padding: 10px 14px;\n border-bottom: 1px solid var(--ax-border);\n}\n.ax-inbox__actor label { display: flex; flex-direction: column; gap: 4px; font-size: 12px; color: var(--ax-muted); }\n.ax-inbox__actor input {\n font: inherit;\n padding: 6px 8px;\n border: 1px solid var(--ax-border);\n border-radius: 6px;\n background: var(--ax-bg);\n color: var(--ax-fg);\n}\n.ax-inbox__cards { list-style: none; margin: 0; padding: 6px; overflow-y: auto; flex: 1; }\n.ax-inbox__card {\n padding: 10px 12px;\n border-radius: 6px;\n margin-bottom: 4px;\n cursor: pointer;\n border: 1px solid transparent;\n}\n.ax-inbox__card:hover { background: var(--ax-surface-2, rgba(127,127,127,0.08)); }\n.ax-inbox__card.is-active { background: var(--ax-surface-2); border-color: var(--ax-border); }\n.ax-inbox__card-title { font-weight: 600; font-size: 13px; margin-bottom: 2px; }\n.ax-inbox__card-meta { font-size: 11px; color: var(--ax-muted); }\n.ax-inbox__card-due { font-size: 11px; color: #d48a00; margin-top: 4px; }\n.ax-inbox__empty { padding: 20px; color: var(--ax-muted); text-align: center; font-size: 13px; }\n.ax-inbox__detail { display: flex; flex-direction: column; min-height: 0; }\n.ax-inbox__detail > header { padding: 14px 18px; border-bottom: 1px solid var(--ax-border); }\n.ax-inbox__detail-body { overflow-y: auto; padding: 18px; flex: 1; }\n.ax-inbox__form { max-width: 560px; display: grid; gap: 14px; }\n.ax-inbox__field { display: flex; flex-direction: column; gap: 4px; }\n.ax-inbox__field label { font-size: 12px; color: var(--ax-muted); font-weight: 600; }\n.ax-inbox__field input, .ax-inbox__field textarea, .ax-inbox__field select {\n font: inherit;\n padding: 8px 10px;\n border: 1px solid var(--ax-border);\n border-radius: 6px;\n background: var(--ax-bg);\n color: var(--ax-fg);\n}\n.ax-inbox__field textarea { min-height: 100px; resize: vertical; }\n.ax-inbox__field-hint { font-size: 11px; color: var(--ax-muted); }\n.ax-inbox__field-error { font-size: 11px; color: #c0392b; }\n.ax-inbox__actions { display: flex; gap: 8px; margin-top: 8px; }\n.ax-inbox__actions button {\n font: inherit;\n padding: 8px 14px;\n border: 1px solid var(--ax-border);\n border-radius: 6px;\n cursor: pointer;\n background: var(--ax-surface-2);\n color: var(--ax-fg);\n}\n.ax-inbox__actions button.is-primary {\n background: #2ecc71; color: white; border-color: #27ae60;\n}\n.ax-inbox__actions button:disabled { opacity: 0.5; cursor: not-allowed; }\n.ax-inbox__icon {\n background: none; border: 1px solid transparent; color: var(--ax-fg); cursor: pointer;\n font-size: 14px; padding: 4px 8px; border-radius: 4px;\n}\n.ax-inbox__icon:hover { background: var(--ax-surface-2); }\n.ax-inbox__toast {\n position: fixed; bottom: 16px; right: 16px; padding: 10px 14px;\n background: var(--ax-fg); color: var(--ax-bg); border-radius: 6px;\n font-size: 13px; z-index: 100;\n}\n`\n\n// Deliberately vanilla JS — no framework dep. Fetches task list, renders\n// per-field inputs, POSTs submission.\nconst INBOX_PAGE_SCRIPT = `\n(function(){\n const $ = (sel) => document.querySelector(sel);\n const state = { tasks: [], selected: null, actor: document.querySelector('.ax-inbox__root').dataset.actor || '' };\n const toast = (msg) => {\n const el = $('#inbox-toast');\n el.textContent = msg;\n el.hidden = false;\n setTimeout(() => { el.hidden = true; }, 2500);\n };\n\n async function fetchTasks() {\n const qs = state.actor ? ('?actor=' + encodeURIComponent(state.actor)) : '';\n try {\n const r = await fetch('/api/workflows/tasks' + qs, { credentials: 'same-origin' });\n if (!r.ok) { toast('fetch failed: ' + r.status); return; }\n const data = await r.json();\n state.tasks = Array.isArray(data.tasks) ? data.tasks : [];\n renderList();\n if (state.selected && !state.tasks.find(t => t.id === state.selected)) {\n state.selected = null;\n renderDetail();\n }\n } catch (e) { toast('fetch error: ' + e.message); }\n }\n\n function renderList() {\n const ul = $('#inbox-tasks');\n const empty = $('#inbox-empty');\n ul.innerHTML = '';\n if (!state.tasks.length) { empty.hidden = false; return; }\n empty.hidden = true;\n for (const t of state.tasks) {\n const li = document.createElement('li');\n li.className = 'ax-inbox__card' + (t.id === state.selected ? ' is-active' : '');\n li.innerHTML =\n '<div class=\"ax-inbox__card-title\">' + escHtml(t.title) + '</div>' +\n '<div class=\"ax-inbox__card-meta\">' + escHtml(t.assignee) + ' · ' + escHtml(t.workflowId) + '</div>' +\n (t.dueAt ? ('<div class=\"ax-inbox__card-due\">due ' + new Date(t.dueAt).toLocaleString() + '</div>') : '');\n li.addEventListener('click', () => { state.selected = t.id; renderList(); renderDetail(); });\n ul.appendChild(li);\n }\n }\n\n function renderDetail() {\n const head = $('#inbox-detail-head');\n const body = $('#inbox-detail-body');\n const t = state.tasks.find(x => x.id === state.selected);\n if (!t) {\n head.innerHTML = '<span class=\"hint\">Select a task to open its form.</span>';\n body.innerHTML = '';\n return;\n }\n head.innerHTML = '<h2 style=\"margin:0;font-size:15px\">' + escHtml(t.title) + '</h2>' +\n (t.description ? '<p class=\"hint\" style=\"margin:6px 0 0\">' + escHtml(t.description) + '</p>' : '');\n const form = document.createElement('form');\n form.className = 'ax-inbox__form';\n form.addEventListener('submit', (e) => { e.preventDefault(); submit(t, 'primary'); });\n for (const field of (t.form.fields || [])) {\n form.appendChild(renderField(field));\n }\n const actions = document.createElement('div');\n actions.className = 'ax-inbox__actions';\n const primary = document.createElement('button');\n primary.type = 'submit';\n primary.className = 'is-primary';\n primary.textContent = t.form.submitLabel || 'Submit';\n actions.appendChild(primary);\n if (t.form.secondaryAction) {\n const secondary = document.createElement('button');\n secondary.type = 'button';\n secondary.textContent = t.form.secondaryAction.label;\n secondary.addEventListener('click', () => submit(t, 'secondary'));\n actions.appendChild(secondary);\n }\n form.appendChild(actions);\n body.innerHTML = '';\n body.appendChild(form);\n }\n\n function renderField(field) {\n const wrap = document.createElement('div');\n wrap.className = 'ax-inbox__field';\n const label = document.createElement('label');\n label.textContent = field.label + (field.required ? ' *' : '');\n wrap.appendChild(label);\n let input;\n switch (field.type) {\n case 'long-text':\n input = document.createElement('textarea');\n break;\n case 'number':\n input = document.createElement('input'); input.type = 'number';\n break;\n case 'boolean':\n input = document.createElement('select');\n for (const v of ['', 'yes', 'no']) {\n const o = document.createElement('option'); o.value = v; o.textContent = v || '—';\n input.appendChild(o);\n }\n break;\n case 'date':\n input = document.createElement('input'); input.type = 'date';\n break;\n case 'select':\n input = document.createElement('select');\n if (!field.required) { const o = document.createElement('option'); o.value = ''; o.textContent = '—'; input.appendChild(o); }\n for (const opt of (field.options || [])) {\n const o = document.createElement('option'); o.value = opt; o.textContent = opt;\n input.appendChild(o);\n }\n break;\n case 'multi-select':\n input = document.createElement('select'); input.multiple = true; input.size = Math.min(6, (field.options||[]).length || 3);\n for (const opt of (field.options || [])) {\n const o = document.createElement('option'); o.value = opt; o.textContent = opt;\n input.appendChild(o);\n }\n break;\n case 'file':\n input = document.createElement('input'); input.type = 'text'; input.placeholder = 'URL or path';\n break;\n default:\n input = document.createElement('input'); input.type = 'text';\n }\n input.name = field.key;\n if (field.defaultValue !== undefined && field.type !== 'multi-select') input.value = String(field.defaultValue);\n wrap.appendChild(input);\n if (field.hint) {\n const hint = document.createElement('div');\n hint.className = 'ax-inbox__field-hint';\n hint.textContent = field.hint;\n wrap.appendChild(hint);\n }\n const err = document.createElement('div');\n err.className = 'ax-inbox__field-error';\n err.dataset.for = field.key;\n wrap.appendChild(err);\n return wrap;\n }\n\n async function submit(task, action) {\n const form = $('.ax-inbox__form');\n if (!form) return;\n const values = {};\n for (const field of (task.form.fields || [])) {\n const el = form.querySelector('[name=\"' + field.key + '\"]');\n if (!el) continue;\n if (field.type === 'multi-select') {\n values[field.key] = Array.from(el.selectedOptions).map(o => o.value);\n } else if (field.type === 'boolean') {\n values[field.key] = el.value;\n } else {\n values[field.key] = el.value;\n }\n }\n form.querySelectorAll('.ax-inbox__field-error').forEach(e => { e.textContent = ''; });\n try {\n const r = await fetch('/api/workflows/tasks/' + encodeURIComponent(task.id) + '/submit', {\n method: 'POST',\n credentials: 'same-origin',\n headers: { 'Content-Type': 'application/json' },\n body: JSON.stringify({ submittedBy: state.actor || 'anonymous', submission: { action, values } }),\n });\n const data = await r.json().catch(() => ({}));\n if (!r.ok) {\n if (data.fieldErrors && Array.isArray(data.fieldErrors)) {\n for (const fe of data.fieldErrors) {\n const node = form.querySelector('[data-for=\"' + fe.field + '\"]');\n if (node) node.textContent = fe.message;\n }\n toast('form has errors');\n } else {\n toast(data.error || 'submit failed');\n }\n return;\n }\n toast('submitted');\n state.selected = null;\n fetchTasks();\n } catch (e) { toast('submit error: ' + e.message); }\n }\n\n function escHtml(s) {\n return String(s).replace(/[&<>\"']/g, c => ({'&':'&','<':'<','>':'>','\"':'"',\"'\":'''})[c]);\n }\n\n $('#inbox-actor').addEventListener('change', (e) => {\n state.actor = e.target.value.trim();\n state.selected = null;\n const url = new URL(window.location.href);\n if (state.actor) url.searchParams.set('actor', state.actor); else url.searchParams.delete('actor');\n history.replaceState({}, '', url.toString());\n fetchTasks();\n });\n $('#inbox-refresh').addEventListener('click', fetchTasks);\n\n fetchTasks();\n setInterval(fetchTasks, 10000);\n})();\n`\n"],"mappings":"sEAwBO,SAASA,EAAgBC,EAAsB,CAAC,EAAW,CAChE,IAAMC,EAAO,2CAA2CC,EAAIF,EAAK,OAAS,EAAE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,yFAOWE,EAAIF,EAAK,OAAS,EAAE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,6DAmB3G,OAAOG,EAAY,CACjB,MAAO,oBACP,UAAW,YACX,SAAU,QACV,MAAOH,EAAK,MACZ,cAAeA,EAAK,cACpB,KAAAC,EACA,IAAKG,EACL,QAAS,WAAWC,YACtB,CAAC,CACH,CAEA,IAAMD,EAAiB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,EA6FjBC,EAAoB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;","names":["renderInboxPage","opts","body","esc","renderShell","INBOX_PAGE_CSS","INBOX_PAGE_SCRIPT"]}
|