@kilnci/cli 0.1.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.
Files changed (130) hide show
  1. package/bin/kiln.js +5 -0
  2. package/dist/base-command.d.ts +21 -0
  3. package/dist/base-command.d.ts.map +1 -0
  4. package/dist/base-command.js +30 -0
  5. package/dist/base-command.js.map +1 -0
  6. package/dist/client.d.ts +166 -0
  7. package/dist/client.d.ts.map +1 -0
  8. package/dist/client.js +321 -0
  9. package/dist/client.js.map +1 -0
  10. package/dist/commands/artifacts.d.ts +17 -0
  11. package/dist/commands/artifacts.d.ts.map +1 -0
  12. package/dist/commands/artifacts.js +96 -0
  13. package/dist/commands/artifacts.js.map +1 -0
  14. package/dist/commands/build.d.ts +15 -0
  15. package/dist/commands/build.d.ts.map +1 -0
  16. package/dist/commands/build.js +79 -0
  17. package/dist/commands/build.js.map +1 -0
  18. package/dist/commands/cancel.d.ts +10 -0
  19. package/dist/commands/cancel.d.ts.map +1 -0
  20. package/dist/commands/cancel.js +27 -0
  21. package/dist/commands/cancel.js.map +1 -0
  22. package/dist/commands/login.d.ts +18 -0
  23. package/dist/commands/login.d.ts.map +1 -0
  24. package/dist/commands/login.js +188 -0
  25. package/dist/commands/login.js.map +1 -0
  26. package/dist/commands/logout.d.ts +7 -0
  27. package/dist/commands/logout.d.ts.map +1 -0
  28. package/dist/commands/logout.js +17 -0
  29. package/dist/commands/logout.js.map +1 -0
  30. package/dist/commands/logs.d.ts +18 -0
  31. package/dist/commands/logs.d.ts.map +1 -0
  32. package/dist/commands/logs.js +139 -0
  33. package/dist/commands/logs.js.map +1 -0
  34. package/dist/commands/org/create.d.ts +13 -0
  35. package/dist/commands/org/create.d.ts.map +1 -0
  36. package/dist/commands/org/create.js +39 -0
  37. package/dist/commands/org/create.js.map +1 -0
  38. package/dist/commands/org/delete.d.ts +13 -0
  39. package/dist/commands/org/delete.d.ts.map +1 -0
  40. package/dist/commands/org/delete.js +44 -0
  41. package/dist/commands/org/delete.js.map +1 -0
  42. package/dist/commands/org/gitlab/remove.d.ts +13 -0
  43. package/dist/commands/org/gitlab/remove.d.ts.map +1 -0
  44. package/dist/commands/org/gitlab/remove.js +51 -0
  45. package/dist/commands/org/gitlab/remove.js.map +1 -0
  46. package/dist/commands/org/gitlab/setup.d.ts +17 -0
  47. package/dist/commands/org/gitlab/setup.d.ts.map +1 -0
  48. package/dist/commands/org/gitlab/setup.js +83 -0
  49. package/dist/commands/org/gitlab/setup.js.map +1 -0
  50. package/dist/commands/org/gitlab/show.d.ts +10 -0
  51. package/dist/commands/org/gitlab/show.d.ts.map +1 -0
  52. package/dist/commands/org/gitlab/show.js +54 -0
  53. package/dist/commands/org/gitlab/show.js.map +1 -0
  54. package/dist/commands/org/gitlab/sync.d.ts +10 -0
  55. package/dist/commands/org/gitlab/sync.d.ts.map +1 -0
  56. package/dist/commands/org/gitlab/sync.js +38 -0
  57. package/dist/commands/org/gitlab/sync.js.map +1 -0
  58. package/dist/commands/org/index.d.ts +11 -0
  59. package/dist/commands/org/index.d.ts.map +1 -0
  60. package/dist/commands/org/index.js +46 -0
  61. package/dist/commands/org/index.js.map +1 -0
  62. package/dist/commands/org/repos/disable.d.ts +11 -0
  63. package/dist/commands/org/repos/disable.d.ts.map +1 -0
  64. package/dist/commands/org/repos/disable.js +32 -0
  65. package/dist/commands/org/repos/disable.js.map +1 -0
  66. package/dist/commands/org/repos/enable.d.ts +11 -0
  67. package/dist/commands/org/repos/enable.d.ts.map +1 -0
  68. package/dist/commands/org/repos/enable.js +32 -0
  69. package/dist/commands/org/repos/enable.js.map +1 -0
  70. package/dist/commands/org/repos.d.ts +14 -0
  71. package/dist/commands/org/repos.d.ts.map +1 -0
  72. package/dist/commands/org/repos.js +54 -0
  73. package/dist/commands/org/repos.js.map +1 -0
  74. package/dist/commands/status.d.ts +17 -0
  75. package/dist/commands/status.d.ts.map +1 -0
  76. package/dist/commands/status.js +73 -0
  77. package/dist/commands/status.js.map +1 -0
  78. package/dist/commands/workers/create.d.ts +15 -0
  79. package/dist/commands/workers/create.d.ts.map +1 -0
  80. package/dist/commands/workers/create.js +74 -0
  81. package/dist/commands/workers/create.js.map +1 -0
  82. package/dist/commands/workers/delete.d.ts +13 -0
  83. package/dist/commands/workers/delete.d.ts.map +1 -0
  84. package/dist/commands/workers/delete.js +40 -0
  85. package/dist/commands/workers/delete.js.map +1 -0
  86. package/dist/commands/workers/index.d.ts +10 -0
  87. package/dist/commands/workers/index.d.ts.map +1 -0
  88. package/dist/commands/workers/index.js +42 -0
  89. package/dist/commands/workers/index.js.map +1 -0
  90. package/dist/commands/workers/logs.d.ts +11 -0
  91. package/dist/commands/workers/logs.d.ts.map +1 -0
  92. package/dist/commands/workers/logs.js +54 -0
  93. package/dist/commands/workers/logs.js.map +1 -0
  94. package/dist/commands/workers/revoke.d.ts +10 -0
  95. package/dist/commands/workers/revoke.d.ts.map +1 -0
  96. package/dist/commands/workers/revoke.js +27 -0
  97. package/dist/commands/workers/revoke.js.map +1 -0
  98. package/dist/commands/workers/start.d.ts +19 -0
  99. package/dist/commands/workers/start.d.ts.map +1 -0
  100. package/dist/commands/workers/start.js +329 -0
  101. package/dist/commands/workers/start.js.map +1 -0
  102. package/dist/commands/workers/status.d.ts +7 -0
  103. package/dist/commands/workers/status.d.ts.map +1 -0
  104. package/dist/commands/workers/status.js +75 -0
  105. package/dist/commands/workers/status.js.map +1 -0
  106. package/dist/commands/workers/stop.d.ts +10 -0
  107. package/dist/commands/workers/stop.d.ts.map +1 -0
  108. package/dist/commands/workers/stop.js +79 -0
  109. package/dist/commands/workers/stop.js.map +1 -0
  110. package/dist/commands/workers/token.d.ts +13 -0
  111. package/dist/commands/workers/token.d.ts.map +1 -0
  112. package/dist/commands/workers/token.js +38 -0
  113. package/dist/commands/workers/token.js.map +1 -0
  114. package/dist/config.d.ts +38 -0
  115. package/dist/config.d.ts.map +1 -0
  116. package/dist/config.js +68 -0
  117. package/dist/config.js.map +1 -0
  118. package/dist/formatters.d.ts +42 -0
  119. package/dist/formatters.d.ts.map +1 -0
  120. package/dist/formatters.js +194 -0
  121. package/dist/formatters.js.map +1 -0
  122. package/dist/index.d.ts +4 -0
  123. package/dist/index.d.ts.map +1 -0
  124. package/dist/index.js +5 -0
  125. package/dist/index.js.map +1 -0
  126. package/dist/lib/workers-helpers.d.ts +20 -0
  127. package/dist/lib/workers-helpers.d.ts.map +1 -0
  128. package/dist/lib/workers-helpers.js +51 -0
  129. package/dist/lib/workers-helpers.js.map +1 -0
  130. package/package.json +56 -0
