specweave 0.28.13 → 0.28.15

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.
Files changed (86) hide show
  1. package/dist/src/cli/commands/archive.d.ts +0 -1
  2. package/dist/src/cli/commands/archive.d.ts.map +1 -1
  3. package/dist/src/cli/commands/archive.js +1 -4
  4. package/dist/src/cli/commands/archive.js.map +1 -1
  5. package/dist/src/cli/commands/import-external.d.ts.map +1 -1
  6. package/dist/src/cli/commands/import-external.js +128 -16
  7. package/dist/src/cli/commands/import-external.js.map +1 -1
  8. package/dist/src/cli/commands/init.js +5 -5
  9. package/dist/src/cli/commands/init.js.map +1 -1
  10. package/dist/src/cli/helpers/init/external-import.d.ts +3 -1
  11. package/dist/src/cli/helpers/init/external-import.d.ts.map +1 -1
  12. package/dist/src/cli/helpers/init/external-import.js +407 -19
  13. package/dist/src/cli/helpers/init/external-import.js.map +1 -1
  14. package/dist/src/cli/helpers/init/next-steps.d.ts.map +1 -1
  15. package/dist/src/cli/helpers/init/next-steps.js +77 -5
  16. package/dist/src/cli/helpers/init/next-steps.js.map +1 -1
  17. package/dist/src/cli/helpers/init/smart-reinit.d.ts +2 -0
  18. package/dist/src/cli/helpers/init/smart-reinit.d.ts.map +1 -1
  19. package/dist/src/cli/helpers/init/smart-reinit.js +371 -36
  20. package/dist/src/cli/helpers/init/smart-reinit.js.map +1 -1
  21. package/dist/src/cli/helpers/init/testing-config.d.ts +5 -2
  22. package/dist/src/cli/helpers/init/testing-config.d.ts.map +1 -1
  23. package/dist/src/cli/helpers/init/testing-config.js +322 -31
  24. package/dist/src/cli/helpers/init/testing-config.js.map +1 -1
  25. package/dist/src/core/feature-deleter/validator.d.ts +1 -0
  26. package/dist/src/core/feature-deleter/validator.d.ts.map +1 -1
  27. package/dist/src/core/feature-deleter/validator.js +8 -10
  28. package/dist/src/core/feature-deleter/validator.js.map +1 -1
  29. package/dist/src/core/increment/increment-archiver.d.ts.map +1 -1
  30. package/dist/src/core/increment/increment-archiver.js +12 -5
  31. package/dist/src/core/increment/increment-archiver.js.map +1 -1
  32. package/dist/src/core/living-docs/feature-archiver.d.ts +25 -3
  33. package/dist/src/core/living-docs/feature-archiver.d.ts.map +1 -1
  34. package/dist/src/core/living-docs/feature-archiver.js +131 -129
  35. package/dist/src/core/living-docs/feature-archiver.js.map +1 -1
  36. package/dist/src/core/living-docs/feature-consistency-validator.d.ts +23 -22
  37. package/dist/src/core/living-docs/feature-consistency-validator.d.ts.map +1 -1
  38. package/dist/src/core/living-docs/feature-consistency-validator.js +68 -150
  39. package/dist/src/core/living-docs/feature-consistency-validator.js.map +1 -1
  40. package/dist/src/core/living-docs/feature-id-manager.d.ts +5 -1
  41. package/dist/src/core/living-docs/feature-id-manager.d.ts.map +1 -1
  42. package/dist/src/core/living-docs/feature-id-manager.js +43 -23
  43. package/dist/src/core/living-docs/feature-id-manager.js.map +1 -1
  44. package/dist/src/core/living-docs/hierarchy-mapper.d.ts +21 -12
  45. package/dist/src/core/living-docs/hierarchy-mapper.d.ts.map +1 -1
  46. package/dist/src/core/living-docs/hierarchy-mapper.js +89 -70
  47. package/dist/src/core/living-docs/hierarchy-mapper.js.map +1 -1
  48. package/dist/src/core/living-docs/living-docs-sync.d.ts +10 -11
  49. package/dist/src/core/living-docs/living-docs-sync.d.ts.map +1 -1
  50. package/dist/src/core/living-docs/living-docs-sync.js +24 -56
  51. package/dist/src/core/living-docs/living-docs-sync.js.map +1 -1
  52. package/dist/src/core/repo-structure/repo-bulk-discovery.d.ts +1 -1
  53. package/dist/src/core/repo-structure/repo-bulk-discovery.d.ts.map +1 -1
  54. package/dist/src/core/repo-structure/repo-bulk-discovery.js +168 -126
  55. package/dist/src/core/repo-structure/repo-bulk-discovery.js.map +1 -1
  56. package/dist/src/core/spec-detector.js +2 -2
  57. package/dist/src/core/spec-detector.js.map +1 -1
  58. package/dist/src/importers/duplicate-detector.d.ts +6 -0
  59. package/dist/src/importers/duplicate-detector.d.ts.map +1 -1
  60. package/dist/src/importers/duplicate-detector.js +8 -2
  61. package/dist/src/importers/duplicate-detector.js.map +1 -1
  62. package/dist/src/importers/external-importer.d.ts +6 -0
  63. package/dist/src/importers/external-importer.d.ts.map +1 -1
  64. package/dist/src/importers/import-coordinator.d.ts +38 -2
  65. package/dist/src/importers/import-coordinator.d.ts.map +1 -1
  66. package/dist/src/importers/import-coordinator.js +142 -5
  67. package/dist/src/importers/import-coordinator.js.map +1 -1
  68. package/dist/src/importers/item-converter.d.ts +39 -1
  69. package/dist/src/importers/item-converter.d.ts.map +1 -1
  70. package/dist/src/importers/item-converter.js +202 -24
  71. package/dist/src/importers/item-converter.js.map +1 -1
  72. package/dist/src/living-docs/fs-id-allocator.d.ts +9 -2
  73. package/dist/src/living-docs/fs-id-allocator.d.ts.map +1 -1
  74. package/dist/src/living-docs/fs-id-allocator.js +24 -10
  75. package/dist/src/living-docs/fs-id-allocator.js.map +1 -1
  76. package/dist/src/sync/sync-metadata.d.ts.map +1 -1
  77. package/dist/src/sync/sync-metadata.js +31 -2
  78. package/dist/src/sync/sync-metadata.js.map +1 -1
  79. package/dist/src/utils/project-detection.d.ts +13 -10
  80. package/dist/src/utils/project-detection.d.ts.map +1 -1
  81. package/dist/src/utils/project-detection.js +26 -11
  82. package/dist/src/utils/project-detection.js.map +1 -1
  83. package/package.json +1 -1
  84. package/plugins/specweave/agents/AGENTS-INDEX.md +0 -9
  85. package/plugins/specweave-github/hooks/.specweave/logs/hooks-debug.log +12 -0
  86. package/plugins/specweave-release/hooks/.specweave/logs/dora-tracking.log +18 -0
