glab-agent 0.2.1 → 0.2.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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "glab-agent",
3
- "version": "0.2.1",
3
+ "version": "0.2.2",
4
4
  "type": "module",
5
5
  "description": "Multi-agent GitLab To-Do watcher with YAML-defined agents, skills, and GitLab registry.",
6
6
  "license": "MIT",
@@ -31,6 +31,7 @@
31
31
  "access": "public"
32
32
  },
33
33
  "scripts": {
34
+ "prepare": "git config core.hooksPath scripts/hooks",
34
35
  "build": "tsc -p tsconfig.build.json",
35
36
  "test": "vitest run",
36
37
  "agent": "tsx src/local-agent/cli.ts",
@@ -713,6 +713,41 @@ Do not skip tests or use --no-verify to bypass hooks.
713
713
  await writeFile(readmePath, readmeContent, "utf8");
714
714
  console.log("Created README.md — product landing page for AI agents.");
715
715
  }
716
+
717
+ // Auto-run wiki setup if remote and token are available
718
+ if (remote) {
719
+ const token = process.env[options?.tokenEnv ?? "GITLAB_TOKEN"];
720
+ if (token) {
721
+ console.log("\nPopulating GitLab Wiki with documentation...");
722
+ try {
723
+ const client = new GitlabGlabClient({ host: remote.host, token });
724
+ const { stdout } = await execFileAsync("glab", ["api", `projects/${encodeURIComponent(remote.projectPath)}`], {
725
+ encoding: "utf8",
726
+ env: { ...process.env, GITLAB_HOST: remote.host, GITLAB_TOKEN: token }
727
+ });
728
+ const projectId = JSON.parse(stdout).id as number;
729
+ const pages = buildWikiPages(remote.host, remote.projectPath);
730
+ const existingPages = await client.listWikiPages(projectId);
731
+ const existingSlugs = new Set(existingPages.map(p => p.slug));
732
+ let created = 0;
733
+ let updated = 0;
734
+ for (const page of pages) {
735
+ try {
736
+ if (existingSlugs.has(page.title)) {
737
+ await client.updateWikiPage(projectId, page.title, page.title, page.content);
738
+ updated++;
739
+ } else {
740
+ await client.createWikiPage(projectId, page.title, page.content);
741
+ created++;
742
+ }
743
+ } catch { /* skip failed pages */ }
744
+ }
745
+ console.log(`✅ Wiki: ${created} created, ${updated} updated. ${wikiUrl(remote.host, remote.projectPath, "home")}`);
746
+ } catch {
747
+ console.log(`Skipped wiki setup (run 'glab-agent wiki setup' manually after pushing to GitLab).`);
748
+ }
749
+ }
750
+ }
716
751
  }
717
752
 
718
753
  // Also append to README.md for universal AI tool compatibility (non-repo mode)
@@ -50,6 +50,7 @@ const ACCEPTED_TODO_ACTIONS = new Set(["mentioned", "directly_addressed"]);
50
50
  export interface LocalAgentConfig {
51
51
  gitlabHost: string;
52
52
  gitlabProjectId?: number;
53
+ gitlabProjectIdExplicit: boolean; // true when YAML explicitly sets project_id
53
54
  gitlabToken: string;
54
55
  agentProvider: AgentProvider;
55
56
  agentRepoPath: string;
@@ -334,7 +335,7 @@ export async function runWatcherCycle(
334
335
 
335
336
  await updateAgentUserStatus(dependencies, "idle", undefined, config);
336
337
 
337
- const todos = config.gitlabProjectId
338
+ const todos = config.gitlabProjectIdExplicit && config.gitlabProjectId
338
339
  ? await dependencies.gitlabClient.listPendingTodos(config.gitlabProjectId)
339
340
  : await dependencies.gitlabClient.listAllPendingTodos();
340
341
  logger.info(`Polled ${todos.length} pending todo(s).`);
@@ -823,7 +824,7 @@ async function notifyPendingTodosWhileBusy(
823
824
  let todos: GitlabTodoItem[];
824
825
 
825
826
  try {
826
- todos = config.gitlabProjectId
827
+ todos = (config.gitlabProjectIdExplicit && config.gitlabProjectId)
827
828
  ? await dependencies.gitlabClient.listMentionedIssueTodos(config.gitlabProjectId)
828
829
  : await dependencies.gitlabClient.listAllPendingTodos();
829
830
  } catch (error) {
@@ -1039,14 +1040,16 @@ export function loadConfigFromAgentDefinition(
1039
1040
  throw new Error(`gitlab.host is required for agent "${def.name}" or must be inferable from git remote.`);
1040
1041
  }
1041
1042
 
1043
+ const explicitProjectId = def.gitlab.project_id;
1042
1044
  const gitlabProjectId =
1043
- def.gitlab.project_id ??
1045
+ explicitProjectId ??
1044
1046
  inferGitlabProjectId(gitlabHost, gitlabToken, agentRepoPath, execFileSyncImpl) ??
1045
1047
  undefined;
1046
1048
 
1047
1049
  return {
1048
1050
  gitlabHost,
1049
1051
  gitlabProjectId,
1052
+ gitlabProjectIdExplicit: explicitProjectId != null,
1050
1053
  gitlabToken,
1051
1054
  agentProvider: def.provider,
1052
1055
  agentRepoPath,
@@ -1181,7 +1184,7 @@ export async function main(argv: string[] = process.argv.slice(2)): Promise<void
1181
1184
  process.exit(1);
1182
1185
  }
1183
1186
 
1184
- logger.info(`Watcher started. mode=${mode} provider=${config.agentProvider} host=${config.gitlabHost}${config.gitlabProjectId ? ` project=${config.gitlabProjectId}` : " project=auto (from todos)"}`);
1187
+ logger.info(`Watcher started. mode=${mode} provider=${config.agentProvider} host=${config.gitlabHost}${config.gitlabProjectId ? ` project=${config.gitlabProjectId}${config.gitlabProjectIdExplicit ? "" : " (inferred, todo polling unfiltered)"}` : " project=auto (from todos)"}`);
1185
1188
 
1186
1189
  if (mode === "run-once") {
1187
1190
  await runWatcherCycle(config, dependencies);