@@ -0,0 +1,54 @@
1
+ import { Flags } from '@oclif/core';
2
+ import { spawn, execSync } from 'child_process';
3
+ import { BaseCommand } from '../../base-command.js';
4
+ const CONTAINER_NAME = 'kiln-local-worker';
5
+ /**
6
+ * Check if a container exists (running or stopped).
7
+ */
8
+ function containerExists(name) {
9
+ try {
10
+ execSync(`docker inspect ${name}`, { stdio: 'pipe' });
11
+ return true;
12
+ }
13
+ catch {
14
+ return false;
15
+ }
16
+ }
17
+ export default class WorkersLogs extends BaseCommand {
18
+ static description = 'View logs from the local worker container.';
19
+ static examples = [
20
+ '<%= config.bin %> workers logs',
21
+ '<%= config.bin %> workers logs --follow',
22
+ '<%= config.bin %> workers logs --tail 100',
23
+ ];
24
+ static flags = {
25
+ follow: Flags.boolean({
26
+ char: 'f',
27
+ description: 'Follow log output',
28
+ default: false,
29
+ }),
30
+ tail: Flags.integer({
31
+ char: 't',
32
+ description: 'Number of lines to show from the end of the logs',
33
+ default: 100,
34
+ }),
35
+ };
36
+ async run() {
37
+ const { flags } = await this.parse(WorkersLogs);
38
+ if (!containerExists(CONTAINER_NAME)) {
39
+ this.error('No local worker container found. Start one with: kiln workers start');
40
+ }
41
+ const args = ['logs', `--tail=${flags.tail}`];
42
+ if (flags.follow) {
43
+ args.push('-f');
44
+ }
45
+ args.push(CONTAINER_NAME);
46
+ const child = spawn('docker', args, {
47
+ stdio: 'inherit',
48
+ });
49
+ child.on('exit', (code) => {
50
+ process.exit(code || 0);
51
+ });
52
+ }
53
+ }
54
+ //# sourceMappingURL=logs.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logs.js","sourceRoot":"","sources":["../../../src/commands/workers/logs.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,MAAM,aAAa,CAAC;AACpC,OAAO,EAAE,KAAK,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAChD,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AAEpD,MAAM,cAAc,GAAG,mBAAmB,CAAC;AAE3C;;GAEG;AACH,SAAS,eAAe,CAAC,IAAY;IACnC,IAAI,CAAC;QACH,QAAQ,CAAC,kBAAkB,IAAI,EAAE,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,CAAC,CAAC;QACtD,OAAO,IAAI,CAAC;IACd,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,KAAK,CAAC;IACf,CAAC;AACH,CAAC;AAED,MAAM,CAAC,OAAO,OAAO,WAAY,SAAQ,WAAW;IAClD,MAAM,CAAU,WAAW,GAAG,4CAA4C,CAAC;IAE3E,MAAM,CAAU,QAAQ,GAAG;QACzB,gCAAgC;QAChC,yCAAyC;QACzC,2CAA2C;KAC5C,CAAC;IAEF,MAAM,CAAU,KAAK,GAAG;QACtB,MAAM,EAAE,KAAK,CAAC,OAAO,CAAC;YACpB,IAAI,EAAE,GAAG;YACT,WAAW,EAAE,mBAAmB;YAChC,OAAO,EAAE,KAAK;SACf,CAAC;QACF,IAAI,EAAE,KAAK,CAAC,OAAO,CAAC;YAClB,IAAI,EAAE,GAAG;YACT,WAAW,EAAE,kDAAkD;YAC/D,OAAO,EAAE,GAAG;SACb,CAAC;KACH,CAAC;IAEK,KAAK,CAAC,GAAG;QACd,MAAM,EAAE,KAAK,EAAE,GAAG,MAAM,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QAEhD,IAAI,CAAC,eAAe,CAAC,cAAc,CAAC,EAAE,CAAC;YACrC,IAAI,CAAC,KAAK,CAAC,qEAAqE,CAAC,CAAC;QACpF,CAAC;QAED,MAAM,IAAI,GAAG,CAAC,MAAM,EAAE,UAAU,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC;QAE9C,IAAI,KAAK,CAAC,MAAM,EAAE,CAAC;YACjB,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAClB,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QAE1B,MAAM,KAAK,GAAG,KAAK,CAAC,QAAQ,EAAE,IAAI,EAAE;YAClC,KAAK,EAAE,SAAS;SACjB,CAAC,CAAC;QAEH,KAAK,CAAC,EAAE,CAAC,MAAM,EAAE,CAAC,IAAI,EAAE,EAAE;YACxB,OAAO,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC;QAC1B,CAAC,CAAC,CAAC;IACL,CAAC"}
@@ -0,0 +1,10 @@
1
+ import { BaseCommand } from '../../base-command.js';
2
+ export default class WorkersRevoke extends BaseCommand {
3
+ static description: string;
4
+ static examples: string[];
5
+ static args: {
6
+ id: import("@oclif/core/interfaces").Arg<string, Record<string, unknown>>;
7
+ };
8
+ run(): Promise<void>;
9
+ }
10
+ //# sourceMappingURL=revoke.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"revoke.d.ts","sourceRoot":"","sources":["../../../src/commands/workers/revoke.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AAEpD,MAAM,CAAC,OAAO,OAAO,aAAc,SAAQ,WAAW;IACpD,OAAgB,WAAW,SAA0D;IAErF,OAAgB,QAAQ,WAEtB;IAEF,OAAgB,IAAI;;MAKlB;IAEW,GAAG,IAAI,OAAO,CAAC,IAAI,CAAC;CAYlC"}
@@ -0,0 +1,27 @@
1
+ import { Args } from '@oclif/core';
2
+ import { BaseCommand } from '../../base-command.js';
3
+ export default class WorkersRevoke extends BaseCommand {
4
+ static description = 'Revoke all active sessions for a worker (admin only)';
5
+ static examples = [
6
+ '<%= config.bin %> workers revoke w_abc123',
7
+ ];
8
+ static args = {
9
+ id: Args.string({
10
+ description: 'Worker ID',
11
+ required: true,
12
+ }),
13
+ };
14
+ async run() {
15
+ const { args } = await this.parse(WorkersRevoke);
16
+ this.requireAuth();
17
+ try {
18
+ await this.client.revokeWorkerSessions(args.id);
19
+ this.log(`All sessions for worker ${args.id} have been revoked.`);
20
+ this.log('The worker will need to re-register with a new token to reconnect.');
21
+ }
22
+ catch (error) {
23
+ this.handleError(error, 'revoke worker sessions');
24
+ }
25
+ }
26
+ }
27
+ //# sourceMappingURL=revoke.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"revoke.js","sourceRoot":"","sources":["../../../src/commands/workers/revoke.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,aAAa,CAAC;AACnC,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AAEpD,MAAM,CAAC,OAAO,OAAO,aAAc,SAAQ,WAAW;IACpD,MAAM,CAAU,WAAW,GAAG,sDAAsD,CAAC;IAErF,MAAM,CAAU,QAAQ,GAAG;QACzB,2CAA2C;KAC5C,CAAC;IAEF,MAAM,CAAU,IAAI,GAAG;QACrB,EAAE,EAAE,IAAI,CAAC,MAAM,CAAC;YACd,WAAW,EAAE,WAAW;YACxB,QAAQ,EAAE,IAAI;SACf,CAAC;KACH,CAAC;IAEK,KAAK,CAAC,GAAG;QACd,MAAM,EAAE,IAAI,EAAE,GAAG,MAAM,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,CAAC;QACjD,IAAI,CAAC,WAAW,EAAE,CAAC;QAEnB,IAAI,CAAC;YACH,MAAM,IAAI,CAAC,MAAM,CAAC,oBAAoB,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;YAChD,IAAI,CAAC,GAAG,CAAC,2BAA2B,IAAI,CAAC,EAAE,qBAAqB,CAAC,CAAC;YAClE,IAAI,CAAC,GAAG,CAAC,oEAAoE,CAAC,CAAC;QACjF,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,CAAC,WAAW,CAAC,KAAK,EAAE,wBAAwB,CAAC,CAAC;QACpD,CAAC;IACH,CAAC"}
@@ -0,0 +1,19 @@
1
+ import { BaseCommand } from '../../base-command.js';
2
+ export default class WorkersStart extends BaseCommand {
3
+ static description: string;
4
+ static examples: string[];
5
+ static flags: {
6
+ name: import("@oclif/core/interfaces").OptionFlag<string | undefined, import("@oclif/core/interfaces").CustomOptions>;
7
+ 'match-email': import("@oclif/core/interfaces").OptionFlag<string | undefined, import("@oclif/core/interfaces").CustomOptions>;
8
+ selector: import("@oclif/core/interfaces").OptionFlag<string | undefined, import("@oclif/core/interfaces").CustomOptions>;
9
+ exclusive: import("@oclif/core/interfaces").BooleanFlag<boolean>;
10
+ 'max-concurrent': import("@oclif/core/interfaces").OptionFlag<number, import("@oclif/core/interfaces").CustomOptions>;
11
+ image: import("@oclif/core/interfaces").OptionFlag<string, import("@oclif/core/interfaces").CustomOptions>;
12
+ detach: import("@oclif/core/interfaces").BooleanFlag<boolean>;
13
+ 'workspace-dir': import("@oclif/core/interfaces").OptionFlag<string, import("@oclif/core/interfaces").CustomOptions>;
14
+ force: import("@oclif/core/interfaces").BooleanFlag<boolean>;
15
+ env: import("@oclif/core/interfaces").OptionFlag<string[], import("@oclif/core/interfaces").CustomOptions>;
16
+ };
17
+ run(): Promise<void>;
18
+ }
19
+ //# sourceMappingURL=start.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"start.d.ts","sourceRoot":"","sources":["../../../src/commands/workers/start.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AAoFpD,MAAM,CAAC,OAAO,OAAO,YAAa,SAAQ,WAAW;IACnD,OAAgB,WAAW,SACuE;IAElG,OAAgB,QAAQ,WAOtB;IAEF,OAAgB,KAAK;;;;;;;;;;;MAiDnB;IAEW,GAAG,IAAI,OAAO,CAAC,IAAI,CAAC;CAgNlC"}
@@ -0,0 +1,329 @@
1
+ import { Flags } from '@oclif/core';
2
+ import { execSync, spawn } from 'child_process';
3
+ import { existsSync } from 'fs';
4
+ import { homedir, hostname, platform } from 'os';
5
+ import { join } from 'path';
6
+ import { BaseCommand } from '../../base-command.js';
7
+ import { loadConfigFile } from '../../config.js';
8
+ import { toDockerAccessibleUrl, parseSelector, parseEnvFlags } from '../../lib/workers-helpers.js';
9
+ const CONTAINER_NAME = 'kiln-local-worker';
10
+ const DEFAULT_IMAGE = 'kiln/worker:latest';
11
+ /**
12
+ * Detect Docker socket location based on platform and environment.
13
+ */
14
+ function detectDockerSocket() {
15
+ const candidates = [];
16
+ if (platform() === 'darwin') {
17
+ // macOS: Docker Desktop, Colima, or standard location
18
+ candidates.push(join(homedir(), '.docker/run/docker.sock'), join(homedir(), '.colima/default/docker.sock'), '/var/run/docker.sock');
19
+ }
20
+ else {
21
+ // Linux: standard location
22
+ candidates.push('/var/run/docker.sock');
23
+ }
24
+ for (const candidate of candidates) {
25
+ if (existsSync(candidate)) {
26
+ return candidate;
27
+ }
28
+ }
29
+ return null;
30
+ }
31
+ /**
32
+ * Get git user email from local git config.
33
+ */
34
+ function getGitEmail() {
35
+ try {
36
+ const email = execSync('git config user.email', { encoding: 'utf-8' }).trim();
37
+ return email || null;
38
+ }
39
+ catch {
40
+ return null;
41
+ }
42
+ }
43
+ /**
44
+ * Check if a container exists (running or stopped).
45
+ */
46
+ function containerExists(name) {
47
+ try {
48
+ execSync(`docker inspect ${name}`, { stdio: 'pipe' });
49
+ return true;
50
+ }
51
+ catch {
52
+ return false;
53
+ }
54
+ }
55
+ /**
56
+ * Check if a container is running.
57
+ */
58
+ function isContainerRunning(name) {
59
+ try {
60
+ const result = execSync(`docker inspect -f '{{.State.Running}}' ${name}`, {
61
+ encoding: 'utf-8',
62
+ stdio: 'pipe',
63
+ }).trim();
64
+ return result === 'true';
65
+ }
66
+ catch {
67
+ return false;
68
+ }
69
+ }
70
+ /**
71
+ * Stop and remove a container.
72
+ */
73
+ function removeContainer(name) {
74
+ try {
75
+ execSync(`docker rm -f ${name}`, { stdio: 'pipe' });
76
+ }
77
+ catch {
78
+ // Ignore errors
79
+ }
80
+ }
81
+ export default class WorkersStart extends BaseCommand {
82
+ static description = 'Start a local worker container that claims builds matching your git email or custom selector.';
83
+ static examples = [
84
+ '<%= config.bin %> workers start',
85
+ '<%= config.bin %> workers start --match-email=alice@example.com',
86
+ '<%= config.bin %> workers start --selector="project.name=myproject"',
87
+ '<%= config.bin %> workers start --exclusive',
88
+ '<%= config.bin %> workers start --name my-workstation --max-concurrent 4',
89
+ '<%= config.bin %> workers start --env AWS_PROFILE=dev --env NPM_TOKEN=xxx',
90
+ ];
91
+ static flags = {
92
+ name: Flags.string({
93
+ char: 'n',
94
+ description: 'Worker name (defaults to hostname)',
95
+ }),
96
+ 'match-email': Flags.string({
97
+ char: 'e',
98
+ description: 'Match builds by git author email (defaults to git config user.email)',
99
+ }),
100
+ selector: Flags.string({
101
+ char: 's',
102
+ description: 'Custom label selector (format: key=value,key2=value2)',
103
+ }),
104
+ exclusive: Flags.boolean({
105
+ char: 'x',
106
+ description: 'Exclusive mode: only claim matching builds, no fallback',
107
+ default: false,
108
+ }),
109
+ 'max-concurrent': Flags.integer({
110
+ char: 'c',
111
+ description: 'Maximum concurrent builds',
112
+ default: 1,
113
+ }),
114
+ image: Flags.string({
115
+ char: 'i',
116
+ description: 'Worker Docker image',
117
+ default: DEFAULT_IMAGE,
118
+ }),
119
+ detach: Flags.boolean({
120
+ char: 'd',
121
+ description: 'Run container in background (detached mode)',
122
+ default: false,
123
+ }),
124
+ 'workspace-dir': Flags.string({
125
+ char: 'w',
126
+ description: 'Local workspace directory for builds',
127
+ default: join(homedir(), '.kiln', 'workspaces'),
128
+ }),
129
+ force: Flags.boolean({
130
+ char: 'f',
131
+ description: 'Force start (removes existing container if present)',
132
+ default: false,
133
+ }),
134
+ env: Flags.string({
135
+ char: 'E',
136
+ description: 'Environment variable to pass to worker (format: KEY=VALUE, can be repeated)',
137
+ multiple: true,
138
+ default: [],
139
+ }),
140
+ };
141
+ async run() {
142
+ const { flags } = await this.parse(WorkersStart);
143
+ this.requireAuth();
144
+ // Check for existing container
145
+ if (containerExists(CONTAINER_NAME)) {
146
+ if (isContainerRunning(CONTAINER_NAME)) {
147
+ if (flags.force) {
148
+ this.log(`Stopping existing worker container...`);
149
+ removeContainer(CONTAINER_NAME);
150
+ }
151
+ else {
152
+ this.error(`A local worker container is already running.\n` +
153
+ `Use 'kiln workers stop' to stop it, or --force to replace it.`);
154
+ }
155
+ }
156
+ else {
157
+ // Container exists but not running, remove it
158
+ this.log(`Removing stopped worker container...`);
159
+ removeContainer(CONTAINER_NAME);
160
+ }
161
+ }
162
+ // Detect Docker socket
163
+ const dockerSocket = detectDockerSocket();
164
+ if (!dockerSocket) {
165
+ this.error(`Could not find Docker socket.\n` +
166
+ `Make sure Docker is installed and running.\n` +
167
+ `Checked locations:\n` +
168
+ ` - /var/run/docker.sock\n` +
169
+ ` - ~/.docker/run/docker.sock (Docker Desktop)\n` +
170
+ ` - ~/.colima/default/docker.sock (Colima)`);
171
+ }
172
+ // Determine selector
173
+ let matchLabels = {};
174
+ let selectorDescription = '';
175
+ if (flags.selector) {
176
+ matchLabels = parseSelector(flags.selector);
177
+ selectorDescription = flags.selector;
178
+ }
179
+ else {
180
+ const email = flags['match-email'] || getGitEmail();
181
+ if (!email) {
182
+ this.error(`Could not determine git email for build matching.\n` +
183
+ `Either:\n` +
184
+ ` - Set git config user.email\n` +
185
+ ` - Use --match-email flag\n` +
186
+ ` - Use --selector for custom matching`);
187
+ }
188
+ matchLabels['git.author.email'] = email;
189
+ selectorDescription = `git.author.email=${email}`;
190
+ }
191
+ const workerName = flags.name || `${hostname()}-local`;
192
+ const selectorMode = flags.exclusive ? 'exclusive' : 'preferred';
193
+ // Clean up existing workers with the same name
194
+ try {
195
+ const workers = await this.client.listWorkers();
196
+ const existingWorkers = workers.filter((w) => w.name === workerName);
197
+ if (existingWorkers.length > 0) {
198
+ this.log(`Cleaning up ${existingWorkers.length} existing worker(s) with name "${workerName}"...`);
199
+ for (const worker of existingWorkers) {
200
+ await this.client.deleteWorker(worker.id);
201
+ }
202
+ }
203
+ }
204
+ catch (error) {
205
+ // Non-fatal: continue even if cleanup fails
206
+ this.warn(`Could not clean up existing workers: ${error instanceof Error ? error.message : String(error)}`);
207
+ }
208
+ // Create worker via API
209
+ this.log(`Creating worker "${workerName}"...`);
210
+ this.log(` Selector: ${selectorDescription}`);
211
+ this.log(` Mode: ${selectorMode}`);
212
+ this.log('');
213
+ let registrationToken;
214
+ let workerId;
215
+ try {
216
+ const result = await this.client.createWorker({
217
+ name: workerName,
218
+ maxConcurrentBuilds: flags['max-concurrent'],
219
+ labels: { type: 'local', owner: workerName },
220
+ selector: { matchLabels },
221
+ selectorMode,
222
+ tokenTtlMinutes: 60 * 24 * 30, // 30 days (max allowed) for local workers
223
+ });
224
+ registrationToken = result.workerToken;
225
+ workerId = result.worker.id;
226
+ this.log(`Worker created with ID: ${workerId}`);
227
+ }
228
+ catch (error) {
229
+ this.handleError(error, 'create worker');
230
+ }
231
+ // Ensure workspace directory exists
232
+ try {
233
+ execSync(`mkdir -p "${flags['workspace-dir']}"`, { stdio: 'pipe' });
234
+ }
235
+ catch (error) {
236
+ this.handleError(error, 'create workspace directory');
237
+ }
238
+ // Resolve workspace directory to absolute path for Docker volume mount
239
+ // We mount at the SAME path on host and container so that sibling containers
240
+ // (spawned by docker compose in builds) can access the same paths
241
+ const absoluteWorkspaceDir = flags['workspace-dir'].startsWith('/')
242
+ ? flags['workspace-dir']
243
+ : join(process.cwd(), flags['workspace-dir']);
244
+ // Merge environment variables from config file and CLI flags
245
+ // Priority: CLI flags override config file
246
+ const configFile = loadConfigFile();
247
+ const configEnv = configFile.workers?.env || {};
248
+ const cliEnv = parseEnvFlags(flags.env);
249
+ const mergedEnv = { ...configEnv, ...cliEnv };
250
+ // Build docker run command
251
+ const dockerArgs = [
252
+ 'run',
253
+ '--name',
254
+ CONTAINER_NAME,
255
+ '--rm',
256
+ '-v',
257
+ `${dockerSocket}:/var/run/docker.sock`,
258
+ '-v',
259
+ `${absoluteWorkspaceDir}:${absoluteWorkspaceDir}`,
260
+ '-e',
261
+ `WORKER_TOKEN=${registrationToken}`,
262
+ '-e',
263
+ `MASTER_URL=${toDockerAccessibleUrl(this.appConfig.url)}`,
264
+ '-e',
265
+ `WORKSPACES_PATH=${absoluteWorkspaceDir}`,
266
+ '-e',
267
+ `MAX_CONCURRENT_BUILDS=${flags['max-concurrent']}`,
268
+ '-e',
269
+ 'SKIP_WORKSPACE_UPLOAD=true', // Local workers keep workspaces on disk, no need to upload
270
+ ];
271
+ // Add user-provided environment variables
272
+ for (const [key, value] of Object.entries(mergedEnv)) {
273
+ dockerArgs.push('-e', `${key}=${value}`);
274
+ }
275
+ if (flags.detach) {
276
+ dockerArgs.push('-d');
277
+ }
278
+ dockerArgs.push(flags.image);
279
+ this.log('');
280
+ this.log(`Starting worker container...`);
281
+ this.log(` Image: ${flags.image}`);
282
+ this.log(` Docker socket: ${dockerSocket}`);
283
+ this.log(` Workspaces: ${absoluteWorkspaceDir}`);
284
+ this.log(` Master URL: ${this.appConfig.url}`);
285
+ if (Object.keys(mergedEnv).length > 0) {
286
+ this.log(` Extra env vars: ${Object.keys(mergedEnv).join(', ')}`);
287
+ }
288
+ this.log('');
289
+ if (flags.detach) {
290
+ // Run detached
291
+ try {
292
+ execSync(`docker ${dockerArgs.join(' ')}`, { stdio: 'pipe' });
293
+ this.log(`Local worker started in background.`);
294
+ this.log('');
295
+ this.log(`Use 'kiln workers stop' to stop it.`);
296
+ this.log(`Use 'kiln workers logs' to view logs.`);
297
+ }
298
+ catch (error) {
299
+ this.handleError(error, 'start worker container');
300
+ }
301
+ }
302
+ else {
303
+ // Run in foreground with signal handling
304
+ this.log(`Worker running (Ctrl+C to stop)...`);
305
+ this.log('');
306
+ const child = spawn('docker', dockerArgs, {
307
+ stdio: 'inherit',
308
+ });
309
+ // Handle graceful shutdown
310
+ const cleanup = () => {
311
+ this.log('\nStopping worker...');
312
+ try {
313
+ execSync(`docker stop ${CONTAINER_NAME}`, { stdio: 'pipe' });
314
+ }
315
+ catch {
316
+ // Container might already be stopped
317
+ }
318
+ };
319
+ process.on('SIGINT', cleanup);
320
+ process.on('SIGTERM', cleanup);
321
+ child.on('exit', (code) => {
322
+ process.removeListener('SIGINT', cleanup);
323
+ process.removeListener('SIGTERM', cleanup);
324
+ process.exit(code || 0);
325
+ });
326
+ }
327
+ }
328
+ }
329
+ //# sourceMappingURL=start.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"start.js","sourceRoot":"","sources":["../../../src/commands/workers/start.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,7 @@
1
+ import { BaseCommand } from '../../base-command.js';
2
+ export default class WorkersStatus extends BaseCommand {
3
+ static description: string;
4
+ static examples: string[];
5
+ run(): Promise<void>;
6
+ }
7
+ //# sourceMappingURL=status.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"status.d.ts","sourceRoot":"","sources":["../../../src/commands/workers/status.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AA0CpD,MAAM,CAAC,OAAO,OAAO,aAAc,SAAQ,WAAW;IACpD,OAAgB,WAAW,SAAoD;IAE/E,OAAgB,QAAQ,WAAwC;IAEnD,GAAG,IAAI,OAAO,CAAC,IAAI,CAAC;CAyClC"}
@@ -0,0 +1,75 @@
1
+ import { execSync } from 'child_process';
2
+ import { BaseCommand } from '../../base-command.js';
3
+ const CONTAINER_NAME = 'kiln-local-worker';
4
+ /**
5
+ * Check if a container exists (running or stopped).
6
+ */
7
+ function containerExists(name) {
8
+ try {
9
+ execSync(`docker inspect ${name}`, { stdio: 'pipe' });
10
+ return true;
11
+ }
12
+ catch {
13
+ return false;
14
+ }
15
+ }
16
+ /**
17
+ * Get container status details.
18
+ */
19
+ function getContainerStatus(name) {
20
+ try {
21
+ const result = execSync(`docker inspect -f '{{.State.Running}}|{{.State.Status}}|{{.State.StartedAt}}|{{.Config.Image}}' ${name}`, { encoding: 'utf-8', stdio: 'pipe' }).trim();
22
+ const [running, status, startedAt, image] = result.split('|');
23
+ return {
24
+ running: running === 'true',
25
+ status,
26
+ startedAt,
27
+ image,
28
+ };
29
+ }
30
+ catch {
31
+ return null;
32
+ }
33
+ }
34
+ export default class WorkersStatus extends BaseCommand {
35
+ static description = 'Show the status of the local worker container.';
36
+ static examples = ['<%= config.bin %> workers status'];
37
+ async run() {
38
+ if (!containerExists(CONTAINER_NAME)) {
39
+ this.log('No local worker container found.');
40
+ this.log('');
41
+ this.log('Start one with: kiln workers start');
42
+ return;
43
+ }
44
+ const status = getContainerStatus(CONTAINER_NAME);
45
+ if (!status) {
46
+ this.error('Failed to get container status');
47
+ }
48
+ this.log('Local Worker Container Status');
49
+ this.log('');
50
+ this.log(` Container: ${CONTAINER_NAME}`);
51
+ this.log(` Image: ${status.image}`);
52
+ this.log(` Status: ${status.status}`);
53
+ this.log(` Running: ${status.running ? 'Yes' : 'No'}`);
54
+ if (status.running) {
55
+ const startedAt = new Date(status.startedAt);
56
+ const uptime = Date.now() - startedAt.getTime();
57
+ const hours = Math.floor(uptime / (1000 * 60 * 60));
58
+ const minutes = Math.floor((uptime % (1000 * 60 * 60)) / (1000 * 60));
59
+ this.log(` Started: ${startedAt.toLocaleString()}`);
60
+ this.log(` Uptime: ${hours}h ${minutes}m`);
61
+ }
62
+ this.log('');
63
+ if (status.running) {
64
+ this.log('Commands:');
65
+ this.log(' kiln workers logs - View logs');
66
+ this.log(' kiln workers logs -f - Follow logs');
67
+ this.log(' kiln workers stop - Stop the worker');
68
+ }
69
+ else {
70
+ this.log('The container exists but is not running.');
71
+ this.log('Start it with: kiln workers start');
72
+ }
73
+ }
74
+ }
75
+ //# sourceMappingURL=status.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"status.js","sourceRoot":"","sources":["../../../src/commands/workers/status.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,10 @@
1
+ import { BaseCommand } from '../../base-command.js';
2
+ export default class WorkersStop extends BaseCommand {
3
+ static description: string;
4
+ static examples: string[];
5
+ static flags: {
6
+ force: import("@oclif/core/interfaces").BooleanFlag<boolean>;
7
+ };
8
+ run(): Promise<void>;
9
+ }
10
+ //# sourceMappingURL=stop.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"stop.d.ts","sourceRoot":"","sources":["../../../src/commands/workers/stop.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AA+BpD,MAAM,CAAC,OAAO,OAAO,WAAY,SAAQ,WAAW;IAClD,OAAgB,WAAW,SAAsC;IAEjE,OAAgB,QAAQ,WAGtB;IAEF,OAAgB,KAAK;;MAMnB;IAEW,GAAG,IAAI,OAAO,CAAC,IAAI,CAAC;CAiClC"}