wizards 0.2.8 → 0.2.9
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/apps/runtime/dist/agents/project-assistant.js +16 -2
- package/apps/runtime/dist/agents/website.js +48 -10
- package/apps/runtime/dist/app.js +2 -0
- package/apps/runtime/dist/db/control-schema.js +18 -1
- package/apps/runtime/dist/db/migrations/control/0007_common_the_hand.sql +15 -0
- package/apps/runtime/dist/db/migrations/control/meta/0007_snapshot.json +460 -0
- package/apps/runtime/dist/db/migrations/control/meta/_journal.json +7 -0
- package/apps/runtime/dist/db/migrations/tenant/0006_hard_war_machine.sql +30 -0
- package/apps/runtime/dist/db/migrations/tenant/meta/0006_snapshot.json +1696 -0
- package/apps/runtime/dist/db/migrations/tenant/meta/_journal.json +7 -0
- package/apps/runtime/dist/db/schema.js +12 -6
- package/apps/runtime/dist/engine/steps.js +3 -0
- package/apps/runtime/dist/env.js +2 -0
- package/apps/runtime/dist/index.js +2 -0
- package/apps/runtime/dist/plugins/events.js +37 -14
- package/apps/runtime/dist/plugins/jobs.js +64 -0
- package/apps/runtime/dist/plugins/loader.js +67 -4
- package/apps/runtime/dist/plugins/public.js +31 -0
- package/apps/runtime/dist/plugins/registry.js +5 -0
- package/apps/runtime/dist/routes/plugin-public.js +59 -0
- package/apps/runtime/dist/routes/plugins.js +1 -1
- package/apps/runtime/dist/routes/studio.js +3 -0
- package/apps/runtime/dist/services/project-files.js +4 -0
- package/apps/runtime/dist/services/project-index.js +69 -9
- package/apps/runtime/dist/services/projects.js +7 -1
- package/apps/runtime/dist/services/spaces.js +2 -0
- package/apps/runtime/dist/tools/index.js +3 -2
- package/apps/runtime/dist/tools/plugin.js +89 -17
- package/apps/runtime/dist/tools/project.js +39 -31
- package/apps/web/dist/assets/Account-ZAqYVN9S.js +1 -0
- package/apps/web/dist/assets/{ChangelogDialog-BNQ9yup8.js → ChangelogDialog-CzdNuUMU.js} +1 -1
- package/apps/web/dist/assets/{ChatPanel-CtE1wcUD.js → ChatPanel-CDkHMh5g.js} +1 -1
- package/apps/web/dist/assets/{EditorPage-CAxamSak.js → EditorPage-D4mertxP.js} +2 -2
- package/apps/web/dist/assets/{FlowPreview-B3IxmikV.js → FlowPreview-DWYKllel.js} +1 -1
- package/apps/web/dist/assets/{Harness-Bo-kwm1H.js → Harness-WJ0jpIl3.js} +1 -1
- package/apps/web/dist/assets/{HomePage-BdIa2zcg.js → HomePage-2Zn7et7Z.js} +1 -1
- package/apps/web/dist/assets/{ImportWizard-DMea5ZH1.js → ImportWizard-Dn7AiRgV.js} +1 -1
- package/apps/web/dist/assets/{LocalRuntime-DFswQjxc.js → LocalRuntime-BggRFDJt.js} +1 -1
- package/apps/web/dist/assets/{NewWizardPage-Cnb6UYme.js → NewWizardPage-k-xPHAwe.js} +2 -2
- package/apps/web/dist/assets/ProjectPage-CZgR1dQj.js +2 -0
- package/apps/web/dist/assets/{PublicRunner-CIHEMLlN.js → PublicRunner-BsvhBQMD.js} +1 -1
- package/apps/web/dist/assets/{RunnerView-COKGppwq.js → RunnerView-0srHaE2T.js} +1 -1
- package/apps/web/dist/assets/SettingsPage-CNsK0n6L.js +1 -0
- package/apps/web/dist/assets/{SetupPage-Bk4qXYZV.js → SetupPage-BXQ6wfWP.js} +1 -1
- package/apps/web/dist/assets/{SharePage-ChEtCkhn.js → SharePage-CA8uuk9K.js} +1 -1
- package/apps/web/dist/assets/changelog-D7O5icPX.js +1 -0
- package/apps/web/dist/assets/{esm-Rtjq9ReB.js → esm-BbARZ7EE.js} +1 -1
- package/apps/web/dist/assets/index-BQQihL4r.js +10 -0
- package/apps/web/dist/assets/{meta-MVWkLr9H.js → meta-Dsb9LZTu.js} +1 -1
- package/apps/web/dist/assets/{outputs-s8BpXH6V.js → outputs-C806GWxt.js} +1 -1
- package/apps/web/dist/index.html +1 -1
- package/node_modules/@engenty-wizards/plugin-sdk/dist/index.d.ts +183 -0
- package/node_modules/@engenty-wizards/plugin-sdk/dist/studio.d.ts +48 -3
- package/node_modules/@engenty-wizards/shared/dist/projects.d.ts +7 -1
- package/package.json +1 -1
- package/apps/web/dist/assets/Account-YJEQEo5k.js +0 -1
- package/apps/web/dist/assets/ProjectPage-CR_FIUya.js +0 -2
- package/apps/web/dist/assets/SettingsPage-BqAogRSI.js +0 -1
- package/apps/web/dist/assets/changelog-C03GWYid.js +0 -1
- package/apps/web/dist/assets/index-BAQ2e4is.js +0 -10
|
@@ -5,6 +5,7 @@ import { z } from "zod";
|
|
|
5
5
|
import { db, schema } from "../db/client.js";
|
|
6
6
|
import { env } from "../env.js";
|
|
7
7
|
import { managed, tenantInfo } from "../manage.js";
|
|
8
|
+
import { spaceChanged } from "../plugins/events.js";
|
|
8
9
|
import { currentTenant } from "../tenants/tenant.js";
|
|
9
10
|
import { mayBuild, requireBuild, requireWritable } from "./access.js";
|
|
10
11
|
import { notFound, ServiceError } from "./errors.js";
|
|
@@ -73,9 +74,11 @@ const synced = () => and(eq(schema.project.tenantId, currentTenant()), eq(schema
|
|
|
73
74
|
async function ensureProject() {
|
|
74
75
|
const any = await db.query.project.findFirst({ where: madeHere() });
|
|
75
76
|
if (!any) {
|
|
77
|
+
const id = nanoid(12);
|
|
76
78
|
await db
|
|
77
79
|
.insert(schema.project)
|
|
78
|
-
.values({ id
|
|
80
|
+
.values({ id, tenantId: currentTenant(), name: "Meine Wizards" });
|
|
81
|
+
spaceChanged("space.created", id);
|
|
79
82
|
}
|
|
80
83
|
}
|
|
81
84
|
/**
|
|
@@ -144,6 +147,7 @@ export async function createProject(_userId, name) {
|
|
|
144
147
|
await db
|
|
145
148
|
.insert(schema.project)
|
|
146
149
|
.values({ id, tenantId: currentTenant(), name, brand: {}, mcpServers: [] });
|
|
150
|
+
spaceChanged("space.created", id);
|
|
147
151
|
return { id };
|
|
148
152
|
}
|
|
149
153
|
export async function updateProject(userId, projectId, patch) {
|
|
@@ -172,6 +176,7 @@ export async function updateProject(userId, projectId, patch) {
|
|
|
172
176
|
updatedAt: new Date(),
|
|
173
177
|
})
|
|
174
178
|
.where(eq(schema.project.id, p.id));
|
|
179
|
+
spaceChanged("space.updated", p.id);
|
|
175
180
|
}
|
|
176
181
|
export function projectProfile(p) {
|
|
177
182
|
return {
|
|
@@ -202,4 +207,5 @@ export async function removeProject(projectId) {
|
|
|
202
207
|
await db
|
|
203
208
|
.delete(schema.project)
|
|
204
209
|
.where(and(eq(schema.project.id, projectId), eq(schema.project.tenantId, currentTenant())));
|
|
210
|
+
spaceChanged("space.deleted", projectId);
|
|
205
211
|
}
|
|
@@ -7,6 +7,7 @@ import { z } from "zod";
|
|
|
7
7
|
import { db, inTransaction, schema } from "../db/client.js";
|
|
8
8
|
import { missingModels, unavoidableSteps } from "../engine/requirements.js";
|
|
9
9
|
import { env } from "../env.js";
|
|
10
|
+
import { spaceChanged } from "../plugins/events.js";
|
|
10
11
|
import { codeOf, putLink } from "../tenants/control.js";
|
|
11
12
|
import { currentTenant } from "../tenants/tenant.js";
|
|
12
13
|
import { asSync, mayBuild } from "./access.js";
|
|
@@ -218,6 +219,7 @@ async function syncSpace(spaceId, space) {
|
|
|
218
219
|
...values,
|
|
219
220
|
});
|
|
220
221
|
}
|
|
222
|
+
spaceChanged(existing ? "space.updated" : "space.created", spaceId);
|
|
221
223
|
const project = await syncedProject(spaceId);
|
|
222
224
|
if (!project) {
|
|
223
225
|
throw notFound();
|
|
@@ -13,7 +13,7 @@ import { browserTools } from "./browser.js";
|
|
|
13
13
|
import { connectorTools } from "./connector.js";
|
|
14
14
|
import { mailTools } from "./mail.js";
|
|
15
15
|
import { assertPublicUrl, safeFetch } from "./net-guard.js";
|
|
16
|
-
import { pluginTools } from "./plugin.js";
|
|
16
|
+
import { pluginTools, spaceContextOf } from "./plugin.js";
|
|
17
17
|
import { projectTools } from "./project.js";
|
|
18
18
|
import { clip, FileKeeper } from "./shared.js";
|
|
19
19
|
import { storeTools } from "./store.js";
|
|
@@ -93,10 +93,11 @@ export async function buildStepTools(step, ctx, resolved, uploads) {
|
|
|
93
93
|
// The wizard's lists and files, the documents the person gave and the project's documents are
|
|
94
94
|
// always at hand.
|
|
95
95
|
Object.assign(tools, storeTools(ctx, uploads, files));
|
|
96
|
-
Object.assign(tools, projectTools(ctx));
|
|
96
|
+
Object.assign(tools, await projectTools(ctx));
|
|
97
97
|
Object.assign(tools, mailTools(step, ctx, files));
|
|
98
98
|
Object.assign(tools, await connectorTools(step, ctx, files));
|
|
99
99
|
Object.assign(tools, await pluginTools(step, ctx));
|
|
100
|
+
Object.assign(tools, (await spaceContextOf(ctx)).tools);
|
|
100
101
|
const sandbox = sandboxCapabilities();
|
|
101
102
|
if (allowed.has("sandbox") && sandbox) {
|
|
102
103
|
const timeoutMs = (seconds) => Math.min((seconds ?? 120) * 1000, 600_000);
|
|
@@ -1,12 +1,32 @@
|
|
|
1
1
|
import { pluginToolOf } from "@engenty-wizards/shared/definition";
|
|
2
2
|
import { createTool } from "@mastra/core/tools";
|
|
3
3
|
import { StepError } from "../engine/types.js";
|
|
4
|
-
import { loadedPlugin, pluginIdsOf } from "../plugins/registry.js";
|
|
5
|
-
import { attempt } from "./shared.js";
|
|
4
|
+
import { loadedPlugin, pluginIdsOf, pluginsOf } from "../plugins/registry.js";
|
|
5
|
+
import { attempt, clip } from "./shared.js";
|
|
6
6
|
/** The model's name of a plugin's tool: `<plugin>_<tool>`, since a tool name takes no dot. */
|
|
7
7
|
export function pluginToolName(plugin, tool) {
|
|
8
8
|
return `${plugin.replaceAll("-", "_")}_${tool}`;
|
|
9
9
|
}
|
|
10
|
+
/** A plugin's tool as an agent step calls it. */
|
|
11
|
+
function stepTool(plugin, tool, ctx) {
|
|
12
|
+
const id = pluginToolName(plugin, tool.name);
|
|
13
|
+
const space = { id: ctx.project.id, name: ctx.project.name };
|
|
14
|
+
return createTool({
|
|
15
|
+
id,
|
|
16
|
+
description: tool.description,
|
|
17
|
+
inputSchema: tool.inputSchema,
|
|
18
|
+
execute: (input) => attempt(async () => tool.execute(input, {
|
|
19
|
+
runId: ctx.runId,
|
|
20
|
+
stepId: ctx.stepId,
|
|
21
|
+
tenantId: ctx.tenantId,
|
|
22
|
+
space,
|
|
23
|
+
project: space,
|
|
24
|
+
wizard: { title: ctx.def.title },
|
|
25
|
+
signal: ctx.signal,
|
|
26
|
+
emit: (message) => ctx.emit("tool", message),
|
|
27
|
+
})),
|
|
28
|
+
});
|
|
29
|
+
}
|
|
10
30
|
/**
|
|
11
31
|
* The tools of plugins a step allowlists as `<plugin>.<tool>`. A step that names a tool this
|
|
12
32
|
* tenant does not have fails: the wizard was written for a runtime with that plugin.
|
|
@@ -23,21 +43,73 @@ export async function pluginTools(step, ctx) {
|
|
|
23
43
|
if (!found) {
|
|
24
44
|
throw new StepError(`Dieser Schritt braucht das Werkzeug „${plugin}.${tool}“. Das Plugin „${plugin}“ ist hier nicht installiert.`);
|
|
25
45
|
}
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
46
|
+
tools[pluginToolName(plugin, tool)] = stepTool(plugin, found, ctx);
|
|
47
|
+
}
|
|
48
|
+
return tools;
|
|
49
|
+
}
|
|
50
|
+
/** A block of a plugin is cut here: the step's instructions stay the step's. */
|
|
51
|
+
const MAX_BLOCK = 8000;
|
|
52
|
+
const contexts = new WeakMap();
|
|
53
|
+
/**
|
|
54
|
+
* What the tenant's plugins add to an agent step of a space's wizard (`registerSpaceContext`):
|
|
55
|
+
* asked once per step, for its instructions and for its tools. A context that fails adds nothing.
|
|
56
|
+
*/
|
|
57
|
+
export function spaceContextOf(ctx) {
|
|
58
|
+
let found = contexts.get(ctx);
|
|
59
|
+
if (!found) {
|
|
60
|
+
found = gather(ctx);
|
|
61
|
+
contexts.set(ctx, found);
|
|
62
|
+
}
|
|
63
|
+
return found;
|
|
64
|
+
}
|
|
65
|
+
async function gather(ctx) {
|
|
66
|
+
const space = { id: ctx.project.id, name: ctx.project.name };
|
|
67
|
+
const result = { blocks: [], tools: {} };
|
|
68
|
+
for (const plugin of await pluginsOf(ctx.tenantId)) {
|
|
69
|
+
for (const context of plugin.contexts) {
|
|
70
|
+
const block = await Promise.resolve()
|
|
71
|
+
.then(() => context.block(space))
|
|
72
|
+
.catch((err) => {
|
|
73
|
+
console.error(`[plugin ${plugin.source.id}] space context:`, err);
|
|
74
|
+
return null;
|
|
75
|
+
});
|
|
76
|
+
if (!block?.trim()) {
|
|
77
|
+
continue;
|
|
78
|
+
}
|
|
79
|
+
result.blocks.push(clip(block.trim(), MAX_BLOCK));
|
|
80
|
+
for (const tool of context.tools ?? []) {
|
|
81
|
+
result.tools[pluginToolName(plugin.source.id, tool.name)] = stepTool(plugin.source.id, tool, ctx);
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
return result;
|
|
86
|
+
}
|
|
87
|
+
/** The tenant's plugins' tools of the space assistant (`registerAssistantTool`). */
|
|
88
|
+
export async function assistantToolsOf(turn) {
|
|
89
|
+
const tools = {};
|
|
90
|
+
for (const plugin of await pluginsOf(turn.tenantId)) {
|
|
91
|
+
for (const tool of plugin.assistantTools.values()) {
|
|
92
|
+
const id = pluginToolName(plugin.source.id, tool.name);
|
|
93
|
+
tools[id] = createTool({
|
|
94
|
+
id,
|
|
95
|
+
description: tool.description,
|
|
96
|
+
inputSchema: tool.inputSchema,
|
|
97
|
+
execute: (input) => attempt(async () => {
|
|
98
|
+
const result = await tool.execute(input, {
|
|
99
|
+
tenantId: turn.tenantId,
|
|
100
|
+
space: turn.space,
|
|
101
|
+
userId: turn.userId,
|
|
102
|
+
signal: turn.signal,
|
|
103
|
+
emit: turn.emit,
|
|
104
|
+
changed: turn.changed,
|
|
105
|
+
});
|
|
106
|
+
if (tool.card) {
|
|
107
|
+
turn.card({ plugin: plugin.source.id, tool: tool.name, data: result ?? null });
|
|
108
|
+
}
|
|
109
|
+
return result;
|
|
110
|
+
}),
|
|
111
|
+
});
|
|
112
|
+
}
|
|
41
113
|
}
|
|
42
114
|
return tools;
|
|
43
115
|
}
|
|
@@ -1,17 +1,21 @@
|
|
|
1
1
|
import { createTool } from "@mastra/core/tools";
|
|
2
2
|
import { z } from "zod";
|
|
3
|
-
import { documentText, searchProject } from "../services/project-index.js";
|
|
3
|
+
import { documentText, hasIndexEntries, searchProject } from "../services/project-index.js";
|
|
4
4
|
import { attempt, clip } from "./shared.js";
|
|
5
|
-
/**
|
|
6
|
-
|
|
5
|
+
/**
|
|
6
|
+
* The project's documents, for every agent step of its wizards: search the index, read one
|
|
7
|
+
* whole. The search also finds what the space's plugins put into the index.
|
|
8
|
+
*/
|
|
9
|
+
export async function projectTools(ctx) {
|
|
7
10
|
const docs = ctx.projectFiles.filter((f) => f.kind === "document");
|
|
8
|
-
|
|
11
|
+
const entries = await hasIndexEntries(ctx.project.id);
|
|
12
|
+
if (!(docs.length || entries)) {
|
|
9
13
|
return {};
|
|
10
14
|
}
|
|
11
|
-
|
|
15
|
+
const tools = {
|
|
12
16
|
project_search: createTool({
|
|
13
17
|
id: "project_search",
|
|
14
|
-
description: "Search the project's documents
|
|
18
|
+
description: "Search the project's documents and what its plugins keep for all wizards (wiki pages, questions and answers), and get the passages that fit best. Ask in their language, with the words they would use.",
|
|
15
19
|
inputSchema: z.object({
|
|
16
20
|
query: z.string().describe("What to look for: a question or keywords"),
|
|
17
21
|
limit: z.number().int().min(1).max(12).optional(),
|
|
@@ -24,30 +28,34 @@ export function projectTools(ctx) {
|
|
|
24
28
|
};
|
|
25
29
|
}),
|
|
26
30
|
}),
|
|
27
|
-
project_document: createTool({
|
|
28
|
-
id: "project_document",
|
|
29
|
-
description: "Read one of the project's documents as text. Long documents come in parts: pass `from` to continue.",
|
|
30
|
-
inputSchema: z.object({
|
|
31
|
-
name: z.string().describe("The document's name, as listed"),
|
|
32
|
-
from: z.number().int().min(0).optional().describe("Character to start at"),
|
|
33
|
-
}),
|
|
34
|
-
execute: ({ name, from }) => attempt(async () => {
|
|
35
|
-
const doc = docs.find((d) => d.name === name) ??
|
|
36
|
-
docs.find((d) => d.name.toLowerCase().includes(name.toLowerCase()));
|
|
37
|
-
if (!doc) {
|
|
38
|
-
throw new Error(`No document "${name}". There are: ${docs.map((d) => d.name).join(", ")}`);
|
|
39
|
-
}
|
|
40
|
-
await ctx.emit("tool", `Liest ${doc.name}`);
|
|
41
|
-
const text = await documentText(doc);
|
|
42
|
-
const start = Math.min(from ?? 0, text.length);
|
|
43
|
-
const part = text.slice(start, start + 12_000);
|
|
44
|
-
return {
|
|
45
|
-
document: doc.name,
|
|
46
|
-
text: clip(part, 12_000),
|
|
47
|
-
next: start + part.length < text.length ? start + part.length : null,
|
|
48
|
-
length: text.length,
|
|
49
|
-
};
|
|
50
|
-
}),
|
|
51
|
-
}),
|
|
52
31
|
};
|
|
32
|
+
if (!docs.length) {
|
|
33
|
+
return tools;
|
|
34
|
+
}
|
|
35
|
+
tools.project_document = createTool({
|
|
36
|
+
id: "project_document",
|
|
37
|
+
description: "Read one of the project's documents as text. Long documents come in parts: pass `from` to continue.",
|
|
38
|
+
inputSchema: z.object({
|
|
39
|
+
name: z.string().describe("The document's name, as listed"),
|
|
40
|
+
from: z.number().int().min(0).optional().describe("Character to start at"),
|
|
41
|
+
}),
|
|
42
|
+
execute: ({ name, from }) => attempt(async () => {
|
|
43
|
+
const doc = docs.find((d) => d.name === name) ??
|
|
44
|
+
docs.find((d) => d.name.toLowerCase().includes(name.toLowerCase()));
|
|
45
|
+
if (!doc) {
|
|
46
|
+
throw new Error(`No document "${name}". There are: ${docs.map((d) => d.name).join(", ")}`);
|
|
47
|
+
}
|
|
48
|
+
await ctx.emit("tool", `Liest ${doc.name}`);
|
|
49
|
+
const text = await documentText(doc);
|
|
50
|
+
const start = Math.min(from ?? 0, text.length);
|
|
51
|
+
const part = text.slice(start, start + 12_000);
|
|
52
|
+
return {
|
|
53
|
+
document: doc.name,
|
|
54
|
+
text: clip(part, 12_000),
|
|
55
|
+
next: start + part.length < text.length ? start + part.length : null,
|
|
56
|
+
length: text.length,
|
|
57
|
+
};
|
|
58
|
+
}),
|
|
59
|
+
});
|
|
60
|
+
return tools;
|
|
53
61
|
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{a as e,n as t,t as n}from"./jsx-runtime-D3jfb0Ew.js";import{c as r,j as i,n as a,nt as o}from"./api-u3nydnnp.js";import{t as s}from"./createLucideIcon-q3MZMmnf.js";import{t as c}from"./check-CUpby_J9.js";import{n as l,r as u}from"./upload-DNRENWzQ.js";import{t as d}from"./external-link-MAL7vJYj.js";import{_ as f,c as p,d as m,h,m as g,n as ee,o as _,r as v,s as y,t as b,y as x}from"./ui-gGAdXx-P.js";import{I as S,O as C,f as w,j as T,o as E,p as D,u as O,v as k}from"./index-BQQihL4r.js";import{n as A}from"./LocalRuntime-BggRFDJt.js";var j={name:`hard-drive`,size:24,node:[[`path`,{d:`M10 16h.01`,key:`1bzywj`}],[`path`,{d:`M2.212 11.577a2 2 0 0 0-.212.896V18a2 2 0 0 0 2 2h16a2 2 0 0 0 2-2v-5.527a2 2 0 0 0-.212-.896L18.55 5.11A2 2 0 0 0 16.76 4H7.24a2 2 0 0 0-1.79 1.11z`,key:`18tbho`}],[`path`,{d:`M21.946 12.013H2.054`,key:`zqlbp7`}],[`path`,{d:`M6 16h.01`,key:`1pmjb7`}]]};j.node;var M=s(j),N={name:`layout-grid`,size:24,node:[[`rect`,{width:`7`,height:`7`,x:`3`,y:`3`,rx:`1`,key:`1g98yp`}],[`rect`,{width:`7`,height:`7`,x:`14`,y:`3`,rx:`1`,key:`6d4xhi`}],[`rect`,{width:`7`,height:`7`,x:`14`,y:`14`,rx:`1`,key:`nxv5o0`}],[`rect`,{width:`7`,height:`7`,x:`3`,y:`14`,rx:`1`,key:`1bb6yr`}]]};N.node;var te=s(N),P={name:`list`,size:24,node:[[`path`,{d:`M3 5h.01`,key:`18ugdj`}],[`path`,{d:`M3 12h.01`,key:`nlz23k`}],[`path`,{d:`M3 19h.01`,key:`noohij`}],[`path`,{d:`M8 5h13`,key:`1pao27`}],[`path`,{d:`M8 12h13`,key:`1za7za`}],[`path`,{d:`M8 19h13`,key:`m83p4d`}]]};P.node;var F=s(P),I=e(t(),1),L=e=>[`project-files`,e];function R(e){return i({queryKey:L(e),queryFn:()=>a.get(`/api/studio/projects/${e}/files`),refetchInterval:e=>e.state.data?.files.some(e=>e.status===`pending`)?2e3:!1})}function z(e,t){return r(`/api/studio/projects/${e}/files/${t}/content`)}function B(e,t=!1){let n=o(),[r,i]=(0,I.useState)(!1),[s,c]=(0,I.useState)(null),l=()=>n.invalidateQueries({queryKey:L(e)}),u=async e=>{c(null);try{await e()}catch(e){c(e.message)}finally{await l()}};return{busy:r,error:s,readOnly:t,upload:async(t,n)=>{i(!0),await u(async()=>{for(let r of n)await a.upload(`/api/studio/projects/${e}/files?kind=${t}`,r),await l()}),i(!1)},describe:(t,n)=>u(()=>a.patch(`/api/studio/projects/${e}/files/${t}`,{description:n})),remove:t=>u(()=>a.del(`/api/studio/projects/${e}/files/${t}`)),reindex:t=>u(()=>a.post(`/api/studio/projects/${e}/files/${t}/reindex`)),order:(t,n)=>u(()=>a.put(`/api/studio/projects/${e}/files/order`,{kind:t,ids:n}))}}function V(e,t){let n=`wz.layout.${e}`,[r,i]=(0,I.useState)(()=>{try{let e=localStorage.getItem(n);return e===`list`||e===`cards`?e:t}catch{return t}});return[r,()=>i(e=>{let t=e===`list`?`cards`:`list`;try{localStorage.setItem(n,t)}catch{}return t})]}function H(e,t,n=700){let[r,i]=(0,I.useState)(`idle`),[a,o]=(0,I.useState)(null),s=JSON.stringify(e),c=(0,I.useRef)(s),l=(0,I.useRef)({value:e,json:s,save:t});l.current={value:e,json:s,save:t};let u=(0,I.useRef)(Promise.resolve()),d=(0,I.useCallback)(()=>{let e=l.current;e.json!==c.current&&(c.current=e.json,i(`saving`),u.current=u.current.then(async()=>{try{await e.save(e.value),o(null),i(`saved`)}catch(e){c.current=``,o(e.message),i(`error`)}}))},[]);return(0,I.useEffect)(()=>{if(s===c.current)return;let e=setTimeout(d,n);return()=>clearTimeout(e)},[s,n,d]),(0,I.useEffect)(()=>d,[d]),{state:r,error:a}}function U(e){return e<1e6?`${Math.max(1,Math.round(e/1e3))} KB`:`${(e/1e6).toFixed(1)} MB`}var W=e(n(),1);function G({id:e,children:t}){return(0,W.jsx)(`div`,{id:e,className:`scroll-mt-24 max-md:scroll-mt-36`,children:t})}function K({title:e,hint:t,save:n,action:r,locked:i,plain:a,children:o}){return(0,W.jsxs)(`section`,{className:`flex flex-col gap-2.5`,children:[(0,W.jsxs)(`div`,{className:`flex items-start justify-between gap-4 px-1`,children:[(0,W.jsxs)(`div`,{className:`min-w-0`,children:[(0,W.jsxs)(`div`,{className:`flex items-center gap-3`,children:[(0,W.jsx)(`h2`,{className:`font-display font-semibold text-lg leading-tight`,children:e}),n?.state===`saving`?(0,W.jsxs)(`span`,{className:`inline-flex items-center gap-1.5 text-[12px] text-ink-3`,children:[(0,W.jsx)(m,{className:`size-3`}),` `,x(`project.saving`)]}):n?.state===`saved`?(0,W.jsxs)(`span`,{className:`inline-flex items-center gap-1 text-[12px] text-moss`,children:[(0,W.jsx)(c,{className:`size-3.5`}),` `,x(`settings.saved`)]}):null]}),t?(0,W.jsx)(`p`,{className:`mt-1 text-[14px] text-ink-3 leading-snug`,children:t}):null]}),r?(0,W.jsx)(`div`,{className:`shrink-0`,children:r}):null]}),a?o:(0,W.jsxs)(ee,{className:`p-5`,children:[i?(0,W.jsx)(`fieldset`,{disabled:!0,className:`min-w-0`,children:o}):o,n?.state===`error`&&n.error?(0,W.jsx)(`p`,{className:`mt-4 text-[14px] text-rose`,children:n.error}):null]})]})}function q({children:e,layout:t,onToggle:n}){return(0,W.jsxs)(`div`,{className:`mb-3 flex items-start gap-2`,children:[(0,W.jsx)(`div`,{className:`min-w-0 flex-1`,children:(0,W.jsx)(`div`,{className:`w-56 max-w-full transition-[width] duration-200 focus-within:w-full has-[input:not(:placeholder-shown)]:w-full`,children:e})}),(0,W.jsx)(_,{label:x(t===`list`?`project.viewCards`:`project.viewList`),onClick:n,children:t===`list`?(0,W.jsx)(te,{className:`size-4`}):(0,W.jsx)(F,{className:`size-4`})})]})}function J({value:e,onChange:t,onEnter:n,placeholder:r,busy:i}){return(0,W.jsxs)(`div`,{className:`relative`,children:[(0,W.jsx)(l,{className:`-translate-y-1/2 pointer-events-none absolute top-1/2 left-3 size-4 text-ink-4`}),(0,W.jsx)(`input`,{type:`search`,value:e,placeholder:r,onChange:e=>t(e.target.value),onKeyDown:e=>e.key===`Enter`&&n?.(),className:`h-9 w-full rounded-lg border border-input bg-card pr-3 pl-9 text-[14px] text-ink outline-none transition placeholder:text-ink-4 focus:border-focus focus:ring-4 focus:ring-focus-glow`}),i?(0,W.jsx)(m,{className:`-translate-y-1/2 absolute top-1/2 right-3 size-4 text-ink-3`}):null]})}function Y({onFiles:e,accept:t,multiple:n=!0,className:r,children:i}){return(0,W.jsxs)(`label`,{onDragOver:e=>{e.preventDefault(),e.currentTarget.dataset.over=`1`},onDragLeave:e=>{delete e.currentTarget.dataset.over},onDrop:t=>{t.preventDefault(),delete t.currentTarget.dataset.over;let r=Array.from(t.dataTransfer.files);r.length&&e(n?r:r.slice(0,1))},className:h(`flex cursor-pointer items-center justify-center gap-2 rounded-lg border border-input border-dashed text-[14px] text-ink-3 transition focus-within:border-focus focus-within:ring-4 focus-within:ring-focus-glow hover:border-ink-4 hover:text-ink data-[over]:border-focus data-[over]:bg-paper-2 data-[over]:text-ink`,r),children:[i,(0,W.jsx)(`input`,{className:`sr-only`,type:`file`,accept:t,multiple:n,onChange:t=>{let n=Array.from(t.target.files??[]);t.target.value=``,n.length&&e(n)}})]})}var X=`mt-1.5 text-[13px] text-ink-3`;function Z(e){let t=o(),[n,r]=(0,I.useState)(!1),i=S({mutationFn:e=>a.post(`/api/studio/account/link`,e),onSuccess:({url:e})=>{A(e),r(!0)}});return(0,I.useEffect)(()=>{if(!n)return;let e=setInterval(()=>void t.invalidateQueries({queryKey:[`me`]}),2e3),i=setTimeout(()=>r(!1),3e5);return()=>{clearInterval(e),clearTimeout(i)}},[n,t]),(0,I.useEffect)(()=>{e&&r(!1)},[e]),{link:i,waiting:n}}function Q({link:e,waiting:t}){return e.isError?(0,W.jsx)(`p`,{className:`text-[13px] text-rose`,children:x(`local.accountFailed`)}):t?(0,W.jsxs)(`p`,{className:`flex items-center gap-2 text-[13px] text-ink-3`,children:[(0,W.jsx)(m,{className:`size-3.5`}),` `,x(`local.accountWaiting`)]}):null}function ne(){let e=Z(!1),{link:t}=e,[n,r]=(0,I.useState)(``);return(0,W.jsxs)(`div`,{className:`flex flex-col divide-y divide-border-soft`,children:[(0,W.jsxs)(`div`,{className:`flex items-start gap-4 py-5 first:pt-0 last:pb-0`,children:[(0,W.jsx)(`div`,{className:`flex size-11 shrink-0 items-center justify-center rounded-full bg-paper-2 text-ink-2`,children:(0,W.jsx)(M,{className:`size-5`})}),(0,W.jsxs)(`div`,{className:`min-w-0`,children:[(0,W.jsx)(`div`,{className:`font-medium text-[15px]`,children:x(`account.local`)}),(0,W.jsx)(`p`,{className:`mt-1 text-[14px] text-ink-3 leading-relaxed`,children:x(`account.localText`)})]})]}),D.account?(0,W.jsxs)(`div`,{className:`flex flex-col gap-4 py-5 last:pb-0`,children:[(0,W.jsxs)(`div`,{children:[(0,W.jsx)(`div`,{className:`font-medium text-[15px]`,children:x(`account.with`)}),(0,W.jsxs)(`ul`,{className:`mt-2 flex flex-col gap-2 text-[14px] text-ink-2 leading-snug`,children:[(0,W.jsxs)(`li`,{className:`flex items-start gap-2.5`,children:[(0,W.jsx)(u,{className:`mt-0.5 size-4 shrink-0 text-amber`}),x(`account.withCredits`)]}),(0,W.jsxs)(`li`,{className:`flex items-start gap-2.5`,children:[(0,W.jsx)(T,{className:`mt-0.5 size-4 shrink-0 text-cobalt`}),x(`account.withCloud`)]})]})]}),(0,W.jsx)(`div`,{children:(0,W.jsx)(b,{busy:t.isPending&&!t.variables?.signup,onClick:()=>t.mutate({}),children:x(`account.signIn`)})})]}):null,D.account?(0,W.jsxs)(`form`,{className:`flex flex-col gap-3 py-5 last:pb-0`,onSubmit:e=>{e.preventDefault(),t.mutate({signup:!0,code:n.trim()||void 0})},children:[(0,W.jsxs)(`div`,{children:[(0,W.jsx)(`div`,{className:`font-medium text-[15px]`,children:x(`account.new`)}),(0,W.jsx)(`p`,{className:`mt-1 text-[14px] text-ink-3 leading-relaxed`,children:x(`account.newHint`)})]}),(0,W.jsxs)(`div`,{className:`flex flex-wrap gap-2`,children:[(0,W.jsx)(y,{value:n,maxLength:64,autoComplete:`off`,spellCheck:!1,placeholder:x(`account.code`),"aria-label":x(`account.code`),onChange:e=>r(e.target.value),className:`w-56 font-mono text-[14px]`}),(0,W.jsx)(b,{type:`submit`,variant:`secondary`,className:`h-11`,busy:t.isPending&&!!t.variables?.signup,children:x(`account.create`)})]}),(0,W.jsx)(Q,{...e})]}):null]})}var $={start:`account.kind.start`,monthly:`account.kind.monthly`,gift:`account.kind.gift`};function re({account:e}){let t=o(),n=Z(e.signedIn),r=S({mutationFn:()=>a.del(`/api/studio/account`),onSuccess:()=>t.invalidateQueries({queryKey:[`me`]})}),i=new Intl.DateTimeFormat(f,{dateStyle:`medium`});return(0,W.jsxs)(`div`,{className:`flex flex-col divide-y divide-border-soft`,children:[(0,W.jsxs)(`div`,{className:`flex flex-wrap items-center gap-x-4 gap-y-3 py-5 first:pt-0`,children:[(0,W.jsxs)(`div`,{className:`min-w-0 flex-1`,children:[(0,W.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,W.jsx)(`span`,{className:`truncate font-medium text-[15px]`,children:e.name||e.email}),e.signedIn?(0,W.jsx)(v,{tone:`live`,children:x(`account.linked`)}):null]}),(0,W.jsx)(`div`,{className:`truncate text-[14px] text-ink-3`,children:e.email})]}),(0,W.jsxs)(`div`,{className:`flex flex-wrap items-center gap-2`,children:[(0,W.jsxs)(b,{variant:`secondary`,onClick:()=>A(e.url),children:[x(`setup.openAccount`),` `,(0,W.jsx)(d,{className:`size-4`})]}),(0,W.jsxs)(b,{variant:`ghost`,busy:r.isPending,onClick:()=>r.mutate(),children:[(0,W.jsx)(C,{className:`size-4`}),` `,x(`nav.logout`)]})]})]}),e.signedIn?null:(0,W.jsxs)(`div`,{className:`flex flex-col gap-3 py-5`,children:[(0,W.jsx)(`p`,{className:`text-[14px] text-ink-2`,children:x(`local.accountExpired`)}),(0,W.jsx)(`div`,{children:(0,W.jsx)(b,{busy:n.link.isPending,onClick:()=>n.link.mutate({}),children:x(`account.signInAgain`)})}),(0,W.jsx)(Q,{...n})]}),e.credits===null?null:(0,W.jsxs)(`div`,{className:`py-5`,children:[(0,W.jsxs)(`div`,{className:`flex flex-wrap items-center gap-x-4 gap-y-3`,children:[(0,W.jsxs)(`div`,{className:`min-w-0 flex-1`,children:[(0,W.jsx)(`div`,{className:`text-[13px] text-ink-3`,children:x(`account.credits`)}),(0,W.jsx)(`div`,{className:`font-display font-semibold text-[22px] tabular-nums leading-tight`,children:x(`nav.credits`,{n:Math.floor(e.credits).toLocaleString()})})]}),(0,W.jsxs)(b,{variant:`secondary`,onClick:()=>A(`${e.url}/billing`),children:[x(`account.topUp`),` `,(0,W.jsx)(d,{className:`size-4`})]})]}),e.expiring.length?(0,W.jsx)(`ul`,{className:`mt-3 flex flex-col gap-1 text-[13px] text-ink-3 tabular-nums`,children:e.expiring.map(e=>(0,W.jsxs)(`li`,{children:[x(`account.expires`,{n:Math.floor(e.credits).toLocaleString(),date:i.format(new Date(e.expiresAt))}),$[e.kind]?(0,W.jsxs)(`span`,{className:`text-ink-4`,children:[` · `,x($[e.kind])]}):null]},`${e.kind}:${e.expiresAt}`))}):null]}),(0,W.jsxs)(`div`,{className:`flex items-start gap-2.5 py-5 text-[14px] text-ink-2 leading-snug last:pb-0`,children:[(0,W.jsx)(T,{className:`mt-0.5 size-4 shrink-0 text-cobalt`}),(0,W.jsx)(`p`,{children:x(`account.cloud`,{host:E(e.cloudUrl)})})]})]})}function ie({me:e,fromAccount:t}){let n=o(),[r,i]=(0,I.useState)(e.profile),s=e=>i(t=>({...t,...e})),c=H(r,async e=>{await a.put(`/api/studio/profile`,e),await n.invalidateQueries({queryKey:[`me`]})});return(0,W.jsx)(K,{title:x(`account.profile`),hint:x(`account.hint`),save:c,children:(0,W.jsxs)(`div`,{className:`flex flex-col gap-6 sm:flex-row sm:gap-8`,children:[(0,W.jsxs)(`div`,{className:`flex shrink-0 flex-col items-center gap-2 sm:w-32`,children:[(0,W.jsx)(`div`,{className:`flex size-20 items-center justify-center overflow-hidden rounded-full bg-ember-tint font-semibold text-[28px] text-ember-strong ring-1 ring-border-soft`,children:e.user.image?(0,W.jsx)(`img`,{src:e.user.image,alt:``,className:`size-full object-cover`}):k(r.name)||`?`}),(0,W.jsx)(`p`,{className:`text-center text-[12px] text-ink-3 leading-snug`,children:x(`account.initials`)})]}),(0,W.jsxs)(`div`,{className:`flex min-w-0 flex-1 flex-col gap-5`,children:[(0,W.jsxs)(`div`,{children:[(0,W.jsx)(p,{children:x(`account.name`)}),(0,W.jsx)(y,{value:r.name,maxLength:80,disabled:t,onChange:e=>s({name:e.target.value})}),(0,W.jsx)(`p`,{className:X,children:x(t?`account.fromAccount`:`account.nameHint`)})]}),(0,W.jsxs)(`div`,{children:[(0,W.jsx)(p,{children:x(`account.about`)}),(0,W.jsx)(g,{minRows:3,maxLength:2e3,value:r.about,onChange:e=>s({about:e.target.value})}),(0,W.jsx)(`p`,{className:X,children:x(`account.aboutHint`)})]}),(0,W.jsxs)(`div`,{className:`grid gap-5 sm:grid-cols-2`,children:[(0,W.jsxs)(`div`,{children:[(0,W.jsx)(p,{children:x(`account.email`)}),(0,W.jsx)(y,{type:`email`,value:r.email,maxLength:200,disabled:t,onChange:e=>s({email:e.target.value})})]}),(0,W.jsxs)(`div`,{children:[(0,W.jsx)(p,{children:x(`account.phone`)}),(0,W.jsx)(y,{type:`tel`,value:r.phone,maxLength:40,onChange:e=>s({phone:e.target.value})})]})]})]})]})})}function ae({me:e}){let t=e.mode===`managed`,n=t||!!e.account;return(0,W.jsxs)(`div`,{className:`flex flex-col gap-9`,children:[(0,W.jsx)(K,{title:x(`account.connection`),hint:x(`account.connectionHint`),children:t?(0,W.jsxs)(`div`,{className:`flex flex-wrap items-center gap-4`,children:[(0,W.jsxs)(`div`,{className:`min-w-0 flex-1`,children:[(0,W.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,W.jsx)(`span`,{className:`truncate font-medium text-[15px]`,children:e.user.name}),(0,W.jsx)(v,{tone:`live`,children:x(`account.linked`)})]}),(0,W.jsx)(`div`,{className:`truncate text-[14px] text-ink-3`,children:e.user.email})]}),e.manageUrl?(0,W.jsxs)(b,{variant:`secondary`,onClick:()=>A(`${e.manageUrl}/account`),children:[x(`setup.openAccount`),` `,(0,W.jsx)(d,{className:`size-4`})]}):null]}):e.account?(0,W.jsx)(re,{account:e.account}):(0,W.jsx)(ne,{})}),(0,W.jsx)(ie,{me:e,fromAccount:n},n?`account`:`own`),(0,W.jsx)(K,{title:x(`account.look`),hint:x(`account.lookHint`),children:(0,W.jsxs)(`div`,{className:`flex flex-col divide-y divide-border-soft`,children:[(0,W.jsxs)(`div`,{className:`flex items-center justify-between gap-4 pb-4`,children:[(0,W.jsx)(`span`,{className:`font-medium text-[14px]`,children:x(`nav.language`)}),(0,W.jsx)(w,{tone:`surface`})]}),(0,W.jsxs)(`div`,{className:`flex items-center justify-between gap-4 pt-4`,children:[(0,W.jsx)(`span`,{className:`font-medium text-[14px]`,children:x(`nav.theme`)}),(0,W.jsx)(O,{})]})]})})]})}export{Y as a,K as c,H as d,B as f,G as i,U as l,R as m,Q as n,q as o,V as p,Z as r,J as s,ae as t,z as u};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{a as e,n as t,t as n}from"./jsx-runtime-D3jfb0Ew.js";import{t as r}from"./preload-helper-CNEI7N0N.js";import{a as i,d as a,h as o,i as s,s as c,y as l}from"./ui-gGAdXx-P.js";var u=e(t(),1),d=e(n(),1);function f(e){switch(e.group){case`Added`:return{label:`NEW`,dot:`bg-moss`};case`Fixed`:return{label:`FIXED`,dot:`bg-amber`};case`Changed`:return{label:`CHANGED`,dot:`bg-cobalt`};case`Performance`:return{label:`PERFORMANCE`,dot:`bg-ember`};case`Deploy`:return{label:`DEPLOY`,dot:`bg-ink-4`};case`Docs`:return{label:`DOCS`,dot:`bg-ink-4`};default:return{label:`OTHER`,dot:`bg-ink-4`}}}var p=e=>e.version?e.version.replace(/^v/,``):l(`about.unreleased`),m=e=>e.timestamp?new Date(e.timestamp*1e3).toISOString().slice(0,10):``,h=e=>e.charAt(0).toUpperCase()+e.slice(1);function g(e,t){let n=t.trim().toLowerCase();if(!n)return e;let r=[];for(let t of e){if(`${p(t)} ${m(t)}`.toLowerCase().includes(n)){r.push(t);continue}let e=t.commits.filter(e=>`${f(e).label} ${e.scope??``} ${e.message}`.toLowerCase().includes(n));e.length>0&&r.push({...t,commits:e})}return r}function _({open:e,onClose:t}){let[n,_]=(0,u.useState)(null),[v,y]=(0,u.useState)(``);(0,u.useEffect)(()=>{if(!e||n)return;let t=!1;return r(()=>import(`./changelog-
|
|
1
|
+
import{a as e,n as t,t as n}from"./jsx-runtime-D3jfb0Ew.js";import{t as r}from"./preload-helper-CNEI7N0N.js";import{a as i,d as a,h as o,i as s,s as c,y as l}from"./ui-gGAdXx-P.js";var u=e(t(),1),d=e(n(),1);function f(e){switch(e.group){case`Added`:return{label:`NEW`,dot:`bg-moss`};case`Fixed`:return{label:`FIXED`,dot:`bg-amber`};case`Changed`:return{label:`CHANGED`,dot:`bg-cobalt`};case`Performance`:return{label:`PERFORMANCE`,dot:`bg-ember`};case`Deploy`:return{label:`DEPLOY`,dot:`bg-ink-4`};case`Docs`:return{label:`DOCS`,dot:`bg-ink-4`};default:return{label:`OTHER`,dot:`bg-ink-4`}}}var p=e=>e.version?e.version.replace(/^v/,``):l(`about.unreleased`),m=e=>e.timestamp?new Date(e.timestamp*1e3).toISOString().slice(0,10):``,h=e=>e.charAt(0).toUpperCase()+e.slice(1);function g(e,t){let n=t.trim().toLowerCase();if(!n)return e;let r=[];for(let t of e){if(`${p(t)} ${m(t)}`.toLowerCase().includes(n)){r.push(t);continue}let e=t.commits.filter(e=>`${f(e).label} ${e.scope??``} ${e.message}`.toLowerCase().includes(n));e.length>0&&r.push({...t,commits:e})}return r}function _({open:e,onClose:t}){let[n,_]=(0,u.useState)(null),[v,y]=(0,u.useState)(``);(0,u.useEffect)(()=>{if(!e||n)return;let t=!1;return r(()=>import(`./changelog-D7O5icPX.js`).then(e=>{t||_(e.default)}),[]),()=>{t=!0}},[e,n]),(0,u.useEffect)(()=>{e||y(``)},[e]);let b=n?g(n,v):[];return(0,d.jsxs)(s,{open:e,onClose:t,title:l(`about.changelog`),wide:!0,children:[(0,d.jsx)(`p`,{className:`-mt-3 mb-4 text-[14px] text-ink-3`,children:l(`about.changelogHint`)}),n===null?(0,d.jsx)(`div`,{className:`flex justify-center py-10 text-ink-3`,children:(0,d.jsx)(a,{})}):n.length===0?(0,d.jsx)(i,{children:l(`about.changelogEmpty`)}):(0,d.jsxs)(d.Fragment,{children:[(0,d.jsx)(c,{type:`search`,value:v,placeholder:l(`about.search`),onChange:e=>y(e.target.value)}),b.length===0?(0,d.jsx)(i,{children:l(`about.noMatches`)}):null,b.map(e=>(0,d.jsxs)(`section`,{className:`mt-6`,children:[(0,d.jsxs)(`h3`,{className:`flex items-baseline gap-3 border-border-soft border-b pb-2 font-display font-semibold text-[16px]`,children:[p(e),(0,d.jsx)(`span`,{className:`font-normal font-sans text-[13px] text-ink-3 tabular-nums`,children:m(e)})]}),(0,d.jsx)(`ul`,{className:`mt-3 flex flex-col gap-2`,children:e.commits.map(e=>{let t=f(e);return(0,d.jsxs)(`li`,{className:`flex items-start gap-2.5 text-[14px]`,children:[(0,d.jsx)(`span`,{className:o(`mt-[7px] size-1.5 shrink-0 rounded-full`,t.dot)}),(0,d.jsxs)(`span`,{className:`min-w-0 text-ink-2`,children:[(0,d.jsxs)(`span`,{className:`font-semibold text-[12px] text-ink tracking-wide`,children:[t.label,e.scope?` [${e.scope}]`:``]}),` `,h(e.message),e.breaking?(0,d.jsx)(`span`,{className:`ml-1.5 rounded-full bg-rose-tint px-1.5 py-0.5 font-medium text-[12px] text-rose`,children:l(`about.breaking`)}):null]})]},e.id)})})]},e.version??`unreleased`))]})]})}export{_ as ChangelogDialog};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{a as e,n as t,t as n}from"./jsx-runtime-D3jfb0Ew.js";import{c as r,d as i,i as a,n as o,nt as s}from"./api-u3nydnnp.js";import{t as c}from"./createLucideIcon-q3MZMmnf.js";import{S as l,T as u,b as d,r as f,y as p}from"./outputs-s8BpXH6V.js";import{t as m}from"./chevron-down-DymW-2BP.js";import{t as h}from"./plus-Du-Jx8aI.js";import{t as g}from"./mic-Bvz4mA2j.js";import{_,d as v,h as y,o as b,y as x}from"./ui-gGAdXx-P.js";import{E as S,T as C}from"./index-BAQ2e4is.js";var w={name:`chevron-up`,size:24,node:[[`path`,{d:`m18 15-6-6-6 6`,key:`153udz`}]]};w.node;var T=c(w),E=e(t(),1),D=!1;function O(){if(!(typeof window>`u`||D))return window.SpeechRecognition??window.webkitSpeechRecognition}var k=typeof navigator<`u`&&!!navigator.mediaDevices?.getUserMedia&&typeof MediaRecorder<`u`;function A(e,t){let n=e.trimEnd(),r=t.trim();return n&&r?`${n} ${r}`:n||r}function j(e,t){let[n,r]=(0,E.useState)(!1),[i,a]=(0,E.useState)(!1),[s,c]=(0,E.useState)(null),l=(0,E.useRef)(e);l.current=e;let u=(0,E.useRef)(t);u.current=t;let d=(0,E.useRef)(null);(0,E.useEffect)(()=>()=>d.current?.stop(),[]);let f=async()=>{let e=l.current,t;try{t=await navigator.mediaDevices.getUserMedia({audio:!0})}catch{c(`denied`);return}let n=[],i=new MediaRecorder(t);i.ondataavailable=e=>e.data.size&&n.push(e.data),i.onstop=async()=>{for(let e of t.getTracks())e.stop();d.current=null,r(!1);let s=(i.mimeType||`audio/webm`).split(`;`)[0],l=new File(n,`dictation`,{type:s});if(l.size){a(!0);try{let{text:t}=await o.upload(`/api/studio/transcribe`,l);t.trim()&&u.current(A(e,t))}catch(e){c(e.message)}finally{a(!1)}}},d.current={stop:()=>i.state!==`inactive`&&i.stop()},i.start(),r(!0)},p=e=>{let t=l.current,n=``,i=new e;i.continuous=!0,i.interimResults=!0,i.lang=_===`de`?`de-DE`:`en-US`,i.onresult=e=>{let r=``;for(let t=Math.max(0,e.resultIndex);t<e.results.length;t++){let i=e.results[t],a=i[0]?.transcript??``;i.isFinal?n=A(n,a):r+=a}u.current(A(t,A(n,r)))},i.onerror=e=>{if(e.error!==`aborted`&&e.error!==`no-speech`){if(e.error===`not-allowed`){c(`denied`);return}D=!0,k&&!n?(i.onend=null,d.current=null,f()):c(e.error)}},i.onend=()=>{d.current=null,r(!1)},d.current={stop:()=>i.stop()},i.start(),r(!0)};return{supported:!!O()||k,listening:n,processing:i,error:s,toggle:()=>{if(i)return;if(d.current){d.current.stop();return}c(null);let e=O();e?p(e):f()}}}var M=e(n(),1),N=/\.(png|jpe?g|gif|webp|avif|svg)$/i;function P(e){let t=e.filter(e=>e.type.startsWith(`image/`));return t.length?Object.fromEntries(t.map(e=>[e.name,URL.createObjectURL(e)])):void 0}function F(e){let t=e.match(/(?:^|\n\n)(?:Angehängt|Attached): ([^\n]+)$/);return t?{text:e.slice(0,t.index).trim(),names:t[1].split(`, `).filter(Boolean)}:{text:e,names:[]}}function I(e,t){if(e.name&&e.name!==`image.png`)return e;let n=e.type.split(`/`)[1]?.replace(`jpeg`,`jpg`)||`png`,r=new Date().toISOString().slice(0,19).replace(/[-:]/g,``).replace(`T`,`-`);return new File([e],`paste-${r}${t?`-${t+1}`:``}.${n}`,{type:e.type})}function L({url:e,label:t,children:n}){return(0,M.jsxs)(`div`,{className:`group relative`,title:t,children:[(0,M.jsx)(`img`,{src:e,alt:t,width:64,height:64,className:`size-16 rounded-lg bg-paper-2 object-cover ring-1 ring-border`}),n]})}function R({names:e,previews:t,fileUrl:n}){let r=e.filter(e=>t?.[e]||n&&N.test(e)),i=e.filter(e=>!r.includes(e));return(0,M.jsxs)(`div`,{className:`flex flex-col items-end gap-1.5`,children:[r.map(e=>{let r=t?.[e]??n?.(e)??``;return(0,M.jsx)(`a`,{href:r,target:`_blank`,rel:`noreferrer`,title:e,children:(0,M.jsx)(`img`,{src:r,alt:e,className:`max-h-60 w-auto max-w-full rounded-xl bg-paper-2 object-contain ring-1 ring-border`})},e)}),i.length?(0,M.jsx)(`div`,{className:`flex flex-wrap justify-end gap-1.5`,children:i.map(e=>(0,M.jsxs)(`span`,{className:`inline-flex max-w-full items-center gap-1.5 rounded-full bg-paper-2 px-2.5 py-1 text-[12px] text-ink-2`,children:[(0,M.jsx)(l,{className:`size-3 shrink-0 text-ink-4`}),(0,M.jsx)(`span`,{className:`truncate`,children:e})]},e))}):null]})}function z(e,t){let n=s(),[i,o]=(0,E.useState)([]),[c,l]=(0,E.useState)(`idle`),[u,d]=(0,E.useState)(null),[f,p]=(0,E.useState)(null),[m,h]=(0,E.useState)(null),[g,_]=(0,E.useState)(null),v=(0,E.useRef)(null);return(0,E.useEffect)(()=>{if(e){if(v.current!==e.id){v.current=e.id,o(e.messages);return}c===`idle`&&o(t=>e.messages.length>=t.length?e.messages:t)}},[e,c]),{messages:i,phase:c,activity:f,thought:m,startedAt:g,error:u,send:async(i,s=[])=>{if(!e||!(i.trim()||s.length)||c!==`idle`)return!1;if(d(null),_(Date.now()),h(null),s.length){l(`thinking`);try{for(let t of s){let n=await fetch(r(`/api/studio/wizards/${e.id}/files/${encodeURIComponent(t.name)}`),{method:`PUT`,credentials:`include`,headers:{"content-type":t.type||`application/octet-stream`},body:t});if(!n.ok){let e=await n.json().catch(()=>({}));throw Error(e.error??n.statusText)}}}catch(t){return d(t.message),l(`idle`),_(null),await n.invalidateQueries({queryKey:[`wizard`,e.id]}),!1}let t=`${x(`editor.attached`)}: ${s.map(e=>e.name).join(`, `)}`;i=i.trim()?`${i}\n\n${t}`:t}let u=`p-${Date.now()}`;o(e=>[...e,{id:`u-${Date.now()}`,role:`user`,content:i,previews:P(s)},{id:u,role:`assistant`,content:``,pending:!0}]),l(`thinking`),p(null);let f=!1;try{await a(`/api/studio/wizards/${e.id}/chat`,{message:i},(e,n)=>{if(e===`text`){let e=JSON.parse(n);o(t=>t.map(t=>t.id===u?{...t,content:t.content+e}:t))}else if(e===`activity`)p(JSON.parse(n));else if(e===`thought`)h(JSON.parse(n));else if(e===`building`)l(`building`);else if(e===`done`){f=!0;let e=JSON.parse(n);o(t=>t.map(t=>t.id===u?{...t,content:e.reply,changed:e.changed,pending:!1}:t)),e.changed&&t(e.draft,e.revision)}else e===`error`&&(f=!0,d(JSON.parse(n).message))}),f||d(x(`editor.chatBroken`))}catch(e){d(e.message)}finally{p(null),h(null),_(null),o(e=>e.filter(e=>!(e.id===u&&!e.content)).map(e=>({...e,pending:!1}))),l(`idle`),await n.invalidateQueries({queryKey:[`wizard`,e.id]}),await n.invalidateQueries({queryKey:[`me`]})}return!0},fileUrl:t=>r(`/api/studio/wizards/${e?.id}/files/${encodeURIComponent(t)}`)}}function B(e){let[t,n]=(0,E.useState)(()=>Date.now());return(0,E.useEffect)(()=>{if(e===null)return;n(Date.now());let t=setInterval(()=>n(Date.now()),1e3);return()=>clearInterval(t)},[e]),e===null?null:Math.max(0,Math.floor((t-e)/1e3))}function V(e){return e<60?`${e} s`:`${Math.floor(e/60)}:${String(e%60).padStart(2,`0`)} min`}function H({chat:e,thought:t,className:n,spinner:r=`size-3.5`}){let i=B(e.startedAt);return(0,M.jsxs)(`div`,{className:y(`min-w-0`,n),children:[(0,M.jsxs)(`div`,{className:`flex min-w-0 items-center gap-2`,children:[(0,M.jsx)(v,{className:y(`shrink-0`,r)}),(0,M.jsx)(`span`,{className:`min-w-0 truncate`,children:e.activity??(e.phase===`building`?x(`editor.building`):x(`editor.thinking`))}),i===null?null:(0,M.jsx)(`span`,{className:`shrink-0 text-ink-4 tabular-nums`,children:V(i)})]}),t&&e.thought?(0,M.jsx)(`p`,{className:`mt-0.5 truncate pl-5.5 text-[12px] text-ink-4`,children:e.thought}):null]})}function U({message:e,fileUrl:t}){let{text:n,names:r}=F(e.content);return(0,M.jsxs)(`div`,{className:`ml-8 flex flex-col items-end gap-1.5 self-end`,children:[r.length?(0,M.jsx)(R,{names:r,previews:e.previews,fileUrl:t}):null,n?(0,M.jsx)(`div`,{className:`rounded-xl rounded-br-md bg-paper-2 px-4 py-2.5 text-[14px] leading-relaxed`,children:(0,M.jsx)(`span`,{className:`whitespace-pre-wrap`,children:n})}):null]})}function W({chat:e,avatar:t,hello:n=x(`editor.chatHello`),placeholder:r=x(`editor.composer`),changedLabel:a=`Ablauf aktualisiert`,compact:o,intro:s,closed:c}){let[_,w]=(0,E.useState)(!1),[D,O]=(0,E.useState)(``),[k,A]=(0,E.useState)([]),N=(0,E.useRef)(null),P=(0,E.useRef)(null),F=(0,E.useRef)(null),R=j(D,O);(0,E.useEffect)(()=>{N.current?.scrollTo({top:N.current.scrollHeight,behavior:`smooth`})},[e.messages,e.phase]),(0,E.useEffect)(()=>{let e=P.current;if(!e)return;let t=()=>{e.style.height=`auto`,e.style.height=D?`${Math.min(e.scrollHeight,200)}px`:``};t();let n=e.clientWidth,r=new ResizeObserver(()=>{e.clientWidth!==n&&(n=e.clientWidth,t())});return r.observe(e),()=>r.disconnect()},[D]);let z=(D.trim()||k.length>0)&&e.phase===`idle`,B=e=>A(t=>[...t.filter(t=>!e.some(e=>e.name===t.name)),...e]),[V,W]=(0,E.useState)(new Map);(0,E.useEffect)(()=>{let e=new Map(k.filter(e=>e.type.startsWith(`image/`)).map(e=>[e,URL.createObjectURL(e)]));return W(e),()=>{for(let t of e.values())URL.revokeObjectURL(t)}},[k]);let G=async()=>{if(!z)return;R.listening&&R.toggle();let t={text:D,files:k};O(``),A([]),await e.send(t.text.trim(),t.files)||(O(t.text),A(t.files))},K=!o||_,q=e.messages.at(-1);return(0,M.jsxs)(`div`,{className:`flex h-full min-h-0 flex-col`,children:[o&&(q||e.error)?(0,M.jsxs)(`button`,{type:`button`,"aria-expanded":_,"aria-label":x(`editor.thread`),onClick:()=>w(e=>!e),className:`flex items-center gap-2 px-4 pt-2.5 pb-0.5 text-left text-[13px] text-ink-3 transition hover:text-ink`,children:[!(e.error||_)&&q?.pending?(0,M.jsx)(H,{chat:e,className:`flex-1`}):(0,M.jsx)(`span`,{className:y(`min-w-0 flex-1 truncate`,e.error&&`text-rose`),children:e.error??(_?x(`editor.thread`):q?.content)}),_?(0,M.jsx)(m,{className:`size-4 shrink-0`}):(0,M.jsx)(T,{className:`size-4 shrink-0`})]}):null,(0,M.jsxs)(`div`,{ref:N,className:y(`min-h-0 flex-1 overflow-y-auto px-5 py-5`,!K&&`hidden`),children:[e.messages.length===0&&!c?s??(0,M.jsxs)(`div`,{className:`flex items-start gap-3`,children:[(0,M.jsx)(i,{kind:t,size:32,interactive:!1}),(0,M.jsx)(`p`,{className:`pt-1 text-[14px] text-ink-2 leading-relaxed`,children:n})]}):null,(0,M.jsx)(`div`,{className:`flex flex-col gap-4`,children:e.messages.map(n=>n.role===`user`?(0,M.jsx)(U,{message:n,fileUrl:e.fileUrl},n.id):(0,M.jsxs)(`div`,{className:`flex items-start gap-3`,children:[(0,M.jsx)(`div`,{className:`shrink-0`,children:(0,M.jsx)(i,{kind:t,size:28,interactive:!1})}),(0,M.jsxs)(`div`,{className:`min-w-0 pt-0.5 text-[14px]`,children:[n.source===`mcp`?(0,M.jsxs)(`div`,{className:`mb-1 inline-flex items-center gap-1.5 text-[12px] text-ink-3`,children:[(0,M.jsx)(S,{className:`size-3`}),` `,x(`editor.viaClient`,{client:n.client??`MCP`})]}):null,n.content?(0,M.jsx)(f,{text:n.content,className:`text-[14px]`}):null,n.pending?(0,M.jsx)(H,{chat:e,thought:!0,className:`mt-1 text-[13px] text-ink-3`}):null,n.changed?(0,M.jsxs)(`div`,{className:`mt-2 inline-flex items-center gap-1.5 rounded-full bg-ember-tint px-2.5 py-0.5 text-[12px] text-ember-strong`,children:[(0,M.jsx)(d,{className:`size-3`}),` `,a]}):null]})]},n.id))}),e.error?(0,M.jsx)(`div`,{className:`mt-4 rounded-lg bg-rose-tint px-3 py-2 text-[13px] text-rose`,children:e.error}):null]}),c?(0,M.jsx)(`p`,{className:`m-3 rounded-xl bg-paper-2 px-4 py-3 text-[13px] text-ink-2 leading-relaxed`,children:c}):(0,M.jsxs)(`div`,{className:o?`p-2`:`p-3`,children:[(0,M.jsxs)(`div`,{className:`rounded-xl bg-card p-1.5 shadow-soft ring-1 ring-border focus-within:ring-focus`,children:[V.size?(0,M.jsx)(`div`,{className:`flex flex-wrap gap-2 px-1 pt-1 pb-1.5`,children:k.map((e,t)=>{let n=V.get(e);return n?(0,M.jsx)(L,{url:n,label:e.name,children:(0,M.jsx)(`button`,{type:`button`,"aria-label":x(`editor.detach`),onClick:()=>A(e=>e.filter((e,n)=>n!==t)),className:`-top-1.5 -right-1.5 absolute flex size-5 items-center justify-center rounded-full bg-ink text-paper opacity-0 shadow-soft transition focus-visible:opacity-100 group-hover:opacity-100`,children:(0,M.jsx)(C,{className:`size-3`})})},`${e.name}-${t}`):null})}):null,k.some(e=>!V.has(e))?(0,M.jsx)(`ul`,{className:`flex flex-wrap gap-1.5 px-1 pt-1 pb-1.5`,children:k.map((e,t)=>V.has(e)?null:(0,M.jsxs)(`li`,{className:`inline-flex max-w-full items-center gap-1.5 rounded-full bg-paper-2 py-1 pr-1 pl-2.5 text-[12px] text-ink-2`,children:[(0,M.jsx)(l,{className:`size-3 shrink-0 text-ink-4`}),(0,M.jsx)(`span`,{className:`truncate`,children:e.name}),(0,M.jsx)(`button`,{type:`button`,"aria-label":x(`editor.detach`),onClick:()=>A(e=>e.filter((e,n)=>n!==t)),className:`inline-flex size-5 shrink-0 items-center justify-center rounded-full text-ink-3 hover:bg-paper-3 hover:text-ink`,children:(0,M.jsx)(C,{className:`size-3`})})]},`${e.name}-${t}`))}):null,(0,M.jsxs)(`div`,{className:`flex items-end gap-1`,children:[(0,M.jsx)(b,{label:x(`editor.attach`),onClick:()=>F.current?.click(),children:(0,M.jsx)(h,{className:`size-4`})}),(0,M.jsx)(`input`,{ref:F,type:`file`,multiple:!0,hidden:!0,onChange:e=>{let t=Array.from(e.target.files??[]);e.target.value=``,B(t)}}),(0,M.jsx)(`textarea`,{ref:P,rows:1,value:D,onChange:e=>O(e.target.value),onPaste:e=>{let t=Array.from(e.clipboardData.files);t.length&&(e.preventDefault(),B(t.map(I)))},onKeyDown:e=>{e.key===`Enter`&&!e.shiftKey&&(e.preventDefault(),G())},placeholder:R.listening?x(`editor.listening`):r,className:`max-h-[200px] min-h-[40px] flex-1 resize-none bg-transparent px-1.5 py-2 text-[14px] outline-none placeholder:text-ink-4`}),R.supported?(0,M.jsx)(b,{label:R.processing?x(`editor.transcribing`):R.listening?x(`editor.voiceStop`):x(`editor.voice`),"aria-pressed":R.listening,disabled:R.processing,onClick:R.toggle,className:y(R.listening&&`bg-rose-tint text-rose hover:bg-rose-tint hover:text-rose`),children:R.processing?(0,M.jsx)(v,{className:`size-4`}):R.listening?(0,M.jsx)(p,{className:`size-3.5 animate-pulse-dot fill-current`}):(0,M.jsx)(g,{className:`size-4`})}):null,(0,M.jsx)(`button`,{type:`button`,onClick:()=>void G(),disabled:!z,className:y(`inline-flex size-9 shrink-0 items-center justify-center rounded-full transition`,z?`bg-primary text-primary-foreground`:`bg-paper-2 text-ink-4`),"aria-label":`Send`,children:(0,M.jsx)(u,{className:`size-4`})})]})]}),R.error?(0,M.jsx)(`p`,{className:`mt-2 px-1 text-[12px] text-rose`,children:R.error===`denied`?x(`editor.micDenied`):R.error}):null]})]})}export{z as i,H as n,P as r,W as t};
|
|
1
|
+
import{a as e,n as t,t as n}from"./jsx-runtime-D3jfb0Ew.js";import{c as r,d as i,i as a,n as o,nt as s}from"./api-u3nydnnp.js";import{t as c}from"./createLucideIcon-q3MZMmnf.js";import{S as l,T as u,b as d,r as f,y as p}from"./outputs-C806GWxt.js";import{t as m}from"./chevron-down-DymW-2BP.js";import{t as h}from"./plus-Du-Jx8aI.js";import{t as g}from"./mic-Bvz4mA2j.js";import{_,d as v,h as y,o as b,y as x}from"./ui-gGAdXx-P.js";import{D as S,E as C}from"./index-BQQihL4r.js";var w={name:`chevron-up`,size:24,node:[[`path`,{d:`m18 15-6-6-6 6`,key:`153udz`}]]};w.node;var T=c(w),E=e(t(),1),D=!1;function O(){if(!(typeof window>`u`||D))return window.SpeechRecognition??window.webkitSpeechRecognition}var k=typeof navigator<`u`&&!!navigator.mediaDevices?.getUserMedia&&typeof MediaRecorder<`u`;function A(e,t){let n=e.trimEnd(),r=t.trim();return n&&r?`${n} ${r}`:n||r}function j(e,t){let[n,r]=(0,E.useState)(!1),[i,a]=(0,E.useState)(!1),[s,c]=(0,E.useState)(null),l=(0,E.useRef)(e);l.current=e;let u=(0,E.useRef)(t);u.current=t;let d=(0,E.useRef)(null);(0,E.useEffect)(()=>()=>d.current?.stop(),[]);let f=async()=>{let e=l.current,t;try{t=await navigator.mediaDevices.getUserMedia({audio:!0})}catch{c(`denied`);return}let n=[],i=new MediaRecorder(t);i.ondataavailable=e=>e.data.size&&n.push(e.data),i.onstop=async()=>{for(let e of t.getTracks())e.stop();d.current=null,r(!1);let s=(i.mimeType||`audio/webm`).split(`;`)[0],l=new File(n,`dictation`,{type:s});if(l.size){a(!0);try{let{text:t}=await o.upload(`/api/studio/transcribe`,l);t.trim()&&u.current(A(e,t))}catch(e){c(e.message)}finally{a(!1)}}},d.current={stop:()=>i.state!==`inactive`&&i.stop()},i.start(),r(!0)},p=e=>{let t=l.current,n=``,i=new e;i.continuous=!0,i.interimResults=!0,i.lang=_===`de`?`de-DE`:`en-US`,i.onresult=e=>{let r=``;for(let t=Math.max(0,e.resultIndex);t<e.results.length;t++){let i=e.results[t],a=i[0]?.transcript??``;i.isFinal?n=A(n,a):r+=a}u.current(A(t,A(n,r)))},i.onerror=e=>{if(e.error!==`aborted`&&e.error!==`no-speech`){if(e.error===`not-allowed`){c(`denied`);return}D=!0,k&&!n?(i.onend=null,d.current=null,f()):c(e.error)}},i.onend=()=>{d.current=null,r(!1)},d.current={stop:()=>i.stop()},i.start(),r(!0)};return{supported:!!O()||k,listening:n,processing:i,error:s,toggle:()=>{if(i)return;if(d.current){d.current.stop();return}c(null);let e=O();e?p(e):f()}}}var M=e(n(),1),N=/\.(png|jpe?g|gif|webp|avif|svg)$/i;function P(e){let t=e.filter(e=>e.type.startsWith(`image/`));return t.length?Object.fromEntries(t.map(e=>[e.name,URL.createObjectURL(e)])):void 0}function F(e){let t=e.match(/(?:^|\n\n)(?:Angehängt|Attached): ([^\n]+)$/);return t?{text:e.slice(0,t.index).trim(),names:t[1].split(`, `).filter(Boolean)}:{text:e,names:[]}}function I(e,t){if(e.name&&e.name!==`image.png`)return e;let n=e.type.split(`/`)[1]?.replace(`jpeg`,`jpg`)||`png`,r=new Date().toISOString().slice(0,19).replace(/[-:]/g,``).replace(`T`,`-`);return new File([e],`paste-${r}${t?`-${t+1}`:``}.${n}`,{type:e.type})}function L({url:e,label:t,children:n}){return(0,M.jsxs)(`div`,{className:`group relative`,title:t,children:[(0,M.jsx)(`img`,{src:e,alt:t,width:64,height:64,className:`size-16 rounded-lg bg-paper-2 object-cover ring-1 ring-border`}),n]})}function R({names:e,previews:t,fileUrl:n}){let r=e.filter(e=>t?.[e]||n&&N.test(e)),i=e.filter(e=>!r.includes(e));return(0,M.jsxs)(`div`,{className:`flex flex-col items-end gap-1.5`,children:[r.map(e=>{let r=t?.[e]??n?.(e)??``;return(0,M.jsx)(`a`,{href:r,target:`_blank`,rel:`noreferrer`,title:e,children:(0,M.jsx)(`img`,{src:r,alt:e,className:`max-h-60 w-auto max-w-full rounded-xl bg-paper-2 object-contain ring-1 ring-border`})},e)}),i.length?(0,M.jsx)(`div`,{className:`flex flex-wrap justify-end gap-1.5`,children:i.map(e=>(0,M.jsxs)(`span`,{className:`inline-flex max-w-full items-center gap-1.5 rounded-full bg-paper-2 px-2.5 py-1 text-[12px] text-ink-2`,children:[(0,M.jsx)(l,{className:`size-3 shrink-0 text-ink-4`}),(0,M.jsx)(`span`,{className:`truncate`,children:e})]},e))}):null]})}function z(e,t){let n=s(),[i,o]=(0,E.useState)([]),[c,l]=(0,E.useState)(`idle`),[u,d]=(0,E.useState)(null),[f,p]=(0,E.useState)(null),[m,h]=(0,E.useState)(null),[g,_]=(0,E.useState)(null),v=(0,E.useRef)(null);return(0,E.useEffect)(()=>{if(e){if(v.current!==e.id){v.current=e.id,o(e.messages);return}c===`idle`&&o(t=>e.messages.length>=t.length?e.messages:t)}},[e,c]),{messages:i,phase:c,activity:f,thought:m,startedAt:g,error:u,send:async(i,s=[])=>{if(!e||!(i.trim()||s.length)||c!==`idle`)return!1;if(d(null),_(Date.now()),h(null),s.length){l(`thinking`);try{for(let t of s){let n=await fetch(r(`/api/studio/wizards/${e.id}/files/${encodeURIComponent(t.name)}`),{method:`PUT`,credentials:`include`,headers:{"content-type":t.type||`application/octet-stream`},body:t});if(!n.ok){let e=await n.json().catch(()=>({}));throw Error(e.error??n.statusText)}}}catch(t){return d(t.message),l(`idle`),_(null),await n.invalidateQueries({queryKey:[`wizard`,e.id]}),!1}let t=`${x(`editor.attached`)}: ${s.map(e=>e.name).join(`, `)}`;i=i.trim()?`${i}\n\n${t}`:t}let u=`p-${Date.now()}`;o(e=>[...e,{id:`u-${Date.now()}`,role:`user`,content:i,previews:P(s)},{id:u,role:`assistant`,content:``,pending:!0}]),l(`thinking`),p(null);let f=!1;try{await a(`/api/studio/wizards/${e.id}/chat`,{message:i},(e,n)=>{if(e===`text`){let e=JSON.parse(n);o(t=>t.map(t=>t.id===u?{...t,content:t.content+e}:t))}else if(e===`activity`)p(JSON.parse(n));else if(e===`thought`)h(JSON.parse(n));else if(e===`building`)l(`building`);else if(e===`done`){f=!0;let e=JSON.parse(n);o(t=>t.map(t=>t.id===u?{...t,content:e.reply,changed:e.changed,pending:!1}:t)),e.changed&&t(e.draft,e.revision)}else e===`error`&&(f=!0,d(JSON.parse(n).message))}),f||d(x(`editor.chatBroken`))}catch(e){d(e.message)}finally{p(null),h(null),_(null),o(e=>e.filter(e=>!(e.id===u&&!e.content)).map(e=>({...e,pending:!1}))),l(`idle`),await n.invalidateQueries({queryKey:[`wizard`,e.id]}),await n.invalidateQueries({queryKey:[`me`]})}return!0},fileUrl:t=>r(`/api/studio/wizards/${e?.id}/files/${encodeURIComponent(t)}`)}}function B(e){let[t,n]=(0,E.useState)(()=>Date.now());return(0,E.useEffect)(()=>{if(e===null)return;n(Date.now());let t=setInterval(()=>n(Date.now()),1e3);return()=>clearInterval(t)},[e]),e===null?null:Math.max(0,Math.floor((t-e)/1e3))}function V(e){return e<60?`${e} s`:`${Math.floor(e/60)}:${String(e%60).padStart(2,`0`)} min`}function H({chat:e,thought:t,className:n,spinner:r=`size-3.5`}){let i=B(e.startedAt);return(0,M.jsxs)(`div`,{className:y(`min-w-0`,n),children:[(0,M.jsxs)(`div`,{className:`flex min-w-0 items-center gap-2`,children:[(0,M.jsx)(v,{className:y(`shrink-0`,r)}),(0,M.jsx)(`span`,{className:`min-w-0 truncate`,children:e.activity??(e.phase===`building`?x(`editor.building`):x(`editor.thinking`))}),i===null?null:(0,M.jsx)(`span`,{className:`shrink-0 text-ink-4 tabular-nums`,children:V(i)})]}),t&&e.thought?(0,M.jsx)(`p`,{className:`mt-0.5 truncate pl-5.5 text-[12px] text-ink-4`,children:e.thought}):null]})}function U({message:e,fileUrl:t}){let{text:n,names:r}=F(e.content);return(0,M.jsxs)(`div`,{className:`ml-8 flex flex-col items-end gap-1.5 self-end`,children:[r.length?(0,M.jsx)(R,{names:r,previews:e.previews,fileUrl:t}):null,n?(0,M.jsx)(`div`,{className:`rounded-xl rounded-br-md bg-paper-2 px-4 py-2.5 text-[14px] leading-relaxed`,children:(0,M.jsx)(`span`,{className:`whitespace-pre-wrap`,children:n})}):null]})}function W({chat:e,avatar:t,hello:n=x(`editor.chatHello`),placeholder:r=x(`editor.composer`),changedLabel:a=`Ablauf aktualisiert`,compact:o,intro:s,closed:c,card:_}){let[w,D]=(0,E.useState)(!1),[O,k]=(0,E.useState)(``),[A,N]=(0,E.useState)([]),P=(0,E.useRef)(null),F=(0,E.useRef)(null),R=(0,E.useRef)(null),z=j(O,k);(0,E.useEffect)(()=>{P.current?.scrollTo({top:P.current.scrollHeight,behavior:`smooth`})},[e.messages,e.phase]),(0,E.useEffect)(()=>{let e=F.current;if(!e)return;let t=()=>{e.style.height=`auto`,e.style.height=O?`${Math.min(e.scrollHeight,200)}px`:``};t();let n=e.clientWidth,r=new ResizeObserver(()=>{e.clientWidth!==n&&(n=e.clientWidth,t())});return r.observe(e),()=>r.disconnect()},[O]);let B=(O.trim()||A.length>0)&&e.phase===`idle`,V=e=>N(t=>[...t.filter(t=>!e.some(e=>e.name===t.name)),...e]),[W,G]=(0,E.useState)(new Map);(0,E.useEffect)(()=>{let e=new Map(A.filter(e=>e.type.startsWith(`image/`)).map(e=>[e,URL.createObjectURL(e)]));return G(e),()=>{for(let t of e.values())URL.revokeObjectURL(t)}},[A]);let K=async()=>{if(!B)return;z.listening&&z.toggle();let t={text:O,files:A};k(``),N([]),await e.send(t.text.trim(),t.files)||(k(t.text),N(t.files))},q=!o||w,J=e.messages.at(-1);return(0,M.jsxs)(`div`,{className:`flex h-full min-h-0 flex-col`,children:[o&&(J||e.error)?(0,M.jsxs)(`button`,{type:`button`,"aria-expanded":w,"aria-label":x(`editor.thread`),onClick:()=>D(e=>!e),className:`flex items-center gap-2 px-4 pt-2.5 pb-0.5 text-left text-[13px] text-ink-3 transition hover:text-ink`,children:[!(e.error||w)&&J?.pending?(0,M.jsx)(H,{chat:e,className:`flex-1`}):(0,M.jsx)(`span`,{className:y(`min-w-0 flex-1 truncate`,e.error&&`text-rose`),children:e.error??(w?x(`editor.thread`):J?.content)}),w?(0,M.jsx)(m,{className:`size-4 shrink-0`}):(0,M.jsx)(T,{className:`size-4 shrink-0`})]}):null,(0,M.jsxs)(`div`,{ref:P,className:y(`min-h-0 flex-1 overflow-y-auto px-5 py-5`,!q&&`hidden`),children:[e.messages.length===0&&!c?s??(0,M.jsxs)(`div`,{className:`flex items-start gap-3`,children:[(0,M.jsx)(i,{kind:t,size:32,interactive:!1}),(0,M.jsx)(`p`,{className:`pt-1 text-[14px] text-ink-2 leading-relaxed`,children:n})]}):null,(0,M.jsx)(`div`,{className:`flex flex-col gap-4`,children:e.messages.map(n=>n.role===`user`?(0,M.jsx)(U,{message:n,fileUrl:e.fileUrl},n.id):(0,M.jsxs)(`div`,{className:`flex items-start gap-3`,children:[(0,M.jsx)(`div`,{className:`shrink-0`,children:(0,M.jsx)(i,{kind:t,size:28,interactive:!1})}),(0,M.jsxs)(`div`,{className:`min-w-0 pt-0.5 text-[14px]`,children:[n.source===`mcp`?(0,M.jsxs)(`div`,{className:`mb-1 inline-flex items-center gap-1.5 text-[12px] text-ink-3`,children:[(0,M.jsx)(S,{className:`size-3`}),` `,x(`editor.viaClient`,{client:n.client??`MCP`})]}):null,n.content?(0,M.jsx)(f,{text:n.content,className:`text-[14px]`}):null,_&&n.cards?.length?(0,M.jsx)(`div`,{className:`mt-2 flex flex-col gap-2`,children:n.cards.map(e=>(0,M.jsx)(E.Fragment,{children:_(e)},e.id))}):null,n.pending?(0,M.jsx)(H,{chat:e,thought:!0,className:`mt-1 text-[13px] text-ink-3`}):null,n.changed?(0,M.jsxs)(`div`,{className:`mt-2 inline-flex items-center gap-1.5 rounded-full bg-ember-tint px-2.5 py-0.5 text-[12px] text-ember-strong`,children:[(0,M.jsx)(d,{className:`size-3`}),` `,a]}):null]})]},n.id))}),e.error?(0,M.jsx)(`div`,{className:`mt-4 rounded-lg bg-rose-tint px-3 py-2 text-[13px] text-rose`,children:e.error}):null]}),c?(0,M.jsx)(`p`,{className:`m-3 rounded-xl bg-paper-2 px-4 py-3 text-[13px] text-ink-2 leading-relaxed`,children:c}):(0,M.jsxs)(`div`,{className:o?`p-2`:`p-3`,children:[(0,M.jsxs)(`div`,{className:`rounded-xl bg-card p-1.5 shadow-soft ring-1 ring-border focus-within:ring-focus`,children:[W.size?(0,M.jsx)(`div`,{className:`flex flex-wrap gap-2 px-1 pt-1 pb-1.5`,children:A.map((e,t)=>{let n=W.get(e);return n?(0,M.jsx)(L,{url:n,label:e.name,children:(0,M.jsx)(`button`,{type:`button`,"aria-label":x(`editor.detach`),onClick:()=>N(e=>e.filter((e,n)=>n!==t)),className:`-top-1.5 -right-1.5 absolute flex size-5 items-center justify-center rounded-full bg-ink text-paper opacity-0 shadow-soft transition focus-visible:opacity-100 group-hover:opacity-100`,children:(0,M.jsx)(C,{className:`size-3`})})},`${e.name}-${t}`):null})}):null,A.some(e=>!W.has(e))?(0,M.jsx)(`ul`,{className:`flex flex-wrap gap-1.5 px-1 pt-1 pb-1.5`,children:A.map((e,t)=>W.has(e)?null:(0,M.jsxs)(`li`,{className:`inline-flex max-w-full items-center gap-1.5 rounded-full bg-paper-2 py-1 pr-1 pl-2.5 text-[12px] text-ink-2`,children:[(0,M.jsx)(l,{className:`size-3 shrink-0 text-ink-4`}),(0,M.jsx)(`span`,{className:`truncate`,children:e.name}),(0,M.jsx)(`button`,{type:`button`,"aria-label":x(`editor.detach`),onClick:()=>N(e=>e.filter((e,n)=>n!==t)),className:`inline-flex size-5 shrink-0 items-center justify-center rounded-full text-ink-3 hover:bg-paper-3 hover:text-ink`,children:(0,M.jsx)(C,{className:`size-3`})})]},`${e.name}-${t}`))}):null,(0,M.jsxs)(`div`,{className:`flex items-end gap-1`,children:[(0,M.jsx)(b,{label:x(`editor.attach`),onClick:()=>R.current?.click(),children:(0,M.jsx)(h,{className:`size-4`})}),(0,M.jsx)(`input`,{ref:R,type:`file`,multiple:!0,hidden:!0,onChange:e=>{let t=Array.from(e.target.files??[]);e.target.value=``,V(t)}}),(0,M.jsx)(`textarea`,{ref:F,rows:1,value:O,onChange:e=>k(e.target.value),onPaste:e=>{let t=Array.from(e.clipboardData.files);t.length&&(e.preventDefault(),V(t.map(I)))},onKeyDown:e=>{e.key===`Enter`&&!e.shiftKey&&(e.preventDefault(),K())},placeholder:z.listening?x(`editor.listening`):r,className:`max-h-[200px] min-h-[40px] flex-1 resize-none bg-transparent px-1.5 py-2 text-[14px] outline-none placeholder:text-ink-4`}),z.supported?(0,M.jsx)(b,{label:z.processing?x(`editor.transcribing`):z.listening?x(`editor.voiceStop`):x(`editor.voice`),"aria-pressed":z.listening,disabled:z.processing,onClick:z.toggle,className:y(z.listening&&`bg-rose-tint text-rose hover:bg-rose-tint hover:text-rose`),children:z.processing?(0,M.jsx)(v,{className:`size-4`}):z.listening?(0,M.jsx)(p,{className:`size-3.5 animate-pulse-dot fill-current`}):(0,M.jsx)(g,{className:`size-4`})}):null,(0,M.jsx)(`button`,{type:`button`,onClick:()=>void K(),disabled:!B,className:y(`inline-flex size-9 shrink-0 items-center justify-center rounded-full transition`,B?`bg-primary text-primary-foreground`:`bg-paper-2 text-ink-4`),"aria-label":`Send`,children:(0,M.jsx)(u,{className:`size-4`})})]})]}),z.error?(0,M.jsx)(`p`,{className:`mt-2 px-1 text-[12px] text-rose`,children:z.error===`denied`?x(`editor.micDenied`):z.error}):null]})]})}export{z as i,H as n,P as r,W as t};
|