refactor: major codebase cleanup - BDD comments, file splitting, bug fixes (#1350)

* style(tests): normalize BDD comments from '// #given' to '// given'

- Replace 4,668 Python-style BDD comments across 107 test files
- Patterns changed: // #given -> // given, // #when -> // when, // #then -> // then
- Also handles no-space variants: //#given -> // given

* fix(rules-injector): prefer output.metadata.filePath over output.title

- Extract file path resolution to dedicated output-path.ts module
- Prefer metadata.filePath which contains actual file path
- Fall back to output.title only when metadata unavailable
- Fixes issue where rules weren't injected when tool output title was a label

* feat(slashcommand): add optional user_message parameter

- Add user_message optional parameter for command arguments
- Model can now call: command='publish' user_message='patch'
- Improves error messages with clearer format guidance
- Helps LLMs understand correct parameter usage

* feat(hooks): restore compaction-context-injector hook

- Restore hook deleted in cbbc7bd0 for session compaction context
- Injects 7 mandatory sections: User Requests, Final Goal, Work Completed,
  Remaining Tasks, Active Working Context, MUST NOT Do, Agent Verification State
- Re-register in hooks/index.ts and main plugin entry

* refactor(background-agent): split manager.ts into focused modules

- Extract constants.ts for TTL values and internal types (52 lines)
- Extract state.ts for TaskStateManager class (204 lines)
- Extract spawner.ts for task creation logic (244 lines)
- Extract result-handler.ts for completion handling (265 lines)
- Reduce manager.ts from 1377 to 755 lines (45% reduction)
- Maintain backward compatible exports

* refactor(agents): split prometheus-prompt.ts into subdirectory

- Move 1196-line prometheus-prompt.ts to prometheus/ subdirectory
- Organize prompt sections into separate files for maintainability
- Update agents/index.ts exports

* refactor(delegate-task): split tools.ts into focused modules

- Extract categories.ts for category definitions and routing
- Extract executor.ts for task execution logic
- Extract helpers.ts for utility functions
- Extract prompt-builder.ts for prompt construction
- Reduce tools.ts complexity with cleaner separation of concerns

* refactor(builtin-skills): split skills.ts into individual skill files

- Move each skill to dedicated file in skills/ subdirectory
- Create barrel export for backward compatibility
- Improve maintainability with focused skill modules

* chore: update import paths and lockfile

- Update prometheus import path after refactor
- Update bun.lock

* fix(tests): complete BDD comment normalization

- Fix remaining #when/#then patterns missed by initial sed
- Affected: state.test.ts, events.test.ts

---------

Co-authored-by: justsisyphus <justsisyphus@users.noreply.github.com>
This commit is contained in:
YeonGyu-Kim
2026-02-01 16:47:50 +09:00
committed by GitHub
parent c83150d9ea
commit f146aeff0f
145 changed files with 10307 additions and 9562 deletions
+60 -60
View File
@@ -37,7 +37,7 @@ describe("createThinkModeHook integration", () => {
describe("GitHub Copilot provider integration", () => {
describe("Claude models", () => {
it("should activate thinking mode for github-copilot Claude with think keyword", async () => {
// #given a github-copilot Claude model and prompt with "think" keyword
// given a github-copilot Claude model and prompt with "think" keyword
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -45,10 +45,10 @@ describe("createThinkModeHook integration", () => {
"Please think deeply about this problem"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should upgrade to high variant and inject thinking config
// then should upgrade to high variant and inject thinking config
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("claude-opus-4-5-high")
expect(message.thinking).toBeDefined()
@@ -61,7 +61,7 @@ describe("createThinkModeHook integration", () => {
})
it("should handle github-copilot Claude with dots in version", async () => {
// #given a github-copilot Claude model with dot format (claude-opus-4.5)
// given a github-copilot Claude model with dot format (claude-opus-4.5)
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -69,17 +69,17 @@ describe("createThinkModeHook integration", () => {
"ultrathink mode"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should upgrade to high variant (hyphen format)
// then should upgrade to high variant (hyphen format)
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("claude-opus-4-5-high")
expect(message.thinking).toBeDefined()
})
it("should handle github-copilot Claude Sonnet", async () => {
// #given a github-copilot Claude Sonnet model
// given a github-copilot Claude Sonnet model
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -87,10 +87,10 @@ describe("createThinkModeHook integration", () => {
"think about this"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should upgrade to high variant
// then should upgrade to high variant
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("claude-sonnet-4-5-high")
expect(message.thinking).toBeDefined()
@@ -99,7 +99,7 @@ describe("createThinkModeHook integration", () => {
describe("Gemini models", () => {
it("should activate thinking mode for github-copilot Gemini Pro", async () => {
// #given a github-copilot Gemini Pro model
// given a github-copilot Gemini Pro model
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -107,10 +107,10 @@ describe("createThinkModeHook integration", () => {
"think about this"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should upgrade to high variant and inject google thinking config
// then should upgrade to high variant and inject google thinking config
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("gemini-3-pro-high")
expect(message.providerOptions).toBeDefined()
@@ -121,7 +121,7 @@ describe("createThinkModeHook integration", () => {
})
it("should activate thinking mode for github-copilot Gemini Flash", async () => {
// #given a github-copilot Gemini Flash model
// given a github-copilot Gemini Flash model
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -129,10 +129,10 @@ describe("createThinkModeHook integration", () => {
"ultrathink"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should upgrade to high variant
// then should upgrade to high variant
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("gemini-3-flash-high")
expect(message.providerOptions).toBeDefined()
@@ -141,7 +141,7 @@ describe("createThinkModeHook integration", () => {
describe("GPT models", () => {
it("should activate thinking mode for github-copilot GPT-5.2", async () => {
// #given a github-copilot GPT-5.2 model
// given a github-copilot GPT-5.2 model
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -149,24 +149,24 @@ describe("createThinkModeHook integration", () => {
"please think"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should upgrade to high variant and inject openai thinking config
// then should upgrade to high variant and inject openai thinking config
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("gpt-5-2-high")
expect(message.reasoning_effort).toBe("high")
})
it("should activate thinking mode for github-copilot GPT-5", async () => {
// #given a github-copilot GPT-5 model
// given a github-copilot GPT-5 model
const hook = createThinkModeHook()
const input = createMockInput("github-copilot", "gpt-5", "think deeply")
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should upgrade to high variant
// then should upgrade to high variant
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("gpt-5-high")
expect(message.reasoning_effort).toBe("high")
@@ -175,7 +175,7 @@ describe("createThinkModeHook integration", () => {
describe("No think keyword", () => {
it("should NOT activate for github-copilot without think keyword", async () => {
// #given a prompt without any think keyword
// given a prompt without any think keyword
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -184,10 +184,10 @@ describe("createThinkModeHook integration", () => {
)
const originalModelID = input.message.model?.modelID
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should NOT change model or inject config
// then should NOT change model or inject config
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe(originalModelID)
expect(message.thinking).toBeUndefined()
@@ -197,7 +197,7 @@ describe("createThinkModeHook integration", () => {
describe("Backwards compatibility with direct providers", () => {
it("should still work for direct anthropic provider", async () => {
// #given direct anthropic provider
// given direct anthropic provider
const hook = createThinkModeHook()
const input = createMockInput(
"anthropic",
@@ -205,17 +205,17 @@ describe("createThinkModeHook integration", () => {
"think about this"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should work as before
// then should work as before
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("claude-sonnet-4-5-high")
expect(message.thinking).toBeDefined()
})
it("should still work for direct google provider", async () => {
// #given direct google provider
// given direct google provider
const hook = createThinkModeHook()
const input = createMockInput(
"google",
@@ -223,31 +223,31 @@ describe("createThinkModeHook integration", () => {
"think about this"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should work as before
// then should work as before
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("gemini-3-pro-high")
expect(message.providerOptions).toBeDefined()
})
it("should still work for direct openai provider", async () => {
// #given direct openai provider
// given direct openai provider
const hook = createThinkModeHook()
const input = createMockInput("openai", "gpt-5", "think about this")
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should work
// then should work
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("gpt-5-high")
expect(message.reasoning_effort).toBe("high")
})
it("should still work for amazon-bedrock provider", async () => {
// #given amazon-bedrock provider
// given amazon-bedrock provider
const hook = createThinkModeHook()
const input = createMockInput(
"amazon-bedrock",
@@ -255,10 +255,10 @@ describe("createThinkModeHook integration", () => {
"think"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should inject bedrock thinking config
// then should inject bedrock thinking config
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("claude-sonnet-4-5-high")
expect(message.reasoningConfig).toBeDefined()
@@ -267,7 +267,7 @@ describe("createThinkModeHook integration", () => {
describe("Already-high variants", () => {
it("should NOT re-upgrade already-high variants", async () => {
// #given an already-high variant model
// given an already-high variant model
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -275,10 +275,10 @@ describe("createThinkModeHook integration", () => {
"think deeply"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should NOT modify the model (already high)
// then should NOT modify the model (already high)
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("claude-opus-4-5-high")
// No additional thinking config should be injected
@@ -286,7 +286,7 @@ describe("createThinkModeHook integration", () => {
})
it("should NOT re-upgrade already-high GPT variants", async () => {
// #given an already-high GPT variant
// given an already-high GPT variant
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -294,10 +294,10 @@ describe("createThinkModeHook integration", () => {
"ultrathink"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should NOT modify the model
// then should NOT modify the model
const message = input.message as MessageWithInjectedProps
expect(input.message.model?.modelID).toBe("gpt-5.2-high")
expect(message.reasoning_effort).toBeUndefined()
@@ -306,7 +306,7 @@ describe("createThinkModeHook integration", () => {
describe("Unknown models", () => {
it("should not crash for unknown models via github-copilot", async () => {
// #given an unknown model type
// given an unknown model type
const hook = createThinkModeHook()
const input = createMockInput(
"github-copilot",
@@ -314,46 +314,46 @@ describe("createThinkModeHook integration", () => {
"think about this"
)
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should not crash and model should remain unchanged
// then should not crash and model should remain unchanged
expect(input.message.model?.modelID).toBe("llama-3-70b")
})
})
describe("Edge cases", () => {
it("should handle missing model gracefully", async () => {
// #given input without a model
// given input without a model
const hook = createThinkModeHook()
const input: ThinkModeInput = {
parts: [{ type: "text", text: "think about this" }],
message: {},
}
// #when the chat.params hook is called
// #then should not crash
// when the chat.params hook is called
// then should not crash
await expect(
hook["chat.params"](input, sessionID)
).resolves.toBeUndefined()
})
it("should handle empty prompt gracefully", async () => {
// #given empty prompt
// given empty prompt
const hook = createThinkModeHook()
const input = createMockInput("github-copilot", "claude-opus-4-5", "")
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should not upgrade (no think keyword)
// then should not upgrade (no think keyword)
expect(input.message.model?.modelID).toBe("claude-opus-4-5")
})
})
describe("Agent-level thinking configuration respect", () => {
it("should NOT inject thinking config when agent has thinking disabled", async () => {
// #given agent with thinking explicitly disabled
// given agent with thinking explicitly disabled
const hook = createThinkModeHook()
const input: ThinkModeInput = {
parts: [{ type: "text", text: "ultrathink deeply" }],
@@ -363,17 +363,17 @@ describe("createThinkModeHook integration", () => {
} as ThinkModeInput["message"],
}
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should NOT override agent's thinking disabled setting
// then should NOT override agent's thinking disabled setting
const message = input.message as MessageWithInjectedProps
expect((message.thinking as { type: string }).type).toBe("disabled")
expect(message.providerOptions).toBeUndefined()
})
it("should NOT inject thinking config when agent has custom providerOptions", async () => {
// #given agent with custom providerOptions
// given agent with custom providerOptions
const hook = createThinkModeHook()
const input: ThinkModeInput = {
parts: [{ type: "text", text: "ultrathink" }],
@@ -385,10 +385,10 @@ describe("createThinkModeHook integration", () => {
} as ThinkModeInput["message"],
}
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should NOT override agent's providerOptions
// then should NOT override agent's providerOptions
const message = input.message as MessageWithInjectedProps
const providerOpts = message.providerOptions as Record<string, unknown>
expect((providerOpts.google as Record<string, unknown>).thinkingConfig).toEqual({
@@ -397,14 +397,14 @@ describe("createThinkModeHook integration", () => {
})
it("should still inject thinking config when agent has no thinking override", async () => {
// #given agent without thinking override
// given agent without thinking override
const hook = createThinkModeHook()
const input = createMockInput("google", "gemini-3-pro", "ultrathink")
// #when the chat.params hook is called
// when the chat.params hook is called
await hook["chat.params"](input, sessionID)
// #then should inject thinking config as normal
// then should inject thinking config as normal
const message = input.message as MessageWithInjectedProps
expect(message.providerOptions).toBeDefined()
})