@@ -15,7 +15,10 @@ import { RateLimiter } from './rate-limiter.js';
15
15
  export class ImportCoordinator {
16
16
  constructor(config) {
17
17
  this.importers = new Map();
18
+ /** Multi-repo importers keyed by "github:owner/repo" */
19
+ this.githubRepoImporters = new Map();
18
20
  this.rateLimiter = null;
21
+ this.importStartTime = 0;
19
22
  this.config = {
20
23
  enableSyncMetadata: true,
21
24
  enableRateLimiting: true,
@@ -33,8 +36,27 @@ export class ImportCoordinator {
33
36
  * Initialize importers based on configuration
34
37
  */
35
38
  initializeImporters() {
36
- // GitHub importer
37
- if (this.config.github) {
39
+ // Multi-repo GitHub support (preferred over single repo)
40
+ if (this.config.githubRepositories && this.config.githubRepositories.length > 0) {
41
+ const token = this.config.githubToken || this.config.github?.token || process.env.GITHUB_TOKEN;
42
+ for (const repo of this.config.githubRepositories) {
43
+ try {
44
+ const importer = new GitHubImporter(repo.owner, repo.repo, token);
45
+ const key = `github:${repo.owner}/${repo.repo}`;
46
+ this.githubRepoImporters.set(key, importer);
47
+ }
48
+ catch (error) {
49
+ console.warn(`Failed to initialize GitHub importer for ${repo.owner}/${repo.repo}: ${error.message}`);
50
+ }
51
+ }
52
+ // If we have multi-repo, don't create single repo importer
53
+ if (this.githubRepoImporters.size > 0) {
54
+ // Mark that we have GitHub configured (for platform detection)
55
+ // We'll handle multi-repo in importAll()
56
+ }
57
+ }
58
+ else if (this.config.github) {
59
+ // Single repo GitHub importer (backwards compatible)
38
60
  try {
39
61
  const importer = new GitHubImporter(this.config.github.owner, this.config.github.repo, this.config.github.token);
40
62
  this.importers.set('github', importer);
@@ -63,7 +85,7 @@ export class ImportCoordinator {
63
85
  console.warn(`Failed to initialize ADO importer: ${error.message}`);
64
86
  }
65
87
  }
66
- if (this.importers.size === 0) {
88
+ if (this.importers.size === 0 && this.githubRepoImporters.size === 0) {
67
89
  throw new Error('No importers configured. Provide at least one platform configuration.');
68
90
  }
69
91
  }
@@ -71,6 +93,7 @@ export class ImportCoordinator {
71
93
  * Import from all configured platforms
72
94
  */
73
95
  async importAll() {
96
+ this.importStartTime = Date.now();
74
97
  const parallel = this.config.parallel !== false; // Default to true
75
98
  if (parallel) {
76
99
  return this.importParallel();
@@ -83,7 +106,16 @@ export class ImportCoordinator {
83
106
  * Import from platforms in parallel
84
107
  */
85
108
  async importParallel() {
86
- const promises = Array.from(this.importers.entries()).map(([platform, importer]) => this.importFromPlatform(platform, importer));
109
+ const promises = [];
110
+ // Add standard platform importers
111
+ for (const [platform, importer] of this.importers.entries()) {
112
+ promises.push(this.importFromPlatform(platform, importer));
113
+ }
114
+ // Add multi-repo GitHub importers
115
+ for (const [key, importer] of this.githubRepoImporters.entries()) {
116
+ const sourceRepo = key.replace('github:', '');
117
+ promises.push(this.importFromGitHubRepo(importer, sourceRepo));
118
+ }
87
119
  const results = await Promise.allSettled(promises);
88
120
  return this.aggregateResults(results);
89
121
  }
@@ -92,6 +124,7 @@ export class ImportCoordinator {
92
124
  */
93
125
  async importSequential() {
94
126
  const results = [];
127
+ // Standard platform importers
95
128
  for (const [platform, importer] of this.importers.entries()) {
96
129
  try {
97
130
  const result = await this.importFromPlatform(platform, importer);
@@ -104,8 +137,98 @@ export class ImportCoordinator {
104
137
  });
105
138
  }
106
139
  }
140
+ // Multi-repo GitHub importers (sequentially to avoid rate limits)
141
+ for (const [key, importer] of this.githubRepoImporters.entries()) {
142
+ const sourceRepo = key.replace('github:', '');
143
+ try {
144
+ const result = await this.importFromGitHubRepo(importer, sourceRepo);
145
+ results.push({ status: 'fulfilled', value: result });
146
+ }
147
+ catch (error) {
148
+ results.push({
149
+ status: 'rejected',
150
+ reason: error,
151
+ });
152
+ }
153
+ }
107
154
  return this.aggregateResults(results);
108
155
  }
156
+ /**
157
+ * Import from a single GitHub repo with source tagging
158
+ */
159
+ async importFromGitHubRepo(importer, sourceRepo) {
160
+ const errors = [];
161
+ const items = [];
162
+ let totalEstimate;
163
+ try {
164
+ // Use pagination for progress tracking
165
+ for await (const page of importer.paginate(this.config.importConfig)) {
166
+ // Tag each item with source repo
167
+ for (const item of page) {
168
+ item.sourceRepo = sourceRepo;
169
+ }
170
+ items.push(...page);
171
+ // Calculate progress info
172
+ const elapsed = (Date.now() - this.importStartTime) / 1000;
173
+ const rate = elapsed > 0 ? items.length / elapsed : 0;
174
+ const eta = totalEstimate && rate > 0 ? (totalEstimate - items.length) / rate : undefined;
175
+ // Report enhanced progress
176
+ if (this.config.onProgressEnhanced) {
177
+ this.config.onProgressEnhanced({
178
+ platform: 'github',
179
+ current: items.length,
180
+ total: totalEstimate,
181
+ percentage: totalEstimate ? Math.round((items.length / totalEstimate) * 100) : undefined,
182
+ rate: Math.round(rate * 10) / 10,
183
+ eta: eta ? Math.round(eta) : undefined,
184
+ sourceRepo,
185
+ });
186
+ }
187
+ // Legacy progress callback
188
+ if (this.config.onProgress) {
189
+ this.config.onProgress(`github (${sourceRepo})`, items.length, totalEstimate);
190
+ }
191
+ }
192
+ // Update sync metadata if enabled
193
+ if (this.config.enableSyncMetadata && items.length > 0) {
194
+ const metadata = {
195
+ lastImport: new Date().toISOString(),
196
+ lastImportCount: items.length,
197
+ lastSyncResult: errors.length > 0 ? 'partial' : 'success',
198
+ };
199
+ try {
200
+ updateSyncMetadata(this.projectRoot, 'github', metadata);
201
+ }
202
+ catch (error) {
203
+ errors.push(`Failed to update sync metadata: ${error.message}`);
204
+ }
205
+ }
206
+ }
207
+ catch (error) {
208
+ errors.push(error.message || String(error));
209
+ if (this.config.enableSyncMetadata) {
210
+ const metadata = {
211
+ lastImport: new Date().toISOString(),
212
+ lastImportCount: 0,
213
+ lastSyncResult: 'failed',
214
+ };
215
+ try {
216
+ updateSyncMetadata(this.projectRoot, 'github', metadata);
217
+ }
218
+ catch {
219
+ // Ignore
220
+ }
221
+ }
222
+ }
223
+ return {
224
+ count: items.length,
225
+ items,
226
+ errors,
227
+ platform: 'github',
228
+ totalEstimate,
229
+ sourceRepo,
230
+ };
231
+ }
109
232
  /**
110
233
  * Import from a single platform with progress tracking
111
234
  */
@@ -212,13 +335,27 @@ export class ImportCoordinator {
212
335
  * Get list of configured platforms
213
336
  */
214
337
  getConfiguredPlatforms() {
215
- return Array.from(this.importers.keys());
338
+ const platforms = Array.from(this.importers.keys());
339
+ // Add 'github' if multi-repo importers are configured
340
+ if (this.githubRepoImporters.size > 0 && !platforms.includes('github')) {
341
+ platforms.push('github');
342
+ }
343
+ return platforms;
216
344
  }
217
345
  /**
218
346
  * Check if a platform is configured
219
347
  */
220
348
  isPlatformConfigured(platform) {
349
+ if (platform === 'github') {
350
+ return this.importers.has(platform) || this.githubRepoImporters.size > 0;
351
+ }
221
352
  return this.importers.has(platform);
222
353
  }
354
+ /**
355
+ * Get list of configured GitHub repositories (for multi-repo support)
356
+ */
357
+ getConfiguredGitHubRepos() {
358
+ return Array.from(this.githubRepoImporters.keys()).map(key => key.replace('github:', ''));
359
+ }
223
360
  }
224
361
  //# sourceMappingURL=import-coordinator.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"import-coordinator.js","sourceRoot":"","sources":["../../../src/importers/import-coordinator.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"import-coordinator.js","sourceRoot":"","sources":["../../../src/importers/import-coordinator.ts"],"names":[],"mappings":"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"}
@@ -27,11 +27,14 @@ export interface ConvertedUserStory {
27
27
  createdAt: string;
28
28
  updatedAt: string;
29
29
  labels: string[];
30
+ sourceRepo?: string;
30
31
  };
31
32
  /** Living docs file path */
32
33
  filePath: string;
33
34
  /** Living docs markdown content */
34
35
  markdown: string;
36
+ /** Feature ID this user story belongs to (when feature allocation enabled) */
37
+ featureId?: string;
35
38
  }
36
39
  export interface ItemConverterOptions {
37
40
  /** Base directory for living docs (e.g., .specweave/docs/internal/specs) */
@@ -42,10 +45,18 @@ export interface ItemConverterOptions {
42
45
  projectRoot?: string;
43
46
  /** Enable feature-level organization with FS-ID allocation */
44
47
  enableFeatureAllocation?: boolean;
48
+ /** Project ID for multi-project mode (default: 'default') */
49
+ projectId?: string;
45
50
  /** Enable duplicate detection (default: true) */
46
51
  enableDuplicateDetection?: boolean;
52
+ /** Auto-archive items older than this many days (default: 30, 0 to disable) */
53
+ autoArchiveAfterDays?: number;
47
54
  /** Callback for skipped duplicates */
48
55
  onDuplicateSkipped?: (externalId: string, existingUsId: string) => void;
56
+ /** Callback for feature folder creation */
57
+ onFeatureCreated?: (featureId: string, featurePath: string) => void;
58
+ /** Callback for archived items */
59
+ onItemArchived?: (usId: string, reason: string) => void;
49
60
  }
50
61
  /**
51
62
  * Convert external items to living docs User Stories
@@ -56,11 +67,18 @@ export interface ItemConverterOptions {
56
67
  export declare class ItemConverter {
57
68
  private options;
58
69
  private duplicateDetector;
70
+ private fsIdAllocator;
71
+ /** Cache of created feature folders to avoid duplicates */
72
+ private createdFeatures;
59
73
  constructor(options: ItemConverterOptions);
60
74
  /**
61
75
  * Convert a single external item to a User Story with E suffix
76
+ *
77
+ * @param item - External item to convert
78
+ * @param usId - User Story ID number
79
+ * @param featureId - Optional feature ID for folder organization
62
80
  */
63
- convertItem(item: ExternalItem, usId: number): ConvertedUserStory;
81
+ convertItem(item: ExternalItem, usId: number, featureId?: string): ConvertedUserStory;
64
82
  /**
65
83
  * Convert multiple external items to User Stories
66
84
  *
@@ -68,10 +86,30 @@ export declare class ItemConverter {
68
86
  * It does NOT create increments.
69
87
  */
70
88
  convertItems(items: ExternalItem[]): Promise<ConvertedUserStory[]>;
89
+ /**
90
+ * Group items by feature (based on source repo or labels)
91
+ * Items without clear grouping go into a default group
92
+ */
93
+ private groupItemsByFeature;
94
+ /**
95
+ * Allocate a feature ID for a group of items
96
+ */
97
+ private allocateFeatureForGroup;
98
+ /**
99
+ * Create feature folder with FEATURE.md
100
+ */
101
+ private createFeatureFolder;
71
102
  /**
72
103
  * Map external status to SpecWeave status
73
104
  */
74
105
  private mapStatus;
106
+ /**
107
+ * Check if an item should be auto-archived based on creation date
108
+ *
109
+ * @param createdAt - Item creation date
110
+ * @returns True if item is older than autoArchiveAfterDays threshold
111
+ */
112
+ private shouldAutoArchive;
75
113
  /**
76
114
  * Generate origin badge for living docs
77
115
  */
@@ -1 +1 @@
1
- {"version":3,"file":"item-converter.d.ts","sourceRoot":"","sources":["../../../src/importers/item-converter.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AAQ3D,MAAM,WAAW,kBAAkB;IACjC,kDAAkD;IAClD,EAAE,EAAE,MAAM,CAAC;IAEX,uBAAuB;IACvB,KAAK,EAAE,MAAM,CAAC;IAEd,6BAA6B;IAC7B,WAAW,EAAE,MAAM,CAAC;IAEpB,0BAA0B;IAC1B,kBAAkB,EAAE,MAAM,EAAE,CAAC;IAE7B,uBAAuB;IACvB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAElB,4CAA4C;IAC5C,MAAM,EAAE,MAAM,CAAC;IAEf,wBAAwB;IACxB,QAAQ,EAAE;QACR,UAAU,EAAE,MAAM,CAAC;QACnB,WAAW,EAAE,MAAM,CAAC;QACpB,gBAAgB,EAAE,QAAQ,GAAG,MAAM,GAAG,KAAK,CAAC;QAC5C,UAAU,EAAE,MAAM,CAAC;QACnB,SAAS,EAAE,MAAM,CAAC;QAClB,SAAS,EAAE,MAAM,CAAC;QAClB,MAAM,EAAE,MAAM,EAAE,CAAC;KAClB,CAAC;IAEF,4BAA4B;IAC5B,QAAQ,EAAE,MAAM,CAAC;IAEjB,mCAAmC;IACnC,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,oBAAoB;IACnC,4EAA4E;IAC5E,QAAQ,EAAE,MAAM,CAAC;IAEjB,4DAA4D;IAC5D,UAAU,CAAC,EAAE,MAAM,CAAC;IAEpB,uDAAuD;IACvD,WAAW,CAAC,EAAE,MAAM,CAAC;IAErB,8DAA8D;IAC9D,uBAAuB,CAAC,EAAE,OAAO,CAAC;IAElC,iDAAiD;IACjD,wBAAwB,CAAC,EAAE,OAAO,CAAC;IAEnC,sCAAsC;IACtC,kBAAkB,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,KAAK,IAAI,CAAC;CACzE;AAED;;;;;GAKG;AACH,qBAAa,aAAa;IACxB,OAAO,CAAC,OAAO,CAAuB;IACtC,OAAO,CAAC,iBAAiB,CAAkC;gBAE/C,OAAO,EAAE,oBAAoB;IAczC;;OAEG;IACH,WAAW,CAAC,IAAI,EAAE,YAAY,EAAE,IAAI,EAAE,MAAM,GAAG,kBAAkB;IA0DjE;;;;;OAKG;IACG,YAAY,CAAC,KAAK,EAAE,YAAY,EAAE,GAAG,OAAO,CAAC,kBAAkB,EAAE,CAAC;IAwCxE;;OAEG;IACH,OAAO,CAAC,SAAS;IAWjB;;OAEG;IACH,OAAO,CAAC,mBAAmB;IAsB3B;;OAEG;IACH,OAAO,CAAC,gBAAgB;IA6ExB;;;;OAIG;IACH,OAAO,CAAC,gBAAgB;IAexB;;;;OAIG;IACH,MAAM,CAAC,2BAA2B,CAAC,WAAW,EAAE,MAAM,GAAG,IAAI;CAsB9D"}
1
+ {"version":3,"file":"item-converter.d.ts","sourceRoot":"","sources":["../../../src/importers/item-converter.ts"],"names":[],"mappings":"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"}
@@ -6,6 +6,7 @@
6
6
  */
7
7
  import * as fs from '../utils/fs-native.js';
8
8
  import path from 'path';
9
+ import { FSIdAllocator } from '../living-docs/fs-id-allocator.js';
9
10
  import { DuplicateDetector } from './duplicate-detector.js';
10
11
  /**
11
12
  * Convert external items to living docs User Stories
@@ -16,8 +17,15 @@ import { DuplicateDetector } from './duplicate-detector.js';
16
17
  export class ItemConverter {
17
18
  constructor(options) {
18
19
  this.duplicateDetector = null;
20
+ this.fsIdAllocator = null;
21
+ /** Cache of created feature folders to avoid duplicates */
22
+ this.createdFeatures = new Map();
19
23
  this.options = {
20
24
  enableDuplicateDetection: true,
25
+ // NOTE: projectId is intentionally NOT defaulted to 'default'
26
+ // - undefined means items go directly to specs/ (no project subfolder)
27
+ // - a string value means items go to specs/{projectId}/
28
+ autoArchiveAfterDays: 30, // Default: archive items older than 1 month
21
29
  ...options,
22
30
  };
23
31
  // Initialize duplicate detector if enabled
@@ -26,11 +34,20 @@ export class ItemConverter {
26
34
  specsDir: this.options.specsDir,
27
35
  });
28
36
  }
37
+ // Initialize FS-ID allocator if feature allocation is enabled
38
+ if (this.options.enableFeatureAllocation && this.options.projectRoot) {
39
+ // Use projectId if provided, otherwise undefined (direct to specs/)
40
+ this.fsIdAllocator = new FSIdAllocator(this.options.projectRoot, this.options.projectId);
41
+ }
29
42
  }
30
43
  /**
31
44
  * Convert a single external item to a User Story with E suffix
45
+ *
46
+ * @param item - External item to convert
47
+ * @param usId - User Story ID number
48
+ * @param featureId - Optional feature ID for folder organization
32
49
  */
33
- convertItem(item, usId) {
50
+ convertItem(item, usId, featureId) {
34
51
  // Generate US-ID with E suffix
35
52
  const id = `US-${String(usId).padStart(3, '0')}E`;
36
53
  // Map external status to SpecWeave status
@@ -55,12 +72,39 @@ export class ItemConverter {
55
72
  importedAt: new Date().toISOString(),
56
73
  createdAt: item.createdAt.toISOString(),
57
74
  updatedAt: item.updatedAt.toISOString(),
58
- labels: item.labels
75
+ labels: item.labels,
76
+ sourceRepo: item.sourceRepo
59
77
  }
60
78
  });
61
- // Generate file path
79
+ // Generate file path (with feature folder if allocated)
62
80
  const fileName = this.generateFileName(id, item.title);
63
- const filePath = path.join(this.options.specsDir, fileName);
81
+ let filePath;
82
+ // Check if item should be auto-archived (older than threshold)
83
+ const shouldArchive = this.shouldAutoArchive(item.createdAt);
84
+ if (featureId && this.options.enableFeatureAllocation) {
85
+ // Feature folder structure:
86
+ // - With projectId: specs/{projectId}/{featureId}/us-xxxe-title.md
87
+ // - Without projectId: specs/{featureId}/us-xxxe-title.md (direct to specs)
88
+ const baseDir = this.options.projectId
89
+ ? path.join(this.options.specsDir, this.options.projectId)
90
+ : this.options.specsDir;
91
+ const targetDir = shouldArchive
92
+ ? path.join(baseDir, '_archive', featureId)
93
+ : path.join(baseDir, featureId);
94
+ filePath = path.join(targetDir, fileName);
95
+ }
96
+ else {
97
+ // Legacy: direct in specs or archive folder
98
+ const targetDir = shouldArchive
99
+ ? path.join(this.options.specsDir, '_archive')
100
+ : this.options.specsDir;
101
+ filePath = path.join(targetDir, fileName);
102
+ }
103
+ // Notify callback if item was archived
104
+ if (shouldArchive && this.options.onItemArchived) {
105
+ const age = Math.floor((Date.now() - item.createdAt.getTime()) / (1000 * 60 * 60 * 24));
106
+ this.options.onItemArchived(id, `Item is ${age} days old (threshold: ${this.options.autoArchiveAfterDays} days)`);
107
+ }
64
108
  return {
65
109
  id,
66
110
  title: item.title,
@@ -75,10 +119,12 @@ export class ItemConverter {
75
119
  importedAt: new Date().toISOString(),
76
120
  createdAt: item.createdAt.toISOString(),
77
121
  updatedAt: item.updatedAt.toISOString(),
78
- labels: item.labels
122
+ labels: item.labels,
123
+ sourceRepo: item.sourceRepo
79
124
  },
80
125
  filePath,
81
- markdown
126
+ markdown,
127
+ featureId
82
128
  };
83
129
  }
84
130
  /**
@@ -93,30 +139,143 @@ export class ItemConverter {
93
139
  let skippedCount = 0;
94
140
  // Ensure specs directory exists
95
141
  fs.mkdirSync(this.options.specsDir, { recursive: true });
96
- // Convert each item
97
- for (let i = 0; i < items.length; i++) {
98
- const item = items[i];
99
- // Check for duplicates if duplicate detection is enabled
100
- if (this.duplicateDetector) {
101
- const existingReference = await this.duplicateDetector.findExternalIdReference(item.id);
102
- if (existingReference) {
103
- skippedCount++;
104
- // Notify callback if provided
105
- if (this.options.onDuplicateSkipped) {
106
- this.options.onDuplicateSkipped(item.id, existingReference.usId);
142
+ // If feature allocation is enabled, scan existing IDs first
143
+ if (this.fsIdAllocator) {
144
+ await this.fsIdAllocator.scanExistingIds();
145
+ }
146
+ // Group items by source (for multi-repo) or treat as single group
147
+ const itemGroups = this.groupItemsByFeature(items);
148
+ // Process each group
149
+ for (const [groupKey, groupItems] of itemGroups.entries()) {
150
+ // Allocate feature ID for this group if feature allocation is enabled
151
+ let featureId;
152
+ if (this.fsIdAllocator && this.options.enableFeatureAllocation && groupItems.length > 0) {
153
+ const firstItem = groupItems[0];
154
+ featureId = await this.allocateFeatureForGroup(firstItem, groupKey);
155
+ }
156
+ // Convert each item in the group
157
+ for (let i = 0; i < groupItems.length; i++) {
158
+ const item = groupItems[i];
159
+ // Check for duplicates if duplicate detection is enabled
160
+ if (this.duplicateDetector) {
161
+ const existingReference = await this.duplicateDetector.findExternalIdReference(item.id);
162
+ if (existingReference) {
163
+ skippedCount++;
164
+ // Notify callback if provided
165
+ if (this.options.onDuplicateSkipped) {
166
+ this.options.onDuplicateSkipped(item.id, existingReference.usId);
167
+ }
168
+ // Skip this item (duplicate)
169
+ continue;
107
170
  }
108
- // Skip this item (duplicate)
109
- continue;
110
171
  }
172
+ const usId = startingId + (converted.length);
173
+ const userStory = this.convertItem(item, usId, featureId);
174
+ converted.push(userStory);
175
+ // Ensure directory exists for feature folders
176
+ const fileDir = path.dirname(userStory.filePath);
177
+ fs.mkdirSync(fileDir, { recursive: true });
178
+ // Write living docs file
179
+ fs.writeFileSync(userStory.filePath, userStory.markdown, 'utf-8');
111
180
  }
112
- const usId = startingId + (i - skippedCount);
113
- const userStory = this.convertItem(item, usId);
114
- converted.push(userStory);
115
- // Write living docs file
116
- fs.writeFileSync(userStory.filePath, userStory.markdown, 'utf-8');
117
181
  }
118
182
  return converted;
119
183
  }
184
+ /**
185
+ * Group items by feature (based on source repo or labels)
186
+ * Items without clear grouping go into a default group
187
+ */
188
+ groupItemsByFeature(items) {
189
+ const groups = new Map();
190
+ for (const item of items) {
191
+ // Group by source repo if available
192
+ const groupKey = item.sourceRepo || 'default';
193
+ if (!groups.has(groupKey)) {
194
+ groups.set(groupKey, []);
195
+ }
196
+ groups.get(groupKey).push(item);
197
+ }
198
+ return groups;
199
+ }
200
+ /**
201
+ * Allocate a feature ID for a group of items
202
+ */
203
+ async allocateFeatureForGroup(firstItem, groupKey) {
204
+ // Check if we already created a feature for this group
205
+ if (this.createdFeatures.has(groupKey)) {
206
+ return this.createdFeatures.get(groupKey);
207
+ }
208
+ if (!this.fsIdAllocator) {
209
+ throw new Error('FSIdAllocator not initialized');
210
+ }
211
+ // Create external work item for allocation
212
+ const workItem = {
213
+ externalId: firstItem.id,
214
+ title: firstItem.sourceRepo || firstItem.title,
215
+ createdAt: firstItem.createdAt.toISOString(),
216
+ externalUrl: firstItem.url
217
+ };
218
+ // Allocate feature ID
219
+ const allocation = await this.fsIdAllocator.allocateId(workItem);
220
+ const featureId = allocation.id;
221
+ // Create feature folder with FEATURE.md
222
+ const featurePath = await this.createFeatureFolder(featureId, firstItem, groupKey);
223
+ // Cache for reuse
224
+ this.createdFeatures.set(groupKey, featureId);
225
+ // Notify callback
226
+ if (this.options.onFeatureCreated) {
227
+ this.options.onFeatureCreated(featureId, featurePath);
228
+ }
229
+ return featureId;
230
+ }
231
+ /**
232
+ * Create feature folder with FEATURE.md
233
+ */
234
+ async createFeatureFolder(featureId, firstItem, groupKey) {
235
+ // Use projectId subfolder if provided, otherwise direct to specs/
236
+ const baseDir = this.options.projectId
237
+ ? path.join(this.options.specsDir, this.options.projectId)
238
+ : this.options.specsDir;
239
+ const featurePath = path.join(baseDir, featureId);
240
+ // Create directory
241
+ fs.mkdirSync(featurePath, { recursive: true });
242
+ // Generate FEATURE.md content
243
+ const featureTitle = firstItem.sourceRepo
244
+ ? `Feature: ${firstItem.sourceRepo} External Items`
245
+ : `Feature: Imported from ${firstItem.platform}`;
246
+ const featureContent = `---
247
+ id: ${featureId}
248
+ title: ${featureTitle}
249
+ origin: external
250
+ source: ${firstItem.platform}
251
+ source_repo: ${firstItem.sourceRepo || 'unknown'}
252
+ created: ${new Date().toISOString()}
253
+ ---
254
+
255
+ # ${featureTitle}
256
+
257
+ **Origin**: 🔗 Imported from ${firstItem.platform}
258
+
259
+ ## Description
260
+
261
+ This feature folder contains User Stories imported from external tools.
262
+
263
+ ${firstItem.sourceRepo ? `**Source Repository**: ${firstItem.sourceRepo}` : ''}
264
+
265
+ ## User Stories
266
+
267
+ User stories in this feature will be listed here.
268
+
269
+ ## Status
270
+
271
+ - **Created**: ${new Date().toISOString()}
272
+ - **Source**: ${firstItem.platform}
273
+ `;
274
+ // Write FEATURE.md
275
+ const featureFile = path.join(featurePath, 'FEATURE.md');
276
+ fs.writeFileSync(featureFile, featureContent, 'utf-8');
277
+ return featurePath;
278
+ }
120
279
  /**
121
280
  * Map external status to SpecWeave status
122
281
  */
@@ -129,6 +288,22 @@ export class ItemConverter {
129
288
  };
130
289
  return statusMap[externalStatus] || 'Open';
131
290
  }
291
+ /**
292
+ * Check if an item should be auto-archived based on creation date
293
+ *
294
+ * @param createdAt - Item creation date
295
+ * @returns True if item is older than autoArchiveAfterDays threshold
296
+ */
297
+ shouldAutoArchive(createdAt) {
298
+ const threshold = this.options.autoArchiveAfterDays;
299
+ // Disabled if threshold is 0 or undefined
300
+ if (!threshold || threshold <= 0) {
301
+ return false;
302
+ }
303
+ const ageMs = Date.now() - createdAt.getTime();
304
+ const ageDays = Math.floor(ageMs / (1000 * 60 * 60 * 24));
305
+ return ageDays >= threshold;
306
+ }
132
307
  /**
133
308
  * Generate origin badge for living docs
134
309
  */
@@ -201,6 +376,9 @@ export class ItemConverter {
201
376
  if (data.metadata.labels.length > 0) {
202
377
  parts.push(`- **Labels**: ${data.metadata.labels.join(', ')}`);
203
378
  }
379
+ if (data.metadata.sourceRepo) {
380
+ parts.push(`- **Source Repository**: ${data.metadata.sourceRepo}`);
381
+ }
204
382
  return parts.join('\n');
205
383
  }
206
384
  /**