specweave 1.0.464 → 1.0.466

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 (109) hide show
  1. package/dist/plugins/specweave/lib/vendor/core/ac-test-validator-cli.d.ts +16 -0
  2. package/dist/plugins/specweave/lib/vendor/core/ac-test-validator-cli.js +139 -0
  3. package/dist/plugins/specweave/lib/vendor/core/ac-test-validator-cli.js.map +1 -0
  4. package/dist/plugins/specweave/lib/vendor/core/ac-test-validator.d.ts +111 -0
  5. package/dist/plugins/specweave/lib/vendor/core/ac-test-validator.js +304 -0
  6. package/dist/plugins/specweave/lib/vendor/core/ac-test-validator.js.map +1 -0
  7. package/dist/plugins/specweave/lib/vendor/core/increment/ac-status-manager.d.ts +115 -0
  8. package/dist/plugins/specweave/lib/vendor/core/increment/ac-status-manager.js +359 -0
  9. package/dist/plugins/specweave/lib/vendor/core/increment/ac-status-manager.js.map +1 -0
  10. package/dist/plugins/specweave/lib/vendor/core/increment/active-increment-manager.d.ts +121 -0
  11. package/dist/plugins/specweave/lib/vendor/core/increment/active-increment-manager.js +273 -0
  12. package/dist/plugins/specweave/lib/vendor/core/increment/active-increment-manager.js.map +1 -0
  13. package/dist/plugins/specweave/lib/vendor/core/increment/auto-transition-manager.d.ts +72 -0
  14. package/dist/plugins/specweave/lib/vendor/core/increment/auto-transition-manager.js +237 -0
  15. package/dist/plugins/specweave/lib/vendor/core/increment/auto-transition-manager.js.map +1 -0
  16. package/dist/plugins/specweave/lib/vendor/core/increment/duplicate-detector.d.ts +52 -0
  17. package/dist/plugins/specweave/lib/vendor/core/increment/duplicate-detector.js +281 -0
  18. package/dist/plugins/specweave/lib/vendor/core/increment/duplicate-detector.js.map +1 -0
  19. package/dist/plugins/specweave/lib/vendor/core/increment/metadata-manager.d.ts +278 -0
  20. package/dist/plugins/specweave/lib/vendor/core/increment/metadata-manager.js +925 -0
  21. package/dist/plugins/specweave/lib/vendor/core/increment/metadata-manager.js.map +1 -0
  22. package/dist/plugins/specweave/lib/vendor/core/increment/status-auto-transition.d.ts +113 -0
  23. package/dist/plugins/specweave/lib/vendor/core/increment/status-auto-transition.js +317 -0
  24. package/dist/plugins/specweave/lib/vendor/core/increment/status-auto-transition.js.map +1 -0
  25. package/dist/plugins/specweave/lib/vendor/core/types/increment-metadata.d.ts +442 -0
  26. package/dist/plugins/specweave/lib/vendor/core/types/increment-metadata.js +246 -0
  27. package/dist/plugins/specweave/lib/vendor/core/types/increment-metadata.js.map +1 -0
  28. package/dist/plugins/specweave/lib/vendor/core/universal-auto-create.d.ts +64 -0
  29. package/dist/plugins/specweave/lib/vendor/core/universal-auto-create.js +228 -0
  30. package/dist/plugins/specweave/lib/vendor/core/universal-auto-create.js.map +1 -0
  31. package/dist/plugins/specweave/lib/vendor/generators/spec/task-parser.d.ts +95 -0
  32. package/dist/plugins/specweave/lib/vendor/generators/spec/task-parser.js +300 -0
  33. package/dist/plugins/specweave/lib/vendor/generators/spec/task-parser.js.map +1 -0
  34. package/dist/plugins/specweave/lib/vendor/sync/config.d.ts +73 -0
  35. package/dist/plugins/specweave/lib/vendor/sync/config.js +132 -0
  36. package/dist/plugins/specweave/lib/vendor/sync/config.js.map +1 -0
  37. package/dist/plugins/specweave/lib/vendor/sync/github-reconciler.d.ts +163 -0
  38. package/dist/plugins/specweave/lib/vendor/sync/github-reconciler.js +898 -0
  39. package/dist/plugins/specweave/lib/vendor/sync/github-reconciler.js.map +1 -0
  40. package/dist/plugins/specweave/lib/vendor/sync/provider-router.d.ts +86 -0
  41. package/dist/plugins/specweave/lib/vendor/sync/provider-router.js +147 -0
  42. package/dist/plugins/specweave/lib/vendor/sync/provider-router.js.map +1 -0
  43. package/dist/plugins/specweave/lib/vendor/sync/status-mapper.d.ts +120 -0
  44. package/dist/plugins/specweave/lib/vendor/sync/status-mapper.js +164 -0
  45. package/dist/plugins/specweave/lib/vendor/sync/status-mapper.js.map +1 -0
  46. package/dist/plugins/specweave/lib/vendor/utils/auth-helpers.d.ts +151 -0
  47. package/dist/plugins/specweave/lib/vendor/utils/auth-helpers.js +359 -0
  48. package/dist/plugins/specweave/lib/vendor/utils/auth-helpers.js.map +1 -0
  49. package/dist/plugins/specweave/lib/vendor/utils/chalk-fallback.d.ts +38 -0
  50. package/dist/plugins/specweave/lib/vendor/utils/chalk-fallback.js +118 -0
  51. package/dist/plugins/specweave/lib/vendor/utils/chalk-fallback.js.map +1 -0
  52. package/dist/plugins/specweave/lib/vendor/utils/clean-env.d.ts +47 -0
  53. package/dist/plugins/specweave/lib/vendor/utils/clean-env.js +63 -0
  54. package/dist/plugins/specweave/lib/vendor/utils/clean-env.js.map +1 -0
  55. package/dist/plugins/specweave/lib/vendor/utils/credential-masker.d.ts +118 -0
  56. package/dist/plugins/specweave/lib/vendor/utils/credential-masker.js +275 -0
  57. package/dist/plugins/specweave/lib/vendor/utils/credential-masker.js.map +1 -0
  58. package/dist/plugins/specweave/lib/vendor/utils/execFileNoThrow.d.ts +99 -0
  59. package/dist/plugins/specweave/lib/vendor/utils/execFileNoThrow.js +149 -0
  60. package/dist/plugins/specweave/lib/vendor/utils/execFileNoThrow.js.map +1 -0
  61. package/dist/plugins/specweave/lib/vendor/utils/feature-id-derivation.d.ts +63 -0
  62. package/dist/plugins/specweave/lib/vendor/utils/feature-id-derivation.js +85 -0
  63. package/dist/plugins/specweave/lib/vendor/utils/feature-id-derivation.js.map +1 -0
  64. package/dist/plugins/specweave/lib/vendor/utils/fs-native.d.ts +219 -0
  65. package/dist/plugins/specweave/lib/vendor/utils/fs-native.js +397 -0
  66. package/dist/plugins/specweave/lib/vendor/utils/fs-native.js.map +1 -0
  67. package/dist/plugins/specweave/lib/vendor/utils/logger.d.ts +56 -0
  68. package/dist/plugins/specweave/lib/vendor/utils/logger.js +123 -0
  69. package/dist/plugins/specweave/lib/vendor/utils/logger.js.map +1 -0
  70. package/dist/plugins/specweave/lib/vendor/utils/translation.d.ts +187 -0
  71. package/dist/plugins/specweave/lib/vendor/utils/translation.js +414 -0
  72. package/dist/plugins/specweave/lib/vendor/utils/translation.js.map +1 -0
  73. package/dist/plugins/specweave-ado/lib/ado-ac-checkbox-sync.js +1 -1
  74. package/dist/plugins/specweave-ado/lib/ado-ac-checkbox-sync.js.map +1 -1
  75. package/dist/plugins/specweave-ado/lib/ado-spec-sync.js +1 -1
  76. package/dist/plugins/specweave-ado/lib/ado-spec-sync.js.map +1 -1
  77. package/dist/plugins/specweave-github/lib/github-ac-checkbox-sync.js +2 -2
  78. package/dist/plugins/specweave-github/lib/github-ac-checkbox-sync.js.map +1 -1
  79. package/dist/plugins/specweave-github/lib/github-feature-sync.d.ts.map +1 -1
  80. package/dist/plugins/specweave-github/lib/github-feature-sync.js +13 -4
  81. package/dist/plugins/specweave-github/lib/github-feature-sync.js.map +1 -1
  82. package/dist/plugins/specweave-jira/lib/jira-ac-checkbox-sync.js +1 -1
  83. package/dist/plugins/specweave-jira/lib/jira-ac-checkbox-sync.js.map +1 -1
  84. package/dist/plugins/specweave-jira/lib/jira-spec-sync.js +1 -1
  85. package/dist/plugins/specweave-jira/lib/jira-spec-sync.js.map +1 -1
  86. package/dist/src/sync/spec-to-living-docs-sync.js +1 -1
  87. package/dist/src/sync/spec-to-living-docs-sync.js.map +1 -1
  88. package/package.json +1 -1
  89. package/plugins/specweave/lib/vendor/utils/auth-helpers.d.ts +151 -0
  90. package/plugins/specweave/lib/vendor/utils/auth-helpers.js +359 -0
  91. package/plugins/specweave/lib/vendor/utils/auth-helpers.js.map +1 -0
  92. package/plugins/specweave/skills/team-lead/SKILL.md +150 -56
  93. package/plugins/specweave/skills/team-lead/agents/backend.md +13 -9
  94. package/plugins/specweave/skills/team-lead/agents/database.md +13 -9
  95. package/plugins/specweave/skills/team-lead/agents/frontend.md +12 -8
  96. package/plugins/specweave/skills/team-lead/agents/security.md +13 -9
  97. package/plugins/specweave/skills/team-lead/agents/testing.md +12 -8
  98. package/plugins/specweave-ado/lib/ado-ac-checkbox-sync.js +1 -1
  99. package/plugins/specweave-ado/lib/ado-ac-checkbox-sync.ts +1 -1
  100. package/plugins/specweave-ado/lib/ado-spec-sync.js +1 -1
  101. package/plugins/specweave-ado/lib/ado-spec-sync.ts +1 -1
  102. package/plugins/specweave-github/lib/github-ac-checkbox-sync.js +1 -1
  103. package/plugins/specweave-github/lib/github-ac-checkbox-sync.ts +2 -2
  104. package/plugins/specweave-github/lib/github-feature-sync.js +11 -3
  105. package/plugins/specweave-github/lib/github-feature-sync.ts +13 -4
  106. package/plugins/specweave-jira/lib/jira-ac-checkbox-sync.js +1 -1
  107. package/plugins/specweave-jira/lib/jira-ac-checkbox-sync.ts +1 -1
  108. package/plugins/specweave-jira/lib/jira-spec-sync.js +1 -1
  109. package/plugins/specweave-jira/lib/jira-spec-sync.ts +1 -1
