bosun 0.33.1 → 0.33.2
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/config.mjs +84 -22
- package/library-manager.mjs +727 -0
- package/package.json +12 -1
- package/repo-root.mjs +39 -20
- package/setup-web-server.mjs +97 -10
- package/setup.mjs +31 -0
- package/shared-state-manager.mjs +83 -10
- package/ui/app.js +3 -1
- package/ui/demo.html +240 -0
- package/ui/index.html +0 -1
- package/ui/modules/icons.js +13 -0
- package/ui/modules/router.js +3 -2
- package/ui/setup.html +22 -8
- package/ui/styles/components.css +10 -10
- package/ui/styles/layout.css +31 -0
- package/ui/styles.css +1 -0
- package/ui/tabs/library.js +695 -0
- package/ui/tabs/workflows.js +27 -2
- package/ui-server.mjs +295 -16
- package/workflow-engine.mjs +822 -0
- package/workflow-migration.mjs +396 -0
- package/workflow-nodes.mjs +1811 -0
- package/workflow-templates/_helpers.mjs +61 -0
- package/workflow-templates/agents.mjs +425 -0
- package/workflow-templates/ci-cd.mjs +77 -0
- package/workflow-templates/github.mjs +432 -0
- package/workflow-templates/planning.mjs +266 -0
- package/workflow-templates/reliability.mjs +351 -0
- package/workflow-templates.mjs +243 -0
- package/workspace-manager.mjs +29 -10
package/config.mjs
CHANGED
|
@@ -65,7 +65,8 @@ function isWslInteropRuntime() {
|
|
|
65
65
|
}
|
|
66
66
|
|
|
67
67
|
function resolveConfigDir(repoRoot) {
|
|
68
|
-
// 1. Explicit env override
|
|
68
|
+
// 1. Explicit env override (BOSUN_HOME supersedes BOSUN_DIR; both are aliases)
|
|
69
|
+
if (process.env.BOSUN_HOME) return resolve(process.env.BOSUN_HOME);
|
|
69
70
|
if (process.env.BOSUN_DIR) return resolve(process.env.BOSUN_DIR);
|
|
70
71
|
|
|
71
72
|
// 2. Platform-aware user home
|
|
@@ -86,6 +87,55 @@ function resolveConfigDir(repoRoot) {
|
|
|
86
87
|
return resolve(baseDir, "bosun");
|
|
87
88
|
}
|
|
88
89
|
|
|
90
|
+
function getConfigSearchDirs(repoRoot) {
|
|
91
|
+
const dirs = new Set();
|
|
92
|
+
if (process.env.BOSUN_HOME) dirs.add(resolve(process.env.BOSUN_HOME));
|
|
93
|
+
if (process.env.BOSUN_DIR) dirs.add(resolve(process.env.BOSUN_DIR));
|
|
94
|
+
dirs.add(resolveConfigDir(repoRoot));
|
|
95
|
+
if (process.env.APPDATA) dirs.add(resolve(process.env.APPDATA, "bosun"));
|
|
96
|
+
if (process.env.LOCALAPPDATA) dirs.add(resolve(process.env.LOCALAPPDATA, "bosun"));
|
|
97
|
+
if (process.env.USERPROFILE) dirs.add(resolve(process.env.USERPROFILE, "bosun"));
|
|
98
|
+
if (process.env.HOME) dirs.add(resolve(process.env.HOME, "bosun"));
|
|
99
|
+
return [...dirs].filter(Boolean);
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
function collectRepoPathsFromConfig(cfg, configDir) {
|
|
103
|
+
const paths = [];
|
|
104
|
+
const pushPath = (path) => {
|
|
105
|
+
if (!path) return;
|
|
106
|
+
paths.push(isAbsolute(path) ? path : resolve(configDir, path));
|
|
107
|
+
};
|
|
108
|
+
|
|
109
|
+
const repos = cfg.repositories || cfg.repos || [];
|
|
110
|
+
if (Array.isArray(repos)) {
|
|
111
|
+
for (const repo of repos) {
|
|
112
|
+
const repoPath = typeof repo === "string" ? repo : (repo?.path || repo?.repoRoot);
|
|
113
|
+
pushPath(repoPath);
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
const workspaces = cfg.workspaces || [];
|
|
118
|
+
if (Array.isArray(workspaces)) {
|
|
119
|
+
for (const ws of workspaces) {
|
|
120
|
+
const wsBase = ws?.path
|
|
121
|
+
? (isAbsolute(ws.path) ? ws.path : resolve(configDir, ws.path))
|
|
122
|
+
: (ws?.id ? resolve(configDir, "workspaces", ws.id) : null);
|
|
123
|
+
const wsRepos = ws?.repos || ws?.repositories || [];
|
|
124
|
+
if (!Array.isArray(wsRepos)) continue;
|
|
125
|
+
for (const repo of wsRepos) {
|
|
126
|
+
const repoPath = typeof repo === "string" ? repo : (repo?.path || repo?.repoRoot);
|
|
127
|
+
if (repoPath) {
|
|
128
|
+
pushPath(repoPath);
|
|
129
|
+
continue;
|
|
130
|
+
}
|
|
131
|
+
if (wsBase && repo?.name) pushPath(resolve(wsBase, repo.name));
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
return paths;
|
|
137
|
+
}
|
|
138
|
+
|
|
89
139
|
function ensurePromptWorkspaceGitIgnore(repoRoot) {
|
|
90
140
|
const gitignorePath = resolve(repoRoot, ".gitignore");
|
|
91
141
|
const entry = "/.bosun/";
|
|
@@ -575,33 +625,26 @@ function detectRepoRoot() {
|
|
|
575
625
|
}
|
|
576
626
|
|
|
577
627
|
// 4. Check bosun config for workspace repos
|
|
578
|
-
const
|
|
628
|
+
const configDirs = getConfigSearchDirs();
|
|
629
|
+
let fallbackRepo = null;
|
|
579
630
|
for (const cfgName of CONFIG_FILES) {
|
|
580
|
-
const
|
|
581
|
-
|
|
631
|
+
for (const configDir of configDirs) {
|
|
632
|
+
const cfgPath = resolve(configDir, cfgName);
|
|
633
|
+
if (!existsSync(cfgPath)) continue;
|
|
582
634
|
try {
|
|
583
635
|
const cfg = JSON.parse(readFileSync(cfgPath, "utf8"));
|
|
584
|
-
|
|
585
|
-
const
|
|
586
|
-
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
if (repoPath && existsSync(resolve(repoPath))) return resolve(repoPath);
|
|
636
|
+
const repoPaths = collectRepoPathsFromConfig(cfg, configDir);
|
|
637
|
+
for (const repoPath of repoPaths) {
|
|
638
|
+
if (!repoPath || !existsSync(repoPath)) continue;
|
|
639
|
+
if (existsSync(resolve(repoPath, ".git"))) return repoPath;
|
|
640
|
+
fallbackRepo ??= repoPath;
|
|
590
641
|
}
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
const ws = workspaces[0];
|
|
595
|
-
const wsRepos = ws?.repos || ws?.repositories || [];
|
|
596
|
-
if (Array.isArray(wsRepos) && wsRepos.length > 0) {
|
|
597
|
-
const primary = wsRepos.find((r) => r.primary) || wsRepos[0];
|
|
598
|
-
const repoPath = primary?.path || primary?.repoRoot;
|
|
599
|
-
if (repoPath && existsSync(resolve(repoPath))) return resolve(repoPath);
|
|
600
|
-
}
|
|
601
|
-
}
|
|
602
|
-
} catch { /* invalid config */ }
|
|
642
|
+
} catch {
|
|
643
|
+
/* invalid config */
|
|
644
|
+
}
|
|
603
645
|
}
|
|
604
646
|
}
|
|
647
|
+
if (fallbackRepo) return fallbackRepo;
|
|
605
648
|
|
|
606
649
|
// 5. Final fallback — warn and return cwd. This is unlikely to be a valid
|
|
607
650
|
// git repo (e.g. when the daemon spawns with cwd=homedir), but returning
|
|
@@ -2069,6 +2112,25 @@ export function loadConfig(argv = process.argv, options = {}) {
|
|
|
2069
2112
|
|
|
2070
2113
|
// First run
|
|
2071
2114
|
isFirstRun,
|
|
2115
|
+
|
|
2116
|
+
// Security controls
|
|
2117
|
+
security: Object.freeze({
|
|
2118
|
+
// List of trusted issue creators (primary GitHub account or configured list)
|
|
2119
|
+
trustedCreators:
|
|
2120
|
+
configData.trustedCreators ||
|
|
2121
|
+
process.env.BOSUN_TRUSTED_CREATORS?.split(",") ||
|
|
2122
|
+
[],
|
|
2123
|
+
// Enforce all new tasks go to backlog unless planner config allows auto-push
|
|
2124
|
+
enforceBacklog:
|
|
2125
|
+
typeof configData.enforceBacklog === "boolean"
|
|
2126
|
+
? configData.enforceBacklog
|
|
2127
|
+
: true,
|
|
2128
|
+
// Control agent triggers: restrict agent activation to trusted sources
|
|
2129
|
+
agentTriggerControl:
|
|
2130
|
+
typeof configData.agentTriggerControl === "boolean"
|
|
2131
|
+
? configData.agentTriggerControl
|
|
2132
|
+
: true,
|
|
2133
|
+
}),
|
|
2072
2134
|
};
|
|
2073
2135
|
|
|
2074
2136
|
return Object.freeze(config);
|