@orderful/droid 0.29.2 → 0.30.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.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,11 @@
1
1
  # @orderful/droid
2
2
 
3
+ ## 0.30.0
4
+
5
+ ### Minor Changes
6
+
7
+ - [#178](https://github.com/Orderful/droid/pull/178) [`77bc5f2`](https://github.com/Orderful/droid/commit/77bc5f24f4340a123cfe9648da134d68895ffefd) Thanks [@frytyler](https://github.com/frytyler)! - Unify skills installation to ~/.claude/skills/ for all platforms. This is the Agent Skills standard location supported by Claude Code, OpenCode, and Cursor. Existing OpenCode skills are automatically migrated to the unified location.
8
+
3
9
  ## 0.29.2
4
10
 
5
11
  ### Patch Changes
package/dist/bin/droid.js CHANGED
@@ -200,15 +200,16 @@ import YAML3 from "yaml";
200
200
  // src/lib/platforms.ts
201
201
  import { join as join2 } from "path";
202
202
  import { homedir as homedir2 } from "os";
203
+ var UNIFIED_SKILLS_PATH = join2(homedir2(), ".claude", "skills");
203
204
  var PLATFORM_PATHS = {
204
205
  ["claude-code" /* ClaudeCode */]: {
205
- skills: join2(homedir2(), ".claude", "skills"),
206
+ skills: UNIFIED_SKILLS_PATH,
206
207
  commands: join2(homedir2(), ".claude", "commands"),
207
208
  agents: join2(homedir2(), ".claude", "agents"),
208
209
  config: join2(homedir2(), ".claude", "CLAUDE.md")
209
210
  },
210
211
  ["opencode" /* OpenCode */]: {
211
- skills: join2(homedir2(), ".config", "opencode", "skill"),
212
+ skills: UNIFIED_SKILLS_PATH,
212
213
  commands: join2(homedir2(), ".config", "opencode", "command"),
213
214
  agents: join2(homedir2(), ".config", "opencode", "agent"),
214
215
  config: join2(homedir2(), ".config", "opencode", "AGENTS.md")
@@ -774,6 +775,56 @@ function createOpenCodePluginCleanupMigration(version2) {
774
775
  }
775
776
  };
776
777
  }
778
+ function createUnifiedSkillsPathMigration(version2) {
779
+ return {
780
+ version: version2,
781
+ description: "Copy OpenCode skills to unified ~/.claude/skills/ location",
782
+ up: () => {
783
+ const oldOpenCodeSkillsPath = join6(
784
+ homedir3(),
785
+ ".config",
786
+ "opencode",
787
+ "skill"
788
+ );
789
+ const unifiedSkillsPath = join6(homedir3(), ".claude", "skills");
790
+ if (!existsSync4(oldOpenCodeSkillsPath)) {
791
+ return;
792
+ }
793
+ if (!existsSync4(unifiedSkillsPath)) {
794
+ mkdirSync3(unifiedSkillsPath, { recursive: true });
795
+ }
796
+ const skillDirs = readdirSync3(oldOpenCodeSkillsPath, { withFileTypes: true }).filter((dirent) => dirent.isDirectory()).map((dirent) => dirent.name);
797
+ for (const skillName of skillDirs) {
798
+ const sourcePath = join6(oldOpenCodeSkillsPath, skillName);
799
+ const destPath = join6(unifiedSkillsPath, skillName);
800
+ if (existsSync4(destPath)) {
801
+ continue;
802
+ }
803
+ try {
804
+ copyDirRecursive(sourcePath, destPath);
805
+ } catch (error) {
806
+ console.warn(
807
+ `Warning: Could not copy skill ${skillName} to unified location: ${error}`
808
+ );
809
+ }
810
+ }
811
+ }
812
+ };
813
+ }
814
+ function copyDirRecursive(src, dest) {
815
+ mkdirSync3(dest, { recursive: true });
816
+ const entries = readdirSync3(src, { withFileTypes: true });
817
+ for (const entry of entries) {
818
+ const srcPath = join6(src, entry.name);
819
+ const destPath = join6(dest, entry.name);
820
+ if (entry.isDirectory()) {
821
+ copyDirRecursive(srcPath, destPath);
822
+ } else {
823
+ const content = readFileSync5(srcPath);
824
+ writeFileSync3(destPath, content);
825
+ }
826
+ }
827
+ }
777
828
  var PACKAGE_MIGRATIONS = [
778
829
  createPlatformSyncMigration("0.25.0"),
779
830
  createConfigSkillNameMigration("0.27.2"),
@@ -781,7 +832,8 @@ var PACKAGE_MIGRATIONS = [
781
832
  createClaudeCodeCommandCleanupMigration("0.28.0"),
782
833
  // Retry: 0.28.0 migration had platform check that prevented running after platform switch
783
834
  createClaudeCodeCommandCleanupMigration("0.28.1"),
784
- createOpenCodePluginCleanupMigration("0.29.2")
835
+ createOpenCodePluginCleanupMigration("0.29.2"),
836
+ createUnifiedSkillsPathMigration("0.30.0")
785
837
  ];
786
838
  var TOOL_MIGRATIONS = {
787
839
  brain: [createConfigDirMigration("droid-brain", "0.2.3")],
@@ -1523,7 +1575,7 @@ async function setupCommand() {
1523
1575
  console.log(chalk2.gray(" Droid permissions already configured in Claude Code"));
1524
1576
  }
1525
1577
  } else if (answers.platform === "opencode" /* OpenCode */) {
1526
- console.log(chalk2.gray(" OpenCode has native skills support - no configuration needed"));
1578
+ console.log(chalk2.gray(" Skills installed to ~/.claude/skills/ (works with Claude Code, OpenCode, and Cursor)"));
1527
1579
  }
1528
1580
  console.log(chalk2.gray("\nRun `droid skills` to browse and install skills."));
1529
1581
  }
@@ -1 +1 @@
1
- {"version":3,"file":"setup.d.ts","sourceRoot":"","sources":["../../src/commands/setup.ts"],"names":[],"mappings":"AAQA,OAAO,EAAE,QAAQ,EAA0D,MAAM,cAAc,CAAC;AA6ChG;;GAEG;AACH,wBAAgB,4BAA4B,CAAC,QAAQ,EAAE,QAAQ,GAAG;IAAE,KAAK,EAAE,MAAM,EAAE,CAAC;IAAC,cAAc,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAgE7H;AAyBD,wBAAsB,YAAY,IAAI,OAAO,CAAC,IAAI,CAAC,CAwGlD"}
1
+ {"version":3,"file":"setup.d.ts","sourceRoot":"","sources":["../../src/commands/setup.ts"],"names":[],"mappings":"AAQA,OAAO,EAAE,QAAQ,EAA0D,MAAM,cAAc,CAAC;AA6ChG;;GAEG;AACH,wBAAgB,4BAA4B,CAAC,QAAQ,EAAE,QAAQ,GAAG;IAAE,KAAK,EAAE,MAAM,EAAE,CAAC;IAAC,cAAc,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAiE7H;AAyBD,wBAAsB,YAAY,IAAI,OAAO,CAAC,IAAI,CAAC,CAwGlD"}
package/dist/index.js CHANGED
@@ -208,15 +208,16 @@ import YAML3 from "yaml";
208
208
  // src/lib/platforms.ts
209
209
  import { join as join2 } from "path";
210
210
  import { homedir as homedir2 } from "os";
211
+ var UNIFIED_SKILLS_PATH = join2(homedir2(), ".claude", "skills");
211
212
  var PLATFORM_PATHS = {
212
213
  ["claude-code" /* ClaudeCode */]: {
213
- skills: join2(homedir2(), ".claude", "skills"),
214
+ skills: UNIFIED_SKILLS_PATH,
214
215
  commands: join2(homedir2(), ".claude", "commands"),
215
216
  agents: join2(homedir2(), ".claude", "agents"),
216
217
  config: join2(homedir2(), ".claude", "CLAUDE.md")
217
218
  },
218
219
  ["opencode" /* OpenCode */]: {
219
- skills: join2(homedir2(), ".config", "opencode", "skill"),
220
+ skills: UNIFIED_SKILLS_PATH,
220
221
  commands: join2(homedir2(), ".config", "opencode", "command"),
221
222
  agents: join2(homedir2(), ".config", "opencode", "agent"),
222
223
  config: join2(homedir2(), ".config", "opencode", "AGENTS.md")
@@ -747,6 +748,56 @@ function createOpenCodePluginCleanupMigration(version) {
747
748
  }
748
749
  };
749
750
  }
751
+ function createUnifiedSkillsPathMigration(version) {
752
+ return {
753
+ version,
754
+ description: "Copy OpenCode skills to unified ~/.claude/skills/ location",
755
+ up: () => {
756
+ const oldOpenCodeSkillsPath = join6(
757
+ homedir3(),
758
+ ".config",
759
+ "opencode",
760
+ "skill"
761
+ );
762
+ const unifiedSkillsPath = join6(homedir3(), ".claude", "skills");
763
+ if (!existsSync4(oldOpenCodeSkillsPath)) {
764
+ return;
765
+ }
766
+ if (!existsSync4(unifiedSkillsPath)) {
767
+ mkdirSync3(unifiedSkillsPath, { recursive: true });
768
+ }
769
+ const skillDirs = readdirSync3(oldOpenCodeSkillsPath, { withFileTypes: true }).filter((dirent) => dirent.isDirectory()).map((dirent) => dirent.name);
770
+ for (const skillName of skillDirs) {
771
+ const sourcePath = join6(oldOpenCodeSkillsPath, skillName);
772
+ const destPath = join6(unifiedSkillsPath, skillName);
773
+ if (existsSync4(destPath)) {
774
+ continue;
775
+ }
776
+ try {
777
+ copyDirRecursive(sourcePath, destPath);
778
+ } catch (error) {
779
+ console.warn(
780
+ `Warning: Could not copy skill ${skillName} to unified location: ${error}`
781
+ );
782
+ }
783
+ }
784
+ }
785
+ };
786
+ }
787
+ function copyDirRecursive(src, dest) {
788
+ mkdirSync3(dest, { recursive: true });
789
+ const entries = readdirSync3(src, { withFileTypes: true });
790
+ for (const entry of entries) {
791
+ const srcPath = join6(src, entry.name);
792
+ const destPath = join6(dest, entry.name);
793
+ if (entry.isDirectory()) {
794
+ copyDirRecursive(srcPath, destPath);
795
+ } else {
796
+ const content = readFileSync5(srcPath);
797
+ writeFileSync3(destPath, content);
798
+ }
799
+ }
800
+ }
750
801
  var PACKAGE_MIGRATIONS = [
751
802
  createPlatformSyncMigration("0.25.0"),
752
803
  createConfigSkillNameMigration("0.27.2"),
@@ -754,7 +805,8 @@ var PACKAGE_MIGRATIONS = [
754
805
  createClaudeCodeCommandCleanupMigration("0.28.0"),
755
806
  // Retry: 0.28.0 migration had platform check that prevented running after platform switch
756
807
  createClaudeCodeCommandCleanupMigration("0.28.1"),
757
- createOpenCodePluginCleanupMigration("0.29.2")
808
+ createOpenCodePluginCleanupMigration("0.29.2"),
809
+ createUnifiedSkillsPathMigration("0.30.0")
758
810
  ];
759
811
  var TOOL_MIGRATIONS = {
760
812
  brain: [createConfigDirMigration("droid-brain", "0.2.3")],
@@ -1 +1 @@
1
- {"version":3,"file":"migrations.d.ts","sourceRoot":"","sources":["../../src/lib/migrations.ts"],"names":[],"mappings":"AAaA,OAAO,EACL,KAAK,SAAS,EAIf,MAAM,SAAS,CAAC;AA2ajB;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,QAAQ,EAAE,MAAM,GAAG,SAAS,EAAE,CAE/D;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAc/D;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CACpC,QAAQ,EAAE,MAAM,EAChB,OAAO,EAAE,MAAM,GACd,IAAI,CAmBN;AAED;;;GAGG;AACH,wBAAgB,aAAa,CAC3B,QAAQ,EAAE,MAAM,EAChB,WAAW,EAAE,MAAM,EACnB,SAAS,EAAE,MAAM,GAChB;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CA2CtC;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,CAC/B,QAAQ,EAAE,MAAM,EAChB,gBAAgB,EAAE,MAAM,GACvB;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAStC;AAED;;;GAGG;AACH,wBAAgB,oBAAoB,CAAC,cAAc,EAAE,MAAM,GAAG;IAC5D,OAAO,EAAE,OAAO,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB,CAyDA"}
1
+ {"version":3,"file":"migrations.d.ts","sourceRoot":"","sources":["../../src/lib/migrations.ts"],"names":[],"mappings":"AAaA,OAAO,EACL,KAAK,SAAS,EAIf,MAAM,SAAS,CAAC;AA8fjB;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,QAAQ,EAAE,MAAM,GAAG,SAAS,EAAE,CAE/D;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAc/D;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CACpC,QAAQ,EAAE,MAAM,EAChB,OAAO,EAAE,MAAM,GACd,IAAI,CAmBN;AAED;;;GAGG;AACH,wBAAgB,aAAa,CAC3B,QAAQ,EAAE,MAAM,EAChB,WAAW,EAAE,MAAM,EACnB,SAAS,EAAE,MAAM,GAChB;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CA2CtC;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,CAC/B,QAAQ,EAAE,MAAM,EAChB,gBAAgB,EAAE,MAAM,GACvB;IAAE,OAAO,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAStC;AAED;;;GAGG;AACH,wBAAgB,oBAAoB,CAAC,cAAc,EAAE,MAAM,GAAG;IAC5D,OAAO,EAAE,OAAO,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB,CAyDA"}
@@ -2,6 +2,9 @@ import { Platform } from './types';
2
2
  /**
3
3
  * Platform-specific paths configuration
4
4
  * Single source of truth for all platform-specific directories
5
+ *
6
+ * Note: Skills are unified to ~/.claude/skills/ (all platforms read this location).
7
+ * Commands and agents remain platform-specific as there's no cross-platform compatibility.
5
8
  */
6
9
  export declare const PLATFORM_PATHS: {
7
10
  readonly "claude-code": {
@@ -1 +1 @@
1
- {"version":3,"file":"platforms.d.ts","sourceRoot":"","sources":["../../src/lib/platforms.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,QAAQ,EAAE,MAAM,SAAS,CAAC;AAEnC;;;GAGG;AACH,eAAO,MAAM,cAAc;;;;;;;;;;;;;CAajB,CAAC;AAEX,MAAM,MAAM,aAAa,GAAG,OAAO,cAAc,CAAC,QAAQ,CAAC,CAAC;AAE5D;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,QAAQ,EAAE,QAAQ,GAAG,aAAa,CAElE;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,QAAQ,EAAE,QAAQ,GAAG,MAAM,CAExD;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,QAAQ,EAAE,QAAQ,GAAG,MAAM,CAE1D;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,QAAQ,EAAE,QAAQ,GAAG,MAAM,CAExD;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,QAAQ,EAAE,QAAQ,GAAG,MAAM,CAExD"}
1
+ {"version":3,"file":"platforms.d.ts","sourceRoot":"","sources":["../../src/lib/platforms.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,QAAQ,EAAE,MAAM,SAAS,CAAC;AAQnC;;;;;;GAMG;AACH,eAAO,MAAM,cAAc;;;;;;;;;;;;;CAajB,CAAC;AAEX,MAAM,MAAM,aAAa,GAAG,OAAO,cAAc,CAAC,QAAQ,CAAC,CAAC;AAE5D;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,QAAQ,EAAE,QAAQ,GAAG,aAAa,CAElE;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,QAAQ,EAAE,QAAQ,GAAG,MAAM,CAExD;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,QAAQ,EAAE,QAAQ,GAAG,MAAM,CAE1D;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,QAAQ,EAAE,QAAQ,GAAG,MAAM,CAExD;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,QAAQ,EAAE,QAAQ,GAAG,MAAM,CAExD"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@orderful/droid",
3
- "version": "0.29.2",
3
+ "version": "0.30.0",
4
4
  "description": "AI workflow toolkit for sharing skills, commands, and agents across the team",
5
5
  "type": "module",
6
6
  "bin": {
@@ -107,8 +107,9 @@ export function configurePlatformPermissions(platform: Platform): { added: strin
107
107
  }
108
108
 
109
109
  if (platform === Platform.OpenCode) {
110
- // OpenCode now has native skills support - no configuration needed
111
- // Ensure config directory exists for when skills are installed
110
+ // Skills are installed to ~/.claude/skills/ (unified location)
111
+ // OpenCode reads from this location via Agent Skills standard compatibility
112
+ // Ensure config directory exists for commands and agents
112
113
  const globalConfigDir = join(homedir(), '.config', 'opencode');
113
114
  if (!existsSync(globalConfigDir)) {
114
115
  mkdirSync(globalConfigDir, { recursive: true });
@@ -243,7 +244,7 @@ export async function setupCommand(): Promise<void> {
243
244
  console.log(chalk.gray(' Droid permissions already configured in Claude Code'));
244
245
  }
245
246
  } else if (answers.platform === Platform.OpenCode) {
246
- console.log(chalk.gray(' OpenCode has native skills support - no configuration needed'));
247
+ console.log(chalk.gray(' Skills installed to ~/.claude/skills/ (works with Claude Code, OpenCode, and Cursor)'));
247
248
  }
248
249
 
249
250
  console.log(chalk.gray('\nRun `droid skills` to browse and install skills.'));
@@ -409,6 +409,88 @@ function createOpenCodePluginCleanupMigration(version: string): Migration {
409
409
  };
410
410
  }
411
411
 
412
+ /**
413
+ * Migration: Copy OpenCode skills to unified ~/.claude/skills/ location
414
+ *
415
+ * All platforms now read skills from ~/.claude/skills/ (Agent Skills standard).
416
+ * This migration copies existing OpenCode skills to the unified location.
417
+ *
418
+ * Strategy:
419
+ * - Additive only: copies skills, never deletes from source
420
+ * - Skip if exists: if skill already in ~/.claude/skills/, don't overwrite
421
+ */
422
+ function createUnifiedSkillsPathMigration(version: string): Migration {
423
+ return {
424
+ version,
425
+ description: 'Copy OpenCode skills to unified ~/.claude/skills/ location',
426
+ up: () => {
427
+ const oldOpenCodeSkillsPath = join(
428
+ homedir(),
429
+ '.config',
430
+ 'opencode',
431
+ 'skill',
432
+ );
433
+ const unifiedSkillsPath = join(homedir(), '.claude', 'skills');
434
+
435
+ // Skip if old OpenCode skills directory doesn't exist
436
+ if (!existsSync(oldOpenCodeSkillsPath)) {
437
+ return;
438
+ }
439
+
440
+ // Ensure unified skills directory exists
441
+ if (!existsSync(unifiedSkillsPath)) {
442
+ mkdirSync(unifiedSkillsPath, { recursive: true });
443
+ }
444
+
445
+ // Get all skill directories from old location
446
+ const skillDirs = readdirSync(oldOpenCodeSkillsPath, { withFileTypes: true })
447
+ .filter((dirent) => dirent.isDirectory())
448
+ .map((dirent) => dirent.name);
449
+
450
+ for (const skillName of skillDirs) {
451
+ const sourcePath = join(oldOpenCodeSkillsPath, skillName);
452
+ const destPath = join(unifiedSkillsPath, skillName);
453
+
454
+ // Skip if already exists in unified location (Claude version wins)
455
+ if (existsSync(destPath)) {
456
+ continue;
457
+ }
458
+
459
+ // Copy skill directory recursively
460
+ try {
461
+ copyDirRecursive(sourcePath, destPath);
462
+ } catch (error) {
463
+ // Non-fatal: Log warning but continue with other skills
464
+ console.warn(
465
+ `Warning: Could not copy skill ${skillName} to unified location: ${error}`,
466
+ );
467
+ }
468
+ }
469
+ },
470
+ };
471
+ }
472
+
473
+ /**
474
+ * Recursively copy a directory
475
+ */
476
+ function copyDirRecursive(src: string, dest: string): void {
477
+ mkdirSync(dest, { recursive: true });
478
+
479
+ const entries = readdirSync(src, { withFileTypes: true });
480
+
481
+ for (const entry of entries) {
482
+ const srcPath = join(src, entry.name);
483
+ const destPath = join(dest, entry.name);
484
+
485
+ if (entry.isDirectory()) {
486
+ copyDirRecursive(srcPath, destPath);
487
+ } else {
488
+ const content = readFileSync(srcPath);
489
+ writeFileSync(destPath, content);
490
+ }
491
+ }
492
+ }
493
+
412
494
  /**
413
495
  * Registry of package-level migrations
414
496
  * These run when the @orderful/droid npm package updates
@@ -423,6 +505,7 @@ const PACKAGE_MIGRATIONS: Migration[] = [
423
505
  // Retry: 0.28.0 migration had platform check that prevented running after platform switch
424
506
  createClaudeCodeCommandCleanupMigration('0.28.1'),
425
507
  createOpenCodePluginCleanupMigration('0.29.2'),
508
+ createUnifiedSkillsPathMigration('0.30.0'),
426
509
  ];
427
510
 
428
511
  /**
@@ -2,19 +2,28 @@ import { join } from 'path';
2
2
  import { homedir } from 'os';
3
3
  import { Platform } from './types';
4
4
 
5
+ /**
6
+ * Unified skills path - all platforms read from ~/.claude/skills/
7
+ * This is the Agent Skills standard location supported by Claude Code, OpenCode, and Cursor.
8
+ */
9
+ const UNIFIED_SKILLS_PATH = join(homedir(), '.claude', 'skills');
10
+
5
11
  /**
6
12
  * Platform-specific paths configuration
7
13
  * Single source of truth for all platform-specific directories
14
+ *
15
+ * Note: Skills are unified to ~/.claude/skills/ (all platforms read this location).
16
+ * Commands and agents remain platform-specific as there's no cross-platform compatibility.
8
17
  */
9
18
  export const PLATFORM_PATHS = {
10
19
  [Platform.ClaudeCode]: {
11
- skills: join(homedir(), '.claude', 'skills'),
20
+ skills: UNIFIED_SKILLS_PATH,
12
21
  commands: join(homedir(), '.claude', 'commands'),
13
22
  agents: join(homedir(), '.claude', 'agents'),
14
23
  config: join(homedir(), '.claude', 'CLAUDE.md'),
15
24
  },
16
25
  [Platform.OpenCode]: {
17
- skills: join(homedir(), '.config', 'opencode', 'skill'),
26
+ skills: UNIFIED_SKILLS_PATH,
18
27
  commands: join(homedir(), '.config', 'opencode', 'command'),
19
28
  agents: join(homedir(), '.config', 'opencode', 'agent'),
20
29
  config: join(homedir(), '.config', 'opencode', 'AGENTS.md'),
@@ -42,9 +42,10 @@ describe("getSkillsInstallPath", () => {
42
42
  expect(path).toBe(join(homedir(), ".claude", "skills"));
43
43
  });
44
44
 
45
- it("should return OpenCode path", () => {
45
+ it("should return unified skills path for OpenCode", () => {
46
+ // OpenCode now uses the unified ~/.claude/skills/ path (Agent Skills standard)
46
47
  const path = getSkillsInstallPath(Platform.OpenCode);
47
- expect(path).toBe(join(homedir(), ".config", "opencode", "skill"));
48
+ expect(path).toBe(join(homedir(), ".claude", "skills"));
48
49
  });
49
50
  });
50
51