@agent-native/core 0.165.3 → 0.167.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/corpus/README.md +1 -1
- package/corpus/templates/analytics/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/analytics/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/analytics/CHANGELOG.md +740 -2
- package/corpus/templates/analytics/app/components/layout/Sidebar.tsx +93 -56
- package/corpus/templates/analytics/app/i18n-data.ts +23 -20
- package/corpus/templates/analytics/app/pages/Settings.tsx +0 -1
- package/corpus/templates/analytics/app/pages/adhoc/explorer/index.tsx +0 -1
- package/corpus/templates/analytics/app/pages/adhoc/explorer-dashboard/index.tsx +1 -1
- package/corpus/templates/analytics/app/pages/adhoc/sql-dashboard/SqlChartCard.tsx +2 -1
- package/corpus/templates/analytics/app/pages/sessions/SessionsPage.tsx +0 -1
- package/corpus/templates/analytics/server/lib/first-party-analytics-backend.ts +0 -32
- package/corpus/templates/analytics/server/lib/session-replay.ts +1 -5
- package/corpus/templates/assets/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/assets/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/assets/CHANGELOG.md +204 -2
- package/corpus/templates/assets/actions/navigate.ts +2 -2
- package/corpus/templates/assets/actions/save-generated-image.ts +0 -5
- package/corpus/templates/assets/app/routes/brand-kits.$id.tsx +2 -262
- package/corpus/templates/assets/app/routes/library.tsx +1 -1
- package/corpus/templates/assets/app/routes/settings.tsx +0 -3
- package/corpus/templates/brain/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/brain/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/brain/CHANGELOG.md +145 -2
- package/corpus/templates/brain/actions/ask-brain.ts +0 -1
- package/corpus/templates/brain/actions/navigate.ts +2 -2
- package/corpus/templates/brain/app/routes/sources.tsx +0 -4
- package/corpus/templates/brain/server/lib/capture-sanitization.ts +0 -11
- package/corpus/templates/calendar/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/calendar/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/calendar/CHANGELOG.md +272 -2
- package/corpus/templates/calendar/app/components/calendar/EventDetailPopover.tsx +0 -20
- package/corpus/templates/calendar/app/pages/CalendarView.tsx +0 -1
- package/corpus/templates/chat/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/chat/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/chat/CHANGELOG.md +89 -2
- package/corpus/templates/chat/actions/navigate.ts +2 -2
- package/corpus/templates/clips/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/clips/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/clips/CHANGELOG.md +865 -2
- package/corpus/templates/clips/actions/import-loom-recording.ts +16 -4
- package/corpus/templates/clips/actions/navigate.ts +2 -2
- package/corpus/templates/clips/app/components/editor/stitch-manager.tsx +0 -1
- package/corpus/templates/clips/app/components/library/space-dialogs.tsx +0 -1
- package/corpus/templates/clips/app/components/meetings/share-meeting-dialog.tsx +0 -1
- package/corpus/templates/clips/app/components/player/clips-share-trigger.tsx +17 -0
- package/corpus/templates/clips/app/components/player/delete-recording-menu.tsx +3 -3
- package/corpus/templates/clips/app/components/player/video-player.tsx +2 -2
- package/corpus/templates/clips/app/components/recorder/recorder-engine.ts +0 -1
- package/corpus/templates/clips/app/components/settings/ai-setup-section.tsx +0 -1
- package/corpus/templates/clips/app/global.css +31 -0
- package/corpus/templates/clips/app/hooks/use-playback-position.ts +0 -2
- package/corpus/templates/clips/app/lib/download-release-channel.ts +10 -0
- package/corpus/templates/clips/app/routes/_app.meetings.$meetingId.tsx +1 -3
- package/corpus/templates/clips/app/routes/download.tsx +67 -44
- package/corpus/templates/clips/app/routes/r.$recordingId.tsx +7 -12
- package/corpus/templates/clips/app/routes/record.tsx +6 -6
- package/corpus/templates/clips/app/routes/share.$shareId.tsx +26 -29
- package/corpus/templates/clips/changelog/2026-08-20-clip-viewer-share-actions.md +6 -0
- package/corpus/templates/clips/changelog/2026-08-20-preparing-recording-countdown-overlay.md +6 -0
- package/corpus/templates/clips/chrome-extension/src/background.ts +0 -13
- package/corpus/templates/clips/chrome-extension/src/overlay.ts +0 -1
- package/corpus/templates/clips/chrome-extension/src/popup.ts +0 -20
- package/corpus/templates/clips/desktop/src/app.tsx +6 -18
- package/corpus/templates/clips/desktop/src/hooks/useMediaDevices.ts +0 -1
- package/corpus/templates/clips/desktop/src/lib/recorder.ts +0 -8
- package/corpus/templates/clips/desktop/src/overlays/preparing.tsx +4 -6
- package/corpus/templates/clips/desktop/src/styles.css +18 -20
- package/corpus/templates/clips/desktop/src-tauri/src/clips/mod.rs +9 -17
- package/corpus/templates/content/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/content/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/content/CHANGELOG.md +503 -2
- package/corpus/templates/content/actions/_database-source-utils.ts +0 -3
- package/corpus/templates/content/actions/attach-content-database-source.ts +1 -4
- package/corpus/templates/content/actions/navigate.ts +2 -2
- package/corpus/templates/content/actions/prepare-builder-source-execution.ts +1 -1
- package/corpus/templates/content/app/components/editor/DocumentProperties.tsx +0 -6
- package/corpus/templates/content/app/components/editor/database/DatabaseView.tsx +0 -580
- package/corpus/templates/content/app/components/editor/database/FormView.tsx +2 -2
- package/corpus/templates/content/app/components/editor/database/filter-sort.ts +1 -1
- package/corpus/templates/content/app/components/editor/database/settings.tsx +0 -23
- package/corpus/templates/content/app/components/editor/database/sidebar.tsx +0 -1
- package/corpus/templates/content/app/components/sidebar/DocumentSidebar.tsx +8 -304
- package/corpus/templates/content/app/hooks/use-documents.ts +0 -1
- package/corpus/templates/content/shared/api.ts +0 -1
- package/corpus/templates/content/shared/builder-mdx.ts +0 -1
- package/corpus/templates/content/shared/nfm.ts +1 -7
- package/corpus/templates/crm/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/crm/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/crm/CHANGELOG.md +31 -2
- package/corpus/templates/crm/actions/merge-crm-records.ts +0 -4
- package/corpus/templates/crm/app/components/crm/record/RecordLists.tsx +0 -1
- package/corpus/templates/crm/server/crm/hubspot-adapter.ts +0 -1
- package/corpus/templates/crm/server/crm/salesforce-adapter.ts +0 -1
- package/corpus/templates/crm/server/db/crm-store.ts +1 -1
- package/corpus/templates/design/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/design/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/design/.generated/bridge/editor-chrome.generated.ts +1 -14
- package/corpus/templates/design/AGENTS.md +2 -1
- package/corpus/templates/design/CHANGELOG.md +870 -2
- package/corpus/templates/design/actions/apply-component-prop-edit.ts +1 -5
- package/corpus/templates/design/actions/generate-design.ts +0 -1
- package/corpus/templates/design/actions/generate-screens.ts +5 -2
- package/corpus/templates/design/actions/go-to-main-component.ts +2 -2
- package/corpus/templates/design/actions/list-design-systems.ts +10 -0
- package/corpus/templates/design/actions/navigate.ts +2 -2
- package/corpus/templates/design/actions/open-component-source.ts +4 -4
- package/corpus/templates/design/actions/present-design-variants.ts +1 -2
- package/corpus/templates/design/actions/run-design-audit.ts +0 -22
- package/corpus/templates/design/actions/show-design-questions.ts +5 -2
- package/corpus/templates/design/app/components/design/DesignCanvas.tsx +19 -8
- package/corpus/templates/design/app/components/design/EditPanel.tsx +11 -183
- package/corpus/templates/design/app/components/design/MultiScreenCanvas.tsx +21 -4
- package/corpus/templates/design/app/components/design/QuestionFlow.tsx +1 -5
- package/corpus/templates/design/app/components/design/bridge/codegen.ts +1 -1
- package/corpus/templates/design/app/components/design/bridge/editor-chrome.bridge.ts +10 -19
- package/corpus/templates/design/app/components/design/edit-panel/appearance-properties.tsx +1 -1
- package/corpus/templates/design/app/components/design/edit-panel/layout-properties.tsx +13 -3
- package/corpus/templates/design/app/components/design/edit-panel/panel-primitives.tsx +38 -32
- package/corpus/templates/design/app/components/design/edit-panel/position-layout-properties.tsx +1 -4
- package/corpus/templates/design/app/components/design/inspector/AlignmentMatrix.tsx +0 -4
- package/corpus/templates/design/app/components/design/inspector/AutoLayoutMatrix.tsx +15 -6
- package/corpus/templates/design/app/components/design/inspector/DesignColorPicker.tsx +2 -2
- package/corpus/templates/design/app/components/visual-editor/NodeRewriteProposal.tsx +0 -1
- package/corpus/templates/design/app/components/visual-editor/ReviewCanvasPins.tsx +1 -1
- package/corpus/templates/design/app/i18n-data.ts +122 -0
- package/corpus/templates/design/app/lib/clipboard-content-lineage.ts +11 -1
- package/corpus/templates/design/app/pages/DesignEditor.tsx +50 -254
- package/corpus/templates/design/app/pages/DesignSystemSetup.tsx +163 -8
- package/corpus/templates/design/app/pages/Index.tsx +17 -0
- package/corpus/templates/design/app/pages/design-editor/canvas-primitive-insert.ts +44 -32
- package/corpus/templates/design/app/pages/design-editor/canvas-primitives.ts +10 -0
- package/corpus/templates/design/app/pages/design-editor/clone-and-pen-edit.ts +49 -3
- package/corpus/templates/design/app/pages/design-editor/clone-idrefs.ts +31 -0
- package/corpus/templates/design/app/pages/design-editor/code-layer-state.ts +28 -0
- package/corpus/templates/design/app/pages/design-editor/commands/add-auto-layout.ts +3 -3
- package/corpus/templates/design/app/pages/design-editor/commands/align-selection.ts +44 -14
- package/corpus/templates/design/app/pages/design-editor/commands/apply-local-content-update.ts +16 -5
- package/corpus/templates/design/app/pages/design-editor/commands/change-selected-z-index.ts +1 -1
- package/corpus/templates/design/app/pages/design-editor/commands/frame-selection.ts +1 -1
- package/corpus/templates/design/app/pages/design-editor/commands/group-selection.ts +1 -1
- package/corpus/templates/design/app/pages/design-editor/commands/nudge-selection.ts +1 -1
- package/corpus/templates/design/app/pages/design-editor/commands/paste-selection.ts +142 -17
- package/corpus/templates/design/app/pages/design-editor/commands/screen-visual-duplicate-change.ts +1 -0
- package/corpus/templates/design/app/pages/design-editor/commands/ungroup-selection.ts +1 -1
- package/corpus/templates/design/app/pages/design-editor/commands/visual-duplicate-change.ts +1 -0
- package/corpus/templates/design/app/pages/design-editor/cross-screen-text-color.ts +25 -9
- package/corpus/templates/design/app/pages/design-editor/editor-state.ts +1 -0
- package/corpus/templates/design/app/pages/design-editor/measure-child-rects.ts +83 -0
- package/corpus/templates/design/app/pages/design-editor/paste-placement.ts +66 -0
- package/corpus/templates/design/server/routes/[...page].get.ts +0 -1
- package/corpus/templates/design/shared/code-layer.ts +120 -70
- package/corpus/templates/design/shared/design-surface-index.ts +0 -1
- package/corpus/templates/design/shared/pen-path.ts +0 -4
- package/corpus/templates/dispatch/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/dispatch/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/dispatch/CHANGELOG.md +196 -2
- package/corpus/templates/dispatch/app/routes/integrations.tsx +0 -109
- package/corpus/templates/factory/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/factory/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/factory/CHANGELOG.md +121 -2
- package/corpus/templates/factory/actions/navigate.ts +2 -2
- package/corpus/templates/factory/app/components/factory/FactoryAuditView.tsx +0 -13
- package/corpus/templates/factory/app/routes/factory.tsx +0 -1
- package/corpus/templates/factory/server/factory-graph/store.ts +0 -1
- package/corpus/templates/forms/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/forms/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/forms/CHANGELOG.md +166 -2
- package/corpus/templates/macros/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/macros/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/macros/CHANGELOG.md +49 -2
- package/corpus/templates/macros/app/components/layout/AppLayout.tsx +0 -1
- package/corpus/templates/mail/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/mail/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/mail/CHANGELOG.md +201 -2
- package/corpus/templates/mail/app/components/email/EmailList.tsx +0 -1
- package/corpus/templates/mail/app/components/layout/AppLayout.tsx +2 -2
- package/corpus/templates/mail/shared/markdown.ts +3 -0
- package/corpus/templates/plan/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/plan/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/plan/CHANGELOG.md +277 -2
- package/corpus/templates/slides/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/slides/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/slides/CHANGELOG.md +437 -2
- package/corpus/templates/slides/actions/add-slide.ts +0 -1
- package/corpus/templates/slides/actions/list-decks.ts +1 -1
- package/corpus/templates/slides/app/components/editor/EditorSidebar.tsx +1 -4
- package/corpus/templates/slides/app/components/editor/SlideContextToolbar.tsx +0 -1
- package/corpus/templates/slides/app/components/editor/SlideEditor.tsx +1 -1
- package/corpus/templates/slides/app/pages/DeckEditor.tsx +1 -6
- package/corpus/templates/tasks/.agents/skills/secrets/SKILL.md +5 -1
- package/corpus/templates/tasks/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/corpus/templates/tasks/CHANGELOG.md +32 -2
- package/corpus/templates/tasks/app/components/layout/Layout.tsx +0 -1
- package/corpus/templates/tasks/app/hooks/use-visible-task-fields.ts +1 -4
- package/corpus/templates/tasks/server/custom-fields/store.ts +1 -6
- package/corpus/templates/tasks/shared/list-screen-snapshot.ts +2 -2
- package/dist/agent/engine/registry.js +27 -14
- package/dist/agent/index.d.ts +1 -1
- package/dist/agent/production-agent.d.ts +19 -6
- package/dist/agent/production-agent.js +57 -16
- package/dist/agent/types.d.ts +3 -0
- package/dist/changelog/parse.d.ts +3 -3
- package/dist/changelog/parse.js +35 -16
- package/dist/client/EnvironmentBadge.d.ts +1 -0
- package/dist/client/EnvironmentBadge.js +7 -0
- package/dist/collab/awareness.d.ts +2 -2
- package/dist/collab/routes.d.ts +1 -1
- package/dist/collab/struct-routes.d.ts +1 -1
- package/dist/config.d.ts +11 -0
- package/dist/config.js +248 -0
- package/dist/deploy/build.js +12 -1
- package/dist/index.d.ts +1 -1
- package/dist/notifications/routes.d.ts +3 -3
- package/dist/observability/routes.d.ts +6 -6
- package/dist/resources/handlers.d.ts +2 -2
- package/dist/secrets/routes.d.ts +9 -9
- package/dist/server/agent-chat/plugin-options.d.ts +3 -2
- package/dist/server/agent-chat-plugin.js +5 -2
- package/dist/server/index.d.ts +1 -1
- package/dist/server/realtime-token.d.ts +1 -1
- package/dist/server/transcribe-voice.d.ts +1 -1
- package/dist/templates/chat/.agents/skills/secrets/SKILL.md +5 -1
- package/dist/templates/chat/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/dist/templates/chat/CHANGELOG.md +89 -2
- package/dist/templates/chat/actions/navigate.ts +2 -2
- package/dist/templates/default/.agents/skills/secrets/SKILL.md +5 -1
- package/dist/templates/default/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/dist/templates/headless/.agents/skills/secrets/SKILL.md +5 -1
- package/dist/templates/workspace-core/.agents/skills/secrets/SKILL.md +5 -1
- package/dist/templates/workspace-core/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/dist/vite/agent-native-config-loader.d.ts +1 -0
- package/dist/vite/agent-native-config-loader.js +3 -3
- package/dist/vite/agents-bundle-plugin.d.ts +1 -1
- package/dist/vite/agents-bundle-plugin.js +13 -1
- package/dist/vite/client.js +14 -14
- package/docs/content/agent-native-config.mdx +62 -11
- package/docs/content/agent-surfaces.mdx +6 -0
- package/docs/content/environment-variables.mdx +5 -2
- package/package.json +3 -3
- package/src/templates/chat/.agents/skills/secrets/SKILL.md +5 -1
- package/src/templates/chat/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/src/templates/chat/CHANGELOG.md +89 -2
- package/src/templates/chat/actions/navigate.ts +2 -2
- package/src/templates/default/.agents/skills/secrets/SKILL.md +5 -1
- package/src/templates/default/.agents/skills/workspace-conventions/SKILL.md +4 -1
- package/src/templates/headless/.agents/skills/secrets/SKILL.md +5 -1
- package/src/templates/workspace-core/.agents/skills/secrets/SKILL.md +5 -1
- package/src/templates/workspace-core/.agents/skills/workspace-conventions/SKILL.md +4 -1
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
export interface FreeformGeometry {
|
|
2
|
+
container: { width: number; height: number } | null;
|
|
3
|
+
children: Record<
|
|
4
|
+
string,
|
|
5
|
+
{ x: number; y: number; width: number; height: number }
|
|
6
|
+
>;
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
const NOTHING_MEASURED: FreeformGeometry = { container: null, children: {} };
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* Container-relative geometry for a node and its direct children, read from
|
|
13
|
+
* whichever preview iframe actually holds the node — the board and each screen
|
|
14
|
+
* have their own document, so a single global iframe lookup finds the wrong one.
|
|
15
|
+
*/
|
|
16
|
+
export function measureFreeformGeometry(nodeId: string): FreeformGeometry {
|
|
17
|
+
if (typeof document === "undefined") return NOTHING_MEASURED;
|
|
18
|
+
const selector = `[data-agent-native-node-id="${CSS.escape(nodeId)}"]`;
|
|
19
|
+
const iframes = Array.from(
|
|
20
|
+
document.querySelectorAll<HTMLIFrameElement>(
|
|
21
|
+
"iframe[data-design-preview-iframe],iframe[data-screen-iframe-id]",
|
|
22
|
+
),
|
|
23
|
+
);
|
|
24
|
+
for (const iframe of iframes) {
|
|
25
|
+
let container: HTMLElement | null = null;
|
|
26
|
+
try {
|
|
27
|
+
container =
|
|
28
|
+
iframe.contentDocument?.querySelector<HTMLElement>(selector) ?? null;
|
|
29
|
+
} catch {
|
|
30
|
+
// Cross-origin preview surfaces are not measurable; try the next one.
|
|
31
|
+
continue;
|
|
32
|
+
}
|
|
33
|
+
if (!container) continue;
|
|
34
|
+
const view = container.ownerDocument.defaultView;
|
|
35
|
+
const origin = container.getBoundingClientRect();
|
|
36
|
+
// Absolute offsets resolve against the padding box, but a client rect is
|
|
37
|
+
// the border box, so a bordered container shifts every child it pins.
|
|
38
|
+
const borders = view?.getComputedStyle(container);
|
|
39
|
+
// Client rects are viewport-relative, so a scrolled container reports its
|
|
40
|
+
// children where they currently sit, not where the content box holds them.
|
|
41
|
+
const originLeft =
|
|
42
|
+
origin.left + edgeWidth(borders?.borderLeftWidth) - container.scrollLeft;
|
|
43
|
+
const originTop =
|
|
44
|
+
origin.top + edgeWidth(borders?.borderTopWidth) - container.scrollTop;
|
|
45
|
+
const rects: Record<
|
|
46
|
+
string,
|
|
47
|
+
{ x: number; y: number; width: number; height: number }
|
|
48
|
+
> = {};
|
|
49
|
+
for (const child of Array.from(container.children)) {
|
|
50
|
+
const childId = child.getAttribute("data-agent-native-node-id");
|
|
51
|
+
if (!childId) continue;
|
|
52
|
+
const rect = child.getBoundingClientRect();
|
|
53
|
+
rects[childId] = {
|
|
54
|
+
x: rect.left - originLeft,
|
|
55
|
+
y: rect.top - originTop,
|
|
56
|
+
width: rect.width,
|
|
57
|
+
height: rect.height,
|
|
58
|
+
};
|
|
59
|
+
}
|
|
60
|
+
// Own box, in the same box-sizing terms as a width/height declaration on
|
|
61
|
+
// this element, so writing it back reproduces the rendered size.
|
|
62
|
+
const own = borders
|
|
63
|
+
? {
|
|
64
|
+
width: Number.parseFloat(borders.width),
|
|
65
|
+
height: Number.parseFloat(borders.height),
|
|
66
|
+
}
|
|
67
|
+
: null;
|
|
68
|
+
return {
|
|
69
|
+
container:
|
|
70
|
+
own && Number.isFinite(own.width) && Number.isFinite(own.height)
|
|
71
|
+
? own
|
|
72
|
+
: null,
|
|
73
|
+
children: rects,
|
|
74
|
+
};
|
|
75
|
+
}
|
|
76
|
+
return NOTHING_MEASURED;
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
function edgeWidth(value: string | undefined): number {
|
|
80
|
+
const parsed = Number.parseFloat(value ?? "");
|
|
81
|
+
// A missing or non-length border computes to no edge; both mean zero inset.
|
|
82
|
+
return Number.isFinite(parsed) ? parsed : 0;
|
|
83
|
+
}
|
|
@@ -131,3 +131,69 @@ export function resolvePastePlacementForSelection(args: {
|
|
|
131
131
|
if (!node) return null;
|
|
132
132
|
return resolvePastePlacement(pasteTargetFromCodeLayerNode(node));
|
|
133
133
|
}
|
|
134
|
+
|
|
135
|
+
export interface PasteSourceAnchor {
|
|
136
|
+
fileId: string;
|
|
137
|
+
/**
|
|
138
|
+
* null when the entries do not share one resolvable parent. Never an empty
|
|
139
|
+
* array — a caller must not read "unresolved" as "insert at the root here",
|
|
140
|
+
* because the stored left/top are relative to a parent that is not there.
|
|
141
|
+
*/
|
|
142
|
+
parentSelectors: string[] | null;
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
/**
|
|
146
|
+
* A copied layer's left/top are parent-relative, so a paste that lands
|
|
147
|
+
* anywhere else reads them in the wrong coordinate space. Null means the
|
|
148
|
+
* source is unknown — never "the document root".
|
|
149
|
+
*/
|
|
150
|
+
export function resolvePasteSourceAnchor(args: {
|
|
151
|
+
entries: ReadonlyArray<{ rootNodeId?: string; sourceFileId: string }>;
|
|
152
|
+
getContent: (fileId: string) => string | undefined;
|
|
153
|
+
}): PasteSourceAnchor | null {
|
|
154
|
+
const first = args.entries[0];
|
|
155
|
+
if (!first) return null;
|
|
156
|
+
if (args.entries.some((entry) => entry.sourceFileId !== first.sourceFileId)) {
|
|
157
|
+
return null;
|
|
158
|
+
}
|
|
159
|
+
const content = args.getContent(first.sourceFileId);
|
|
160
|
+
if (!content) return null;
|
|
161
|
+
const projection = buildCodeLayerProjection(content);
|
|
162
|
+
const unresolved: PasteSourceAnchor = {
|
|
163
|
+
fileId: first.sourceFileId,
|
|
164
|
+
parentSelectors: null,
|
|
165
|
+
};
|
|
166
|
+
const parentIds = args.entries.map((entry) => {
|
|
167
|
+
const node = entry.rootNodeId
|
|
168
|
+
? projection.nodes.find(
|
|
169
|
+
(candidate) =>
|
|
170
|
+
candidate.dataAttributes["data-agent-native-node-id"] ===
|
|
171
|
+
entry.rootNodeId || candidate.id === entry.rootNodeId,
|
|
172
|
+
)
|
|
173
|
+
: undefined;
|
|
174
|
+
return node?.parentId ?? null;
|
|
175
|
+
});
|
|
176
|
+
const [sharedParentId] = parentIds;
|
|
177
|
+
// Layers copied out of different parents have no common coordinate space, so
|
|
178
|
+
// forcing them into the first one's parent moves the rest.
|
|
179
|
+
if (!sharedParentId || parentIds.some((id) => id !== sharedParentId)) {
|
|
180
|
+
return unresolved;
|
|
181
|
+
}
|
|
182
|
+
const parent = projection.nodes.find(
|
|
183
|
+
(candidate) => candidate.id === sharedParentId,
|
|
184
|
+
);
|
|
185
|
+
if (!parent) return unresolved;
|
|
186
|
+
const parentNodeId = parent.dataAttributes["data-agent-native-node-id"];
|
|
187
|
+
const parentSelectors = [
|
|
188
|
+
// A node-id selector is unique by construction; the projection's
|
|
189
|
+
// class/path aliases can match several siblings, and
|
|
190
|
+
// insertClonedHtmlLayers fails closed on that ambiguity.
|
|
191
|
+
parentNodeId
|
|
192
|
+
? `[data-agent-native-node-id="${parentNodeId.replace(/["\\]/g, "\\$&")}"]`
|
|
193
|
+
: null,
|
|
194
|
+
parent.selector,
|
|
195
|
+
...parent.selectors,
|
|
196
|
+
].filter((selector): selector is string => Boolean(selector));
|
|
197
|
+
if (parentSelectors.length === 0) return unresolved;
|
|
198
|
+
return { fileId: first.sourceFileId, parentSelectors };
|
|
199
|
+
}
|
|
@@ -498,6 +498,17 @@ export interface AutoLayoutEditIntent {
|
|
|
498
498
|
enabled: boolean;
|
|
499
499
|
direction?: "row" | "column";
|
|
500
500
|
gap?: string;
|
|
501
|
+
/**
|
|
502
|
+
* Measured child geometry, container-relative, keyed by stable node id.
|
|
503
|
+
* Supplied when disabling so children keep their rendered positions and
|
|
504
|
+
* become freely draggable; without it they re-stack in block flow.
|
|
505
|
+
*/
|
|
506
|
+
childRects?: Record<
|
|
507
|
+
string,
|
|
508
|
+
{ x: number; y: number; width: number; height: number }
|
|
509
|
+
>;
|
|
510
|
+
/** Rendered size of the container, so it cannot collapse once flow empties. */
|
|
511
|
+
containerRect?: { width: number; height: number };
|
|
501
512
|
}
|
|
502
513
|
|
|
503
514
|
/**
|
|
@@ -950,17 +961,6 @@ function cssIdent(value: string): string | null {
|
|
|
950
961
|
return null;
|
|
951
962
|
}
|
|
952
963
|
|
|
953
|
-
function unquoteHtmlAttributeValue(value: string): string {
|
|
954
|
-
const trimmed = value.trim();
|
|
955
|
-
if (
|
|
956
|
-
(trimmed.startsWith('"') && trimmed.endsWith('"')) ||
|
|
957
|
-
(trimmed.startsWith("'") && trimmed.endsWith("'"))
|
|
958
|
-
) {
|
|
959
|
-
return trimmed.slice(1, -1);
|
|
960
|
-
}
|
|
961
|
-
return trimmed;
|
|
962
|
-
}
|
|
963
|
-
|
|
964
964
|
function escapeHtmlAttribute(value: string): string {
|
|
965
965
|
return value
|
|
966
966
|
.replace(/&/g, "&")
|
|
@@ -1777,18 +1777,6 @@ function utilityToStyleProperty(
|
|
|
1777
1777
|
return null;
|
|
1778
1778
|
}
|
|
1779
1779
|
|
|
1780
|
-
function classStyleToken(token: string): StyleToken | null {
|
|
1781
|
-
const { utility } = parseClassToken(token);
|
|
1782
|
-
const mapped = utilityToStyleProperty(utility);
|
|
1783
|
-
if (!mapped) return null;
|
|
1784
|
-
const { property, confidence } = mapped;
|
|
1785
|
-
// The legacy value field preserves the original full token (including prefix)
|
|
1786
|
-
// for backward compatibility. The responsive path uses `breakpointValues`.
|
|
1787
|
-
const value =
|
|
1788
|
-
property === "display" ? (utility === "hidden" ? "none" : utility) : token;
|
|
1789
|
-
return { property, value, token, source: "class", confidence };
|
|
1790
|
-
}
|
|
1791
|
-
|
|
1792
1780
|
function layoutFor(
|
|
1793
1781
|
element: ParsedElement,
|
|
1794
1782
|
parent: ParsedElement | undefined,
|
|
@@ -3385,43 +3373,6 @@ const FLEX_ITEM_STRIP_PROPS = [
|
|
|
3385
3373
|
"order",
|
|
3386
3374
|
] as const;
|
|
3387
3375
|
|
|
3388
|
-
/**
|
|
3389
|
-
* Apply display:flex + direction + gap to a raw open-tag string and return it.
|
|
3390
|
-
* Only touches the style attribute.
|
|
3391
|
-
*/
|
|
3392
|
-
function addAutoLayoutStyleToOpenTag(
|
|
3393
|
-
openTag: string,
|
|
3394
|
-
element: ParsedElement,
|
|
3395
|
-
html: string,
|
|
3396
|
-
direction: "row" | "column",
|
|
3397
|
-
gap: string,
|
|
3398
|
-
): string {
|
|
3399
|
-
const currentStyle = attributeValue(element, "style");
|
|
3400
|
-
let declarations = parseStyleDeclarations(currentStyle);
|
|
3401
|
-
const setOrReplace = (prop: string, val: string) => {
|
|
3402
|
-
const existing = declarations.find((d) => d.property === prop);
|
|
3403
|
-
if (existing) {
|
|
3404
|
-
existing.value = val;
|
|
3405
|
-
} else {
|
|
3406
|
-
declarations.push({ property: prop, value: val });
|
|
3407
|
-
}
|
|
3408
|
-
};
|
|
3409
|
-
setOrReplace("display", "flex");
|
|
3410
|
-
setOrReplace("flex-direction", direction);
|
|
3411
|
-
setOrReplace("gap", gap);
|
|
3412
|
-
const nextStyle = serializeStyleDeclarations(declarations);
|
|
3413
|
-
// We work on a scratch copy relative to element boundaries
|
|
3414
|
-
const attr = getAttribute(element, "style");
|
|
3415
|
-
if (attr) {
|
|
3416
|
-
return `${openTag.slice(0, attr.start - element.start)}${attr.name}="${escapeHtmlAttribute(nextStyle)}"${openTag.slice(attr.end - element.start)}`;
|
|
3417
|
-
}
|
|
3418
|
-
// Insert before closing >
|
|
3419
|
-
const closeChar = openTag.endsWith("/>")
|
|
3420
|
-
? openTag.length - 2
|
|
3421
|
-
: openTag.length - 1;
|
|
3422
|
-
return `${openTag.slice(0, closeChar)} style="${escapeHtmlAttribute(nextStyle)}"${openTag.slice(closeChar)}`;
|
|
3423
|
-
}
|
|
3424
|
-
|
|
3425
3376
|
/**
|
|
3426
3377
|
* Strip absolute-positioning properties from a child's inline style, applying
|
|
3427
3378
|
* the edit directly to the html string at the child element's source spans.
|
|
@@ -3889,6 +3840,13 @@ function applyUnwrap(
|
|
|
3889
3840
|
/**
|
|
3890
3841
|
* CONVERT: toggle auto-layout (display:flex) on an existing container.
|
|
3891
3842
|
*/
|
|
3843
|
+
/** Whether an existing min-width/min-height already preserves `extent` px. */
|
|
3844
|
+
function holdsOpen(value: string, extent: number): boolean {
|
|
3845
|
+
const trimmed = value.trim();
|
|
3846
|
+
if (!/^[\d.]+px$/i.test(trimmed)) return !/^0[a-z%]*$/i.test(trimmed);
|
|
3847
|
+
return Number.parseFloat(trimmed) >= extent;
|
|
3848
|
+
}
|
|
3849
|
+
|
|
3892
3850
|
function applyAutoLayout(
|
|
3893
3851
|
html: string,
|
|
3894
3852
|
build: ProjectionBuild,
|
|
@@ -3907,21 +3865,113 @@ function applyAutoLayout(
|
|
|
3907
3865
|
if (!element) return "conflict";
|
|
3908
3866
|
|
|
3909
3867
|
if (!enabled) {
|
|
3910
|
-
|
|
3868
|
+
const childRects = intent.childRects;
|
|
3869
|
+
const hasRects = !!childRects && Object.keys(childRects).length > 0;
|
|
3911
3870
|
const currentStyle = attributeValue(element, "style");
|
|
3912
|
-
|
|
3913
|
-
const
|
|
3914
|
-
|
|
3915
|
-
|
|
3916
|
-
|
|
3917
|
-
|
|
3871
|
+
const declarations = parseStyleDeclarations(currentStyle);
|
|
3872
|
+
const setOnContainer = (property: string, value: string) => {
|
|
3873
|
+
const existing = declarations.find((d) => d.property === property);
|
|
3874
|
+
if (existing) existing.value = value;
|
|
3875
|
+
else declarations.push({ property, value });
|
|
3876
|
+
};
|
|
3877
|
+
setOnContainer("display", "block");
|
|
3878
|
+
if (hasRects) {
|
|
3879
|
+
// Absolute children resolve against the nearest positioned ancestor, so
|
|
3880
|
+
// a static container would let them escape to the page.
|
|
3881
|
+
const position = declarations.find((d) => d.property === "position");
|
|
3882
|
+
if (!position || position.value === "static") {
|
|
3883
|
+
setOnContainer("position", "relative");
|
|
3884
|
+
}
|
|
3885
|
+
// With every child absolute the content box is empty, so a hug-sized
|
|
3886
|
+
// container collapses and overflow:hidden then hides what we just pinned.
|
|
3887
|
+
const rect = intent.containerRect;
|
|
3888
|
+
if (rect) {
|
|
3889
|
+
for (const [property, value] of [
|
|
3890
|
+
["min-width", rect.width],
|
|
3891
|
+
["min-height", rect.height],
|
|
3892
|
+
] as const) {
|
|
3893
|
+
const existing = declarations.find((d) => d.property === property);
|
|
3894
|
+
// `min-height: 0` is the standard flex idiom and holds nothing open.
|
|
3895
|
+
// Only a px minimum at least as large as the measured extent does.
|
|
3896
|
+
if (existing && !holdsOpen(existing.value, value)) {
|
|
3897
|
+
existing.value = `${Math.round(value)}px`;
|
|
3898
|
+
} else if (!existing) {
|
|
3899
|
+
declarations.push({ property, value: `${Math.round(value)}px` });
|
|
3900
|
+
}
|
|
3901
|
+
}
|
|
3902
|
+
}
|
|
3903
|
+
}
|
|
3904
|
+
let result = replaceOrInsertAttribute(
|
|
3905
|
+
html,
|
|
3906
|
+
element,
|
|
3907
|
+
"style",
|
|
3908
|
+
serializeStyleDeclarations(declarations),
|
|
3909
|
+
);
|
|
3910
|
+
if (!hasRects) {
|
|
3911
|
+
return {
|
|
3912
|
+
content: result,
|
|
3913
|
+
capability: { kind: "style", properties: ["display"], confidence: 0.9 },
|
|
3914
|
+
};
|
|
3915
|
+
}
|
|
3916
|
+
|
|
3917
|
+
const updatedElements = parseHtmlElements(result);
|
|
3918
|
+
const targetAttr = attributeValue(element, "data-agent-native-node-id");
|
|
3919
|
+
const updatedTarget =
|
|
3920
|
+
(targetAttr
|
|
3921
|
+
? updatedElements.find(
|
|
3922
|
+
(fe) =>
|
|
3923
|
+
attributeValue(fe, "data-agent-native-node-id") === targetAttr,
|
|
3924
|
+
)
|
|
3925
|
+
: undefined) ??
|
|
3926
|
+
updatedElements.find((fe) => fe.start === element.start);
|
|
3927
|
+
if (updatedTarget) {
|
|
3928
|
+
// Reverse order keeps earlier offsets valid as each write shifts the rest.
|
|
3929
|
+
for (const childIndex of [...updatedTarget.childIndexes].reverse()) {
|
|
3930
|
+
const child = updatedElements[childIndex];
|
|
3931
|
+
if (!child) continue;
|
|
3932
|
+
const childId = attributeValue(child, "data-agent-native-node-id");
|
|
3933
|
+
const rect = childId ? childRects[childId] : undefined;
|
|
3934
|
+
if (!rect) continue;
|
|
3935
|
+
const childDecls = parseStyleDeclarations(
|
|
3936
|
+
attributeValue(child, "style"),
|
|
3937
|
+
);
|
|
3938
|
+
const setOnChild = (property: string, value: string) => {
|
|
3939
|
+
const existing = childDecls.find((d) => d.property === property);
|
|
3940
|
+
if (existing) existing.value = value;
|
|
3941
|
+
else childDecls.push({ property, value });
|
|
3942
|
+
};
|
|
3943
|
+
// The measured rect is a border box placed by its margin edge, so a
|
|
3944
|
+
// content-box child would grow by its padding and a margin would shift
|
|
3945
|
+
// it off the position we just measured.
|
|
3946
|
+
setOnChild("box-sizing", "border-box");
|
|
3947
|
+
setOnChild("margin", "0");
|
|
3948
|
+
setOnChild("position", "absolute");
|
|
3949
|
+
setOnChild("left", `${Math.round(rect.x)}px`);
|
|
3950
|
+
setOnChild("top", `${Math.round(rect.y)}px`);
|
|
3951
|
+
setOnChild("width", `${Math.round(rect.width)}px`);
|
|
3952
|
+
setOnChild("height", `${Math.round(rect.height)}px`);
|
|
3953
|
+
result = replaceOrInsertAttribute(
|
|
3954
|
+
result,
|
|
3955
|
+
child,
|
|
3956
|
+
"style",
|
|
3957
|
+
serializeStyleDeclarations(childDecls),
|
|
3958
|
+
);
|
|
3959
|
+
}
|
|
3918
3960
|
}
|
|
3919
|
-
const nextStyle = serializeStyleDeclarations(declarations);
|
|
3920
3961
|
return {
|
|
3921
|
-
content:
|
|
3962
|
+
content: result,
|
|
3922
3963
|
capability: {
|
|
3923
3964
|
kind: "style",
|
|
3924
|
-
properties: [
|
|
3965
|
+
properties: [
|
|
3966
|
+
"display",
|
|
3967
|
+
"position",
|
|
3968
|
+
"min-width",
|
|
3969
|
+
"min-height",
|
|
3970
|
+
"left",
|
|
3971
|
+
"top",
|
|
3972
|
+
"width",
|
|
3973
|
+
"height",
|
|
3974
|
+
],
|
|
3925
3975
|
confidence: 0.9,
|
|
3926
3976
|
},
|
|
3927
3977
|
};
|
|
@@ -38,7 +38,11 @@ connection exists:
|
|
|
38
38
|
register a `kind: "oauth"` entry so the shared UI renders Connect and the
|
|
39
39
|
runtime owns status, refresh, and reauthorization.
|
|
40
40
|
- **Deploy- or app-level configuration** - use deployment/runtime
|
|
41
|
-
configuration, not a per-user secret row.
|
|
41
|
+
configuration, not a per-user secret row. For a non-secret public setting
|
|
42
|
+
already represented by `AgentNativeConfig`, put the default in
|
|
43
|
+
`agent-native.config.ts` and use its `AGENT_NATIVE_CONFIG_<PATH>` alias only
|
|
44
|
+
for a deployment override. Never put a credential or provider key in that
|
|
45
|
+
public namespace.
|
|
42
46
|
- **Account, customer, manager, or other non-secret identifier** - store it as
|
|
43
47
|
scoped connection metadata or app data, not as a masked secret field.
|
|
44
48
|
|
|
@@ -55,7 +55,10 @@ Preview before `--apply`, commit `agent-native.ejections.json`, and never edit
|
|
|
55
55
|
ZIPs, screenshots, thumbnails, session replay chunks) in configured file/blob
|
|
56
56
|
storage and persist only URLs, ids, or handles.
|
|
57
57
|
- Store shared runtime configuration in the workspace root `.env`; use
|
|
58
|
-
`apps/<app>/.env` only for app-specific overrides.
|
|
58
|
+
`apps/<app>/.env` only for app-specific overrides. For public app behavior,
|
|
59
|
+
prefer the default in `agent-native.config.ts` and use the deterministic
|
|
60
|
+
`AGENT_NATIVE_CONFIG_<UPPER_SNAKE_PATH>` alias only when a non-secret value
|
|
61
|
+
needs a deployment override. Never hardcode API keys,
|
|
59
62
|
tokens, webhook URLs, signing secrets, private Builder/internal data, customer
|
|
60
63
|
data, or credential-looking literals in source, docs, prompts, fixtures,
|
|
61
64
|
application state, action responses, or generated app content. Use
|
|
@@ -3,8 +3,6 @@
|
|
|
3
3
|
All notable user-facing changes to Agent-Native Dispatch are documented here. Open it any
|
|
4
4
|
time from the command menu (Cmd+K → "What's new").
|
|
5
5
|
|
|
6
|
-
Older updates live in [the changelog folder](./changelog/) and are included in the in-app "What's new" view.
|
|
7
|
-
|
|
8
6
|
## 2026-08-20
|
|
9
7
|
|
|
10
8
|
### Fixed
|
|
@@ -57,3 +55,199 @@ Older updates live in [the changelog folder](./changelog/) and are included in t
|
|
|
57
55
|
### Added
|
|
58
56
|
|
|
59
57
|
- Chat-first navigation keeps conversations central while opening workspace apps and watched sessions beside them.
|
|
58
|
+
|
|
59
|
+
## 2026-08-07
|
|
60
|
+
|
|
61
|
+
### Changed
|
|
62
|
+
|
|
63
|
+
- Language selection now lives in Settings instead of the Dispatch header.
|
|
64
|
+
|
|
65
|
+
## 2026-08-06
|
|
66
|
+
|
|
67
|
+
### Improved
|
|
68
|
+
|
|
69
|
+
- Dispatch keeps everyday navigation focused while management tools live in a dedicated Admin area
|
|
70
|
+
- Ready workspace apps stay one click away in a compact Dispatch navigation rail
|
|
71
|
+
|
|
72
|
+
### Security
|
|
73
|
+
|
|
74
|
+
- Shared Vault values and management are now restricted to workspace owners and admins
|
|
75
|
+
|
|
76
|
+
## 2026-08-05
|
|
77
|
+
|
|
78
|
+
### Fixed
|
|
79
|
+
|
|
80
|
+
- Transactional email catalogs and delivery activity are available in Dispatch again.
|
|
81
|
+
|
|
82
|
+
## 2026-08-04
|
|
83
|
+
|
|
84
|
+
### Improved
|
|
85
|
+
|
|
86
|
+
- Dispatch keeps connected chats out of local history by default and lets you show all sources on demand.
|
|
87
|
+
|
|
88
|
+
## 2026-08-03
|
|
89
|
+
|
|
90
|
+
### Improved
|
|
91
|
+
|
|
92
|
+
- Automation details now show scheduler checks, past runs, and actionable failure diagnostics
|
|
93
|
+
|
|
94
|
+
## 2026-07-30
|
|
95
|
+
|
|
96
|
+
### Improved
|
|
97
|
+
|
|
98
|
+
- Delegated Dispatch work can now continue reliably in the background.
|
|
99
|
+
- Thread Debug now lists recent failed agent runs across connected workspace apps for one-click inspection.
|
|
100
|
+
|
|
101
|
+
## 2026-07-29
|
|
102
|
+
|
|
103
|
+
### Added
|
|
104
|
+
|
|
105
|
+
- Browser chat can securely connect the Agent-Native Chrome extension to Dispatch with page context.
|
|
106
|
+
|
|
107
|
+
### Fixed
|
|
108
|
+
|
|
109
|
+
- Workspace members without admin access now see a clear permission message when opening usage metrics.
|
|
110
|
+
|
|
111
|
+
## 2026-07-28
|
|
112
|
+
|
|
113
|
+
### Improved
|
|
114
|
+
|
|
115
|
+
- Pending apps are hidden by default and app ownership details are available from the overflow menu
|
|
116
|
+
|
|
117
|
+
## 2026-07-27
|
|
118
|
+
|
|
119
|
+
### Improved
|
|
120
|
+
|
|
121
|
+
- Creating an app from a curated template now uses clearer, more direct language.
|
|
122
|
+
- Thread Debug can open a run directly from the copied request ID in an Agent Native chat.
|
|
123
|
+
|
|
124
|
+
## 2026-07-26
|
|
125
|
+
|
|
126
|
+
### Fixed
|
|
127
|
+
|
|
128
|
+
- Slack replies now recover after a connected app finishes an update, without repeating the update or losing the delivered reply from future thread context.
|
|
129
|
+
|
|
130
|
+
## 2026-07-25
|
|
131
|
+
|
|
132
|
+
### Improved
|
|
133
|
+
|
|
134
|
+
- App branding now uses the product name without the Agent-Native prefix.
|
|
135
|
+
- Settings navigation now keeps Manage agent as a dedicated linked destination at the bottom.
|
|
136
|
+
|
|
137
|
+
## 2026-07-24
|
|
138
|
+
|
|
139
|
+
### Improved
|
|
140
|
+
|
|
141
|
+
- Secondary controls and dashboard surfaces now use quieter borderless styling.
|
|
142
|
+
- Sidebar utility controls now follow a consistent footer order.
|
|
143
|
+
|
|
144
|
+
### Fixed
|
|
145
|
+
|
|
146
|
+
- Signing in now reliably puts you in your company's workspace instead of stranding you in a personal one, and the workspace switcher stays reachable when the sidebar is collapsed.
|
|
147
|
+
|
|
148
|
+
## 2026-07-23
|
|
149
|
+
|
|
150
|
+
### Improved
|
|
151
|
+
|
|
152
|
+
- Agent settings are clearly labeled Manage agent in the sidebar.
|
|
153
|
+
- Dispatch keeps messaging setup and destination details behind focused expandable panels.
|
|
154
|
+
|
|
155
|
+
## 2026-07-22
|
|
156
|
+
|
|
157
|
+
### Improved
|
|
158
|
+
|
|
159
|
+
- Manage agent navigation now uses the connected-nodes icon.
|
|
160
|
+
|
|
161
|
+
## 2026-07-21
|
|
162
|
+
|
|
163
|
+
### Fixed
|
|
164
|
+
|
|
165
|
+
- Slack agent requests recover automatically when the first background handoff is interrupted.
|
|
166
|
+
|
|
167
|
+
## 2026-07-17
|
|
168
|
+
|
|
169
|
+
### Added
|
|
170
|
+
|
|
171
|
+
- Dispatch now offers curated workspace templates that can be used to create private apps.
|
|
172
|
+
|
|
173
|
+
### Improved
|
|
174
|
+
|
|
175
|
+
- Dispatch now links to other available apps from the Apps page.
|
|
176
|
+
|
|
177
|
+
### Fixed
|
|
178
|
+
|
|
179
|
+
- The agent chat sidebar stays closed until you open it or start a chat handoff.
|
|
180
|
+
|
|
181
|
+
## 2026-07-14
|
|
182
|
+
|
|
183
|
+
### Fixed
|
|
184
|
+
|
|
185
|
+
- Dispatch now distinguishes connected agents from locally mounted apps when routing cross-app work.
|
|
186
|
+
|
|
187
|
+
## 2026-07-13
|
|
188
|
+
|
|
189
|
+
### Added
|
|
190
|
+
|
|
191
|
+
- New Agent page: see and manage your agent's context, files, connections, jobs, and external access in one place
|
|
192
|
+
|
|
193
|
+
## 2026-07-11
|
|
194
|
+
|
|
195
|
+
### Improved
|
|
196
|
+
|
|
197
|
+
- Dispatch MCP connections now start with safer app access and stay signed in more reliably in ChatGPT.
|
|
198
|
+
- Overview and Chat now share a cleaner flow with cross-app prompting, smoother transitions, and a stable bottom chat field.
|
|
199
|
+
|
|
200
|
+
### Fixed
|
|
201
|
+
|
|
202
|
+
- Data loading failures now show a clear error with a retry option instead of appearing as empty lists.
|
|
203
|
+
|
|
204
|
+
## 2026-07-10
|
|
205
|
+
|
|
206
|
+
### Added
|
|
207
|
+
|
|
208
|
+
- Connect Slack workspaces with OAuth, Agent view, and direct messages, then manage channel identity, memory, routines, policies, and AI budgets.
|
|
209
|
+
- Microsoft Teams bots and Discord slash commands can now connect with verified webhooks, while Telegram topics and WhatsApp replies preserve conversation context.
|
|
210
|
+
|
|
211
|
+
### Improved
|
|
212
|
+
|
|
213
|
+
- Dispatch now has a cleaner chat history and quieter sidebar identity.
|
|
214
|
+
- Dispatch now groups its workspace controls more clearly and adds an Operations console for agent monitoring, experiments, feedback, and Code-mode database inspection.
|
|
215
|
+
- Slack and Telegram now route uptime-monitor requests to Analytics and return the created monitor link
|
|
216
|
+
|
|
217
|
+
## 2026-07-08
|
|
218
|
+
|
|
219
|
+
### Added
|
|
220
|
+
|
|
221
|
+
- Added an Automations page to review, pause, and create scheduled or event-triggered jobs.
|
|
222
|
+
|
|
223
|
+
### Improved
|
|
224
|
+
|
|
225
|
+
- Destinations now shows outbound delivery-queue health, and Overview links quietly to Automations and other workspace tools.
|
|
226
|
+
- Settings are cleaner and searchable, with a consistent navigation that jumps straight to any setting.
|
|
227
|
+
|
|
228
|
+
## 2026-07-07
|
|
229
|
+
|
|
230
|
+
### Improved
|
|
231
|
+
|
|
232
|
+
- Overview is now just Ask Dispatch and a list of apps you can open.
|
|
233
|
+
|
|
234
|
+
## 2026-06-29
|
|
235
|
+
|
|
236
|
+
### Fixed
|
|
237
|
+
|
|
238
|
+
- Integration layouts now adapt cleanly when the agent sidebar narrows the app.
|
|
239
|
+
|
|
240
|
+
## 2026-06-27
|
|
241
|
+
|
|
242
|
+
### Fixed
|
|
243
|
+
|
|
244
|
+
- Traditional Chinese copy now uses Taiwan terminology and clearer technical wording.
|
|
245
|
+
|
|
246
|
+
## 2026-06-24
|
|
247
|
+
|
|
248
|
+
### Added
|
|
249
|
+
|
|
250
|
+
- A new Settings page gives quick access to language, workspace, and agent preferences.
|
|
251
|
+
- Added a language picker and localized app chrome for supported languages.
|
|
252
|
+
|
|
253
|
+
For the full list of updates, see the [changelog folder](./changelog/).
|