@brainfile/cli 0.11.1 → 0.12.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/brainfile.md +82 -5
- package/dist/cli.js +30 -3
- package/dist/cli.js.map +1 -1
- package/dist/commands/archive.d.ts +15 -2
- package/dist/commands/archive.d.ts.map +1 -1
- package/dist/commands/archive.js +351 -23
- package/dist/commands/archive.js.map +1 -1
- package/dist/commands/auth.d.ts +26 -0
- package/dist/commands/auth.d.ts.map +1 -0
- package/dist/commands/auth.js +141 -0
- package/dist/commands/auth.js.map +1 -0
- package/dist/tui/BrainfileTUI.d.ts.map +1 -1
- package/dist/tui/BrainfileTUI.js +69 -36
- package/dist/tui/BrainfileTUI.js.map +1 -1
- package/dist/tui/components/ArchivePanel.d.ts +3 -2
- package/dist/tui/components/ArchivePanel.d.ts.map +1 -1
- package/dist/tui/components/ArchivePanel.js +7 -6
- package/dist/tui/components/ArchivePanel.js.map +1 -1
- package/dist/tui/components/Header.d.ts +4 -1
- package/dist/tui/components/Header.d.ts.map +1 -1
- package/dist/tui/components/Header.js +25 -1
- package/dist/tui/components/Header.js.map +1 -1
- package/dist/tui/components/HelpOverlay.d.ts +3 -1
- package/dist/tui/components/HelpOverlay.d.ts.map +1 -1
- package/dist/tui/components/HelpOverlay.js +38 -1
- package/dist/tui/components/HelpOverlay.js.map +1 -1
- package/dist/tui/components/MainPanelTabs.d.ts +3 -2
- package/dist/tui/components/MainPanelTabs.d.ts.map +1 -1
- package/dist/tui/components/MainPanelTabs.js +20 -1
- package/dist/tui/components/MainPanelTabs.js.map +1 -1
- package/dist/tui/components/RulesPanel.d.ts +3 -2
- package/dist/tui/components/RulesPanel.d.ts.map +1 -1
- package/dist/tui/components/RulesPanel.js +20 -6
- package/dist/tui/components/RulesPanel.js.map +1 -1
- package/dist/tui/components/StackedTaskList.d.ts +26 -0
- package/dist/tui/components/StackedTaskList.d.ts.map +1 -0
- package/dist/tui/components/StackedTaskList.js +120 -0
- package/dist/tui/components/StackedTaskList.js.map +1 -0
- package/dist/tui/components/StatusBar.d.ts +3 -2
- package/dist/tui/components/StatusBar.d.ts.map +1 -1
- package/dist/tui/components/StatusBar.js +6 -3
- package/dist/tui/components/StatusBar.js.map +1 -1
- package/dist/tui/components/TaskCard.d.ts +3 -1
- package/dist/tui/components/TaskCard.d.ts.map +1 -1
- package/dist/tui/components/TaskCard.js +3 -2
- package/dist/tui/components/TaskCard.js.map +1 -1
- package/dist/tui/components/index.d.ts +2 -0
- package/dist/tui/components/index.d.ts.map +1 -1
- package/dist/tui/components/index.js +4 -1
- package/dist/tui/components/index.js.map +1 -1
- package/dist/tui/hooks/useKeyboardNavigation.d.ts +6 -2
- package/dist/tui/hooks/useKeyboardNavigation.d.ts.map +1 -1
- package/dist/tui/hooks/useKeyboardNavigation.js +88 -40
- package/dist/tui/hooks/useKeyboardNavigation.js.map +1 -1
- package/dist/tui/types.d.ts +9 -0
- package/dist/tui/types.d.ts.map +1 -1
- package/dist/tui/types.js +7 -1
- package/dist/tui/types.js.map +1 -1
- package/dist/utils/auth-store.d.ts +69 -0
- package/dist/utils/auth-store.d.ts.map +1 -0
- package/dist/utils/auth-store.js +308 -0
- package/dist/utils/auth-store.js.map +1 -0
- package/dist/utils/config.d.ts +89 -0
- package/dist/utils/config.d.ts.map +1 -0
- package/dist/utils/config.js +211 -0
- package/dist/utils/config.js.map +1 -0
- package/dist/utils/github-auth.d.ts +56 -0
- package/dist/utils/github-auth.d.ts.map +1 -0
- package/dist/utils/github-auth.js +341 -0
- package/dist/utils/github-auth.js.map +1 -0
- package/dist/utils/linear-auth.d.ts +59 -0
- package/dist/utils/linear-auth.d.ts.map +1 -0
- package/dist/utils/linear-auth.js +295 -0
- package/dist/utils/linear-auth.js.map +1 -0
- package/package.json +3 -2
|
@@ -0,0 +1,308 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Authentication token storage for Brainfile CLI
|
|
4
|
+
*
|
|
5
|
+
* Stores tokens with the following priority:
|
|
6
|
+
* 1. System keychain (via keytar, if available)
|
|
7
|
+
* 2. Config file (~/.config/brainfile/auth.json)
|
|
8
|
+
* 3. Environment variables (read-only)
|
|
9
|
+
*
|
|
10
|
+
* @packageDocumentation
|
|
11
|
+
*/
|
|
12
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
13
|
+
if (k2 === undefined) k2 = k;
|
|
14
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
15
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
16
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
17
|
+
}
|
|
18
|
+
Object.defineProperty(o, k2, desc);
|
|
19
|
+
}) : (function(o, m, k, k2) {
|
|
20
|
+
if (k2 === undefined) k2 = k;
|
|
21
|
+
o[k2] = m[k];
|
|
22
|
+
}));
|
|
23
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
24
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
25
|
+
}) : function(o, v) {
|
|
26
|
+
o["default"] = v;
|
|
27
|
+
});
|
|
28
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
29
|
+
var ownKeys = function(o) {
|
|
30
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
31
|
+
var ar = [];
|
|
32
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
33
|
+
return ar;
|
|
34
|
+
};
|
|
35
|
+
return ownKeys(o);
|
|
36
|
+
};
|
|
37
|
+
return function (mod) {
|
|
38
|
+
if (mod && mod.__esModule) return mod;
|
|
39
|
+
var result = {};
|
|
40
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
41
|
+
__setModuleDefault(result, mod);
|
|
42
|
+
return result;
|
|
43
|
+
};
|
|
44
|
+
})();
|
|
45
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
46
|
+
exports.authStore = exports.AuthStore = void 0;
|
|
47
|
+
exports.getGitHubCLIToken = getGitHubCLIToken;
|
|
48
|
+
exports.isGitHubCLIAvailable = isGitHubCLIAvailable;
|
|
49
|
+
const fs = __importStar(require("fs"));
|
|
50
|
+
const path = __importStar(require("path"));
|
|
51
|
+
const child_process_1 = require("child_process");
|
|
52
|
+
const config_1 = require("./config");
|
|
53
|
+
// ============================================================================
|
|
54
|
+
// Constants
|
|
55
|
+
// ============================================================================
|
|
56
|
+
const SERVICE_NAME = 'brainfile';
|
|
57
|
+
const AUTH_FILE = path.join((0, config_1.getConfigDir)(), 'auth.json');
|
|
58
|
+
const ENV_VAR_MAP = {
|
|
59
|
+
github: ['GITHUB_TOKEN', 'GH_TOKEN'],
|
|
60
|
+
linear: ['LINEAR_API_KEY', 'LINEAR_TOKEN'],
|
|
61
|
+
};
|
|
62
|
+
// ============================================================================
|
|
63
|
+
// Keytar Integration (Optional)
|
|
64
|
+
// ============================================================================
|
|
65
|
+
let keytar = null;
|
|
66
|
+
let keytarChecked = false;
|
|
67
|
+
/**
|
|
68
|
+
* Try to load keytar (system keychain integration)
|
|
69
|
+
* Returns null if keytar is not available
|
|
70
|
+
*/
|
|
71
|
+
function getKeytar() {
|
|
72
|
+
if (keytarChecked) {
|
|
73
|
+
return keytar;
|
|
74
|
+
}
|
|
75
|
+
keytarChecked = true;
|
|
76
|
+
try {
|
|
77
|
+
// Dynamic require to make keytar optional
|
|
78
|
+
keytar = require('keytar');
|
|
79
|
+
return keytar;
|
|
80
|
+
}
|
|
81
|
+
catch {
|
|
82
|
+
// keytar not installed or native module not built
|
|
83
|
+
return null;
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
// ============================================================================
|
|
87
|
+
// GitHub CLI Integration
|
|
88
|
+
// ============================================================================
|
|
89
|
+
/**
|
|
90
|
+
* Try to get GitHub token from gh CLI
|
|
91
|
+
* @returns Token from gh CLI, or null if not available
|
|
92
|
+
*/
|
|
93
|
+
function getGitHubCLIToken() {
|
|
94
|
+
try {
|
|
95
|
+
const token = (0, child_process_1.execSync)('gh auth token', {
|
|
96
|
+
encoding: 'utf-8',
|
|
97
|
+
stdio: ['pipe', 'pipe', 'pipe'],
|
|
98
|
+
}).trim();
|
|
99
|
+
if (token && token.length > 0) {
|
|
100
|
+
return token;
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
catch {
|
|
104
|
+
// gh CLI not installed or not authenticated
|
|
105
|
+
}
|
|
106
|
+
return null;
|
|
107
|
+
}
|
|
108
|
+
/**
|
|
109
|
+
* Check if gh CLI is installed and authenticated
|
|
110
|
+
*/
|
|
111
|
+
function isGitHubCLIAvailable() {
|
|
112
|
+
return getGitHubCLIToken() !== null;
|
|
113
|
+
}
|
|
114
|
+
// ============================================================================
|
|
115
|
+
// Auth Store Class
|
|
116
|
+
// ============================================================================
|
|
117
|
+
class AuthStore {
|
|
118
|
+
/**
|
|
119
|
+
* Get a token for a provider
|
|
120
|
+
* Checks: env vars → keychain → config file → gh CLI (for github)
|
|
121
|
+
*/
|
|
122
|
+
async get(provider) {
|
|
123
|
+
// 1. Check environment variables
|
|
124
|
+
const envToken = this.getFromEnv(provider);
|
|
125
|
+
if (envToken) {
|
|
126
|
+
return envToken;
|
|
127
|
+
}
|
|
128
|
+
// 2. Check system keychain
|
|
129
|
+
const kt = getKeytar();
|
|
130
|
+
if (kt) {
|
|
131
|
+
try {
|
|
132
|
+
const keychainToken = await kt.getPassword(SERVICE_NAME, provider);
|
|
133
|
+
if (keychainToken) {
|
|
134
|
+
return keychainToken;
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
catch {
|
|
138
|
+
// Keychain access failed, continue to next option
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
// 3. Check config file
|
|
142
|
+
const fileToken = this.getFromFile(provider);
|
|
143
|
+
if (fileToken) {
|
|
144
|
+
return fileToken;
|
|
145
|
+
}
|
|
146
|
+
// 4. For GitHub, check gh CLI as last resort
|
|
147
|
+
if (provider === 'github') {
|
|
148
|
+
return getGitHubCLIToken();
|
|
149
|
+
}
|
|
150
|
+
return null;
|
|
151
|
+
}
|
|
152
|
+
/**
|
|
153
|
+
* Get stored token info (includes metadata like username)
|
|
154
|
+
*/
|
|
155
|
+
async getTokenInfo(provider) {
|
|
156
|
+
// Check config file for metadata
|
|
157
|
+
const authData = this.loadAuthFile();
|
|
158
|
+
return authData[provider] || null;
|
|
159
|
+
}
|
|
160
|
+
/**
|
|
161
|
+
* Store a token for a provider
|
|
162
|
+
* Stores in: keychain (if available) AND config file (for metadata)
|
|
163
|
+
*/
|
|
164
|
+
async set(provider, token, metadata) {
|
|
165
|
+
const storedToken = {
|
|
166
|
+
token,
|
|
167
|
+
savedAt: new Date().toISOString(),
|
|
168
|
+
...metadata,
|
|
169
|
+
};
|
|
170
|
+
// 1. Try to store in keychain
|
|
171
|
+
const kt = getKeytar();
|
|
172
|
+
if (kt) {
|
|
173
|
+
try {
|
|
174
|
+
await kt.setPassword(SERVICE_NAME, provider, token);
|
|
175
|
+
}
|
|
176
|
+
catch {
|
|
177
|
+
// Keychain storage failed, will fall back to file
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
// 2. Store in config file (always, for metadata)
|
|
181
|
+
this.saveToFile(provider, storedToken);
|
|
182
|
+
}
|
|
183
|
+
/**
|
|
184
|
+
* Clear a token for a provider
|
|
185
|
+
*/
|
|
186
|
+
async clear(provider) {
|
|
187
|
+
// 1. Remove from keychain
|
|
188
|
+
const kt = getKeytar();
|
|
189
|
+
if (kt) {
|
|
190
|
+
try {
|
|
191
|
+
await kt.deletePassword(SERVICE_NAME, provider);
|
|
192
|
+
}
|
|
193
|
+
catch {
|
|
194
|
+
// Ignore errors
|
|
195
|
+
}
|
|
196
|
+
}
|
|
197
|
+
// 2. Remove from config file
|
|
198
|
+
this.removeFromFile(provider);
|
|
199
|
+
}
|
|
200
|
+
/**
|
|
201
|
+
* Check if a provider is authenticated
|
|
202
|
+
*/
|
|
203
|
+
async isAuthenticated(provider) {
|
|
204
|
+
const token = await this.get(provider);
|
|
205
|
+
return token !== null;
|
|
206
|
+
}
|
|
207
|
+
/**
|
|
208
|
+
* Get authentication status for all providers
|
|
209
|
+
*/
|
|
210
|
+
async getStatus() {
|
|
211
|
+
const result = {
|
|
212
|
+
github: { authenticated: false },
|
|
213
|
+
linear: { authenticated: false },
|
|
214
|
+
};
|
|
215
|
+
for (const provider of ['github', 'linear']) {
|
|
216
|
+
// Check env first
|
|
217
|
+
if (this.getFromEnv(provider)) {
|
|
218
|
+
result[provider] = { authenticated: true, source: 'environment' };
|
|
219
|
+
continue;
|
|
220
|
+
}
|
|
221
|
+
// Check keychain
|
|
222
|
+
const kt = getKeytar();
|
|
223
|
+
if (kt) {
|
|
224
|
+
try {
|
|
225
|
+
const token = await kt.getPassword(SERVICE_NAME, provider);
|
|
226
|
+
if (token) {
|
|
227
|
+
const info = await this.getTokenInfo(provider);
|
|
228
|
+
result[provider] = {
|
|
229
|
+
authenticated: true,
|
|
230
|
+
source: 'keychain',
|
|
231
|
+
username: info?.username,
|
|
232
|
+
};
|
|
233
|
+
continue;
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
catch {
|
|
237
|
+
// Continue to next check
|
|
238
|
+
}
|
|
239
|
+
}
|
|
240
|
+
// Check config file
|
|
241
|
+
const fileToken = this.getFromFile(provider);
|
|
242
|
+
if (fileToken) {
|
|
243
|
+
const info = await this.getTokenInfo(provider);
|
|
244
|
+
result[provider] = {
|
|
245
|
+
authenticated: true,
|
|
246
|
+
source: 'config',
|
|
247
|
+
username: info?.username,
|
|
248
|
+
};
|
|
249
|
+
continue;
|
|
250
|
+
}
|
|
251
|
+
// For GitHub, check gh CLI
|
|
252
|
+
if (provider === 'github' && getGitHubCLIToken()) {
|
|
253
|
+
result[provider] = { authenticated: true, source: 'gh-cli' };
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
return result;
|
|
257
|
+
}
|
|
258
|
+
// ============================================================================
|
|
259
|
+
// Private Methods
|
|
260
|
+
// ============================================================================
|
|
261
|
+
getFromEnv(provider) {
|
|
262
|
+
const vars = ENV_VAR_MAP[provider];
|
|
263
|
+
for (const varName of vars) {
|
|
264
|
+
const value = process.env[varName];
|
|
265
|
+
if (value && value.length > 0) {
|
|
266
|
+
return value;
|
|
267
|
+
}
|
|
268
|
+
}
|
|
269
|
+
return null;
|
|
270
|
+
}
|
|
271
|
+
loadAuthFile() {
|
|
272
|
+
try {
|
|
273
|
+
if (fs.existsSync(AUTH_FILE)) {
|
|
274
|
+
const content = fs.readFileSync(AUTH_FILE, 'utf-8');
|
|
275
|
+
return JSON.parse(content);
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
catch {
|
|
279
|
+
// File corrupted or unreadable
|
|
280
|
+
}
|
|
281
|
+
return {};
|
|
282
|
+
}
|
|
283
|
+
saveAuthFile(data) {
|
|
284
|
+
(0, config_1.ensureConfigDir)();
|
|
285
|
+
fs.writeFileSync(AUTH_FILE, JSON.stringify(data, null, 2), {
|
|
286
|
+
encoding: 'utf-8',
|
|
287
|
+
mode: 0o600, // Owner read/write only
|
|
288
|
+
});
|
|
289
|
+
}
|
|
290
|
+
getFromFile(provider) {
|
|
291
|
+
const data = this.loadAuthFile();
|
|
292
|
+
return data[provider]?.token || null;
|
|
293
|
+
}
|
|
294
|
+
saveToFile(provider, tokenInfo) {
|
|
295
|
+
const data = this.loadAuthFile();
|
|
296
|
+
data[provider] = tokenInfo;
|
|
297
|
+
this.saveAuthFile(data);
|
|
298
|
+
}
|
|
299
|
+
removeFromFile(provider) {
|
|
300
|
+
const data = this.loadAuthFile();
|
|
301
|
+
delete data[provider];
|
|
302
|
+
this.saveAuthFile(data);
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
exports.AuthStore = AuthStore;
|
|
306
|
+
// Export singleton instance
|
|
307
|
+
exports.authStore = new AuthStore();
|
|
308
|
+
//# sourceMappingURL=auth-store.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"auth-store.js","sourceRoot":"","sources":["../../src/utils/auth-store.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Configuration file management for Brainfile CLI
|
|
3
|
+
*
|
|
4
|
+
* Handles reading/writing ~/.config/brainfile/config.json for:
|
|
5
|
+
* - Archive destination defaults
|
|
6
|
+
* - GitHub connection details (owner, repo)
|
|
7
|
+
* - Linear connection details (teamId)
|
|
8
|
+
* - User preferences
|
|
9
|
+
*
|
|
10
|
+
* @packageDocumentation
|
|
11
|
+
*/
|
|
12
|
+
export interface GitHubConfig {
|
|
13
|
+
/** GitHub repository owner (username or org) */
|
|
14
|
+
owner?: string;
|
|
15
|
+
/** GitHub repository name */
|
|
16
|
+
repo?: string;
|
|
17
|
+
/** Extra labels to add to archived issues */
|
|
18
|
+
labels?: string[];
|
|
19
|
+
}
|
|
20
|
+
export interface LinearConfig {
|
|
21
|
+
/** Linear team ID */
|
|
22
|
+
teamId?: string;
|
|
23
|
+
/** Linear project ID (optional) */
|
|
24
|
+
projectId?: string;
|
|
25
|
+
}
|
|
26
|
+
export interface ArchiveConfig {
|
|
27
|
+
/** Default archive destination: 'local' | 'github' | 'linear' */
|
|
28
|
+
default?: 'local' | 'github' | 'linear';
|
|
29
|
+
/** GitHub-specific settings */
|
|
30
|
+
github?: GitHubConfig;
|
|
31
|
+
/** Linear-specific settings */
|
|
32
|
+
linear?: LinearConfig;
|
|
33
|
+
}
|
|
34
|
+
export interface BrainfileConfig {
|
|
35
|
+
/** Archive configuration */
|
|
36
|
+
archive?: ArchiveConfig;
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Get the path to the config directory
|
|
40
|
+
*/
|
|
41
|
+
export declare function getConfigDir(): string;
|
|
42
|
+
/**
|
|
43
|
+
* Get the path to the config file
|
|
44
|
+
*/
|
|
45
|
+
export declare function getConfigPath(): string;
|
|
46
|
+
/**
|
|
47
|
+
* Ensure the config directory exists
|
|
48
|
+
*/
|
|
49
|
+
export declare function ensureConfigDir(): void;
|
|
50
|
+
/**
|
|
51
|
+
* Load the config file
|
|
52
|
+
* @returns Config object, or empty object if file doesn't exist
|
|
53
|
+
*/
|
|
54
|
+
export declare function loadConfig(): BrainfileConfig;
|
|
55
|
+
/**
|
|
56
|
+
* Save the config file
|
|
57
|
+
* @param config - Config object to save
|
|
58
|
+
*/
|
|
59
|
+
export declare function saveConfig(config: BrainfileConfig): void;
|
|
60
|
+
/**
|
|
61
|
+
* Update specific config values (merges with existing)
|
|
62
|
+
* @param updates - Partial config to merge
|
|
63
|
+
*/
|
|
64
|
+
export declare function updateConfig(updates: Partial<BrainfileConfig>): BrainfileConfig;
|
|
65
|
+
/**
|
|
66
|
+
* Get archive configuration with defaults
|
|
67
|
+
*/
|
|
68
|
+
export declare function getArchiveConfig(): ArchiveConfig;
|
|
69
|
+
/**
|
|
70
|
+
* Set archive default destination
|
|
71
|
+
*/
|
|
72
|
+
export declare function setArchiveDefault(destination: 'local' | 'github' | 'linear'): void;
|
|
73
|
+
/**
|
|
74
|
+
* Set GitHub configuration
|
|
75
|
+
*/
|
|
76
|
+
export declare function setGitHubConfig(github: GitHubConfig): void;
|
|
77
|
+
/**
|
|
78
|
+
* Set Linear configuration
|
|
79
|
+
*/
|
|
80
|
+
export declare function setLinearConfig(linear: LinearConfig): void;
|
|
81
|
+
/**
|
|
82
|
+
* Get the effective archive destination
|
|
83
|
+
* Priority: brainfile.md archive.destination > config default > 'local'
|
|
84
|
+
*
|
|
85
|
+
* @param brainfileDestination - Destination from brainfile.md (if any)
|
|
86
|
+
* @returns The effective destination
|
|
87
|
+
*/
|
|
88
|
+
export declare function getEffectiveArchiveDestination(brainfileDestination?: string): 'local' | 'github' | 'linear';
|
|
89
|
+
//# sourceMappingURL=config.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../src/utils/config.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAUH,MAAM,WAAW,YAAY;IAC3B,gDAAgD;IAChD,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,6BAA6B;IAC7B,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,6CAA6C;IAC7C,MAAM,CAAC,EAAE,MAAM,EAAE,CAAC;CACnB;AAED,MAAM,WAAW,YAAY;IAC3B,qBAAqB;IACrB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,mCAAmC;IACnC,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,aAAa;IAC5B,iEAAiE;IACjE,OAAO,CAAC,EAAE,OAAO,GAAG,QAAQ,GAAG,QAAQ,CAAC;IACxC,+BAA+B;IAC/B,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB,+BAA+B;IAC/B,MAAM,CAAC,EAAE,YAAY,CAAC;CACvB;AAED,MAAM,WAAW,eAAe;IAC9B,4BAA4B;IAC5B,OAAO,CAAC,EAAE,aAAa,CAAC;CACzB;AAaD;;GAEG;AACH,wBAAgB,YAAY,IAAI,MAAM,CAErC;AAED;;GAEG;AACH,wBAAgB,aAAa,IAAI,MAAM,CAEtC;AAED;;GAEG;AACH,wBAAgB,eAAe,IAAI,IAAI,CAItC;AAED;;;GAGG;AACH,wBAAgB,UAAU,IAAI,eAAe,CAW5C;AAED;;;GAGG;AACH,wBAAgB,UAAU,CAAC,MAAM,EAAE,eAAe,GAAG,IAAI,CAMxD;AAED;;;GAGG;AACH,wBAAgB,YAAY,CAAC,OAAO,EAAE,OAAO,CAAC,eAAe,CAAC,GAAG,eAAe,CAK/E;AAED;;GAEG;AACH,wBAAgB,gBAAgB,IAAI,aAAa,CAGhD;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,WAAW,EAAE,OAAO,GAAG,QAAQ,GAAG,QAAQ,GAAG,IAAI,CAKlF;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,MAAM,EAAE,YAAY,GAAG,IAAI,CAK1D;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,MAAM,EAAE,YAAY,GAAG,IAAI,CAK1D;AAED;;;;;;GAMG;AACH,wBAAgB,8BAA8B,CAC5C,oBAAoB,CAAC,EAAE,MAAM,GAC5B,OAAO,GAAG,QAAQ,GAAG,QAAQ,CAc/B"}
|
|
@@ -0,0 +1,211 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Configuration file management for Brainfile CLI
|
|
4
|
+
*
|
|
5
|
+
* Handles reading/writing ~/.config/brainfile/config.json for:
|
|
6
|
+
* - Archive destination defaults
|
|
7
|
+
* - GitHub connection details (owner, repo)
|
|
8
|
+
* - Linear connection details (teamId)
|
|
9
|
+
* - User preferences
|
|
10
|
+
*
|
|
11
|
+
* @packageDocumentation
|
|
12
|
+
*/
|
|
13
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
14
|
+
if (k2 === undefined) k2 = k;
|
|
15
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
16
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
17
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
18
|
+
}
|
|
19
|
+
Object.defineProperty(o, k2, desc);
|
|
20
|
+
}) : (function(o, m, k, k2) {
|
|
21
|
+
if (k2 === undefined) k2 = k;
|
|
22
|
+
o[k2] = m[k];
|
|
23
|
+
}));
|
|
24
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
25
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
26
|
+
}) : function(o, v) {
|
|
27
|
+
o["default"] = v;
|
|
28
|
+
});
|
|
29
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
30
|
+
var ownKeys = function(o) {
|
|
31
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
32
|
+
var ar = [];
|
|
33
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
34
|
+
return ar;
|
|
35
|
+
};
|
|
36
|
+
return ownKeys(o);
|
|
37
|
+
};
|
|
38
|
+
return function (mod) {
|
|
39
|
+
if (mod && mod.__esModule) return mod;
|
|
40
|
+
var result = {};
|
|
41
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
42
|
+
__setModuleDefault(result, mod);
|
|
43
|
+
return result;
|
|
44
|
+
};
|
|
45
|
+
})();
|
|
46
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
47
|
+
exports.getConfigDir = getConfigDir;
|
|
48
|
+
exports.getConfigPath = getConfigPath;
|
|
49
|
+
exports.ensureConfigDir = ensureConfigDir;
|
|
50
|
+
exports.loadConfig = loadConfig;
|
|
51
|
+
exports.saveConfig = saveConfig;
|
|
52
|
+
exports.updateConfig = updateConfig;
|
|
53
|
+
exports.getArchiveConfig = getArchiveConfig;
|
|
54
|
+
exports.setArchiveDefault = setArchiveDefault;
|
|
55
|
+
exports.setGitHubConfig = setGitHubConfig;
|
|
56
|
+
exports.setLinearConfig = setLinearConfig;
|
|
57
|
+
exports.getEffectiveArchiveDestination = getEffectiveArchiveDestination;
|
|
58
|
+
const fs = __importStar(require("fs"));
|
|
59
|
+
const path = __importStar(require("path"));
|
|
60
|
+
const os = __importStar(require("os"));
|
|
61
|
+
// ============================================================================
|
|
62
|
+
// Constants
|
|
63
|
+
// ============================================================================
|
|
64
|
+
const CONFIG_DIR = path.join(os.homedir(), '.config', 'brainfile');
|
|
65
|
+
const CONFIG_FILE = path.join(CONFIG_DIR, 'config.json');
|
|
66
|
+
// ============================================================================
|
|
67
|
+
// Config Functions
|
|
68
|
+
// ============================================================================
|
|
69
|
+
/**
|
|
70
|
+
* Get the path to the config directory
|
|
71
|
+
*/
|
|
72
|
+
function getConfigDir() {
|
|
73
|
+
return CONFIG_DIR;
|
|
74
|
+
}
|
|
75
|
+
/**
|
|
76
|
+
* Get the path to the config file
|
|
77
|
+
*/
|
|
78
|
+
function getConfigPath() {
|
|
79
|
+
return CONFIG_FILE;
|
|
80
|
+
}
|
|
81
|
+
/**
|
|
82
|
+
* Ensure the config directory exists
|
|
83
|
+
*/
|
|
84
|
+
function ensureConfigDir() {
|
|
85
|
+
if (!fs.existsSync(CONFIG_DIR)) {
|
|
86
|
+
fs.mkdirSync(CONFIG_DIR, { recursive: true, mode: 0o700 });
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
/**
|
|
90
|
+
* Load the config file
|
|
91
|
+
* @returns Config object, or empty object if file doesn't exist
|
|
92
|
+
*/
|
|
93
|
+
function loadConfig() {
|
|
94
|
+
try {
|
|
95
|
+
if (fs.existsSync(CONFIG_FILE)) {
|
|
96
|
+
const content = fs.readFileSync(CONFIG_FILE, 'utf-8');
|
|
97
|
+
return JSON.parse(content);
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
catch (error) {
|
|
101
|
+
// If file is corrupted, return empty config
|
|
102
|
+
console.error(`Warning: Could not read config file: ${error}`);
|
|
103
|
+
}
|
|
104
|
+
return {};
|
|
105
|
+
}
|
|
106
|
+
/**
|
|
107
|
+
* Save the config file
|
|
108
|
+
* @param config - Config object to save
|
|
109
|
+
*/
|
|
110
|
+
function saveConfig(config) {
|
|
111
|
+
ensureConfigDir();
|
|
112
|
+
fs.writeFileSync(CONFIG_FILE, JSON.stringify(config, null, 2), {
|
|
113
|
+
encoding: 'utf-8',
|
|
114
|
+
mode: 0o600, // Owner read/write only
|
|
115
|
+
});
|
|
116
|
+
}
|
|
117
|
+
/**
|
|
118
|
+
* Update specific config values (merges with existing)
|
|
119
|
+
* @param updates - Partial config to merge
|
|
120
|
+
*/
|
|
121
|
+
function updateConfig(updates) {
|
|
122
|
+
const current = loadConfig();
|
|
123
|
+
const updated = deepMerge(current, updates);
|
|
124
|
+
saveConfig(updated);
|
|
125
|
+
return updated;
|
|
126
|
+
}
|
|
127
|
+
/**
|
|
128
|
+
* Get archive configuration with defaults
|
|
129
|
+
*/
|
|
130
|
+
function getArchiveConfig() {
|
|
131
|
+
const config = loadConfig();
|
|
132
|
+
return config.archive || { default: 'local' };
|
|
133
|
+
}
|
|
134
|
+
/**
|
|
135
|
+
* Set archive default destination
|
|
136
|
+
*/
|
|
137
|
+
function setArchiveDefault(destination) {
|
|
138
|
+
const config = loadConfig();
|
|
139
|
+
config.archive = config.archive || {};
|
|
140
|
+
config.archive.default = destination;
|
|
141
|
+
saveConfig(config);
|
|
142
|
+
}
|
|
143
|
+
/**
|
|
144
|
+
* Set GitHub configuration
|
|
145
|
+
*/
|
|
146
|
+
function setGitHubConfig(github) {
|
|
147
|
+
const config = loadConfig();
|
|
148
|
+
config.archive = config.archive || {};
|
|
149
|
+
config.archive.github = { ...config.archive.github, ...github };
|
|
150
|
+
saveConfig(config);
|
|
151
|
+
}
|
|
152
|
+
/**
|
|
153
|
+
* Set Linear configuration
|
|
154
|
+
*/
|
|
155
|
+
function setLinearConfig(linear) {
|
|
156
|
+
const config = loadConfig();
|
|
157
|
+
config.archive = config.archive || {};
|
|
158
|
+
config.archive.linear = { ...config.archive.linear, ...linear };
|
|
159
|
+
saveConfig(config);
|
|
160
|
+
}
|
|
161
|
+
/**
|
|
162
|
+
* Get the effective archive destination
|
|
163
|
+
* Priority: brainfile.md archive.destination > config default > 'local'
|
|
164
|
+
*
|
|
165
|
+
* @param brainfileDestination - Destination from brainfile.md (if any)
|
|
166
|
+
* @returns The effective destination
|
|
167
|
+
*/
|
|
168
|
+
function getEffectiveArchiveDestination(brainfileDestination) {
|
|
169
|
+
// Priority 1: brainfile.md setting
|
|
170
|
+
if (brainfileDestination && isValidDestination(brainfileDestination)) {
|
|
171
|
+
return brainfileDestination;
|
|
172
|
+
}
|
|
173
|
+
// Priority 2: config default
|
|
174
|
+
const config = getArchiveConfig();
|
|
175
|
+
if (config.default && isValidDestination(config.default)) {
|
|
176
|
+
return config.default;
|
|
177
|
+
}
|
|
178
|
+
// Priority 3: fallback to local
|
|
179
|
+
return 'local';
|
|
180
|
+
}
|
|
181
|
+
// ============================================================================
|
|
182
|
+
// Helper Functions
|
|
183
|
+
// ============================================================================
|
|
184
|
+
function isValidDestination(dest) {
|
|
185
|
+
return ['local', 'github', 'linear'].includes(dest);
|
|
186
|
+
}
|
|
187
|
+
/**
|
|
188
|
+
* Deep merge two objects
|
|
189
|
+
*/
|
|
190
|
+
function deepMerge(target, source) {
|
|
191
|
+
const result = { ...target };
|
|
192
|
+
for (const key in source) {
|
|
193
|
+
if (Object.prototype.hasOwnProperty.call(source, key)) {
|
|
194
|
+
const sourceValue = source[key];
|
|
195
|
+
const targetValue = result[key];
|
|
196
|
+
if (sourceValue !== null &&
|
|
197
|
+
typeof sourceValue === 'object' &&
|
|
198
|
+
!Array.isArray(sourceValue) &&
|
|
199
|
+
targetValue !== null &&
|
|
200
|
+
typeof targetValue === 'object' &&
|
|
201
|
+
!Array.isArray(targetValue)) {
|
|
202
|
+
result[key] = deepMerge(targetValue, sourceValue);
|
|
203
|
+
}
|
|
204
|
+
else {
|
|
205
|
+
result[key] = sourceValue;
|
|
206
|
+
}
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
return result;
|
|
210
|
+
}
|
|
211
|
+
//# sourceMappingURL=config.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config.js","sourceRoot":"","sources":["../../src/utils/config.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* GitHub Authentication for Brainfile CLI
|
|
3
|
+
*
|
|
4
|
+
* Supports:
|
|
5
|
+
* 1. Piggyback on gh CLI auth (if available)
|
|
6
|
+
* 2. OAuth Device Flow (browser-based, no server needed)
|
|
7
|
+
* 3. Personal Access Token (manual entry)
|
|
8
|
+
*
|
|
9
|
+
* @packageDocumentation
|
|
10
|
+
*/
|
|
11
|
+
/**
|
|
12
|
+
* Check if GitHub is already authenticated
|
|
13
|
+
*/
|
|
14
|
+
export declare function isGitHubAuthenticated(): Promise<boolean>;
|
|
15
|
+
/**
|
|
16
|
+
* Get the current GitHub token (from any source)
|
|
17
|
+
*/
|
|
18
|
+
export declare function getGitHubToken(): Promise<string | null>;
|
|
19
|
+
/**
|
|
20
|
+
* Authenticate with GitHub using the best available method
|
|
21
|
+
*
|
|
22
|
+
* Priority:
|
|
23
|
+
* 1. Use existing gh CLI auth
|
|
24
|
+
* 2. OAuth Device Flow
|
|
25
|
+
* 3. Manual PAT entry
|
|
26
|
+
*/
|
|
27
|
+
export declare function authenticateGitHub(options: {
|
|
28
|
+
usePAT?: boolean;
|
|
29
|
+
token?: string;
|
|
30
|
+
silent?: boolean;
|
|
31
|
+
}): Promise<{
|
|
32
|
+
success: boolean;
|
|
33
|
+
username?: string;
|
|
34
|
+
error?: string;
|
|
35
|
+
}>;
|
|
36
|
+
/**
|
|
37
|
+
* Create a GitHub Issue
|
|
38
|
+
*/
|
|
39
|
+
export declare function createGitHubIssue(options: {
|
|
40
|
+
owner: string;
|
|
41
|
+
repo: string;
|
|
42
|
+
title: string;
|
|
43
|
+
body: string;
|
|
44
|
+
labels?: string[];
|
|
45
|
+
state?: 'open' | 'closed';
|
|
46
|
+
}): Promise<{
|
|
47
|
+
success: boolean;
|
|
48
|
+
issueNumber?: number;
|
|
49
|
+
issueUrl?: string;
|
|
50
|
+
error?: string;
|
|
51
|
+
}>;
|
|
52
|
+
/**
|
|
53
|
+
* Logout from GitHub
|
|
54
|
+
*/
|
|
55
|
+
export declare function logoutGitHub(): Promise<void>;
|
|
56
|
+
//# sourceMappingURL=github-auth.d.ts.map
|