specweave 1.0.53 → 1.0.55
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/src/core/auto/circuit-breaker.d.ts +146 -0
- package/dist/src/core/auto/circuit-breaker.d.ts.map +1 -0
- package/dist/src/core/auto/circuit-breaker.js +328 -0
- package/dist/src/core/auto/circuit-breaker.js.map +1 -0
- package/dist/src/core/auto/config.d.ts +34 -0
- package/dist/src/core/auto/config.d.ts.map +1 -0
- package/dist/src/core/auto/config.js +198 -0
- package/dist/src/core/auto/config.js.map +1 -0
- package/dist/src/core/auto/cost-estimator.d.ts +53 -0
- package/dist/src/core/auto/cost-estimator.d.ts.map +1 -0
- package/dist/src/core/auto/cost-estimator.js +150 -0
- package/dist/src/core/auto/cost-estimator.js.map +1 -0
- package/dist/src/core/auto/human-gate.d.ts +102 -0
- package/dist/src/core/auto/human-gate.d.ts.map +1 -0
- package/dist/src/core/auto/human-gate.js +295 -0
- package/dist/src/core/auto/human-gate.js.map +1 -0
- package/dist/src/core/auto/increment-queue.d.ts +100 -0
- package/dist/src/core/auto/increment-queue.d.ts.map +1 -0
- package/dist/src/core/auto/increment-queue.js +290 -0
- package/dist/src/core/auto/increment-queue.js.map +1 -0
- package/dist/src/core/auto/index.d.ts +19 -0
- package/dist/src/core/auto/index.d.ts.map +1 -0
- package/dist/src/core/auto/index.js +30 -0
- package/dist/src/core/auto/index.js.map +1 -0
- package/dist/src/core/auto/logger.d.ts +108 -0
- package/dist/src/core/auto/logger.d.ts.map +1 -0
- package/dist/src/core/auto/logger.js +357 -0
- package/dist/src/core/auto/logger.js.map +1 -0
- package/dist/src/core/auto/report-generator.d.ts +67 -0
- package/dist/src/core/auto/report-generator.d.ts.map +1 -0
- package/dist/src/core/auto/report-generator.js +287 -0
- package/dist/src/core/auto/report-generator.js.map +1 -0
- package/dist/src/core/auto/session-state.d.ts +98 -0
- package/dist/src/core/auto/session-state.d.ts.map +1 -0
- package/dist/src/core/auto/session-state.js +296 -0
- package/dist/src/core/auto/session-state.js.map +1 -0
- package/dist/src/core/auto/sync-checkpoint.d.ts +106 -0
- package/dist/src/core/auto/sync-checkpoint.d.ts.map +1 -0
- package/dist/src/core/auto/sync-checkpoint.js +258 -0
- package/dist/src/core/auto/sync-checkpoint.js.map +1 -0
- package/dist/src/core/auto/test-gate.d.ts +98 -0
- package/dist/src/core/auto/test-gate.d.ts.map +1 -0
- package/dist/src/core/auto/test-gate.js +258 -0
- package/dist/src/core/auto/test-gate.js.map +1 -0
- package/dist/src/core/auto/types.d.ts +122 -0
- package/dist/src/core/auto/types.d.ts.map +1 -0
- package/dist/src/core/auto/types.js +27 -0
- package/dist/src/core/auto/types.js.map +1 -0
- package/package.json +1 -1
- package/plugins/specweave/commands/auto-status.md +124 -0
- package/plugins/specweave/commands/auto.md +244 -0
- package/plugins/specweave/commands/cancel-auto.md +79 -0
- package/plugins/specweave/hooks/stop-auto.sh +188 -0
- package/plugins/specweave/scripts/auto-status.sh +231 -0
- package/plugins/specweave/scripts/cancel-auto.sh +146 -0
- package/plugins/specweave/scripts/setup-auto.sh +245 -0
- package/plugins/specweave/skills/docs-updater/.!31934!SKILL.md +20 -0
- package/plugins/specweave/skills/docs-updater/.!31935!SKILL.md +20 -0
- package/plugins/specweave/skills/docs-updater/.!31936!SKILL.md +20 -0
- package/plugins/specweave-release/commands/npm.md +28 -1
- package/src/templates/CLAUDE.md.template +57 -0
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Circuit Breaker Module
|
|
3
|
+
*
|
|
4
|
+
* Protects auto from external service failures.
|
|
5
|
+
* Implements the circuit breaker pattern for:
|
|
6
|
+
* - GitHub API
|
|
7
|
+
* - JIRA API
|
|
8
|
+
* - Azure DevOps API
|
|
9
|
+
* - Custom external services
|
|
10
|
+
*/
|
|
11
|
+
export type CircuitState = 'closed' | 'open' | 'half-open';
|
|
12
|
+
export interface CircuitBreakerConfig {
|
|
13
|
+
/** Number of failures before opening circuit */
|
|
14
|
+
failureThreshold: number;
|
|
15
|
+
/** Time in ms before trying half-open */
|
|
16
|
+
resetTimeout: number;
|
|
17
|
+
/** Number of successes in half-open to close */
|
|
18
|
+
successThreshold: number;
|
|
19
|
+
/** Time window for counting failures */
|
|
20
|
+
failureWindow: number;
|
|
21
|
+
}
|
|
22
|
+
export interface CircuitStatus {
|
|
23
|
+
state: CircuitState;
|
|
24
|
+
failures: number;
|
|
25
|
+
successes: number;
|
|
26
|
+
lastFailure?: string;
|
|
27
|
+
lastSuccess?: string;
|
|
28
|
+
openedAt?: string;
|
|
29
|
+
nextRetryAt?: string;
|
|
30
|
+
queuedOperations: QueuedOperation[];
|
|
31
|
+
}
|
|
32
|
+
export interface QueuedOperation {
|
|
33
|
+
id: string;
|
|
34
|
+
operation: string;
|
|
35
|
+
params: unknown;
|
|
36
|
+
queuedAt: string;
|
|
37
|
+
retryCount: number;
|
|
38
|
+
}
|
|
39
|
+
export declare class CircuitBreaker {
|
|
40
|
+
private name;
|
|
41
|
+
private config;
|
|
42
|
+
private status;
|
|
43
|
+
private failureTimestamps;
|
|
44
|
+
private projectRoot;
|
|
45
|
+
constructor(name: string, projectRoot: string, config?: Partial<CircuitBreakerConfig>);
|
|
46
|
+
/**
|
|
47
|
+
* Execute an operation with circuit breaker protection
|
|
48
|
+
*/
|
|
49
|
+
execute<T>(operation: () => Promise<T>): Promise<T>;
|
|
50
|
+
/**
|
|
51
|
+
* Check if circuit is open (blocking calls)
|
|
52
|
+
*/
|
|
53
|
+
isOpen(): boolean;
|
|
54
|
+
/**
|
|
55
|
+
* Check if circuit allows calls (closed or half-open)
|
|
56
|
+
*/
|
|
57
|
+
isCallAllowed(): boolean;
|
|
58
|
+
/**
|
|
59
|
+
* Record a successful operation
|
|
60
|
+
*/
|
|
61
|
+
recordSuccess(): void;
|
|
62
|
+
/**
|
|
63
|
+
* Record a failed operation
|
|
64
|
+
*/
|
|
65
|
+
recordFailure(error?: unknown): void;
|
|
66
|
+
/**
|
|
67
|
+
* Transition to a new state
|
|
68
|
+
*/
|
|
69
|
+
private transitionTo;
|
|
70
|
+
/**
|
|
71
|
+
* Queue an operation for later retry
|
|
72
|
+
*/
|
|
73
|
+
queueOperation(operation: string, params: unknown): string;
|
|
74
|
+
/**
|
|
75
|
+
* Process queued operations
|
|
76
|
+
*/
|
|
77
|
+
private processQueue;
|
|
78
|
+
/**
|
|
79
|
+
* Get current status
|
|
80
|
+
*/
|
|
81
|
+
getStatus(): CircuitStatus;
|
|
82
|
+
/**
|
|
83
|
+
* Get circuit name
|
|
84
|
+
*/
|
|
85
|
+
getName(): string;
|
|
86
|
+
/**
|
|
87
|
+
* Force reset circuit (for testing/recovery)
|
|
88
|
+
*/
|
|
89
|
+
reset(): void;
|
|
90
|
+
/**
|
|
91
|
+
* Load status from session
|
|
92
|
+
*/
|
|
93
|
+
private loadStatus;
|
|
94
|
+
/**
|
|
95
|
+
* Save status to session
|
|
96
|
+
*/
|
|
97
|
+
private saveStatus;
|
|
98
|
+
/**
|
|
99
|
+
* Log state transition
|
|
100
|
+
*/
|
|
101
|
+
private logTransition;
|
|
102
|
+
}
|
|
103
|
+
/**
|
|
104
|
+
* Error thrown when circuit is open
|
|
105
|
+
*/
|
|
106
|
+
export declare class CircuitOpenError extends Error {
|
|
107
|
+
circuitName: string;
|
|
108
|
+
retryAfter: string;
|
|
109
|
+
constructor(circuitName: string, retryAfter: string);
|
|
110
|
+
}
|
|
111
|
+
/**
|
|
112
|
+
* Circuit Breaker Registry for managing multiple breakers
|
|
113
|
+
*/
|
|
114
|
+
export declare class CircuitBreakerRegistry {
|
|
115
|
+
private breakers;
|
|
116
|
+
private projectRoot;
|
|
117
|
+
constructor(projectRoot: string);
|
|
118
|
+
/**
|
|
119
|
+
* Get or create a circuit breaker
|
|
120
|
+
*/
|
|
121
|
+
getBreaker(name: string, config?: Partial<CircuitBreakerConfig>): CircuitBreaker;
|
|
122
|
+
/**
|
|
123
|
+
* Get status of all breakers
|
|
124
|
+
*/
|
|
125
|
+
getAllStatus(): Record<string, CircuitStatus>;
|
|
126
|
+
/**
|
|
127
|
+
* Check if any circuit is open
|
|
128
|
+
*/
|
|
129
|
+
hasOpenCircuit(): boolean;
|
|
130
|
+
/**
|
|
131
|
+
* Reset all circuits
|
|
132
|
+
*/
|
|
133
|
+
resetAll(): void;
|
|
134
|
+
/**
|
|
135
|
+
* Create default service breakers
|
|
136
|
+
*/
|
|
137
|
+
initializeDefaults(): void;
|
|
138
|
+
}
|
|
139
|
+
/**
|
|
140
|
+
* Parse rate limit headers and extract retry time
|
|
141
|
+
*/
|
|
142
|
+
export declare function parseRateLimitHeaders(headers: Record<string, string | undefined>): {
|
|
143
|
+
limited: boolean;
|
|
144
|
+
retryAfter: number;
|
|
145
|
+
};
|
|
146
|
+
//# sourceMappingURL=circuit-breaker.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"circuit-breaker.d.ts","sourceRoot":"","sources":["../../../../src/core/auto/circuit-breaker.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,328 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Circuit Breaker Module
|
|
3
|
+
*
|
|
4
|
+
* Protects auto from external service failures.
|
|
5
|
+
* Implements the circuit breaker pattern for:
|
|
6
|
+
* - GitHub API
|
|
7
|
+
* - JIRA API
|
|
8
|
+
* - Azure DevOps API
|
|
9
|
+
* - Custom external services
|
|
10
|
+
*/
|
|
11
|
+
import * as fs from 'fs';
|
|
12
|
+
import * as path from 'path';
|
|
13
|
+
const DEFAULT_CONFIG = {
|
|
14
|
+
failureThreshold: 3,
|
|
15
|
+
resetTimeout: 60000, // 1 minute
|
|
16
|
+
successThreshold: 2,
|
|
17
|
+
failureWindow: 300000, // 5 minutes
|
|
18
|
+
};
|
|
19
|
+
export class CircuitBreaker {
|
|
20
|
+
constructor(name, projectRoot, config = {}) {
|
|
21
|
+
this.failureTimestamps = [];
|
|
22
|
+
this.name = name;
|
|
23
|
+
this.projectRoot = projectRoot;
|
|
24
|
+
this.config = { ...DEFAULT_CONFIG, ...config };
|
|
25
|
+
this.status = this.loadStatus() || {
|
|
26
|
+
state: 'closed',
|
|
27
|
+
failures: 0,
|
|
28
|
+
successes: 0,
|
|
29
|
+
queuedOperations: [],
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* Execute an operation with circuit breaker protection
|
|
34
|
+
*/
|
|
35
|
+
async execute(operation) {
|
|
36
|
+
if (this.isOpen()) {
|
|
37
|
+
throw new CircuitOpenError(this.name, this.status.nextRetryAt || '');
|
|
38
|
+
}
|
|
39
|
+
try {
|
|
40
|
+
const result = await operation();
|
|
41
|
+
this.recordSuccess();
|
|
42
|
+
return result;
|
|
43
|
+
}
|
|
44
|
+
catch (error) {
|
|
45
|
+
this.recordFailure(error);
|
|
46
|
+
throw error;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* Check if circuit is open (blocking calls)
|
|
51
|
+
*/
|
|
52
|
+
isOpen() {
|
|
53
|
+
if (this.status.state === 'open') {
|
|
54
|
+
// Check if ready for half-open
|
|
55
|
+
if (this.status.openedAt) {
|
|
56
|
+
const openedTime = new Date(this.status.openedAt).getTime();
|
|
57
|
+
const now = Date.now();
|
|
58
|
+
if (now - openedTime >= this.config.resetTimeout) {
|
|
59
|
+
this.transitionTo('half-open');
|
|
60
|
+
return false;
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
return true;
|
|
64
|
+
}
|
|
65
|
+
return false;
|
|
66
|
+
}
|
|
67
|
+
/**
|
|
68
|
+
* Check if circuit allows calls (closed or half-open)
|
|
69
|
+
*/
|
|
70
|
+
isCallAllowed() {
|
|
71
|
+
return !this.isOpen();
|
|
72
|
+
}
|
|
73
|
+
/**
|
|
74
|
+
* Record a successful operation
|
|
75
|
+
*/
|
|
76
|
+
recordSuccess() {
|
|
77
|
+
this.status.successes++;
|
|
78
|
+
this.status.lastSuccess = new Date().toISOString();
|
|
79
|
+
if (this.status.state === 'half-open') {
|
|
80
|
+
if (this.status.successes >= this.config.successThreshold) {
|
|
81
|
+
this.transitionTo('closed');
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
else if (this.status.state === 'closed') {
|
|
85
|
+
// Reset failure count on success
|
|
86
|
+
this.status.failures = 0;
|
|
87
|
+
this.failureTimestamps = [];
|
|
88
|
+
}
|
|
89
|
+
this.saveStatus();
|
|
90
|
+
}
|
|
91
|
+
/**
|
|
92
|
+
* Record a failed operation
|
|
93
|
+
*/
|
|
94
|
+
recordFailure(error) {
|
|
95
|
+
const now = Date.now();
|
|
96
|
+
// Clean old failures outside window
|
|
97
|
+
this.failureTimestamps = this.failureTimestamps.filter((ts) => now - ts < this.config.failureWindow);
|
|
98
|
+
this.failureTimestamps.push(now);
|
|
99
|
+
this.status.failures = this.failureTimestamps.length;
|
|
100
|
+
this.status.lastFailure = new Date().toISOString();
|
|
101
|
+
// Check if should open
|
|
102
|
+
if (this.status.state === 'half-open') {
|
|
103
|
+
this.transitionTo('open');
|
|
104
|
+
}
|
|
105
|
+
else if (this.status.state === 'closed' &&
|
|
106
|
+
this.status.failures >= this.config.failureThreshold) {
|
|
107
|
+
this.transitionTo('open');
|
|
108
|
+
}
|
|
109
|
+
this.saveStatus();
|
|
110
|
+
}
|
|
111
|
+
/**
|
|
112
|
+
* Transition to a new state
|
|
113
|
+
*/
|
|
114
|
+
transitionTo(state) {
|
|
115
|
+
const previousState = this.status.state;
|
|
116
|
+
this.status.state = state;
|
|
117
|
+
if (state === 'open') {
|
|
118
|
+
this.status.openedAt = new Date().toISOString();
|
|
119
|
+
this.status.nextRetryAt = new Date(Date.now() + this.config.resetTimeout).toISOString();
|
|
120
|
+
this.status.successes = 0;
|
|
121
|
+
}
|
|
122
|
+
else if (state === 'closed') {
|
|
123
|
+
this.status.failures = 0;
|
|
124
|
+
this.status.successes = 0;
|
|
125
|
+
this.status.openedAt = undefined;
|
|
126
|
+
this.status.nextRetryAt = undefined;
|
|
127
|
+
this.failureTimestamps = [];
|
|
128
|
+
// Process queued operations
|
|
129
|
+
this.processQueue();
|
|
130
|
+
}
|
|
131
|
+
else if (state === 'half-open') {
|
|
132
|
+
this.status.successes = 0;
|
|
133
|
+
}
|
|
134
|
+
this.logTransition(previousState, state);
|
|
135
|
+
this.saveStatus();
|
|
136
|
+
}
|
|
137
|
+
/**
|
|
138
|
+
* Queue an operation for later retry
|
|
139
|
+
*/
|
|
140
|
+
queueOperation(operation, params) {
|
|
141
|
+
const id = `op-${Date.now()}-${Math.random().toString(36).substring(7)}`;
|
|
142
|
+
this.status.queuedOperations.push({
|
|
143
|
+
id,
|
|
144
|
+
operation,
|
|
145
|
+
params,
|
|
146
|
+
queuedAt: new Date().toISOString(),
|
|
147
|
+
retryCount: 0,
|
|
148
|
+
});
|
|
149
|
+
this.saveStatus();
|
|
150
|
+
return id;
|
|
151
|
+
}
|
|
152
|
+
/**
|
|
153
|
+
* Process queued operations
|
|
154
|
+
*/
|
|
155
|
+
processQueue() {
|
|
156
|
+
// In a real implementation, this would retry queued operations
|
|
157
|
+
// For now, we just clear the queue (operations would need to be re-triggered)
|
|
158
|
+
if (this.status.queuedOperations.length > 0) {
|
|
159
|
+
console.log(`[CircuitBreaker:${this.name}] Circuit closed. ${this.status.queuedOperations.length} queued operations need manual retry.`);
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
/**
|
|
163
|
+
* Get current status
|
|
164
|
+
*/
|
|
165
|
+
getStatus() {
|
|
166
|
+
return { ...this.status };
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* Get circuit name
|
|
170
|
+
*/
|
|
171
|
+
getName() {
|
|
172
|
+
return this.name;
|
|
173
|
+
}
|
|
174
|
+
/**
|
|
175
|
+
* Force reset circuit (for testing/recovery)
|
|
176
|
+
*/
|
|
177
|
+
reset() {
|
|
178
|
+
this.transitionTo('closed');
|
|
179
|
+
this.status.queuedOperations = [];
|
|
180
|
+
this.saveStatus();
|
|
181
|
+
}
|
|
182
|
+
/**
|
|
183
|
+
* Load status from session
|
|
184
|
+
*/
|
|
185
|
+
loadStatus() {
|
|
186
|
+
const sessionPath = path.join(this.projectRoot, '.specweave', 'state', 'auto-session.json');
|
|
187
|
+
if (!fs.existsSync(sessionPath))
|
|
188
|
+
return null;
|
|
189
|
+
try {
|
|
190
|
+
const session = JSON.parse(fs.readFileSync(sessionPath, 'utf-8'));
|
|
191
|
+
return session.circuitBreakers?.[this.name] || null;
|
|
192
|
+
}
|
|
193
|
+
catch {
|
|
194
|
+
return null;
|
|
195
|
+
}
|
|
196
|
+
}
|
|
197
|
+
/**
|
|
198
|
+
* Save status to session
|
|
199
|
+
*/
|
|
200
|
+
saveStatus() {
|
|
201
|
+
const sessionPath = path.join(this.projectRoot, '.specweave', 'state', 'auto-session.json');
|
|
202
|
+
if (!fs.existsSync(sessionPath))
|
|
203
|
+
return;
|
|
204
|
+
try {
|
|
205
|
+
const session = JSON.parse(fs.readFileSync(sessionPath, 'utf-8'));
|
|
206
|
+
session.circuitBreakers = session.circuitBreakers || {};
|
|
207
|
+
session.circuitBreakers[this.name] = this.status;
|
|
208
|
+
fs.writeFileSync(sessionPath, JSON.stringify(session, null, 2));
|
|
209
|
+
}
|
|
210
|
+
catch {
|
|
211
|
+
// Ignore errors
|
|
212
|
+
}
|
|
213
|
+
}
|
|
214
|
+
/**
|
|
215
|
+
* Log state transition
|
|
216
|
+
*/
|
|
217
|
+
logTransition(from, to) {
|
|
218
|
+
const logsDir = path.join(this.projectRoot, '.specweave', 'logs');
|
|
219
|
+
try {
|
|
220
|
+
if (!fs.existsSync(logsDir)) {
|
|
221
|
+
fs.mkdirSync(logsDir, { recursive: true });
|
|
222
|
+
}
|
|
223
|
+
const logEntry = {
|
|
224
|
+
timestamp: new Date().toISOString(),
|
|
225
|
+
circuit: this.name,
|
|
226
|
+
event: 'state_change',
|
|
227
|
+
from,
|
|
228
|
+
to,
|
|
229
|
+
failures: this.status.failures,
|
|
230
|
+
queuedOps: this.status.queuedOperations.length,
|
|
231
|
+
};
|
|
232
|
+
fs.appendFileSync(path.join(logsDir, 'circuit-breakers.log'), JSON.stringify(logEntry) + '\n');
|
|
233
|
+
}
|
|
234
|
+
catch {
|
|
235
|
+
// Ignore logging errors
|
|
236
|
+
}
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
/**
|
|
240
|
+
* Error thrown when circuit is open
|
|
241
|
+
*/
|
|
242
|
+
export class CircuitOpenError extends Error {
|
|
243
|
+
constructor(circuitName, retryAfter) {
|
|
244
|
+
super(`Circuit breaker '${circuitName}' is open. Retry after ${retryAfter}`);
|
|
245
|
+
this.circuitName = circuitName;
|
|
246
|
+
this.retryAfter = retryAfter;
|
|
247
|
+
this.name = 'CircuitOpenError';
|
|
248
|
+
}
|
|
249
|
+
}
|
|
250
|
+
/**
|
|
251
|
+
* Circuit Breaker Registry for managing multiple breakers
|
|
252
|
+
*/
|
|
253
|
+
export class CircuitBreakerRegistry {
|
|
254
|
+
constructor(projectRoot) {
|
|
255
|
+
this.breakers = new Map();
|
|
256
|
+
this.projectRoot = projectRoot;
|
|
257
|
+
}
|
|
258
|
+
/**
|
|
259
|
+
* Get or create a circuit breaker
|
|
260
|
+
*/
|
|
261
|
+
getBreaker(name, config) {
|
|
262
|
+
if (!this.breakers.has(name)) {
|
|
263
|
+
this.breakers.set(name, new CircuitBreaker(name, this.projectRoot, config));
|
|
264
|
+
}
|
|
265
|
+
return this.breakers.get(name);
|
|
266
|
+
}
|
|
267
|
+
/**
|
|
268
|
+
* Get status of all breakers
|
|
269
|
+
*/
|
|
270
|
+
getAllStatus() {
|
|
271
|
+
const status = {};
|
|
272
|
+
for (const [name, breaker] of this.breakers) {
|
|
273
|
+
status[name] = breaker.getStatus();
|
|
274
|
+
}
|
|
275
|
+
return status;
|
|
276
|
+
}
|
|
277
|
+
/**
|
|
278
|
+
* Check if any circuit is open
|
|
279
|
+
*/
|
|
280
|
+
hasOpenCircuit() {
|
|
281
|
+
for (const breaker of this.breakers.values()) {
|
|
282
|
+
if (breaker.isOpen()) {
|
|
283
|
+
return true;
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
return false;
|
|
287
|
+
}
|
|
288
|
+
/**
|
|
289
|
+
* Reset all circuits
|
|
290
|
+
*/
|
|
291
|
+
resetAll() {
|
|
292
|
+
for (const breaker of this.breakers.values()) {
|
|
293
|
+
breaker.reset();
|
|
294
|
+
}
|
|
295
|
+
}
|
|
296
|
+
/**
|
|
297
|
+
* Create default service breakers
|
|
298
|
+
*/
|
|
299
|
+
initializeDefaults() {
|
|
300
|
+
this.getBreaker('github', { failureThreshold: 3, resetTimeout: 60000 });
|
|
301
|
+
this.getBreaker('jira', { failureThreshold: 5, resetTimeout: 120000 });
|
|
302
|
+
this.getBreaker('ado', { failureThreshold: 5, resetTimeout: 120000 });
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
/**
|
|
306
|
+
* Parse rate limit headers and extract retry time
|
|
307
|
+
*/
|
|
308
|
+
export function parseRateLimitHeaders(headers) {
|
|
309
|
+
// GitHub style
|
|
310
|
+
const remaining = parseInt(headers['x-ratelimit-remaining'] || '', 10);
|
|
311
|
+
const reset = parseInt(headers['x-ratelimit-reset'] || '', 10);
|
|
312
|
+
if (!isNaN(remaining) && remaining <= 0 && !isNaN(reset)) {
|
|
313
|
+
return {
|
|
314
|
+
limited: true,
|
|
315
|
+
retryAfter: Math.max(0, reset * 1000 - Date.now()),
|
|
316
|
+
};
|
|
317
|
+
}
|
|
318
|
+
// Standard Retry-After header
|
|
319
|
+
const retryAfter = headers['retry-after'];
|
|
320
|
+
if (retryAfter) {
|
|
321
|
+
const seconds = parseInt(retryAfter, 10);
|
|
322
|
+
if (!isNaN(seconds)) {
|
|
323
|
+
return { limited: true, retryAfter: seconds * 1000 };
|
|
324
|
+
}
|
|
325
|
+
}
|
|
326
|
+
return { limited: false, retryAfter: 0 };
|
|
327
|
+
}
|
|
328
|
+
//# sourceMappingURL=circuit-breaker.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"circuit-breaker.js","sourceRoot":"","sources":["../../../../src/core/auto/circuit-breaker.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Auto Configuration Loader
|
|
3
|
+
* Loads auto settings from .specweave/config.json with sensible defaults
|
|
4
|
+
*/
|
|
5
|
+
import { AutoConfig } from './types.js';
|
|
6
|
+
export interface ConfigLoadResult {
|
|
7
|
+
config: AutoConfig;
|
|
8
|
+
source: 'file' | 'defaults' | 'merged';
|
|
9
|
+
warnings: string[];
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* Load auto configuration from project config file
|
|
13
|
+
*/
|
|
14
|
+
export declare function loadAutoConfig(projectRoot: string): ConfigLoadResult;
|
|
15
|
+
/**
|
|
16
|
+
* Save auto configuration to project config file
|
|
17
|
+
*/
|
|
18
|
+
export declare function saveAutoConfig(projectRoot: string, autoConfig: Partial<AutoConfig>): void;
|
|
19
|
+
/**
|
|
20
|
+
* Check if auto is enabled in config
|
|
21
|
+
*/
|
|
22
|
+
export declare function isAutoEnabled(projectRoot: string): boolean;
|
|
23
|
+
/**
|
|
24
|
+
* Get effective mode based on config and flags
|
|
25
|
+
*/
|
|
26
|
+
export declare function getEffectiveMode(projectRoot: string, flags: {
|
|
27
|
+
auto?: boolean;
|
|
28
|
+
manual?: boolean;
|
|
29
|
+
simple?: boolean;
|
|
30
|
+
}): {
|
|
31
|
+
mode: 'auto' | 'manual';
|
|
32
|
+
simple: boolean;
|
|
33
|
+
};
|
|
34
|
+
//# sourceMappingURL=config.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../../../src/core/auto/config.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,OAAO,EAAE,UAAU,EAAuB,MAAM,YAAY,CAAC;AAK7D,MAAM,WAAW,gBAAgB;IAC/B,MAAM,EAAE,UAAU,CAAC;IACnB,MAAM,EAAE,MAAM,GAAG,UAAU,GAAG,QAAQ,CAAC;IACvC,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,WAAW,EAAE,MAAM,GAAG,gBAAgB,CAyCpE;AAyGD;;GAEG;AACH,wBAAgB,cAAc,CAC5B,WAAW,EAAE,MAAM,EACnB,UAAU,EAAE,OAAO,CAAC,UAAU,CAAC,GAC9B,IAAI,CA6BN;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAO1D;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAC9B,WAAW,EAAE,MAAM,EACnB,KAAK,EAAE;IAAE,IAAI,CAAC,EAAE,OAAO,CAAC;IAAC,MAAM,CAAC,EAAE,OAAO,CAAC;IAAC,MAAM,CAAC,EAAE,OAAO,CAAA;CAAE,GAC5D;IAAE,IAAI,EAAE,MAAM,GAAG,QAAQ,CAAC;IAAC,MAAM,EAAE,OAAO,CAAA;CAAE,CAiB9C"}
|