@@ -0,0 +1,151 @@
1
+ /**
2
+ * Authentication Helpers for Issue Tracker Integration
3
+ *
4
+ * Provides unified authentication detection for GitHub, Azure DevOps, and Jira
5
+ * Works in both CLI (init flow) and test environments
6
+ *
7
+ * @module utils/auth-helpers
8
+ */
9
+ /**
10
+ * Check if a GitHub token is an OAuth token (gho_ prefix)
11
+ *
12
+ * OAuth tokens from `gh auth` typically lack `repo` scope for private repositories.
13
+ * Only PATs (ghp_) or Fine-grained tokens (github_pat_) have explicit repo access.
14
+ *
15
+ * Token prefixes:
16
+ * - gho_ = OAuth App token (from gh auth) - may lack repo scope!
17
+ * - ghp_ = Classic Personal Access Token - has explicit scopes
18
+ * - ghs_ = GitHub App server-to-server token
19
+ * - ghu_ = GitHub App user-to-server token
20
+ * - github_pat_ = Fine-grained Personal Access Token
21
+ */
22
+ export declare function isOAuthToken(token: string): boolean;
23
+ /**
24
+ * Check if a GitHub token is a Personal Access Token (classic or fine-grained)
25
+ * These tokens have explicit repo scope and work with private repositories.
26
+ */
27
+ export declare function isPersonalAccessToken(token: string): boolean;
28
+ export interface GitHubAuth {
29
+ token: string;
30
+ source: 'GITHUB_TOKEN' | 'GH_TOKEN' | 'gh-cli' | 'none';
31
+ /**
32
+ * Whether this is an OAuth token (gho_ prefix) which may lack repo scope.
33
+ * OAuth tokens from `gh auth` typically cannot access private repos unless
34
+ * the user explicitly granted repo scope during authentication.
35
+ */
36
+ isOAuthToken?: boolean;
37
+ }
38
+ export interface AzureDevOpsAuth {
39
+ pat: string;
40
+ org: string;
41
+ project: string;
42
+ }
43
+ export interface JiraAuth {
44
+ token: string;
45
+ email: string;
46
+ domain: string;
47
+ }
48
+ /**
49
+ * Get GitHub authentication token from project .env file
50
+ * Priority: .env GITHUB_TOKEN > .env GH_TOKEN > process.env > gh CLI
51
+ *
52
+ * CRITICAL (2025-11-26): This function MUST be used when projectRoot is available
53
+ * to properly load tokens from .env file. The original getGitHubAuth() only
54
+ * reads process.env which is empty unless dotenv is explicitly loaded.
55
+ *
56
+ * @param projectRoot - Path to project root containing .env file
57
+ * @returns GitHub authentication with source information
58
+ */
59
+ export declare function getGitHubAuthFromProject(projectRoot: string): GitHubAuth;
60
+ /**
61
+ * Get GitHub authentication token
62
+ * Priority: GITHUB_TOKEN (CI) > GH_TOKEN (custom) > gh CLI config (local)
63
+ *
64
+ * WARNING: This function only reads from process.env, NOT from .env files!
65
+ * If you have access to projectRoot, use getGitHubAuthFromProject() instead.
66
+ */
67
+ export declare function getGitHubAuth(): GitHubAuth;
68
+ /**
69
+ * Get Azure DevOps authentication from project .env file
70
+ * Priority: .env file > process.env
71
+ *
72
+ * CRITICAL (2025-12-04): This function MUST be used when projectRoot is available
73
+ * to properly load tokens from .env file. The original getAzureDevOpsAuth() only
74
+ * reads process.env which is empty unless dotenv is explicitly loaded.
75
+ *
76
+ * @param projectRoot - Path to project root containing .env file
77
+ * @returns Azure DevOps authentication or null if not found
78
+ */
79
+ export declare function getAzureDevOpsAuthFromProject(projectRoot: string): AzureDevOpsAuth | null;
80
+ /**
81
+ * Get Azure DevOps authentication
82
+ * Requires: AZURE_DEVOPS_PAT, AZURE_DEVOPS_ORG, AZURE_DEVOPS_PROJECT
83
+ *
84
+ * WARNING: This function only reads from process.env, NOT from .env files!
85
+ * If you have access to projectRoot, use getAzureDevOpsAuthFromProject() instead.
86
+ */
87
+ export declare function getAzureDevOpsAuth(): AzureDevOpsAuth | null;
88
+ /**
89
+ * Get Jira authentication
90
+ * Requires: JIRA_API_TOKEN, JIRA_EMAIL, JIRA_DOMAIN
91
+ */
92
+ export declare function getJiraAuth(): JiraAuth | null;
93
+ /**
94
+ * Check if integration tests should run
95
+ * Returns true if RUN_INTEGRATION_TESTS=true or if in CI environment
96
+ */
97
+ export declare function shouldRunIntegrationTests(): boolean;
98
+ /**
99
+ * Check if credentials are available for a service
100
+ */
101
+ export declare function hasGitHubCredentials(): boolean;
102
+ /**
103
+ * Check if GitHub credentials are available (project-aware)
104
+ * Uses getGitHubAuthFromProject() to also check .env file
105
+ *
106
+ * @param projectRoot - Path to project root containing .env file
107
+ * @returns True if credentials are available
108
+ */
109
+ export declare function hasGitHubCredentialsFromProject(projectRoot: string): boolean;
110
+ export declare function hasAzureDevOpsCredentials(): boolean;
111
+ /**
112
+ * Check if Azure DevOps credentials are available (project-aware)
113
+ * Uses getAzureDevOpsAuthFromProject() to also check .env file
114
+ *
115
+ * @param projectRoot - Path to project root containing .env file
116
+ * @returns True if credentials are available
117
+ */
118
+ export declare function hasAzureDevOpsCredentialsFromProject(projectRoot: string): boolean;
119
+ export declare function hasJiraCredentials(): boolean;
120
+ /**
121
+ * Get Jira authentication from project files
122
+ *
123
+ * CRITICAL (2025-12-12): This function MUST be used when projectRoot is available.
124
+ *
125
+ * Configuration sources (ADR-0194 compliant):
126
+ * - Domain: config.json → issueTracker.domain (CONFIGURATION, committed)
127
+ * - Token: .env → JIRA_API_TOKEN (SECRET, gitignored)
128
+ * - Email: .env → JIRA_EMAIL (SECRET, gitignored)
129
+ *
130
+ * @param projectRoot - Path to project root containing .env and .specweave/config.json
131
+ * @returns Jira authentication or null if not found
132
+ */
133
+ export declare function getJiraAuthFromProject(projectRoot: string): JiraAuth | null;
134
+ /**
135
+ * Check if Jira credentials are available (project-aware)
136
+ * Uses getJiraAuthFromProject() to also check .env file
137
+ *
138
+ * @param projectRoot - Path to project root containing .env file
139
+ * @returns True if credentials are available
140
+ */
141
+ export declare function hasJiraCredentialsFromProject(projectRoot: string): boolean;
142
+ /**
143
+ * Get credential status summary (for debugging)
144
+ */
145
+ export declare function getCredentialStatus(): {
146
+ github: string;
147
+ ado: boolean;
148
+ jira: boolean;
149
+ integrationTestsEnabled: boolean;
150
+ };
151
+ //# sourceMappingURL=auth-helpers.d.ts.map
@@ -0,0 +1,359 @@
1
+ /**
2
+ * Authentication Helpers for Issue Tracker Integration
3
+ *
4
+ * Provides unified authentication detection for GitHub, Azure DevOps, and Jira
5
+ * Works in both CLI (init flow) and test environments
6
+ *
7
+ * @module utils/auth-helpers
8
+ */
9
+ import * as fs from 'fs';
10
+ import * as path from 'path';
11
+ import * as os from 'os';
12
+ import * as yaml from 'js-yaml';
13
+ import { execSync } from 'child_process';
14
+ /**
15
+ * Check if a GitHub token is an OAuth token (gho_ prefix)
16
+ *
17
+ * OAuth tokens from `gh auth` typically lack `repo` scope for private repositories.
18
+ * Only PATs (ghp_) or Fine-grained tokens (github_pat_) have explicit repo access.
19
+ *
20
+ * Token prefixes:
21
+ * - gho_ = OAuth App token (from gh auth) - may lack repo scope!
22
+ * - ghp_ = Classic Personal Access Token - has explicit scopes
23
+ * - ghs_ = GitHub App server-to-server token
24
+ * - ghu_ = GitHub App user-to-server token
25
+ * - github_pat_ = Fine-grained Personal Access Token
26
+ */
27
+ export function isOAuthToken(token) {
28
+ return token.startsWith('gho_');
29
+ }
30
+ /**
31
+ * Check if a GitHub token is a Personal Access Token (classic or fine-grained)
32
+ * These tokens have explicit repo scope and work with private repositories.
33
+ */
34
+ export function isPersonalAccessToken(token) {
35
+ return token.startsWith('ghp_') || token.startsWith('github_pat_');
36
+ }
37
+ /**
38
+ * Parse a simple .env file and return key-value pairs
39
+ * (Inline implementation to avoid circular dependencies)
40
+ */
41
+ function parseEnvFileSimple(content) {
42
+ const result = {};
43
+ const lines = content.split('\n');
44
+ for (const line of lines) {
45
+ const trimmed = line.trim();
46
+ if (!trimmed || trimmed.startsWith('#'))
47
+ continue;
48
+ const eqIndex = trimmed.indexOf('=');
49
+ if (eqIndex === -1)
50
+ continue;
51
+ const key = trimmed.slice(0, eqIndex).trim();
52
+ let value = trimmed.slice(eqIndex + 1).trim();
53
+ // Remove surrounding quotes if present
54
+ if ((value.startsWith('"') && value.endsWith('"')) ||
55
+ (value.startsWith("'") && value.endsWith("'"))) {
56
+ value = value.slice(1, -1);
57
+ }
58
+ result[key] = value;
59
+ }
60
+ return result;
61
+ }
62
+ /**
63
+ * Get GitHub authentication token from project .env file
64
+ * Priority: .env GITHUB_TOKEN > .env GH_TOKEN > process.env > gh CLI
65
+ *
66
+ * CRITICAL (2025-11-26): This function MUST be used when projectRoot is available
67
+ * to properly load tokens from .env file. The original getGitHubAuth() only
68
+ * reads process.env which is empty unless dotenv is explicitly loaded.
69
+ *
70
+ * @param projectRoot - Path to project root containing .env file
71
+ * @returns GitHub authentication with source information
72
+ */
73
+ export function getGitHubAuthFromProject(projectRoot) {
74
+ // 1. First, try to read from project .env file
75
+ try {
76
+ const envPath = path.join(projectRoot, '.env');
77
+ if (fs.existsSync(envPath)) {
78
+ const content = fs.readFileSync(envPath, 'utf-8');
79
+ const envVars = parseEnvFileSimple(content);
80
+ // Check GITHUB_TOKEN first (standard)
81
+ if (envVars.GITHUB_TOKEN) {
82
+ return {
83
+ token: envVars.GITHUB_TOKEN,
84
+ source: 'GITHUB_TOKEN',
85
+ isOAuthToken: isOAuthToken(envVars.GITHUB_TOKEN)
86
+ };
87
+ }
88
+ // Check GH_TOKEN (alternative)
89
+ if (envVars.GH_TOKEN) {
90
+ return {
91
+ token: envVars.GH_TOKEN,
92
+ source: 'GH_TOKEN',
93
+ isOAuthToken: isOAuthToken(envVars.GH_TOKEN)
94
+ };
95
+ }
96
+ }
97
+ }
98
+ catch {
99
+ // Silently fail - .env file is optional
100
+ }
101
+ // 2. Fall back to existing getGitHubAuth() for process.env and gh CLI
102
+ return getGitHubAuth();
103
+ }
104
+ /**
105
+ * Get GitHub authentication token
106
+ * Priority: GITHUB_TOKEN (CI) > GH_TOKEN (custom) > gh CLI config (local)
107
+ *
108
+ * WARNING: This function only reads from process.env, NOT from .env files!
109
+ * If you have access to projectRoot, use getGitHubAuthFromProject() instead.
110
+ */
111
+ export function getGitHubAuth() {
112
+ // 1. Check GITHUB_TOKEN (auto-provided in GitHub Actions)
113
+ if (process.env.GITHUB_TOKEN) {
114
+ return {
115
+ token: process.env.GITHUB_TOKEN,
116
+ source: 'GITHUB_TOKEN',
117
+ isOAuthToken: isOAuthToken(process.env.GITHUB_TOKEN)
118
+ };
119
+ }
120
+ // 2. Check GH_TOKEN (custom PAT from .env)
121
+ if (process.env.GH_TOKEN) {
122
+ return {
123
+ token: process.env.GH_TOKEN,
124
+ source: 'GH_TOKEN',
125
+ isOAuthToken: isOAuthToken(process.env.GH_TOKEN)
126
+ };
127
+ }
128
+ // 3. Try to get token via gh CLI command (works with Keychain, plain-text, etc.)
129
+ try {
130
+ const token = execSync('gh auth token', { encoding: 'utf-8', stdio: ['pipe', 'pipe', 'pipe'] }).trim();
131
+ if (token && token.length > 0) {
132
+ return { token, source: 'gh-cli', isOAuthToken: isOAuthToken(token) };
133
+ }
134
+ }
135
+ catch (error) {
136
+ // gh CLI not installed or not authenticated - silently fail
137
+ }
138
+ // 4. Fallback: Try to parse gh CLI config directly (~/.config/gh/hosts.yml)
139
+ // This covers edge cases where gh CLI isn't available but config file exists
140
+ try {
141
+ const ghConfigPath = path.join(os.homedir(), '.config', 'gh', 'hosts.yml');
142
+ if (fs.existsSync(ghConfigPath)) {
143
+ // Security: Use JSON_SCHEMA to prevent arbitrary code execution via YAML
144
+ // This only allows JSON-safe types (strings, numbers, booleans, arrays, objects)
145
+ const config = yaml.load(fs.readFileSync(ghConfigPath, 'utf8'), {
146
+ schema: yaml.JSON_SCHEMA
147
+ });
148
+ const token = config?.['github.com']?.oauth_token;
149
+ if (token) {
150
+ return { token, source: 'gh-cli', isOAuthToken: isOAuthToken(token) };
151
+ }
152
+ }
153
+ }
154
+ catch (error) {
155
+ // Silently fail - gh CLI config is optional
156
+ }
157
+ return { token: '', source: 'none', isOAuthToken: false };
158
+ }
159
+ /**
160
+ * Get Azure DevOps authentication from project .env file
161
+ * Priority: .env file > process.env
162
+ *
163
+ * CRITICAL (2025-12-04): This function MUST be used when projectRoot is available
164
+ * to properly load tokens from .env file. The original getAzureDevOpsAuth() only
165
+ * reads process.env which is empty unless dotenv is explicitly loaded.
166
+ *
167
+ * @param projectRoot - Path to project root containing .env file
168
+ * @returns Azure DevOps authentication or null if not found
169
+ */
170
+ export function getAzureDevOpsAuthFromProject(projectRoot) {
171
+ // 1. First, try to read from project .env file
172
+ try {
173
+ const envPath = path.join(projectRoot, '.env');
174
+ if (fs.existsSync(envPath)) {
175
+ const content = fs.readFileSync(envPath, 'utf-8');
176
+ const envVars = parseEnvFileSimple(content);
177
+ const pat = envVars.AZURE_DEVOPS_PAT;
178
+ const org = envVars.AZURE_DEVOPS_ORG;
179
+ const project = envVars.AZURE_DEVOPS_PROJECT;
180
+ if (pat) {
181
+ // PAT found in .env - return it (org/project might come from config.json)
182
+ return {
183
+ pat,
184
+ org: org || process.env.AZURE_DEVOPS_ORG || '',
185
+ project: project || process.env.AZURE_DEVOPS_PROJECT || ''
186
+ };
187
+ }
188
+ }
189
+ }
190
+ catch {
191
+ // Silently fail - .env file is optional
192
+ }
193
+ // 2. Fall back to process.env
194
+ return getAzureDevOpsAuth();
195
+ }
196
+ /**
197
+ * Get Azure DevOps authentication
198
+ * Requires: AZURE_DEVOPS_PAT, AZURE_DEVOPS_ORG, AZURE_DEVOPS_PROJECT
199
+ *
200
+ * WARNING: This function only reads from process.env, NOT from .env files!
201
+ * If you have access to projectRoot, use getAzureDevOpsAuthFromProject() instead.
202
+ */
203
+ export function getAzureDevOpsAuth() {
204
+ const pat = process.env.AZURE_DEVOPS_PAT;
205
+ const org = process.env.AZURE_DEVOPS_ORG;
206
+ const project = process.env.AZURE_DEVOPS_PROJECT;
207
+ if (!pat || !org || !project) {
208
+ return null;
209
+ }
210
+ return { pat, org, project };
211
+ }
212
+ /**
213
+ * Get Jira authentication
214
+ * Requires: JIRA_API_TOKEN, JIRA_EMAIL, JIRA_DOMAIN
215
+ */
216
+ export function getJiraAuth() {
217
+ const token = process.env.JIRA_API_TOKEN;
218
+ const email = process.env.JIRA_EMAIL;
219
+ const domain = process.env.JIRA_DOMAIN;
220
+ if (!token || !email || !domain) {
221
+ return null;
222
+ }
223
+ return { token, email, domain };
224
+ }
225
+ /**
226
+ * Check if integration tests should run
227
+ * Returns true if RUN_INTEGRATION_TESTS=true or if in CI environment
228
+ */
229
+ export function shouldRunIntegrationTests() {
230
+ // Explicitly enabled
231
+ if (process.env.RUN_INTEGRATION_TESTS === 'true') {
232
+ return true;
233
+ }
234
+ // In CI environment (GitHub Actions)
235
+ if (process.env.CI === 'true') {
236
+ return true;
237
+ }
238
+ return false;
239
+ }
240
+ /**
241
+ * Check if credentials are available for a service
242
+ */
243
+ export function hasGitHubCredentials() {
244
+ const auth = getGitHubAuth();
245
+ return auth.source !== 'none';
246
+ }
247
+ /**
248
+ * Check if GitHub credentials are available (project-aware)
249
+ * Uses getGitHubAuthFromProject() to also check .env file
250
+ *
251
+ * @param projectRoot - Path to project root containing .env file
252
+ * @returns True if credentials are available
253
+ */
254
+ export function hasGitHubCredentialsFromProject(projectRoot) {
255
+ const auth = getGitHubAuthFromProject(projectRoot);
256
+ return auth.source !== 'none';
257
+ }
258
+ export function hasAzureDevOpsCredentials() {
259
+ return getAzureDevOpsAuth() !== null;
260
+ }
261
+ /**
262
+ * Check if Azure DevOps credentials are available (project-aware)
263
+ * Uses getAzureDevOpsAuthFromProject() to also check .env file
264
+ *
265
+ * @param projectRoot - Path to project root containing .env file
266
+ * @returns True if credentials are available
267
+ */
268
+ export function hasAzureDevOpsCredentialsFromProject(projectRoot) {
269
+ const auth = getAzureDevOpsAuthFromProject(projectRoot);
270
+ return auth !== null && !!auth.pat;
271
+ }
272
+ export function hasJiraCredentials() {
273
+ return getJiraAuth() !== null;
274
+ }
275
+ /**
276
+ * Get Jira authentication from project files
277
+ *
278
+ * CRITICAL (2025-12-12): This function MUST be used when projectRoot is available.
279
+ *
280
+ * Configuration sources (ADR-0194 compliant):
281
+ * - Domain: config.json → issueTracker.domain (CONFIGURATION, committed)
282
+ * - Token: .env → JIRA_API_TOKEN (SECRET, gitignored)
283
+ * - Email: .env → JIRA_EMAIL (SECRET, gitignored)
284
+ *
285
+ * @param projectRoot - Path to project root containing .env and .specweave/config.json
286
+ * @returns Jira authentication or null if not found
287
+ */
288
+ export function getJiraAuthFromProject(projectRoot) {
289
+ let domain = '';
290
+ let token = '';
291
+ let email = '';
292
+ // 1. Read DOMAIN from config.json (configuration, not secret)
293
+ try {
294
+ const configPath = path.join(projectRoot, '.specweave', 'config.json');
295
+ if (fs.existsSync(configPath)) {
296
+ const configContent = fs.readFileSync(configPath, 'utf-8');
297
+ const config = JSON.parse(configContent);
298
+ domain = config.issueTracker?.domain || '';
299
+ }
300
+ }
301
+ catch {
302
+ // Silently fail - config.json is optional
303
+ }
304
+ // 2. Read SECRETS from .env file (token and email)
305
+ try {
306
+ const envPath = path.join(projectRoot, '.env');
307
+ if (fs.existsSync(envPath)) {
308
+ const content = fs.readFileSync(envPath, 'utf-8');
309
+ const envVars = parseEnvFileSimple(content);
310
+ token = envVars.JIRA_API_TOKEN || '';
311
+ email = envVars.JIRA_EMAIL || '';
312
+ // DEPRECATED: Support JIRA_DOMAIN in .env for backwards compatibility
313
+ // New projects should use config.json → issueTracker.domain
314
+ if (!domain && (envVars.JIRA_HOST || envVars.JIRA_DOMAIN)) {
315
+ domain = envVars.JIRA_HOST || envVars.JIRA_DOMAIN || '';
316
+ }
317
+ }
318
+ }
319
+ catch {
320
+ // Silently fail - .env file is optional
321
+ }
322
+ // 3. Fall back to process.env for secrets (if not found in .env)
323
+ if (!token)
324
+ token = process.env.JIRA_API_TOKEN || '';
325
+ if (!email)
326
+ email = process.env.JIRA_EMAIL || '';
327
+ // DEPRECATED: process.env fallback for domain
328
+ if (!domain)
329
+ domain = process.env.JIRA_DOMAIN || process.env.JIRA_HOST || '';
330
+ // All three required
331
+ if (token && email && domain) {
332
+ return { token, email, domain };
333
+ }
334
+ return null;
335
+ }
336
+ /**
337
+ * Check if Jira credentials are available (project-aware)
338
+ * Uses getJiraAuthFromProject() to also check .env file
339
+ *
340
+ * @param projectRoot - Path to project root containing .env file
341
+ * @returns True if credentials are available
342
+ */
343
+ export function hasJiraCredentialsFromProject(projectRoot) {
344
+ const auth = getJiraAuthFromProject(projectRoot);
345
+ return auth !== null;
346
+ }
347
+ /**
348
+ * Get credential status summary (for debugging)
349
+ */
350
+ export function getCredentialStatus() {
351
+ const github = getGitHubAuth();
352
+ return {
353
+ github: github.source,
354
+ ado: hasAzureDevOpsCredentials(),
355
+ jira: hasJiraCredentials(),
356
+ integrationTestsEnabled: shouldRunIntegrationTests()
357
+ };
358
+ }
359
+ //# sourceMappingURL=auth-helpers.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth-helpers.js","sourceRoot":"","sources":["../../../src/utils/auth-helpers.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,38 @@
1
+ /**
2
+ * Chalk Fallback Utility
3
+ *
4
+ * Provides chalk-like API for colored console output with graceful fallback
5
+ * to plain text when chalk is not available (e.g., in marketplace plugins).
6
+ *
7
+ * This enables AC test validator to work in both:
8
+ * 1. Full npm-installed environments (uses real chalk)
9
+ * 2. Marketplace plugin environments (uses ANSI codes or plain text)
10
+ */
11
+ type ChalkInput = string | number;
12
+ interface ChalkFn {
13
+ (text: ChalkInput): string;
14
+ bold: ChalkFn;
15
+ }
16
+ interface ChalkInstance {
17
+ red: ChalkFn;
18
+ green: ChalkFn;
19
+ yellow: ChalkFn;
20
+ blue: ChalkFn;
21
+ gray: ChalkFn;
22
+ bold: ChalkFn & {
23
+ (text: string): string;
24
+ };
25
+ }
26
+ /**
27
+ * Chalk-compatible API using ANSI codes
28
+ * Falls back to plain text if terminal doesn't support colors
29
+ */
30
+ export declare const chalkFallback: ChalkInstance;
31
+ export declare function getChalk(): Promise<ChalkInstance>;
32
+ /**
33
+ * Synchronous chalk getter - uses fallback if chalk wasn't pre-loaded
34
+ * Call getChalk() at module init to try loading real chalk first
35
+ */
36
+ export declare function getChalkSync(): ChalkInstance;
37
+ export default chalkFallback;
38
+ //# sourceMappingURL=chalk-fallback.d.ts.map
@@ -0,0 +1,118 @@
1
+ /**
2
+ * Chalk Fallback Utility
3
+ *
4
+ * Provides chalk-like API for colored console output with graceful fallback
5
+ * to plain text when chalk is not available (e.g., in marketplace plugins).
6
+ *
7
+ * This enables AC test validator to work in both:
8
+ * 1. Full npm-installed environments (uses real chalk)
9
+ * 2. Marketplace plugin environments (uses ANSI codes or plain text)
10
+ */
11
+ // Simple ANSI color codes for terminal output
12
+ const ANSI = {
13
+ reset: '\x1b[0m',
14
+ bold: '\x1b[1m',
15
+ red: '\x1b[31m',
16
+ green: '\x1b[32m',
17
+ yellow: '\x1b[33m',
18
+ blue: '\x1b[34m',
19
+ gray: '\x1b[90m',
20
+ };
21
+ // Check if we're in a TTY that supports colors
22
+ const supportsColor = process.stdout?.isTTY ?? false;
23
+ /**
24
+ * Creates a chalk-like color function
25
+ */
26
+ function createColorFn(colorCode) {
27
+ const fn = ((text) => {
28
+ const str = String(text);
29
+ if (!supportsColor)
30
+ return str;
31
+ return `${colorCode}${str}${ANSI.reset}`;
32
+ });
33
+ // Add chainable modifiers
34
+ fn.bold = ((text) => {
35
+ const str = String(text);
36
+ if (!supportsColor)
37
+ return str;
38
+ return `${ANSI.bold}${colorCode}${str}${ANSI.reset}`;
39
+ });
40
+ return fn;
41
+ }
42
+ /**
43
+ * Creates a bold color function
44
+ */
45
+ function createBoldColorFn(colorCode) {
46
+ const fn = ((text) => {
47
+ const str = String(text);
48
+ if (!supportsColor)
49
+ return str;
50
+ return `${ANSI.bold}${colorCode}${str}${ANSI.reset}`;
51
+ });
52
+ fn.bold = fn;
53
+ return fn;
54
+ }
55
+ /**
56
+ * Chalk-compatible API using ANSI codes
57
+ * Falls back to plain text if terminal doesn't support colors
58
+ */
59
+ export const chalkFallback = {
60
+ red: createColorFn(ANSI.red),
61
+ green: createColorFn(ANSI.green),
62
+ yellow: createColorFn(ANSI.yellow),
63
+ blue: createColorFn(ANSI.blue),
64
+ gray: createColorFn(ANSI.gray),
65
+ bold: Object.assign(((text) => {
66
+ const str = String(text);
67
+ if (!supportsColor)
68
+ return str;
69
+ return `${ANSI.bold}${str}${ANSI.reset}`;
70
+ }), {
71
+ bold: ((text) => {
72
+ const str = String(text);
73
+ if (!supportsColor)
74
+ return str;
75
+ return `${ANSI.bold}${str}${ANSI.reset}`;
76
+ }),
77
+ }),
78
+ };
79
+ // Add nested color methods to bold
80
+ chalkFallback.bold.red = createBoldColorFn(ANSI.red);
81
+ chalkFallback.bold.green = createBoldColorFn(ANSI.green);
82
+ chalkFallback.bold.yellow = createBoldColorFn(ANSI.yellow);
83
+ chalkFallback.bold.blue = createBoldColorFn(ANSI.blue);
84
+ chalkFallback.bold.gray = createBoldColorFn(ANSI.gray);
85
+ // Add bold method to color functions for chaining like chalk.green.bold()
86
+ chalkFallback.red.bold = createBoldColorFn(ANSI.red);
87
+ chalkFallback.green.bold = createBoldColorFn(ANSI.green);
88
+ chalkFallback.yellow.bold = createBoldColorFn(ANSI.yellow);
89
+ chalkFallback.blue.bold = createBoldColorFn(ANSI.blue);
90
+ chalkFallback.gray.bold = createBoldColorFn(ANSI.gray);
91
+ /**
92
+ * Try to import chalk, fall back to ANSI implementation
93
+ */
94
+ let resolvedChalk = null;
95
+ export async function getChalk() {
96
+ if (resolvedChalk)
97
+ return resolvedChalk;
98
+ try {
99
+ // Try to dynamically import chalk
100
+ const chalkModule = await import('chalk');
101
+ resolvedChalk = chalkModule.default;
102
+ return resolvedChalk;
103
+ }
104
+ catch {
105
+ // Chalk not available, use fallback
106
+ resolvedChalk = chalkFallback;
107
+ return resolvedChalk;
108
+ }
109
+ }
110
+ /**
111
+ * Synchronous chalk getter - uses fallback if chalk wasn't pre-loaded
112
+ * Call getChalk() at module init to try loading real chalk first
113
+ */
114
+ export function getChalkSync() {
115
+ return resolvedChalk ?? chalkFallback;
116
+ }
117
+ export default chalkFallback;
118
+ //# sourceMappingURL=chalk-fallback.js.map