opencode-swarm 6.84.6 → 6.84.7

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.
@@ -5,6 +5,7 @@
5
5
  * Write-trigger hook that incrementally updates the graph when write tools are called.
6
6
  * Wrapped in try/catch — failures are logged but never block plugin initialization.
7
7
  */
8
+ import { type RepoGraph } from '../tools/repo-graph';
8
9
  export interface RepoGraphBuilderHook {
9
10
  init(): Promise<void>;
10
11
  toolAfter(input: {
@@ -17,8 +18,15 @@ export interface RepoGraphBuilderHook {
17
18
  }): Promise<void>;
18
19
  }
19
20
  export interface RepoGraphDeps {
20
- buildWorkspaceGraph: (workspace: string, options?: any) => any;
21
- saveGraph: (workspace: string, graph: any) => Promise<void>;
22
- updateGraphForFiles: (workspace: string, files: string[], options?: any) => Promise<any>;
21
+ buildWorkspaceGraph: (workspace: string, options?: {
22
+ maxFileSizeBytes?: number;
23
+ maxFiles?: number;
24
+ }) => RepoGraph;
25
+ saveGraph: (workspace: string, graph: RepoGraph, options?: {
26
+ createAtomic?: boolean;
27
+ }) => Promise<void>;
28
+ updateGraphForFiles: (workspace: string, files: string[], options?: {
29
+ forceRebuild?: boolean;
30
+ }) => Promise<RepoGraph>;
23
31
  }
24
32
  export declare function createRepoGraphBuilderHook(workspaceRoot: string, deps?: Partial<RepoGraphDeps>): RepoGraphBuilderHook;
package/dist/index.js CHANGED
@@ -23112,11 +23112,11 @@ function dcExtractPowerShellTargets(segment) {
23112
23112
  function redactShellCommand(cmd) {
23113
23113
  if (typeof cmd !== "string")
23114
23114
  return "";
23115
- let out2 = cmd.replace(/\b([A-Z_]*(?:TOKEN|SECRET|PASSWORD|PASSWD|API[_]?KEY|APIKEY|AUTH|CREDENTIAL|PRIVATE[_]?KEY|ACCESS[_]?KEY)[A-Z_0-9]*)\s*=\s*(\S+)/gi, "$1=[REDACTED]");
23115
+ let out2 = cmd.replace(/\b([A-Z_]*(?:TOKEN|SECRET|PASSWORD|PASSWD|API[_]?KEY|APIKEY|AUTH|CREDENTIAL|PRIVATE[_]?KEY|ACCESS[_]?KEY|_KEY)[A-Z_0-9]*)\s*=\s*(\S+)/gi, "$1=[REDACTED]");
23116
23116
  out2 = out2.replace(/--([a-zA-Z-]*(?:token|secret|password|passwd|api[_-]?key|apikey|auth|credential|private[_-]?key|access[_-]?key)[a-zA-Z-]*)=(\S+)/gi, "--$1=[REDACTED]");
23117
23117
  out2 = out2.replace(/(--[a-zA-Z-]*(?:token|secret|password|passwd|api[_-]?key|apikey|auth|credential|private[_-]?key|access[_-]?key)[a-zA-Z-]*)(\s+)(?!--)(\S+)/gi, "$1$2[REDACTED]");
23118
23118
  out2 = out2.replace(/\b(Bearer|Basic)\s+[A-Za-z0-9+/=._-]{4,}/gi, "$1 [REDACTED]");
23119
- out2 = out2.replace(/(-H\s+['"]?(?:Authorization|X-API-Key|X-Auth-Token):\s*)([^'">\s][^'">\n]*)(['"]?)/gi, "$1[REDACTED]$3");
23119
+ out2 = out2.replace(/(-H\s+['"]?(?:Authorization|X-API-Key|X-Auth-Token|[A-Za-z][A-Za-z-]*-(?:key|token|secret|auth|credential)):\s*)([^'">\s][^'">\n]*)(['"]?)/gi, "$1[REDACTED]$3");
23120
23120
  return out2;
23121
23121
  }
23122
23122
  function createGuardrailsHooks(directory, directoryOrConfig, config2, authorityConfig) {
@@ -62828,7 +62828,7 @@ var init_curator_drift = __esm(() => {
62828
62828
 
62829
62829
  // src/index.ts
62830
62830
  init_agents();
62831
- import * as path103 from "path";
62831
+ import * as path104 from "path";
62832
62832
 
62833
62833
  // src/background/index.ts
62834
62834
  init_event_bus();
@@ -88084,6 +88084,67 @@ init_write_retro();
88084
88084
  // src/index.ts
88085
88085
  init_utils();
88086
88086
 
88087
+ // src/utils/gitignore-warning.ts
88088
+ import * as fs87 from "fs";
88089
+ import * as path103 from "path";
88090
+ var _gitignoreWarningEmitted = false;
88091
+ function findGitRoot(startDir) {
88092
+ let current = startDir;
88093
+ while (true) {
88094
+ try {
88095
+ const gitPath = path103.join(current, ".git");
88096
+ const stat4 = fs87.statSync(gitPath);
88097
+ if (stat4.isDirectory()) {
88098
+ return current;
88099
+ }
88100
+ } catch {}
88101
+ const parent = path103.dirname(current);
88102
+ if (parent === current) {
88103
+ return null;
88104
+ }
88105
+ current = parent;
88106
+ }
88107
+ }
88108
+ function fileCoversSwarm(content) {
88109
+ for (const rawLine of content.split(`
88110
+ `)) {
88111
+ const line = rawLine.trim();
88112
+ if (line.startsWith("#") || line.length === 0)
88113
+ continue;
88114
+ if (line === ".swarm" || line === ".swarm/")
88115
+ return true;
88116
+ }
88117
+ return false;
88118
+ }
88119
+ function readFileSafe(filePath) {
88120
+ try {
88121
+ return fs87.readFileSync(filePath, "utf8");
88122
+ } catch {
88123
+ return null;
88124
+ }
88125
+ }
88126
+ function warnIfSwarmNotGitignored(directory) {
88127
+ if (_gitignoreWarningEmitted)
88128
+ return;
88129
+ try {
88130
+ const gitRoot = findGitRoot(directory);
88131
+ if (!gitRoot)
88132
+ return;
88133
+ const gitignoreContent = readFileSafe(path103.join(gitRoot, ".gitignore"));
88134
+ if (gitignoreContent !== null && fileCoversSwarm(gitignoreContent)) {
88135
+ _gitignoreWarningEmitted = true;
88136
+ return;
88137
+ }
88138
+ const excludeContent = readFileSafe(path103.join(gitRoot, ".git", "info", "exclude"));
88139
+ if (excludeContent !== null && fileCoversSwarm(excludeContent)) {
88140
+ _gitignoreWarningEmitted = true;
88141
+ return;
88142
+ }
88143
+ _gitignoreWarningEmitted = true;
88144
+ console.warn('[opencode-swarm] WARNING: .swarm/ is not in your .gitignore. Shell audit logs may contain API keys. Add ".swarm/" to your .gitignore to prevent accidental commits.');
88145
+ } catch {}
88146
+ }
88147
+
88087
88148
  // src/utils/tool-output.ts
88088
88149
  function truncateToolOutput(output, maxLines, toolName, tailLines = 10) {
88089
88150
  if (!output) {
@@ -88130,6 +88191,7 @@ var OpenCodeSwarm = async (ctx) => {
88130
88191
  swarmState.opencodeClient = ctx.client;
88131
88192
  await loadSnapshot(ctx.directory);
88132
88193
  initTelemetry(ctx.directory);
88194
+ warnIfSwarmNotGitignored(ctx.directory);
88133
88195
  const repoGraphHook = createRepoGraphBuilderHook(ctx.directory);
88134
88196
  repoGraphHook.init().catch(() => {});
88135
88197
  const agents = getAgentConfigs(config3, ctx.directory);
@@ -88249,7 +88311,7 @@ var OpenCodeSwarm = async (ctx) => {
88249
88311
  const { PreflightTriggerManager: PTM } = await Promise.resolve().then(() => (init_trigger(), exports_trigger));
88250
88312
  preflightTriggerManager = new PTM(automationConfig);
88251
88313
  const { AutomationStatusArtifact: ASA } = await Promise.resolve().then(() => (init_status_artifact(), exports_status_artifact));
88252
- const swarmDir = path103.resolve(ctx.directory, ".swarm");
88314
+ const swarmDir = path104.resolve(ctx.directory, ".swarm");
88253
88315
  statusArtifact = new ASA(swarmDir);
88254
88316
  statusArtifact.updateConfig(automationConfig.mode, automationConfig.capabilities);
88255
88317
  if (automationConfig.capabilities?.evidence_auto_summaries === true) {
@@ -0,0 +1,17 @@
1
+ /**
2
+ * Module-level flag so the warning fires at most once per process.
3
+ * Exported for test reset purposes only — do not use in production code.
4
+ */
5
+ export declare let _gitignoreWarningEmitted: boolean;
6
+ /**
7
+ * Reset the deduplication flag. Exposed for test isolation only.
8
+ */
9
+ export declare function resetGitignoreWarningState(): void;
10
+ /**
11
+ * Checks whether `.swarm/` is covered by `.gitignore` or `.git/info/exclude`
12
+ * in the git repo rooted at or above `directory`. If not covered, emits a
13
+ * single `console.warn`. Fires at most once per process.
14
+ *
15
+ * Never throws — any file-system error silently skips the check.
16
+ */
17
+ export declare function warnIfSwarmNotGitignored(directory: string): void;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "opencode-swarm",
3
- "version": "6.84.6",
3
+ "version": "6.84.7",
4
4
  "description": "Architect-centric agentic swarm plugin for OpenCode - hub-and-spoke orchestration with SME consultation, code generation, and QA review",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",