claudemesh-cli 1.9.5 → 1.11.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.
@@ -88,7 +88,7 @@ __export(exports_urls, {
88
88
  VERSION: () => VERSION,
89
89
  URLS: () => URLS
90
90
  });
91
- var URLS, VERSION = "1.9.5", env;
91
+ var URLS, VERSION = "1.11.0", env;
92
92
  var init_urls = __esm(() => {
93
93
  URLS = {
94
94
  BROKER: process.env.CLAUDEMESH_BROKER_URL ?? "wss://ic.claudemesh.com/ws",
@@ -362,12 +362,11 @@ async function request(opts) {
362
362
  signal: controller.signal
363
363
  });
364
364
  if (!res.ok) {
365
- let body;
365
+ const text2 = await res.text();
366
+ let body = text2;
366
367
  try {
367
- body = await res.json();
368
- } catch {
369
- body = await res.text();
370
- }
368
+ body = JSON.parse(text2);
369
+ } catch {}
371
370
  throw new ApiError(res.status, res.statusText, body);
372
371
  }
373
372
  const text = await res.text();
@@ -12285,6 +12284,109 @@ var init_notification = __esm(() => {
12285
12284
  init_exit_codes();
12286
12285
  });
12287
12286
 
12287
+ // src/commands/me.ts
12288
+ var exports_me = {};
12289
+ __export(exports_me, {
12290
+ runMeTopics: () => runMeTopics,
12291
+ runMe: () => runMe
12292
+ });
12293
+ async function runMe(flags) {
12294
+ return withRestKey({
12295
+ meshSlug: flags.mesh ?? null,
12296
+ purpose: "workspace-overview",
12297
+ capabilities: ["read"]
12298
+ }, async ({ secret }) => {
12299
+ const ws = await request({
12300
+ path: "/api/v1/me/workspace",
12301
+ token: secret
12302
+ });
12303
+ if (flags.json) {
12304
+ console.log(JSON.stringify(ws, null, 2));
12305
+ return EXIT.SUCCESS;
12306
+ }
12307
+ render.section(`${clay("workspace")} — ${bold(ws.userId.slice(0, 8))} ${dim(`· ${ws.totals.meshes} mesh${ws.totals.meshes === 1 ? "" : "es"}`)}`);
12308
+ const totalsLine = [
12309
+ `${green(String(ws.totals.online))}/${ws.totals.peers} online`,
12310
+ `${ws.totals.topics} topic${ws.totals.topics === 1 ? "" : "s"}`,
12311
+ ws.totals.unreadMentions > 0 ? yellow(`${ws.totals.unreadMentions} unread @you`) : dim("0 unread @you")
12312
+ ].join(dim(" · "));
12313
+ process.stdout.write(" " + totalsLine + `
12314
+
12315
+ `);
12316
+ if (ws.meshes.length === 0) {
12317
+ process.stdout.write(dim(" no meshes joined — run `claudemesh new` or accept an invite\n"));
12318
+ return EXIT.SUCCESS;
12319
+ }
12320
+ const slugWidth = Math.max(...ws.meshes.map((m) => m.slug.length), 8);
12321
+ for (const m of ws.meshes) {
12322
+ const slug = cyan(m.slug.padEnd(slugWidth));
12323
+ const peers = `${m.online}/${m.peers}`;
12324
+ const role = dim(m.myRole);
12325
+ const unread = m.unreadMentions > 0 ? " " + yellow(`${m.unreadMentions} @you`) : "";
12326
+ process.stdout.write(` ${slug} ${peers.padStart(5)} online ${dim(String(m.topics).padStart(2) + " topics")} ${role}${unread}
12327
+ `);
12328
+ }
12329
+ return EXIT.SUCCESS;
12330
+ });
12331
+ }
12332
+ async function runMeTopics(flags) {
12333
+ return withRestKey({
12334
+ meshSlug: flags.mesh ?? null,
12335
+ purpose: "workspace-topics",
12336
+ capabilities: ["read"]
12337
+ }, async ({ secret }) => {
12338
+ const ws = await request({
12339
+ path: "/api/v1/me/topics",
12340
+ token: secret
12341
+ });
12342
+ const visible = flags.unread ? ws.topics.filter((t) => t.unread > 0) : ws.topics;
12343
+ if (flags.json) {
12344
+ console.log(JSON.stringify({ topics: visible, totals: ws.totals }, null, 2));
12345
+ return EXIT.SUCCESS;
12346
+ }
12347
+ render.section(`${clay("topics")} — ${ws.totals.topics} across all meshes ${dim(ws.totals.unread > 0 ? `· ${ws.totals.unread} unread` : "· all read")}`);
12348
+ if (visible.length === 0) {
12349
+ process.stdout.write(dim(flags.unread ? ` no unread topics
12350
+ ` : " no topics — run `claudemesh topic create #general`\n"));
12351
+ return EXIT.SUCCESS;
12352
+ }
12353
+ const slugWidth = Math.max(...visible.map((t) => t.meshSlug.length), 6);
12354
+ const nameWidth = Math.max(...visible.map((t) => t.name.length), 8);
12355
+ for (const t of visible) {
12356
+ const slug = dim(t.meshSlug.padEnd(slugWidth));
12357
+ const name = cyan(t.name.padEnd(nameWidth));
12358
+ const unread = t.unread > 0 ? yellow(`${t.unread} unread`.padStart(10)) : dim("·".padStart(10));
12359
+ const last = t.lastMessageAt ? dim(formatRelativeTime(t.lastMessageAt)) : dim("never");
12360
+ process.stdout.write(` ${slug} ${name} ${unread} ${last}
12361
+ `);
12362
+ }
12363
+ return EXIT.SUCCESS;
12364
+ });
12365
+ }
12366
+ function formatRelativeTime(iso) {
12367
+ const then = new Date(iso).getTime();
12368
+ const now = Date.now();
12369
+ const sec = Math.max(0, Math.floor((now - then) / 1000));
12370
+ if (sec < 60)
12371
+ return `${sec}s ago`;
12372
+ if (sec < 3600)
12373
+ return `${Math.floor(sec / 60)}m ago`;
12374
+ if (sec < 86400)
12375
+ return `${Math.floor(sec / 3600)}h ago`;
12376
+ if (sec < 86400 * 30)
12377
+ return `${Math.floor(sec / 86400)}d ago`;
12378
+ if (sec < 86400 * 365)
12379
+ return `${Math.floor(sec / (86400 * 30))}mo ago`;
12380
+ return `${Math.floor(sec / (86400 * 365))}y ago`;
12381
+ }
12382
+ var init_me = __esm(() => {
12383
+ init_with_rest_key();
12384
+ init_client();
12385
+ init_render();
12386
+ init_styles();
12387
+ init_exit_codes();
12388
+ });
12389
+
12288
12390
  // src/commands/member.ts
12289
12391
  var exports_member = {};
12290
12392
  __export(exports_member, {
@@ -13924,6 +14026,8 @@ Topic (conversation scope, v0.2.0)
13924
14026
  claudemesh topic tail <topic> live SSE tail [--limit --forward-only]
13925
14027
  claudemesh topic post <t> <msg> encrypted REST post (v0.3.0 v2) [--reply-to <id>]
13926
14028
  claudemesh send "#topic" "msg" send to a topic (WS path, v1 plaintext)
14029
+ claudemesh me cross-mesh workspace overview (v0.4.0)
14030
+ claudemesh me topics cross-mesh topic list [--unread]
13927
14031
  claudemesh member list mesh roster with online state [--online]
13928
14032
  claudemesh notification list recent @-mentions of you [--since <ISO>]
13929
14033
 
@@ -14781,6 +14885,26 @@ async function main() {
14781
14885
  }
14782
14886
  break;
14783
14887
  }
14888
+ case "me": {
14889
+ const sub = positionals[0];
14890
+ const f = {
14891
+ mesh: flags.mesh,
14892
+ json: !!flags.json
14893
+ };
14894
+ if (!sub || sub === "workspace" || sub === "overview") {
14895
+ const { runMe: runMe2 } = await Promise.resolve().then(() => (init_me(), exports_me));
14896
+ process.exit(await runMe2(f));
14897
+ } else if (sub === "topics") {
14898
+ const { runMeTopics: runMeTopics2 } = await Promise.resolve().then(() => (init_me(), exports_me));
14899
+ process.exit(await runMeTopics2({ ...f, unread: !!flags.unread }));
14900
+ } else {
14901
+ console.error(`Usage: claudemesh me (cross-mesh overview)
14902
+ claudemesh me topics (cross-mesh topic list)
14903
+ claudemesh me topics --unread (only unread topics)`);
14904
+ process.exit(EXIT.INVALID_ARGS);
14905
+ }
14906
+ break;
14907
+ }
14784
14908
  case "member":
14785
14909
  case "members": {
14786
14910
  const sub = positionals[0] ?? "list";
@@ -14846,4 +14970,4 @@ main().catch((err) => {
14846
14970
  process.exit(EXIT.INTERNAL_ERROR);
14847
14971
  });
14848
14972
 
14849
- //# debugId=DFCA83812E690F9B64756E2164756E21
14973
+ //# debugId=9953681D906F7F1E64756E2164756E21