@wibeco/bridge 0.2.1 → 0.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{chunk-FLTLCZ6E.js → chunk-A7KGZ7NX.js} +22 -8
- package/dist/{chunk-YV3UV2XJ.js → chunk-XMEA243L.js} +91 -10
- package/dist/cli.js +12 -2
- package/dist/codex-hook.js +2 -2
- package/dist/index.d.ts +6 -4
- package/dist/index.js +1 -1
- package/package.json +1 -1
- package/templates/cursor/wibe-activity.mdc.example +14 -0
|
@@ -15,6 +15,7 @@ var hookEventKindSchema = z.enum([
|
|
|
15
15
|
"shell.completed",
|
|
16
16
|
"mcp.started",
|
|
17
17
|
"mcp.completed",
|
|
18
|
+
"progress.shared",
|
|
18
19
|
"unknown"
|
|
19
20
|
]);
|
|
20
21
|
var safeScalarSchema = z.union([z.string(), z.number(), z.boolean(), z.null()]);
|
|
@@ -328,6 +329,7 @@ function eventTypeForHook(event) {
|
|
|
328
329
|
if (event.kind === "presence.heartbeat") return "presence.heartbeat";
|
|
329
330
|
if (event.kind === "session.ended") return "presence.stopped";
|
|
330
331
|
if (event.kind === "file.changed") return "workspace.files_changed";
|
|
332
|
+
if (event.kind === "progress.shared") return "agent.progress_shared";
|
|
331
333
|
if (event.kind === "shell.completed" && event.outcome && isTestHookEvent(event)) {
|
|
332
334
|
return "workspace.test_completed";
|
|
333
335
|
}
|
|
@@ -352,7 +354,13 @@ function toEnvelope(event, options) {
|
|
|
352
354
|
...Array.isArray(event.metadata.paths) ? event.metadata.paths.filter((path) => typeof path === "string") : [],
|
|
353
355
|
...typeof event.metadata.path === "string" ? [event.metadata.path] : []
|
|
354
356
|
];
|
|
355
|
-
const payload = event.kind === "
|
|
357
|
+
const payload = event.kind === "progress.shared" ? {
|
|
358
|
+
title: event.metadata.title,
|
|
359
|
+
summary: event.metadata.summary,
|
|
360
|
+
paths,
|
|
361
|
+
phase: event.metadata.phase,
|
|
362
|
+
confidence: event.metadata.confidence
|
|
363
|
+
} : event.kind === "file.changed" ? {
|
|
356
364
|
paths,
|
|
357
365
|
tool: event.source,
|
|
358
366
|
agent_name: event.source,
|
|
@@ -556,6 +564,7 @@ import { homedir } from "os";
|
|
|
556
564
|
import { join } from "path";
|
|
557
565
|
var PRESENCE_HEARTBEAT_INTERVAL_MS = 45e3;
|
|
558
566
|
var MAX_SESSION_DURATION_MS = 12 * 60 * 60 * 1e3;
|
|
567
|
+
var MAX_SESSION_LINE_COUNT = 1e7;
|
|
559
568
|
async function startPresenceSession(source, sessionId, cwd = process.cwd()) {
|
|
560
569
|
const statePath = presenceStatePath(source, sessionId, cwd);
|
|
561
570
|
await rm(statePath, { force: true });
|
|
@@ -611,11 +620,14 @@ async function updatePresenceSession(source, sessionId, event, cwd = process.cwd
|
|
|
611
620
|
const state = await readPresenceState(statePath);
|
|
612
621
|
if (!state) return void 0;
|
|
613
622
|
const measuredAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
614
|
-
|
|
623
|
+
const isHeartbeat = event.kind === "presence.heartbeat";
|
|
624
|
+
if (!isHeartbeat) accrueModelTime(state, measuredAt);
|
|
615
625
|
const model = typeof event.metadata.model === "string" ? event.metadata.model : void 0;
|
|
616
626
|
if (model) state.model = model;
|
|
617
|
-
|
|
618
|
-
|
|
627
|
+
if (!isHeartbeat) {
|
|
628
|
+
state.linesAdded += safeCount(event.metadata.lines_added);
|
|
629
|
+
state.linesDeleted += safeCount(event.metadata.lines_deleted);
|
|
630
|
+
}
|
|
619
631
|
const workingLinesAdded = optionalCount(
|
|
620
632
|
event.metadata.working_tree_lines_added
|
|
621
633
|
);
|
|
@@ -624,17 +636,19 @@ async function updatePresenceSession(source, sessionId, event, cwd = process.cwd
|
|
|
624
636
|
);
|
|
625
637
|
if (workingLinesAdded !== void 0) {
|
|
626
638
|
state.baselineLinesAdded ??= workingLinesAdded;
|
|
627
|
-
|
|
628
|
-
|
|
639
|
+
const workingDelta = Math.max(
|
|
640
|
+
0,
|
|
629
641
|
workingLinesAdded - state.baselineLinesAdded
|
|
630
642
|
);
|
|
643
|
+
state.linesAdded = isHeartbeat && state.linesAdded > MAX_SESSION_LINE_COUNT ? workingDelta : Math.max(state.linesAdded, workingDelta);
|
|
631
644
|
}
|
|
632
645
|
if (workingLinesDeleted !== void 0) {
|
|
633
646
|
state.baselineLinesDeleted ??= workingLinesDeleted;
|
|
634
|
-
|
|
635
|
-
|
|
647
|
+
const workingDelta = Math.max(
|
|
648
|
+
0,
|
|
636
649
|
workingLinesDeleted - state.baselineLinesDeleted
|
|
637
650
|
);
|
|
651
|
+
state.linesDeleted = isHeartbeat && state.linesDeleted > MAX_SESSION_LINE_COUNT ? workingDelta : Math.max(state.linesDeleted, workingDelta);
|
|
638
652
|
}
|
|
639
653
|
const paths = [
|
|
640
654
|
...Array.isArray(event.metadata.paths) ? event.metadata.paths.filter(
|
|
@@ -17,7 +17,7 @@ import {
|
|
|
17
17
|
startPresenceSession,
|
|
18
18
|
stopPresenceSession,
|
|
19
19
|
updatePresenceSession
|
|
20
|
-
} from "./chunk-
|
|
20
|
+
} from "./chunk-A7KGZ7NX.js";
|
|
21
21
|
|
|
22
22
|
// src/cli/commands.ts
|
|
23
23
|
import { access, cp, mkdir, readFile, writeFile } from "fs/promises";
|
|
@@ -64,7 +64,8 @@ async function setupCommand(requestedAdapter, options = {}) {
|
|
|
64
64
|
adapter,
|
|
65
65
|
source,
|
|
66
66
|
cwd,
|
|
67
|
-
appUrl
|
|
67
|
+
appUrl,
|
|
68
|
+
options.projectId
|
|
68
69
|
);
|
|
69
70
|
const heartbeat2 = await sendVerificationHeartbeat(
|
|
70
71
|
existingCredential,
|
|
@@ -153,7 +154,8 @@ Confirm code ${authorization.user_code}
|
|
|
153
154
|
adapter,
|
|
154
155
|
source,
|
|
155
156
|
cwd,
|
|
156
|
-
appUrl
|
|
157
|
+
appUrl,
|
|
158
|
+
token.projectId
|
|
157
159
|
);
|
|
158
160
|
const heartbeat = await sendVerificationHeartbeat(credential, adapter, "setup");
|
|
159
161
|
return {
|
|
@@ -235,7 +237,16 @@ async function emitCommand(adapter, eventName, input) {
|
|
|
235
237
|
mappedEvent.sessionId,
|
|
236
238
|
mappedEvent
|
|
237
239
|
);
|
|
238
|
-
if (mappedEvent.kind === "
|
|
240
|
+
if (mappedEvent.kind === "file.changed" && metrics) {
|
|
241
|
+
mappedEvent = {
|
|
242
|
+
...mappedEvent,
|
|
243
|
+
metadata: {
|
|
244
|
+
...mappedEvent.metadata,
|
|
245
|
+
lines_added: metrics.lines_added,
|
|
246
|
+
lines_deleted: metrics.lines_deleted
|
|
247
|
+
}
|
|
248
|
+
};
|
|
249
|
+
} else if (mappedEvent.kind === "presence.heartbeat" && metrics) {
|
|
239
250
|
const publicMetadata = { ...mappedEvent.metadata };
|
|
240
251
|
delete publicMetadata.working_tree_paths;
|
|
241
252
|
delete publicMetadata.paths;
|
|
@@ -274,6 +285,62 @@ async function emitCommand(adapter, eventName, input) {
|
|
|
274
285
|
message: result.error ? `Queued ${event.kind}; delivery failed: ${result.error}` : `Delivered ${result.sent} event(s); ${result.remaining} queued.`
|
|
275
286
|
};
|
|
276
287
|
}
|
|
288
|
+
async function shareProgressCommand(options, cwd = process.cwd()) {
|
|
289
|
+
const projectConfig = await readProjectConfig(
|
|
290
|
+
join(cwd, ".wibe", "project.json")
|
|
291
|
+
);
|
|
292
|
+
const credential = await loadCredential(cwd);
|
|
293
|
+
if (!projectConfig || !credential) {
|
|
294
|
+
throw new Error("Wibe is not authorized in this repository. Run wibe setup first.");
|
|
295
|
+
}
|
|
296
|
+
const summary = options.summary?.trim() ?? "";
|
|
297
|
+
const wordCount = summary.split(/\s+/).filter(Boolean).length;
|
|
298
|
+
if (wordCount < 8 || wordCount > 22 || summary.length > 500) {
|
|
299
|
+
throw new Error("Progress summary must contain 8\u201322 words.");
|
|
300
|
+
}
|
|
301
|
+
const title = options.title?.trim();
|
|
302
|
+
if (title && title.length > 120) {
|
|
303
|
+
throw new Error("Progress title must be 120 characters or fewer.");
|
|
304
|
+
}
|
|
305
|
+
const phases = [
|
|
306
|
+
"planning",
|
|
307
|
+
"implementing",
|
|
308
|
+
"validating",
|
|
309
|
+
"blocked",
|
|
310
|
+
"shipped"
|
|
311
|
+
];
|
|
312
|
+
if (options.phase && !phases.includes(options.phase)) {
|
|
313
|
+
throw new Error(`Progress phase must be one of: ${phases.join(", ")}.`);
|
|
314
|
+
}
|
|
315
|
+
if (options.confidence !== void 0 && (!Number.isFinite(options.confidence) || options.confidence < 0 || options.confidence > 1)) {
|
|
316
|
+
throw new Error("Progress confidence must be between 0 and 1.");
|
|
317
|
+
}
|
|
318
|
+
const repo = await detectRepository(cwd);
|
|
319
|
+
const event = createHookEvent({
|
|
320
|
+
source: projectConfig.adapter,
|
|
321
|
+
kind: "progress.shared",
|
|
322
|
+
metadata: {
|
|
323
|
+
summary,
|
|
324
|
+
...title ? { title } : {},
|
|
325
|
+
...options.phase ? { phase: options.phase } : {},
|
|
326
|
+
...options.confidence !== void 0 ? { confidence: options.confidence } : {}
|
|
327
|
+
},
|
|
328
|
+
...repo ? { repo } : {}
|
|
329
|
+
});
|
|
330
|
+
const result = await new SignedBatchClient({
|
|
331
|
+
endpoint: `${credential.appUrl}/api/events/batch`,
|
|
332
|
+
accessToken: credential.accessToken,
|
|
333
|
+
organizationId: credential.organizationId,
|
|
334
|
+
projectId: credential.projectId,
|
|
335
|
+
repositoryId: credential.repositoryId,
|
|
336
|
+
deviceId: credential.deviceId,
|
|
337
|
+
queue: new JsonFileOfflineQueue(queuePath())
|
|
338
|
+
}).capture(event);
|
|
339
|
+
return {
|
|
340
|
+
exitCode: result.error ? 1 : 0,
|
|
341
|
+
message: result.error ? `Progress was queued; delivery failed: ${result.error}` : `Shared progress with Wibe; ${result.remaining} event(s) queued.`
|
|
342
|
+
};
|
|
343
|
+
}
|
|
277
344
|
async function doctorCommand(cwd = process.cwd(), requestedRepository) {
|
|
278
345
|
const credential = await loadCredential(cwd);
|
|
279
346
|
const projectConfig = await readProjectConfig(join(cwd, ".wibe", "project.json"));
|
|
@@ -293,7 +360,7 @@ async function doctorCommand(cwd = process.cwd(), requestedRepository) {
|
|
|
293
360
|
adapterError = error instanceof Error ? error.message : String(error);
|
|
294
361
|
}
|
|
295
362
|
const heartbeat = credential && adapter && repositoryMatches ? await sendVerificationHeartbeat(credential, adapter, "doctor") : void 0;
|
|
296
|
-
const nativeConfig = adapter ? await validateNativeConfigs(adapter, cwd) : { hooks: false, mcp: false };
|
|
363
|
+
const nativeConfig = adapter ? await validateNativeConfigs(adapter, cwd) : { hooks: false, mcp: false, activityRule: false };
|
|
297
364
|
const checks = [
|
|
298
365
|
["node", Number(process.versions.node.split(".")[0]) >= 20],
|
|
299
366
|
["git repository", Boolean(repository)],
|
|
@@ -312,6 +379,7 @@ async function doctorCommand(cwd = process.cwd(), requestedRepository) {
|
|
|
312
379
|
],
|
|
313
380
|
["agent hooks configuration", nativeConfig.hooks],
|
|
314
381
|
["MCP endpoint configuration", nativeConfig.mcp],
|
|
382
|
+
["agent activity instructions", nativeConfig.activityRule],
|
|
315
383
|
[
|
|
316
384
|
heartbeat?.error ? `verification heartbeat (${heartbeat.error})` : "verification heartbeat",
|
|
317
385
|
Boolean(heartbeat && !heartbeat.error)
|
|
@@ -358,10 +426,11 @@ function openBrowser(url) {
|
|
|
358
426
|
}
|
|
359
427
|
execFile(executable, args, () => void 0);
|
|
360
428
|
}
|
|
361
|
-
async function installNativeConfigs(adapter, source, cwd, appUrl) {
|
|
429
|
+
async function installNativeConfigs(adapter, source, cwd, appUrl, projectId) {
|
|
362
430
|
const files = adapter === "cursor" ? [
|
|
363
431
|
["hooks.json.example", ".cursor/hooks.json"],
|
|
364
|
-
["mcp.json.example", ".cursor/mcp.json"]
|
|
432
|
+
["mcp.json.example", ".cursor/mcp.json"],
|
|
433
|
+
["wibe-activity.mdc.example", ".cursor/rules/wibe-activity.mdc"]
|
|
365
434
|
] : adapter === "claude-code" ? [
|
|
366
435
|
["settings.json.example", ".claude/settings.json"],
|
|
367
436
|
["mcp.json.example", ".mcp.json"]
|
|
@@ -377,7 +446,7 @@ async function installNativeConfigs(adapter, source, cwd, appUrl) {
|
|
|
377
446
|
await mkdir(resolve(destinationPath, ".."), { recursive: true });
|
|
378
447
|
await writeFile(
|
|
379
448
|
destinationPath,
|
|
380
|
-
template.replaceAll("${env:WIBE_APP_URL}", appUrl).replaceAll("${WIBE_APP_URL}", appUrl),
|
|
449
|
+
template.replaceAll("${env:WIBE_APP_URL}", appUrl).replaceAll("${WIBE_APP_URL}", appUrl).replaceAll("${WIBE_PROJECT_ID}", projectId),
|
|
381
450
|
{ mode: 384 }
|
|
382
451
|
);
|
|
383
452
|
installed.push(destinationName);
|
|
@@ -408,7 +477,7 @@ async function validateNativeConfigs(adapter, cwd) {
|
|
|
408
477
|
} catch {
|
|
409
478
|
mcp = false;
|
|
410
479
|
}
|
|
411
|
-
return { hooks, mcp };
|
|
480
|
+
return { hooks, mcp, activityRule: true };
|
|
412
481
|
}
|
|
413
482
|
const hookPath = adapter === "cursor" ? join(cwd, ".cursor", "hooks.json") : join(cwd, ".claude", "settings.json");
|
|
414
483
|
const mcpPath = adapter === "cursor" ? join(cwd, ".cursor", "mcp.json") : join(cwd, ".mcp.json");
|
|
@@ -418,9 +487,20 @@ async function validateNativeConfigs(adapter, cwd) {
|
|
|
418
487
|
if (!isRecord(value.mcpServers)) return false;
|
|
419
488
|
const wibe = value.mcpServers.wibe;
|
|
420
489
|
return isRecord(wibe) && typeof wibe.url === "string" && wibe.url.replace(/\/$/, "").endsWith("/api/mcp");
|
|
421
|
-
})
|
|
490
|
+
}),
|
|
491
|
+
activityRule: adapter !== "cursor" || await validText(
|
|
492
|
+
join(cwd, ".cursor", "rules", "wibe-activity.mdc"),
|
|
493
|
+
(value) => value.includes("alwaysApply: true") && value.includes("wibe_share_progress") && value.includes("wibe share-progress")
|
|
494
|
+
)
|
|
422
495
|
};
|
|
423
496
|
}
|
|
497
|
+
async function validText(path, predicate) {
|
|
498
|
+
try {
|
|
499
|
+
return predicate(await readFile(path, "utf8"));
|
|
500
|
+
} catch {
|
|
501
|
+
return false;
|
|
502
|
+
}
|
|
503
|
+
}
|
|
424
504
|
async function validJson(path, predicate) {
|
|
425
505
|
try {
|
|
426
506
|
const value = JSON.parse(await readFile(path, "utf8"));
|
|
@@ -573,6 +653,7 @@ export {
|
|
|
573
653
|
setupCommand,
|
|
574
654
|
statusCommand,
|
|
575
655
|
emitCommand,
|
|
656
|
+
shareProgressCommand,
|
|
576
657
|
doctorCommand,
|
|
577
658
|
parseAdapter
|
|
578
659
|
};
|
package/dist/cli.js
CHANGED
|
@@ -4,11 +4,12 @@ import {
|
|
|
4
4
|
emitCommand,
|
|
5
5
|
parseAdapter,
|
|
6
6
|
setupCommand,
|
|
7
|
+
shareProgressCommand,
|
|
7
8
|
statusCommand
|
|
8
|
-
} from "./chunk-
|
|
9
|
+
} from "./chunk-XMEA243L.js";
|
|
9
10
|
import {
|
|
10
11
|
runPresenceHeartbeat
|
|
11
|
-
} from "./chunk-
|
|
12
|
+
} from "./chunk-A7KGZ7NX.js";
|
|
12
13
|
|
|
13
14
|
// src/cli.ts
|
|
14
15
|
var HELP = `wibe-bridge <command>
|
|
@@ -20,6 +21,7 @@ Commands:
|
|
|
20
21
|
Use --reauthorize only to replace a rejected or revoked device token.
|
|
21
22
|
status
|
|
22
23
|
emit --adapter <name> --event <hook-name> (JSON payload on stdin)
|
|
24
|
+
share-progress --summary <8-22 words> [--title <title>] [--phase <phase>] [--confidence <0-1>]
|
|
23
25
|
doctor [--repository <owner/repo>]`;
|
|
24
26
|
async function main() {
|
|
25
27
|
const [command, ...args] = process.argv.slice(2);
|
|
@@ -46,6 +48,14 @@ async function main() {
|
|
|
46
48
|
return;
|
|
47
49
|
} else if (command === "doctor") {
|
|
48
50
|
result = await doctorCommand(process.cwd(), option(args, "--repository"));
|
|
51
|
+
} else if (command === "share-progress") {
|
|
52
|
+
const confidence = option(args, "--confidence");
|
|
53
|
+
result = await shareProgressCommand({
|
|
54
|
+
summary: option(args, "--summary"),
|
|
55
|
+
title: option(args, "--title"),
|
|
56
|
+
phase: option(args, "--phase"),
|
|
57
|
+
confidence: confidence === void 0 ? void 0 : Number(confidence)
|
|
58
|
+
});
|
|
49
59
|
} else if (command === "_presence-heartbeat") {
|
|
50
60
|
parseAdapter(option(args, "--adapter"));
|
|
51
61
|
const statePath = option(args, "--state");
|
package/dist/codex-hook.js
CHANGED
package/dist/index.d.ts
CHANGED
|
@@ -19,6 +19,7 @@ declare const hookEventKindSchema: z.ZodEnum<{
|
|
|
19
19
|
"shell.completed": "shell.completed";
|
|
20
20
|
"mcp.started": "mcp.started";
|
|
21
21
|
"mcp.completed": "mcp.completed";
|
|
22
|
+
"progress.shared": "progress.shared";
|
|
22
23
|
unknown: "unknown";
|
|
23
24
|
}>;
|
|
24
25
|
type HookEventKind = z.infer<typeof hookEventKindSchema>;
|
|
@@ -48,6 +49,7 @@ declare const canonicalHookEventSchema: z.ZodObject<{
|
|
|
48
49
|
"shell.completed": "shell.completed";
|
|
49
50
|
"mcp.started": "mcp.started";
|
|
50
51
|
"mcp.completed": "mcp.completed";
|
|
52
|
+
"progress.shared": "progress.shared";
|
|
51
53
|
unknown: "unknown";
|
|
52
54
|
}>;
|
|
53
55
|
occurredAt: z.ZodString;
|
|
@@ -74,7 +76,7 @@ declare function mapClaudeCodeHook(eventName: string, input: unknown): {
|
|
|
74
76
|
id: string;
|
|
75
77
|
version: 1;
|
|
76
78
|
source: "cursor" | "claude-code" | "codex";
|
|
77
|
-
kind: "presence.heartbeat" | "session.started" | "session.ended" | "lifecycle.before" | "lifecycle.after" | "tool.started" | "tool.completed" | "file.changed" | "shell.started" | "shell.completed" | "mcp.started" | "mcp.completed" | "unknown";
|
|
79
|
+
kind: "presence.heartbeat" | "session.started" | "session.ended" | "lifecycle.before" | "lifecycle.after" | "tool.started" | "tool.completed" | "file.changed" | "shell.started" | "shell.completed" | "mcp.started" | "mcp.completed" | "progress.shared" | "unknown";
|
|
78
80
|
occurredAt: string;
|
|
79
81
|
metadata: Record<string, SafeValue>;
|
|
80
82
|
sessionId?: string | undefined;
|
|
@@ -92,7 +94,7 @@ declare function mapCodexHook(eventName: string, input: unknown): {
|
|
|
92
94
|
id: string;
|
|
93
95
|
version: 1;
|
|
94
96
|
source: "cursor" | "claude-code" | "codex";
|
|
95
|
-
kind: "presence.heartbeat" | "session.started" | "session.ended" | "lifecycle.before" | "lifecycle.after" | "tool.started" | "tool.completed" | "file.changed" | "shell.started" | "shell.completed" | "mcp.started" | "mcp.completed" | "unknown";
|
|
97
|
+
kind: "presence.heartbeat" | "session.started" | "session.ended" | "lifecycle.before" | "lifecycle.after" | "tool.started" | "tool.completed" | "file.changed" | "shell.started" | "shell.completed" | "mcp.started" | "mcp.completed" | "progress.shared" | "unknown";
|
|
96
98
|
occurredAt: string;
|
|
97
99
|
metadata: Record<string, SafeValue>;
|
|
98
100
|
sessionId?: string | undefined;
|
|
@@ -110,7 +112,7 @@ declare function mapCursorHook(eventName: string, input: unknown): {
|
|
|
110
112
|
id: string;
|
|
111
113
|
version: 1;
|
|
112
114
|
source: "cursor" | "claude-code" | "codex";
|
|
113
|
-
kind: "presence.heartbeat" | "session.started" | "session.ended" | "lifecycle.before" | "lifecycle.after" | "tool.started" | "tool.completed" | "file.changed" | "shell.started" | "shell.completed" | "mcp.started" | "mcp.completed" | "unknown";
|
|
115
|
+
kind: "presence.heartbeat" | "session.started" | "session.ended" | "lifecycle.before" | "lifecycle.after" | "tool.started" | "tool.completed" | "file.changed" | "shell.started" | "shell.completed" | "mcp.started" | "mcp.completed" | "progress.shared" | "unknown";
|
|
114
116
|
occurredAt: string;
|
|
115
117
|
metadata: Record<string, SafeValue>;
|
|
116
118
|
sessionId?: string | undefined;
|
|
@@ -237,7 +239,7 @@ interface SignedBatchClientOptions {
|
|
|
237
239
|
batchSize?: number;
|
|
238
240
|
timeoutMs?: number;
|
|
239
241
|
}
|
|
240
|
-
declare function eventTypeForHook(event: CanonicalHookEvent): "presence.heartbeat" | "presence.started" | "presence.stopped" | "workspace.files_changed" | "workspace.test_completed" | null;
|
|
242
|
+
declare function eventTypeForHook(event: CanonicalHookEvent): "presence.heartbeat" | "presence.started" | "presence.stopped" | "workspace.files_changed" | "agent.progress_shared" | "workspace.test_completed" | null;
|
|
241
243
|
interface FlushResult {
|
|
242
244
|
sent: number;
|
|
243
245
|
remaining: number;
|
package/dist/index.js
CHANGED
package/package.json
CHANGED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Share meaningful coding-agent milestones with Wibe
|
|
3
|
+
alwaysApply: true
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Wibe activity
|
|
7
|
+
|
|
8
|
+
- This repository is connected to Wibe project `${WIBE_PROJECT_ID}`.
|
|
9
|
+
- After a plan is settled, share it with `wibe_share_plan` when that tool is available.
|
|
10
|
+
- After a meaningful implementation, validation, blocker, or completion milestone, call `wibe_share_progress`.
|
|
11
|
+
- Write one concrete 8–22 word sentence. Use present progressive for active work and past tense for completed work.
|
|
12
|
+
- Mention validation or blockers when material. Never include prompts, source code, secrets, raw commands, praise, hype, or speculation.
|
|
13
|
+
- Do not publish routine tool calls or repeated updates. Wait at least 90 seconds between progress updates unless reporting a blocker or completion.
|
|
14
|
+
- If the Wibe MCP tools are unavailable, run `npx --yes --package @wibeco/bridge@latest wibe share-progress --summary "<summary>" --phase <planning|implementing|validating|blocked|shipped>`.
|