@team-ai/teamai-cli 0.22.3 → 0.22.4

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/cli.js CHANGED
@@ -61237,12 +61237,31 @@ function isBindPromptEnabled() {
61237
61237
  const normalized = flag.toLowerCase();
61238
61238
  return normalized !== "0" && normalized !== "false";
61239
61239
  }
61240
- function resolveProjectPromptMode(config) {
61241
- if (config.projectPromptMode === "auto" || config.projectPromptMode === "manual") {
61242
- return config.projectPromptMode;
61240
+ function resolveProjectAssociationMode(config) {
61241
+ if (config.projectAssociationMode === "auto" || config.projectAssociationMode === "manual") {
61242
+ return config.projectAssociationMode;
61243
61243
  }
61244
61244
  return "unset";
61245
61245
  }
61246
+ function bindingHintText(projects) {
61247
+ const skipNum = projects.length + 1;
61248
+ const choices = projects.map((p2, i2) => `${i2 + 1}. \u7ED1\u5B9A\u5230\u300C${p2.name}\u300D\u9879\u76EE`);
61249
+ const actions = projects.map((p2, i2) => `- \u7528\u6237\u56DE\u590D ${i2 + 1} \u2192 \u6267\u884C \`teamai bind-project --project-id ${p2.id}\`\uFF0C\u5B8C\u6210\u540E\u56DE\u590D"\u7ED1\u5B9A\u5B8C\u6210\uFF0C\u8BF7\u5F00\u65B0\u4F1A\u8BDD\u751F\u6548"`);
61250
+ return [
61251
+ `${BINDING_HINT_HEADER} \u4F60\u5FC5\u987B\u539F\u6837\u5C55\u793A\u4E0B\u9762\u7684\u9009\u9879\u5217\u8868\uFF0C\u4E0D\u5F97\u4FEE\u6539\u7F16\u53F7\u6216\u5185\u5BB9\u3002\u7B49\u7528\u6237\u56DE\u590D\u6570\u5B57\u540E\u6267\u884C\u5BF9\u5E94\u547D\u4EE4\u3002`,
61252
+ "",
61253
+ "---",
61254
+ "\u5F53\u524D\u5DE5\u4F5C\u533A\u672A\u7ED1\u5B9AClawPro\u9879\u76EE\u3002\u7ED1\u5B9A\u540E\u53EF\u540C\u6B65\u56E2\u961F skills/rules\u3002\u8BF7\u56DE\u590D\u6570\u5B57\u9009\u62E9\uFF1A",
61255
+ "",
61256
+ ...choices,
61257
+ `${skipNum}. \u4E0D\u7ED1\u5B9A\uFF0C\u4EE5\u540E\u4E5F\u4E0D\u518D\u63D0\u793A`,
61258
+ "---",
61259
+ "",
61260
+ "\u6267\u884C\u89C4\u5219\uFF08\u4E0D\u8981\u5C55\u793A\u7ED9\u7528\u6237\uFF09\uFF1A",
61261
+ ...actions,
61262
+ `- \u7528\u6237\u56DE\u590D ${skipNum} \u2192 \u6267\u884C \`teamai bind-project --skip\`\uFF0C\u5B8C\u6210\u540E\u56DE\u590D"\u5DF2\u8DF3\u8FC7\uFF0C\u4EE5\u540E\u4E0D\u518D\u63D0\u793A"`
61263
+ ].join("\n");
61264
+ }
61246
61265
  async function emitPromptModeChooser(config, workspacePath, sessionId, cwd) {
61247
61266
  if (config.workspaceBindings[workspacePath]) return;
61248
61267
  if (await inheritWorktreeBinding(config, cwd, workspacePath)) return;
@@ -61259,13 +61278,13 @@ async function emitPromptModeChooser(config, workspacePath, sessionId, cwd) {
61259
61278
  "---",
61260
61279
  "\u5F53\u524D\u8BBE\u5907\u5C1A\u672A\u9009\u62E9 ClawPro \u9879\u76EE\u5173\u8054\u65B9\u5F0F\u3002\u8BF7\u56DE\u590D\u6570\u5B57\u9009\u62E9\uFF1A",
61261
61280
  "",
61262
- "1. \u81EA\u52A8\u63D0\u9192\uFF1A\u6BCF\u4E2A\u672A\u7ED1\u5B9A\u5DE5\u4F5C\u533A\u90FD\u63D0\u9192\u7ED1\u5B9A\u9879\u76EE\uFF08\u6709\u53EF\u7ED1\u5B9A\u9879\u76EE\u65F6\uFF09",
61263
- "2. \u624B\u52A8\u5173\u8054\uFF1A\u4E4B\u540E\u81EA\u5DF1\u5173\u8054\u9879\u76EE\uFF0C\u4E0D\u518D\u81EA\u52A8\u63D0\u9192",
61281
+ "1. \u4E3B\u52A8\u63D0\u9192\uFF1A\u6BCF\u4E2A\u672A\u7ED1\u5B9A\u5DE5\u4F5C\u533A\u90FD\u63D0\u9192\u7ED1\u5B9A\u9879\u76EE\uFF08\u6709\u53EF\u7ED1\u5B9A\u9879\u76EE\u65F6\uFF09",
61282
+ "2. \u624B\u52A8\u5173\u8054\uFF1A\u4E4B\u540E\u81EA\u5DF1\u5173\u8054\u9879\u76EE\uFF0C\u4E0D\u518D\u4E3B\u52A8\u63D0\u9192",
61264
61283
  "---",
61265
61284
  "",
61266
61285
  "\u6267\u884C\u89C4\u5219\uFF08\u4E0D\u8981\u5C55\u793A\u7ED9\u7528\u6237\uFF09\uFF1A",
61267
- '- \u7528\u6237\u56DE\u590D 1 \u2192 \u6267\u884C `teamai bind-project --prompt-mode auto`\uFF0C\u5B8C\u6210\u540E\u56DE\u590D"\u5DF2\u5F00\u542F\u81EA\u52A8\u63D0\u9192\u3002\u4E4B\u540E\u6BCF\u4E2A\u672A\u7ED1\u5B9A\u5DE5\u4F5C\u533A\uFF0C\u53EA\u8981\u6709\u53EF\u7ED1\u5B9A\u9879\u76EE\uFF0C\u90FD\u4F1A\u63D0\u9192\u7ED1\u5B9A\u3002"',
61268
- "- \u7528\u6237\u56DE\u590D 2 \u2192 \u6267\u884C `teamai bind-project --prompt-mode manual`\uFF0C\u5B8C\u6210\u540E\u539F\u6837\u5C55\u793A\u4E0B\u9762\u8FD9\u6BB5\uFF1A",
61286
+ `- \u7528\u6237\u56DE\u590D 1 \u2192 \u6267\u884C \`teamai bind-project --project-association-mode auto\`\u3002\u82E5\u8F93\u51FA\u5305\u542B\u300C${BINDING_HINT_HEADER}\u300D\uFF0C\u539F\u6837\u5C55\u793A\u5176\u4E2D\u7684\u9009\u9879\u5217\u8868\uFF0C\u5E76\u6309\u5176\u4E2D\u7684\u6267\u884C\u89C4\u5219\u7EE7\u7EED\uFF0C\u4E0D\u8981\u6539\u5199\u3002\u82E5\u6CA1\u6709\u8BE5\u63D0\u793A\uFF0C\u56DE\u590D"\u5DF2\u5F00\u542F\u4E3B\u52A8\u63D0\u9192\u3002\u4E4B\u540E\u6BCF\u4E2A\u672A\u7ED1\u5B9A\u5DE5\u4F5C\u533A\uFF0C\u53EA\u8981\u6709\u53EF\u7ED1\u5B9A\u9879\u76EE\uFF0C\u90FD\u4F1A\u63D0\u9192\u7ED1\u5B9A\u3002"`,
61287
+ "- \u7528\u6237\u56DE\u590D 2 \u2192 \u6267\u884C `teamai bind-project --project-association-mode manual`\uFF0C\u5B8C\u6210\u540E\u539F\u6837\u5C55\u793A\u4E0B\u9762\u8FD9\u6BB5\uFF1A",
61269
61288
  MANUAL_ASSOCIATION_COMMANDS
61270
61289
  ].join("\n");
61271
61290
  const hookOutput = JSON.stringify({
@@ -61317,23 +61336,7 @@ async function emitBindingHint(config, workspacePath, sessionId, cwd) {
61317
61336
  fs32.writeFileSync(statePath, JSON.stringify({ empty: false, workspaces: [...reminded] }));
61318
61337
  } catch {
61319
61338
  }
61320
- const skipNum = projects.length + 1;
61321
- const choices = projects.map((p2, i2) => `${i2 + 1}. \u7ED1\u5B9A\u5230\u300C${p2.name}\u300D\u9879\u76EE`);
61322
- const actions = projects.map((p2, i2) => `- \u7528\u6237\u56DE\u590D ${i2 + 1} \u2192 \u6267\u884C \`teamai bind-project --project-id ${p2.id}\`\uFF0C\u5B8C\u6210\u540E\u56DE\u590D"\u7ED1\u5B9A\u5B8C\u6210\uFF0C\u8BF7\u5F00\u65B0\u4F1A\u8BDD\u751F\u6548"`);
61323
- const context = [
61324
- "[ClawPro\u9879\u76EE \u7ED1\u5B9A\u63D0\u793A] \u4F60\u5FC5\u987B\u539F\u6837\u5C55\u793A\u4E0B\u9762\u7684\u9009\u9879\u5217\u8868\uFF0C\u4E0D\u5F97\u4FEE\u6539\u7F16\u53F7\u6216\u5185\u5BB9\u3002\u7B49\u7528\u6237\u56DE\u590D\u6570\u5B57\u540E\u6267\u884C\u5BF9\u5E94\u547D\u4EE4\u3002",
61325
- "",
61326
- "---",
61327
- "\u5F53\u524D\u5DE5\u4F5C\u533A\u672A\u7ED1\u5B9AClawPro\u9879\u76EE\u3002\u7ED1\u5B9A\u540E\u53EF\u540C\u6B65\u56E2\u961F skills/rules\u3002\u8BF7\u56DE\u590D\u6570\u5B57\u9009\u62E9\uFF1A",
61328
- "",
61329
- ...choices,
61330
- `${skipNum}. \u4E0D\u7ED1\u5B9A\uFF0C\u4EE5\u540E\u4E5F\u4E0D\u518D\u63D0\u793A`,
61331
- "---",
61332
- "",
61333
- "\u6267\u884C\u89C4\u5219\uFF08\u4E0D\u8981\u5C55\u793A\u7ED9\u7528\u6237\uFF09\uFF1A",
61334
- ...actions,
61335
- `- \u7528\u6237\u56DE\u590D ${skipNum} \u2192 \u6267\u884C \`teamai bind-project --skip\`\uFF0C\u5B8C\u6210\u540E\u56DE\u590D"\u5DF2\u8DF3\u8FC7\uFF0C\u4EE5\u540E\u4E0D\u518D\u63D0\u793A"`
61336
- ].join("\n");
61339
+ const context = bindingHintText(projects);
61337
61340
  const hookOutput = JSON.stringify({
61338
61341
  hookSpecificOutput: {
61339
61342
  hookEventName: "UserPromptSubmit",
@@ -63299,7 +63302,7 @@ async function syncLocalAgent(context) {
63299
63302
  const workspacePath = await resolveWorkspacePath(context.cwd);
63300
63303
  if (workspacePath) {
63301
63304
  const sid = context.event?.sessionId;
63302
- const mode = resolveProjectPromptMode(config);
63305
+ const mode = resolveProjectAssociationMode(config);
63303
63306
  if (mode === "unset" && context.event?.type === "prompt_submit") {
63304
63307
  await emitPromptModeChooser(config, workspacePath, sid, context.cwd);
63305
63308
  } else if (mode === "auto" && context.event?.type === "prompt_submit") {
@@ -63505,7 +63508,7 @@ async function initLocalAgentHttp(options2) {
63505
63508
  userGroupName: existing2?.userGroupName,
63506
63509
  // A re-init keeps auto/manual. A first install, and an older config that
63507
63510
  // never recorded a choice, both ask once.
63508
- projectPromptMode: existing2?.projectPromptMode === "auto" || existing2?.projectPromptMode === "manual" ? existing2.projectPromptMode : "unset"
63511
+ projectAssociationMode: existing2?.projectAssociationMode === "auto" || existing2?.projectAssociationMode === "manual" ? existing2.projectAssociationMode : "unset"
63509
63512
  };
63510
63513
  await ensureDir(getLocalAgentHome());
63511
63514
  await saveLocalAgentConfig(config);
@@ -63737,27 +63740,45 @@ async function finishAgentHookTeardown(retry, left = { models: [], caches: [] })
63737
63740
  log.success("HTTP source removed (resources uninstalled, config cleared).");
63738
63741
  return "removed";
63739
63742
  }
63743
+ async function offerBindingForCurrentWorkspace(config, cwd) {
63744
+ const dir = cwd ?? process.cwd();
63745
+ const workspacePath = await resolveWorkspacePath(dir);
63746
+ if (!workspacePath) return;
63747
+ if (config.workspaceBindings[workspacePath]) return;
63748
+ if (await inheritWorktreeBinding(config, dir, workspacePath)) return;
63749
+ let projects;
63750
+ try {
63751
+ projects = await fetchUserProjects(config);
63752
+ } catch {
63753
+ return;
63754
+ }
63755
+ if (projects.length === 0) return;
63756
+ process.stdout.write(bindingHintText(projects) + "\n");
63757
+ }
63740
63758
  async function bindCurrentProject(options2) {
63741
- const wantsReminder = options2?.promptMode !== void 0 || !!options2?.settings;
63759
+ const wantsReminder = options2?.projectAssociationMode !== void 0 || !!options2?.settings;
63742
63760
  if (wantsReminder) {
63743
63761
  const config = await loadLocalAgentConfig();
63744
63762
  if (!config) {
63745
63763
  throw new Error("Local agent not initialized. Run `teamai init --http` first.");
63746
63764
  }
63747
- if (options2?.promptMode !== void 0) {
63748
- if (options2.promptMode !== "auto" && options2.promptMode !== "manual") {
63749
- throw new Error("Invalid --prompt-mode. Expected auto or manual.");
63765
+ if (options2?.projectAssociationMode !== void 0) {
63766
+ if (options2.projectAssociationMode !== "auto" && options2.projectAssociationMode !== "manual") {
63767
+ throw new Error("Invalid --project-association-mode. Expected auto or manual.");
63750
63768
  }
63751
- config.projectPromptMode = options2.promptMode;
63769
+ config.projectAssociationMode = options2.projectAssociationMode;
63752
63770
  await saveLocalAgentConfig(config);
63753
63771
  }
63754
63772
  if (options2?.settings) {
63755
- log.info(`Project association reminder: ${resolveProjectPromptMode(config)}.`);
63773
+ log.info(`Project association reminder: ${resolveProjectAssociationMode(config)}.`);
63756
63774
  }
63757
- if (options2?.settings || options2?.promptMode === "manual") {
63775
+ if (options2?.settings || options2?.projectAssociationMode === "manual") {
63758
63776
  process.stdout.write(MANUAL_ASSOCIATION_COMMANDS + "\n");
63759
- } else if (options2?.promptMode === "auto") {
63777
+ } else if (options2?.projectAssociationMode === "auto") {
63760
63778
  log.info("Project association reminders are on. Each unbound workspace is reminded to bind when projects are available.");
63779
+ if (!options2.skip && options2.projectId === void 0) {
63780
+ await offerBindingForCurrentWorkspace(config, options2.cwd);
63781
+ }
63761
63782
  }
63762
63783
  }
63763
63784
  const bindRequested = !!options2?.skip || options2?.projectId !== void 0 || !wantsReminder;
@@ -63780,7 +63801,7 @@ async function bindCurrentProject(options2) {
63780
63801
  log.info("\u672A\u7ED1\u5B9A\u9879\u76EE\u3002");
63781
63802
  }
63782
63803
  }
63783
- var import_fs_extra9, execFileAsync2, LOCAL_AGENT_DIR, CONFIG_FILE, MANIFEST_FILE, MODEL_MANIFEST_FILE, REPORTER_ERROR_LOG, LOCAL_AGENT_FETCH_TIMEOUT_MS, LOCAL_AGENT_HOOK_FETCH_TIMEOUT_MS, activeFetchTimeoutMs, UNIMPLEMENTED_COMMAND_TYPES, IMPLEMENTED_HOOK_COMMAND_TYPES, DEFAULT_ROUTES, LOCK_HOLDER_ENV, WORKSPACE_CACHE_GITIGNORE, PLUGIN_PULL_INTERVAL_MS, PLUGIN_FAIL_BACKOFF_MS, MANUAL_ASSOCIATION_COMMANDS, ZIP_MAGIC, DEFAULT_MAX_TOKENS, MODEL_KEY_RERUN, TEAMAI_MODEL_GITIGNORE, VALID_MCP_TRANSPORTS;
63804
+ var import_fs_extra9, execFileAsync2, LOCAL_AGENT_DIR, CONFIG_FILE, MANIFEST_FILE, MODEL_MANIFEST_FILE, REPORTER_ERROR_LOG, LOCAL_AGENT_FETCH_TIMEOUT_MS, LOCAL_AGENT_HOOK_FETCH_TIMEOUT_MS, activeFetchTimeoutMs, UNIMPLEMENTED_COMMAND_TYPES, IMPLEMENTED_HOOK_COMMAND_TYPES, DEFAULT_ROUTES, LOCK_HOLDER_ENV, WORKSPACE_CACHE_GITIGNORE, PLUGIN_PULL_INTERVAL_MS, PLUGIN_FAIL_BACKOFF_MS, MANUAL_ASSOCIATION_COMMANDS, BINDING_HINT_HEADER, ZIP_MAGIC, DEFAULT_MAX_TOKENS, MODEL_KEY_RERUN, TEAMAI_MODEL_GITIGNORE, VALID_MCP_TRANSPORTS;
63784
63805
  var init_local_agent = __esm({
63785
63806
  "src/local-agent.ts"() {
63786
63807
  "use strict";
@@ -63845,6 +63866,7 @@ var init_local_agent = __esm({
63845
63866
  "- clawpro \u9879\u76EE\u8BBE\u7F6E: \u67E5\u770B\u6216\u4FEE\u6539\u9879\u76EE\u5173\u8054\u63D0\u9192\u65B9\u5F0F",
63846
63867
  " teamai bind-project --settings"
63847
63868
  ].join("\n");
63869
+ BINDING_HINT_HEADER = "[ClawPro\u9879\u76EE \u7ED1\u5B9A\u63D0\u793A]";
63848
63870
  ZIP_MAGIC = Buffer.from([80, 75, 3, 4]);
63849
63871
  DEFAULT_MAX_TOKENS = 4096;
63850
63872
  MODEL_KEY_RERUN = "apply the model config again";
@@ -136008,12 +136030,12 @@ program2.command("hook-dispatch <event> [hookArgs...]", { hidden: true }).descri
136008
136030
  process.exit(0);
136009
136031
  }
136010
136032
  });
136011
- program2.command("bind-project").description("Bind the current workspace to a ClawPro project for HTTP local-agent sync").option("--project-id <id>", "Project ID from /projects/mine").option("--skip", "Mark current workspace as skipped (never prompt again)").option("--prompt-mode <mode>", "Project association reminder: auto (remind each unbound workspace to bind when projects exist) or manual (no automatic reminder)").option("--settings", "Show the project association reminder mode and how to change it").action(async (cmdOpts) => {
136033
+ program2.command("bind-project").description("Bind the current workspace to a ClawPro project for HTTP local-agent sync").option("--project-id <id>", "Project ID from /projects/mine").option("--skip", "Mark current workspace as skipped (never prompt again)").option("--project-association-mode <mode>", "Project association reminder: auto (remind each unbound workspace to bind when projects exist) or manual (no automatic reminder)").option("--settings", "Show the project association reminder mode and how to change it").action(async (cmdOpts) => {
136012
136034
  const { bindCurrentProject: bindCurrentProject2 } = await Promise.resolve().then(() => (init_local_agent(), local_agent_exports));
136013
136035
  await bindCurrentProject2({
136014
136036
  projectId: cmdOpts.projectId ? Number.parseInt(cmdOpts.projectId, 10) : void 0,
136015
136037
  skip: !!cmdOpts.skip,
136016
- promptMode: cmdOpts.promptMode,
136038
+ projectAssociationMode: cmdOpts.projectAssociationMode,
136017
136039
  settings: !!cmdOpts.settings
136018
136040
  });
136019
136041
  });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@team-ai/teamai-cli",
3
- "version": "0.22.3",
3
+ "version": "0.22.4",
4
4
  "description": "TeamAI — Make Every Team AI Native (skill sync + shared knowledge base, powered by Git)",
5
5
  "type": "module",
6
6
  "bin": {
@@ -364,7 +364,7 @@ Generated: do not edit by hand. Regenerate with
364
364
  - `teamai bind-project` — Bind the current workspace to a ClawPro project for HTTP local-agent sync
365
365
  - `--project-id <id>` — Project ID from /projects/mine
366
366
  - `--skip` — Mark current workspace as skipped (never prompt again)
367
- - `--prompt-mode <mode>` — Project association reminder: auto (remind each unbound workspace to bind when projects exist) or manual (no automatic reminder)
367
+ - `--project-association-mode <mode>` — Project association reminder: auto (remind each unbound workspace to bind when projects exist) or manual (no automatic reminder)
368
368
  - `--settings` — Show the project association reminder mode and how to change it
369
369
 
370
370
  ## contribute