@alertee/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 (45) hide show
  1. package/dist/api.d.ts +77 -0
  2. package/dist/api.d.ts.map +1 -0
  3. package/dist/api.js +52 -0
  4. package/dist/api.js.map +1 -0
  5. package/dist/commands/checks/create.d.ts +2 -0
  6. package/dist/commands/checks/create.d.ts.map +1 -0
  7. package/dist/commands/checks/create.js +68 -0
  8. package/dist/commands/checks/create.js.map +1 -0
  9. package/dist/commands/checks/list.d.ts +2 -0
  10. package/dist/commands/checks/list.d.ts.map +1 -0
  11. package/dist/commands/checks/list.js +35 -0
  12. package/dist/commands/checks/list.js.map +1 -0
  13. package/dist/commands/link.d.ts +2 -0
  14. package/dist/commands/link.d.ts.map +1 -0
  15. package/dist/commands/link.js +29 -0
  16. package/dist/commands/link.js.map +1 -0
  17. package/dist/commands/login.d.ts +4 -0
  18. package/dist/commands/login.d.ts.map +1 -0
  19. package/dist/commands/login.js +133 -0
  20. package/dist/commands/login.js.map +1 -0
  21. package/dist/commands/logout.d.ts +2 -0
  22. package/dist/commands/logout.d.ts.map +1 -0
  23. package/dist/commands/logout.js +6 -0
  24. package/dist/commands/logout.js.map +1 -0
  25. package/dist/commands/whoami.d.ts +2 -0
  26. package/dist/commands/whoami.d.ts.map +1 -0
  27. package/dist/commands/whoami.js +13 -0
  28. package/dist/commands/whoami.js.map +1 -0
  29. package/dist/config.d.ts +35 -0
  30. package/dist/config.d.ts.map +1 -0
  31. package/dist/config.js +68 -0
  32. package/dist/config.js.map +1 -0
  33. package/dist/index.d.ts +3 -0
  34. package/dist/index.d.ts.map +1 -0
  35. package/dist/index.js +47 -0
  36. package/dist/index.js.map +1 -0
  37. package/dist/intervals.d.ts +15 -0
  38. package/dist/intervals.d.ts.map +1 -0
  39. package/dist/intervals.js +36 -0
  40. package/dist/intervals.js.map +1 -0
  41. package/dist/mcp.d.ts +7 -0
  42. package/dist/mcp.d.ts.map +1 -0
  43. package/dist/mcp.js +191 -0
  44. package/dist/mcp.js.map +1 -0
  45. package/package.json +27 -0
package/dist/api.d.ts ADDED
@@ -0,0 +1,77 @@
1
+ import { Config } from './config.js';
2
+ export declare class ApiError extends Error {
3
+ readonly status: number;
4
+ constructor(status: number, message: string);
5
+ }
6
+ export declare function createClient(config: Config): {
7
+ listTokens: () => Promise<{
8
+ tokens: TokenItem[];
9
+ }>;
10
+ listOrganizations: () => Promise<{
11
+ organizations: OrgItem[];
12
+ }>;
13
+ listConnections: () => Promise<{
14
+ connections: ConnectionItem[];
15
+ }>;
16
+ listChecks: () => Promise<{
17
+ checks: CheckItem[];
18
+ }>;
19
+ createCheck: (body: CreateCheckBody) => Promise<{
20
+ check: CheckItem;
21
+ }>;
22
+ };
23
+ export interface TokenItem {
24
+ id: string;
25
+ name: string;
26
+ prefix: string;
27
+ created_at: string;
28
+ last_used_at: string | null;
29
+ expires_at: string | null;
30
+ }
31
+ /**
32
+ * GET /organizations returns each org nested under `organization`, alongside
33
+ * the caller's role. (Matches backend organization.UserOrganization.)
34
+ */
35
+ export interface OrgItem {
36
+ organization: {
37
+ id: string;
38
+ name: string;
39
+ slug: string;
40
+ };
41
+ role: string;
42
+ joined_at: string;
43
+ }
44
+ export interface ConnectionItem {
45
+ id: string;
46
+ name: string;
47
+ type: string;
48
+ }
49
+ /**
50
+ * GET /checks returns db.Check rows serialized with Go PascalCase field names
51
+ * (no json tags on the sqlc model). Interval/LastStatus are sql.Null* wrappers.
52
+ */
53
+ export interface CheckItem {
54
+ ID: string;
55
+ Name: string;
56
+ ConnectionID: string;
57
+ Interval: {
58
+ CheckInterval: string;
59
+ Valid: boolean;
60
+ } | null;
61
+ LastStatus: {
62
+ CheckStatus: string;
63
+ Valid: boolean;
64
+ } | null;
65
+ }
66
+ export interface CreateCheckBody {
67
+ name: string;
68
+ connection_id: string;
69
+ query: string;
70
+ condition: {
71
+ type: string;
72
+ value: string;
73
+ };
74
+ interval: string;
75
+ alert_group_id?: string;
76
+ }
77
+ //# sourceMappingURL=api.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../src/api.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAA6C,MAAM,aAAa,CAAA;AAE/E,qBAAa,QAAS,SAAQ,KAAK;aAEf,MAAM,EAAE,MAAM;gBAAd,MAAM,EAAE,MAAM,EAC9B,OAAO,EAAE,MAAM;CAKlB;AAED,wBAAgB,YAAY,CAAC,MAAM,EAAE,MAAM;;gBAoCnB,SAAS,EAAE;;;uBAIJ,OAAO,EAAE;;;qBAIX,cAAc,EAAE;;;gBAIrB,SAAS,EAAE;;wBAEX,eAAe;eAChB,SAAS;;EAE/B;AAED,MAAM,WAAW,SAAS;IACxB,EAAE,EAAE,MAAM,CAAA;IACV,IAAI,EAAE,MAAM,CAAA;IACZ,MAAM,EAAE,MAAM,CAAA;IACd,UAAU,EAAE,MAAM,CAAA;IAClB,YAAY,EAAE,MAAM,GAAG,IAAI,CAAA;IAC3B,UAAU,EAAE,MAAM,GAAG,IAAI,CAAA;CAC1B;AAED;;;GAGG;AACH,MAAM,WAAW,OAAO;IACtB,YAAY,EAAE;QACZ,EAAE,EAAE,MAAM,CAAA;QACV,IAAI,EAAE,MAAM,CAAA;QACZ,IAAI,EAAE,MAAM,CAAA;KACb,CAAA;IACD,IAAI,EAAE,MAAM,CAAA;IACZ,SAAS,EAAE,MAAM,CAAA;CAClB;AAED,MAAM,WAAW,cAAc;IAC7B,EAAE,EAAE,MAAM,CAAA;IACV,IAAI,EAAE,MAAM,CAAA;IACZ,IAAI,EAAE,MAAM,CAAA;CACb;AAED;;;GAGG;AACH,MAAM,WAAW,SAAS;IACxB,EAAE,EAAE,MAAM,CAAA;IACV,IAAI,EAAE,MAAM,CAAA;IACZ,YAAY,EAAE,MAAM,CAAA;IACpB,QAAQ,EAAE;QAAE,aAAa,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,OAAO,CAAA;KAAE,GAAG,IAAI,CAAA;IAC1D,UAAU,EAAE;QAAE,WAAW,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,OAAO,CAAA;KAAE,GAAG,IAAI,CAAA;CAC3D;AAED,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAA;IACZ,aAAa,EAAE,MAAM,CAAA;IACrB,KAAK,EAAE,MAAM,CAAA;IACb,SAAS,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,CAAA;IAC1C,QAAQ,EAAE,MAAM,CAAA;IAChB,cAAc,CAAC,EAAE,MAAM,CAAA;CACxB"}
package/dist/api.js ADDED
@@ -0,0 +1,52 @@
1
+ import { resolveApiUrl, resolveOrgId, resolveToken } from './config.js';
2
+ export class ApiError extends Error {
3
+ status;
4
+ constructor(status, message) {
5
+ super(message);
6
+ this.status = status;
7
+ this.name = 'ApiError';
8
+ }
9
+ }
10
+ export function createClient(config) {
11
+ const baseUrl = resolveApiUrl(config);
12
+ const headers = {
13
+ Authorization: `Bearer ${resolveToken(config) ?? config.token}`,
14
+ 'Content-Type': 'application/json',
15
+ };
16
+ const orgId = resolveOrgId(config);
17
+ if (orgId) {
18
+ headers['X-Organization-ID'] = orgId;
19
+ }
20
+ async function request(method, path, body) {
21
+ const res = await fetch(`${baseUrl}${path}`, {
22
+ method,
23
+ headers,
24
+ body: body !== undefined ? JSON.stringify(body) : undefined,
25
+ });
26
+ if (!res.ok) {
27
+ let msg = res.statusText;
28
+ try {
29
+ const err = (await res.json());
30
+ if (err.message)
31
+ msg = err.message;
32
+ }
33
+ catch { }
34
+ throw new ApiError(res.status, msg);
35
+ }
36
+ if (res.status === 204)
37
+ return undefined;
38
+ return res.json();
39
+ }
40
+ return {
41
+ // Auth
42
+ listTokens: () => request('GET', '/auth/tokens'),
43
+ // Organizations
44
+ listOrganizations: () => request('GET', '/organizations'),
45
+ // Connections
46
+ listConnections: () => request('GET', '/connections'),
47
+ // Checks
48
+ listChecks: () => request('GET', '/checks'),
49
+ createCheck: (body) => request('POST', '/checks', body),
50
+ };
51
+ }
52
+ //# sourceMappingURL=api.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"api.js","sourceRoot":"","sources":["../src/api.ts"],"names":[],"mappings":"AAAA,OAAO,EAAU,aAAa,EAAE,YAAY,EAAE,YAAY,EAAE,MAAM,aAAa,CAAA;AAE/E,MAAM,OAAO,QAAS,SAAQ,KAAK;IAEf;IADlB,YACkB,MAAc,EAC9B,OAAe;QAEf,KAAK,CAAC,OAAO,CAAC,CAAA;QAHE,WAAM,GAAN,MAAM,CAAQ;QAI9B,IAAI,CAAC,IAAI,GAAG,UAAU,CAAA;IACxB,CAAC;CACF;AAED,MAAM,UAAU,YAAY,CAAC,MAAc;IACzC,MAAM,OAAO,GAAG,aAAa,CAAC,MAAM,CAAC,CAAA;IACrC,MAAM,OAAO,GAA2B;QACtC,aAAa,EAAE,UAAU,YAAY,CAAC,MAAM,CAAC,IAAI,MAAM,CAAC,KAAK,EAAE;QAC/D,cAAc,EAAE,kBAAkB;KACnC,CAAA;IACD,MAAM,KAAK,GAAG,YAAY,CAAC,MAAM,CAAC,CAAA;IAClC,IAAI,KAAK,EAAE,CAAC;QACV,OAAO,CAAC,mBAAmB,CAAC,GAAG,KAAK,CAAA;IACtC,CAAC;IAED,KAAK,UAAU,OAAO,CACpB,MAAc,EACd,IAAY,EACZ,IAAc;QAEd,MAAM,GAAG,GAAG,MAAM,KAAK,CAAC,GAAG,OAAO,GAAG,IAAI,EAAE,EAAE;YAC3C,MAAM;YACN,OAAO;YACP,IAAI,EAAE,IAAI,KAAK,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,SAAS;SAC5D,CAAC,CAAA;QACF,IAAI,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;YACZ,IAAI,GAAG,GAAG,GAAG,CAAC,UAAU,CAAA;YACxB,IAAI,CAAC;gBACH,MAAM,GAAG,GAAG,CAAC,MAAM,GAAG,CAAC,IAAI,EAAE,CAAyB,CAAA;gBACtD,IAAI,GAAG,CAAC,OAAO;oBAAE,GAAG,GAAG,GAAG,CAAC,OAAO,CAAA;YACpC,CAAC;YAAC,MAAM,CAAC,CAAA,CAAC;YACV,MAAM,IAAI,QAAQ,CAAC,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,CAAA;QACrC,CAAC;QACD,IAAI,GAAG,CAAC,MAAM,KAAK,GAAG;YAAE,OAAO,SAAc,CAAA;QAC7C,OAAO,GAAG,CAAC,IAAI,EAAgB,CAAA;IACjC,CAAC;IAED,OAAO;QACL,OAAO;QACP,UAAU,EAAE,GAAG,EAAE,CACf,OAAO,CAA0B,KAAK,EAAE,cAAc,CAAC;QAEzD,gBAAgB;QAChB,iBAAiB,EAAE,GAAG,EAAE,CACtB,OAAO,CAA+B,KAAK,EAAE,gBAAgB,CAAC;QAEhE,cAAc;QACd,eAAe,EAAE,GAAG,EAAE,CACpB,OAAO,CAAoC,KAAK,EAAE,cAAc,CAAC;QAEnE,SAAS;QACT,UAAU,EAAE,GAAG,EAAE,CACf,OAAO,CAA0B,KAAK,EAAE,SAAS,CAAC;QAEpD,WAAW,EAAE,CAAC,IAAqB,EAAE,EAAE,CACrC,OAAO,CAAuB,MAAM,EAAE,SAAS,EAAE,IAAI,CAAC;KACzD,CAAA;AACH,CAAC"}
@@ -0,0 +1,2 @@
1
+ export declare function createCheck(): Promise<void>;
2
+ //# sourceMappingURL=create.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"create.d.ts","sourceRoot":"","sources":["../../../src/commands/checks/create.ts"],"names":[],"mappings":"AAKA,wBAAsB,WAAW,IAAI,OAAO,CAAC,IAAI,CAAC,CAsEjD"}
@@ -0,0 +1,68 @@
1
+ import { input, number, select } from '@inquirer/prompts';
2
+ import { createClient } from '../../api.js';
3
+ import { requireConfig, resolveOrgId, resolveWebUrl, usingEnvToken } from '../../config.js';
4
+ import { INTERVAL_CHOICES } from '../../intervals.js';
5
+ export async function createCheck() {
6
+ const config = requireConfig();
7
+ if (!resolveOrgId(config) && !usingEnvToken()) {
8
+ console.error('No organization linked. Run: alertee link (or set ALERTEE_ORG)');
9
+ process.exit(1);
10
+ }
11
+ const client = createClient(config);
12
+ // Fetch connections to let user choose
13
+ let connections;
14
+ try {
15
+ const resp = await client.listConnections();
16
+ connections = resp.connections;
17
+ }
18
+ catch (err) {
19
+ console.error('Failed to fetch connections:', err.message);
20
+ process.exit(1);
21
+ }
22
+ if (connections.length === 0) {
23
+ console.error('No database connections found. Add one at app.alertee.app/settings?tab=connections');
24
+ process.exit(1);
25
+ }
26
+ const name = await input({ message: 'Check name:' });
27
+ const connectionId = await select({
28
+ message: 'Database connection:',
29
+ choices: connections.map((c) => ({ name: `${c.name} (${c.type})`, value: c.id })),
30
+ });
31
+ const query = await input({
32
+ message: 'SQL query (must return a single numeric value):',
33
+ validate: (v) => v.trim().length > 0 || 'Query is required',
34
+ });
35
+ const conditionType = await select({
36
+ message: 'Condition type:',
37
+ choices: [
38
+ { name: 'Greater than', value: 'greater_than' },
39
+ { name: 'Less than', value: 'less_than' },
40
+ { name: 'Equal to', value: 'equals' },
41
+ { name: 'Not equal to', value: 'not_equals' },
42
+ ],
43
+ });
44
+ const threshold = await number({
45
+ message: 'Threshold value:',
46
+ validate: (v) => v !== undefined || 'Required',
47
+ });
48
+ const interval = await select({
49
+ message: 'Check interval:',
50
+ choices: INTERVAL_CHOICES,
51
+ });
52
+ try {
53
+ const resp = await client.createCheck({
54
+ name,
55
+ connection_id: connectionId,
56
+ query,
57
+ condition: { type: conditionType, value: String(threshold) },
58
+ interval,
59
+ });
60
+ console.log(`\nCheck created: ${resp.check.ID}`);
61
+ console.log(`View at: ${resolveWebUrl()}/checks/${resp.check.ID}`);
62
+ }
63
+ catch (err) {
64
+ console.error('Failed to create check:', err.message);
65
+ process.exit(1);
66
+ }
67
+ }
68
+ //# sourceMappingURL=create.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"create.js","sourceRoot":"","sources":["../../../src/commands/checks/create.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function listChecks(): Promise<void>;
2
+ //# sourceMappingURL=list.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list.d.ts","sourceRoot":"","sources":["../../../src/commands/checks/list.ts"],"names":[],"mappings":"AAIA,wBAAsB,UAAU,IAAI,OAAO,CAAC,IAAI,CAAC,CAgChD"}
@@ -0,0 +1,35 @@
1
+ import { createClient } from '../../api.js';
2
+ import { requireConfig, resolveOrgId, usingEnvToken } from '../../config.js';
3
+ import { formatInterval } from '../../intervals.js';
4
+ export async function listChecks() {
5
+ const config = requireConfig();
6
+ if (!resolveOrgId(config) && !usingEnvToken()) {
7
+ console.error('No organization linked. Run: alertee link (or set ALERTEE_ORG)');
8
+ process.exit(1);
9
+ }
10
+ const client = createClient(config);
11
+ let data;
12
+ try {
13
+ data = await client.listChecks();
14
+ }
15
+ catch (err) {
16
+ console.error('Failed to list checks:', err.message);
17
+ process.exit(1);
18
+ }
19
+ const checks = data.checks;
20
+ if (checks.length === 0) {
21
+ console.log('No checks found.');
22
+ return;
23
+ }
24
+ const nameWidth = Math.max(4, ...checks.map((c) => (c.Name ?? '').length));
25
+ const header = `${'NAME'.padEnd(nameWidth)} STATUS INTERVAL`;
26
+ console.log(header);
27
+ console.log('─'.repeat(header.length));
28
+ for (const c of checks) {
29
+ const name = c.Name ?? '(unnamed)';
30
+ const status = c.LastStatus?.Valid ? c.LastStatus.CheckStatus : '—';
31
+ const interval = c.Interval?.Valid ? formatInterval(c.Interval.CheckInterval) : '—';
32
+ console.log(`${name.padEnd(nameWidth)} ${status.padEnd(12)} ${interval}`);
33
+ }
34
+ }
35
+ //# sourceMappingURL=list.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list.js","sourceRoot":"","sources":["../../../src/commands/checks/list.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,cAAc,CAAA;AAC3C,OAAO,EAAE,aAAa,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,iBAAiB,CAAA;AAC5E,OAAO,EAAE,cAAc,EAAE,MAAM,oBAAoB,CAAA;AAEnD,MAAM,CAAC,KAAK,UAAU,UAAU;IAC9B,MAAM,MAAM,GAAG,aAAa,EAAE,CAAA;IAC9B,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,IAAI,CAAC,aAAa,EAAE,EAAE,CAAC;QAC9C,OAAO,CAAC,KAAK,CAAC,gEAAgE,CAAC,CAAA;QAC/E,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;IAED,MAAM,MAAM,GAAG,YAAY,CAAC,MAAM,CAAC,CAAA;IACnC,IAAI,IAAmD,CAAA;IACvD,IAAI,CAAC;QACH,IAAI,GAAG,MAAM,MAAM,CAAC,UAAU,EAAE,CAAA;IAClC,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,CAAC,KAAK,CAAC,wBAAwB,EAAG,GAAa,CAAC,OAAO,CAAC,CAAA;QAC/D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;IAED,MAAM,MAAM,GAAG,IAAI,CAAC,MAAM,CAAA;IAC1B,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACxB,OAAO,CAAC,GAAG,CAAC,kBAAkB,CAAC,CAAA;QAC/B,OAAM;IACR,CAAC;IAED,MAAM,SAAS,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,GAAG,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,IAAI,EAAE,CAAC,CAAC,MAAM,CAAC,CAAC,CAAA;IAC1E,MAAM,MAAM,GAAG,GAAG,MAAM,CAAC,MAAM,CAAC,SAAS,CAAC,yBAAyB,CAAA;IACnE,OAAO,CAAC,GAAG,CAAC,MAAM,CAAC,CAAA;IACnB,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,CAAA;IACtC,KAAK,MAAM,CAAC,IAAI,MAAM,EAAE,CAAC;QACvB,MAAM,IAAI,GAAG,CAAC,CAAC,IAAI,IAAI,WAAW,CAAA;QAClC,MAAM,MAAM,GAAG,CAAC,CAAC,UAAU,EAAE,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,UAAU,CAAC,WAAW,CAAC,CAAC,CAAC,GAAG,CAAA;QACnE,MAAM,QAAQ,GAAG,CAAC,CAAC,QAAQ,EAAE,KAAK,CAAC,CAAC,CAAC,cAAc,CAAC,CAAC,CAAC,QAAQ,CAAC,aAAa,CAAC,CAAC,CAAC,CAAC,GAAG,CAAA;QACnF,OAAO,CAAC,GAAG,CAAC,GAAG,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,KAAK,MAAM,CAAC,MAAM,CAAC,EAAE,CAAC,IAAI,QAAQ,EAAE,CAAC,CAAA;IAC5E,CAAC;AACH,CAAC"}
@@ -0,0 +1,2 @@
1
+ export declare function link(): Promise<void>;
2
+ //# sourceMappingURL=link.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"link.d.ts","sourceRoot":"","sources":["../../src/commands/link.ts"],"names":[],"mappings":"AAIA,wBAAsB,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC,CA2B1C"}
@@ -0,0 +1,29 @@
1
+ import { select } from '@inquirer/prompts';
2
+ import { createClient } from '../api.js';
3
+ import { loadConfig, requireConfig, saveConfig } from '../config.js';
4
+ export async function link() {
5
+ const config = requireConfig();
6
+ const client = createClient(config);
7
+ let orgs;
8
+ try {
9
+ const resp = await client.listOrganizations();
10
+ orgs = resp.organizations;
11
+ }
12
+ catch (err) {
13
+ console.error('Failed to fetch organizations:', err.message);
14
+ process.exit(1);
15
+ }
16
+ if (orgs.length === 0) {
17
+ console.error('No organizations found. Create one at app.alertee.app.');
18
+ process.exit(1);
19
+ }
20
+ const orgId = await select({
21
+ message: 'Select an organization:',
22
+ choices: orgs.map((o) => ({ name: o.organization.name, value: o.organization.id })),
23
+ });
24
+ const org = orgs.find((o) => o.organization.id === orgId).organization;
25
+ const existing = loadConfig();
26
+ saveConfig({ ...config, ...existing, organizationId: org.id, organizationName: org.name });
27
+ console.log(`Linked to "${org.name}".`);
28
+ }
29
+ //# sourceMappingURL=link.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"link.js","sourceRoot":"","sources":["../../src/commands/link.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,mBAAmB,CAAA;AAC1C,OAAO,EAAE,YAAY,EAAE,MAAM,WAAW,CAAA;AACxC,OAAO,EAAE,UAAU,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,cAAc,CAAA;AAEpE,MAAM,CAAC,KAAK,UAAU,IAAI;IACxB,MAAM,MAAM,GAAG,aAAa,EAAE,CAAA;IAC9B,MAAM,MAAM,GAAG,YAAY,CAAC,MAAM,CAAC,CAAA;IAEnC,IAAI,IAA2E,CAAA;IAC/E,IAAI,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,MAAM,CAAC,iBAAiB,EAAE,CAAA;QAC7C,IAAI,GAAG,IAAI,CAAC,aAAa,CAAA;IAC3B,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,CAAC,KAAK,CAAC,gCAAgC,EAAG,GAAa,CAAC,OAAO,CAAC,CAAA;QACvE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;IAED,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACtB,OAAO,CAAC,KAAK,CAAC,wDAAwD,CAAC,CAAA;QACvE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;IAED,MAAM,KAAK,GAAG,MAAM,MAAM,CAAC;QACzB,OAAO,EAAE,yBAAyB;QAClC,OAAO,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,IAAI,EAAE,CAAC,CAAC,YAAY,CAAC,IAAI,EAAE,KAAK,EAAE,CAAC,CAAC,YAAY,CAAC,EAAE,EAAE,CAAC,CAAC;KACpF,CAAC,CAAA;IAEF,MAAM,GAAG,GAAG,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,YAAY,CAAC,EAAE,KAAK,KAAK,CAAE,CAAC,YAAY,CAAA;IACvE,MAAM,QAAQ,GAAG,UAAU,EAAE,CAAA;IAC7B,UAAU,CAAC,EAAE,GAAG,MAAM,EAAE,GAAG,QAAQ,EAAE,cAAc,EAAE,GAAG,CAAC,EAAE,EAAE,gBAAgB,EAAE,GAAG,CAAC,IAAI,EAAE,CAAC,CAAA;IAC1F,OAAO,CAAC,GAAG,CAAC,cAAc,GAAG,CAAC,IAAI,IAAI,CAAC,CAAA;AACzC,CAAC"}
@@ -0,0 +1,4 @@
1
+ export declare function login(opts?: {
2
+ browser?: boolean;
3
+ }): Promise<void>;
4
+ //# sourceMappingURL=login.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"login.d.ts","sourceRoot":"","sources":["../../src/commands/login.ts"],"names":[],"mappings":"AA0FA,wBAAsB,KAAK,CAAC,IAAI,GAAE;IAAE,OAAO,CAAC,EAAE,OAAO,CAAA;CAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAkE3E"}
@@ -0,0 +1,133 @@
1
+ import { spawn } from 'node:child_process';
2
+ import { createHash, randomBytes } from 'node:crypto';
3
+ import * as http from 'node:http';
4
+ import { resolveApiUrl, resolveWebUrl, saveConfig } from '../config.js';
5
+ const CALLBACK_TIMEOUT_MS = 5 * 60 * 1000;
6
+ function base64url(buf) {
7
+ return buf.toString('base64url');
8
+ }
9
+ function openBrowser(url) {
10
+ try {
11
+ if (process.platform === 'darwin') {
12
+ spawn('open', [url], { detached: true, stdio: 'ignore' }).unref();
13
+ }
14
+ else if (process.platform === 'win32') {
15
+ spawn('cmd', ['/c', 'start', '', url], { detached: true, stdio: 'ignore' }).unref();
16
+ }
17
+ else {
18
+ spawn('xdg-open', [url], { detached: true, stdio: 'ignore' }).unref();
19
+ }
20
+ }
21
+ catch {
22
+ // Browser couldn't be opened automatically; the URL is printed as a fallback.
23
+ }
24
+ }
25
+ const RESULT_PAGE = (heading, body) => `<!doctype html>
26
+ <html><head><meta charset="utf-8"><title>Alertee CLI</title>
27
+ <style>body{font-family:system-ui,sans-serif;display:flex;align-items:center;justify-content:center;height:100vh;margin:0;background:#0a0a0a;color:#fafafa}
28
+ .card{text-align:center;max-width:28rem;padding:2rem}h1{font-size:1.25rem;margin:0 0 .5rem}p{color:#a1a1aa;margin:0}</style></head>
29
+ <body><div class="card"><h1>${heading}</h1><p>${body}</p></div></body></html>`;
30
+ /**
31
+ * Start a loopback HTTP server on an OS-assigned port and resolve when the
32
+ * browser redirects back to /callback (or on timeout).
33
+ */
34
+ function startCallbackServer() {
35
+ return new Promise((resolve, reject) => {
36
+ let settle;
37
+ const callback = new Promise((res) => {
38
+ settle = res;
39
+ });
40
+ const server = http.createServer((req, res) => {
41
+ const reqUrl = new URL(req.url ?? '', 'http://127.0.0.1');
42
+ if (reqUrl.pathname !== '/callback') {
43
+ res.writeHead(404);
44
+ res.end();
45
+ return;
46
+ }
47
+ const error = reqUrl.searchParams.get('error') ?? undefined;
48
+ res.writeHead(200, { 'Content-Type': 'text/html' });
49
+ res.end(error
50
+ ? RESULT_PAGE('Authorization cancelled', 'You can close this tab and return to your terminal.')
51
+ : RESULT_PAGE("You're signed in", 'You can close this tab and return to your terminal.'));
52
+ settle({
53
+ code: reqUrl.searchParams.get('code') ?? undefined,
54
+ error,
55
+ state: reqUrl.searchParams.get('state') ?? undefined,
56
+ });
57
+ server.close();
58
+ });
59
+ server.on('error', reject);
60
+ server.listen(0, '127.0.0.1', () => {
61
+ const { port } = server.address();
62
+ const timer = setTimeout(() => {
63
+ server.close();
64
+ settle({ error: 'timeout' });
65
+ }, CALLBACK_TIMEOUT_MS);
66
+ timer.unref();
67
+ resolve({ port, waitForCallback: () => callback });
68
+ });
69
+ });
70
+ }
71
+ export async function login(opts = {}) {
72
+ const apiUrl = resolveApiUrl(null);
73
+ const webUrl = resolveWebUrl();
74
+ // PKCE: the verifier never leaves this process; only its SHA-256 challenge
75
+ // travels through the browser, so an intercepted code can't be exchanged.
76
+ const verifier = base64url(randomBytes(32));
77
+ const challenge = base64url(createHash('sha256').update(verifier).digest());
78
+ const state = randomBytes(16).toString('hex');
79
+ const { port, waitForCallback } = await startCallbackServer();
80
+ const authorizeUrl = `${webUrl}/cli/authorize?port=${port}` +
81
+ `&state=${encodeURIComponent(state)}` +
82
+ `&challenge=${encodeURIComponent(challenge)}`;
83
+ if (opts.browser === false) {
84
+ console.log('Open this URL in your browser to authorize the CLI:\n');
85
+ console.log(` ${authorizeUrl}\n`);
86
+ }
87
+ else {
88
+ console.log('Opening your browser to authorize the CLI…');
89
+ console.log(`If it doesn't open, visit:\n ${authorizeUrl}\n`);
90
+ openBrowser(authorizeUrl);
91
+ }
92
+ const result = await waitForCallback();
93
+ if (result.error === 'timeout') {
94
+ console.error('Timed out waiting for authorization. Run `alertee login` to try again.');
95
+ process.exit(1);
96
+ }
97
+ if (result.error || !result.code) {
98
+ console.error('Authorization was cancelled or failed.');
99
+ process.exit(1);
100
+ }
101
+ if (result.state !== state) {
102
+ console.error('Authorization failed: state mismatch (possible tampering). Try again.');
103
+ process.exit(1);
104
+ }
105
+ let token;
106
+ try {
107
+ const res = await fetch(`${apiUrl}/auth/cli/token`, {
108
+ method: 'POST',
109
+ headers: { 'Content-Type': 'application/json' },
110
+ body: JSON.stringify({ code: result.code, code_verifier: verifier }),
111
+ });
112
+ if (!res.ok) {
113
+ let msg = res.statusText;
114
+ try {
115
+ const err = (await res.json());
116
+ if (err.message)
117
+ msg = err.message;
118
+ }
119
+ catch { }
120
+ throw new Error(msg);
121
+ }
122
+ const data = (await res.json());
123
+ token = data.token;
124
+ }
125
+ catch (err) {
126
+ console.error('Failed to complete login:', err.message);
127
+ process.exit(1);
128
+ }
129
+ saveConfig({ token, apiUrl });
130
+ console.log('');
131
+ console.log('Logged in. Run `alertee link` to connect to an organization.');
132
+ }
133
+ //# sourceMappingURL=login.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"login.js","sourceRoot":"","sources":["../../src/commands/login.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function logout(): void;
2
+ //# sourceMappingURL=logout.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logout.d.ts","sourceRoot":"","sources":["../../src/commands/logout.ts"],"names":[],"mappings":"AAEA,wBAAgB,MAAM,IAAI,IAAI,CAG7B"}
@@ -0,0 +1,6 @@
1
+ import { clearConfig } from '../config.js';
2
+ export function logout() {
3
+ clearConfig();
4
+ console.log('Logged out.');
5
+ }
6
+ //# sourceMappingURL=logout.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logout.js","sourceRoot":"","sources":["../../src/commands/logout.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,cAAc,CAAA;AAE1C,MAAM,UAAU,MAAM;IACpB,WAAW,EAAE,CAAA;IACb,OAAO,CAAC,GAAG,CAAC,aAAa,CAAC,CAAA;AAC5B,CAAC"}
@@ -0,0 +1,2 @@
1
+ export declare function whoami(): void;
2
+ //# sourceMappingURL=whoami.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"whoami.d.ts","sourceRoot":"","sources":["../../src/commands/whoami.ts"],"names":[],"mappings":"AAEA,wBAAgB,MAAM,IAAI,IAAI,CAS7B"}
@@ -0,0 +1,13 @@
1
+ import { requireConfig } from '../config.js';
2
+ export function whoami() {
3
+ const config = requireConfig();
4
+ console.log(`API URL: ${config.apiUrl}`);
5
+ console.log(`Token: ${config.token.slice(0, 12)}…`);
6
+ if (config.organizationId) {
7
+ console.log(`Organization: ${config.organizationName ?? config.organizationId}`);
8
+ }
9
+ else {
10
+ console.log(`Organization: (none — run alertee link)`);
11
+ }
12
+ }
13
+ //# sourceMappingURL=whoami.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"whoami.js","sourceRoot":"","sources":["../../src/commands/whoami.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,cAAc,CAAA;AAE5C,MAAM,UAAU,MAAM;IACpB,MAAM,MAAM,GAAG,aAAa,EAAE,CAAA;IAC9B,OAAO,CAAC,GAAG,CAAC,iBAAiB,MAAM,CAAC,MAAM,EAAE,CAAC,CAAA;IAC7C,OAAO,CAAC,GAAG,CAAC,iBAAiB,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,CAAC,CAAA;IAC1D,IAAI,MAAM,CAAC,cAAc,EAAE,CAAC;QAC1B,OAAO,CAAC,GAAG,CAAC,iBAAiB,MAAM,CAAC,gBAAgB,IAAI,MAAM,CAAC,cAAc,EAAE,CAAC,CAAA;IAClF,CAAC;SAAM,CAAC;QACN,OAAO,CAAC,GAAG,CAAC,yCAAyC,CAAC,CAAA;IACxD,CAAC;AACH,CAAC"}
@@ -0,0 +1,35 @@
1
+ export interface Config {
2
+ token: string;
3
+ apiUrl: string;
4
+ organizationId?: string;
5
+ organizationName?: string;
6
+ }
7
+ declare const DEFAULT_API_URL = "https://prod-alertee-gru2.encr.app";
8
+ declare const DEFAULT_WEB_URL = "https://app.alertee.app";
9
+ /**
10
+ * Resolve the API base URL. Precedence: ALERTEE_API_URL env var > saved
11
+ * config > default. The override lets the CLI target staging or PR
12
+ * environments (and works before the api.alertee.app custom domain is live).
13
+ */
14
+ export declare function resolveApiUrl(config?: Config | null): string;
15
+ /** Resolve the web app URL used for the browser login flow. */
16
+ export declare function resolveWebUrl(): string;
17
+ /**
18
+ * Resolve the auth token. Precedence: ALERTEE_TOKEN env var (for CI /
19
+ * non-interactive use) > saved config.
20
+ */
21
+ export declare function resolveToken(config?: Config | null): string | undefined;
22
+ /**
23
+ * Resolve the organization id. Precedence: ALERTEE_ORG env var > saved config.
24
+ * When neither is set the backend falls back to the user's default organization
25
+ * (see authenticateWithPAT), so commands still work in CI with just a token.
26
+ */
27
+ export declare function resolveOrgId(config?: Config | null): string | undefined;
28
+ /** True when credentials come from the environment (CI / non-interactive). */
29
+ export declare function usingEnvToken(): boolean;
30
+ export declare function loadConfig(): Config | null;
31
+ export declare function saveConfig(config: Config): void;
32
+ export declare function clearConfig(): void;
33
+ export declare function requireConfig(): Config;
34
+ export { DEFAULT_API_URL, DEFAULT_WEB_URL };
35
+ //# sourceMappingURL=config.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAOA,MAAM,WAAW,MAAM;IACrB,KAAK,EAAE,MAAM,CAAA;IACb,MAAM,EAAE,MAAM,CAAA;IACd,cAAc,CAAC,EAAE,MAAM,CAAA;IACvB,gBAAgB,CAAC,EAAE,MAAM,CAAA;CAC1B;AAED,QAAA,MAAM,eAAe,uCAAuC,CAAA;AAC5D,QAAA,MAAM,eAAe,4BAA4B,CAAA;AAEjD;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,MAAM,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,MAAM,CAE5D;AAED,+DAA+D;AAC/D,wBAAgB,aAAa,IAAI,MAAM,CAEtC;AAED;;;GAGG;AACH,wBAAgB,YAAY,CAAC,MAAM,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,MAAM,GAAG,SAAS,CAEvE;AAED;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,MAAM,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,MAAM,GAAG,SAAS,CAEvE;AAED,8EAA8E;AAC9E,wBAAgB,aAAa,IAAI,OAAO,CAEvC;AAED,wBAAgB,UAAU,IAAI,MAAM,GAAG,IAAI,CAO1C;AAED,wBAAgB,UAAU,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAG/C;AAED,wBAAgB,WAAW,IAAI,IAAI,CAIlC;AAED,wBAAgB,aAAa,IAAI,MAAM,CAQtC;AAED,OAAO,EAAE,eAAe,EAAE,eAAe,EAAE,CAAA"}
package/dist/config.js ADDED
@@ -0,0 +1,68 @@
1
+ import { existsSync, mkdirSync, readFileSync, writeFileSync } from 'node:fs';
2
+ import { homedir } from 'node:os';
3
+ import { join } from 'node:path';
4
+ const CONFIG_DIR = join(homedir(), '.config', 'alertee');
5
+ const CONFIG_PATH = join(CONFIG_DIR, 'config.json');
6
+ const DEFAULT_API_URL = 'https://prod-alertee-gru2.encr.app';
7
+ const DEFAULT_WEB_URL = 'https://app.alertee.app';
8
+ /**
9
+ * Resolve the API base URL. Precedence: ALERTEE_API_URL env var > saved
10
+ * config > default. The override lets the CLI target staging or PR
11
+ * environments (and works before the api.alertee.app custom domain is live).
12
+ */
13
+ export function resolveApiUrl(config) {
14
+ return process.env.ALERTEE_API_URL || config?.apiUrl || DEFAULT_API_URL;
15
+ }
16
+ /** Resolve the web app URL used for the browser login flow. */
17
+ export function resolveWebUrl() {
18
+ return process.env.ALERTEE_WEB_URL || DEFAULT_WEB_URL;
19
+ }
20
+ /**
21
+ * Resolve the auth token. Precedence: ALERTEE_TOKEN env var (for CI /
22
+ * non-interactive use) > saved config.
23
+ */
24
+ export function resolveToken(config) {
25
+ return process.env.ALERTEE_TOKEN || config?.token;
26
+ }
27
+ /**
28
+ * Resolve the organization id. Precedence: ALERTEE_ORG env var > saved config.
29
+ * When neither is set the backend falls back to the user's default organization
30
+ * (see authenticateWithPAT), so commands still work in CI with just a token.
31
+ */
32
+ export function resolveOrgId(config) {
33
+ return process.env.ALERTEE_ORG || config?.organizationId;
34
+ }
35
+ /** True when credentials come from the environment (CI / non-interactive). */
36
+ export function usingEnvToken() {
37
+ return !!process.env.ALERTEE_TOKEN;
38
+ }
39
+ export function loadConfig() {
40
+ if (!existsSync(CONFIG_PATH))
41
+ return null;
42
+ try {
43
+ return JSON.parse(readFileSync(CONFIG_PATH, 'utf8'));
44
+ }
45
+ catch {
46
+ return null;
47
+ }
48
+ }
49
+ export function saveConfig(config) {
50
+ mkdirSync(CONFIG_DIR, { recursive: true });
51
+ writeFileSync(CONFIG_PATH, JSON.stringify(config, null, 2), 'utf8');
52
+ }
53
+ export function clearConfig() {
54
+ if (existsSync(CONFIG_PATH)) {
55
+ writeFileSync(CONFIG_PATH, '', 'utf8');
56
+ }
57
+ }
58
+ export function requireConfig() {
59
+ const config = loadConfig();
60
+ const token = resolveToken(config);
61
+ if (!token) {
62
+ console.error('Not logged in. Run: alertee login');
63
+ process.exit(1);
64
+ }
65
+ return { ...config, token, apiUrl: resolveApiUrl(config) };
66
+ }
67
+ export { DEFAULT_API_URL, DEFAULT_WEB_URL };
68
+ //# sourceMappingURL=config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,SAAS,CAAA;AAC5E,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAA;AACjC,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAA;AAEhC,MAAM,UAAU,GAAG,IAAI,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,SAAS,CAAC,CAAA;AACxD,MAAM,WAAW,GAAG,IAAI,CAAC,UAAU,EAAE,aAAa,CAAC,CAAA;AASnD,MAAM,eAAe,GAAG,oCAAoC,CAAA;AAC5D,MAAM,eAAe,GAAG,yBAAyB,CAAA;AAEjD;;;;GAIG;AACH,MAAM,UAAU,aAAa,CAAC,MAAsB;IAClD,OAAO,OAAO,CAAC,GAAG,CAAC,eAAe,IAAI,MAAM,EAAE,MAAM,IAAI,eAAe,CAAA;AACzE,CAAC;AAED,+DAA+D;AAC/D,MAAM,UAAU,aAAa;IAC3B,OAAO,OAAO,CAAC,GAAG,CAAC,eAAe,IAAI,eAAe,CAAA;AACvD,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,YAAY,CAAC,MAAsB;IACjD,OAAO,OAAO,CAAC,GAAG,CAAC,aAAa,IAAI,MAAM,EAAE,KAAK,CAAA;AACnD,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,YAAY,CAAC,MAAsB;IACjD,OAAO,OAAO,CAAC,GAAG,CAAC,WAAW,IAAI,MAAM,EAAE,cAAc,CAAA;AAC1D,CAAC;AAED,8EAA8E;AAC9E,MAAM,UAAU,aAAa;IAC3B,OAAO,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,aAAa,CAAA;AACpC,CAAC;AAED,MAAM,UAAU,UAAU;IACxB,IAAI,CAAC,UAAU,CAAC,WAAW,CAAC;QAAE,OAAO,IAAI,CAAA;IACzC,IAAI,CAAC;QACH,OAAO,IAAI,CAAC,KAAK,CAAC,YAAY,CAAC,WAAW,EAAE,MAAM,CAAC,CAAW,CAAA;IAChE,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,IAAI,CAAA;IACb,CAAC;AACH,CAAC;AAED,MAAM,UAAU,UAAU,CAAC,MAAc;IACvC,SAAS,CAAC,UAAU,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAA;IAC1C,aAAa,CAAC,WAAW,EAAE,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC,EAAE,MAAM,CAAC,CAAA;AACrE,CAAC;AAED,MAAM,UAAU,WAAW;IACzB,IAAI,UAAU,CAAC,WAAW,CAAC,EAAE,CAAC;QAC5B,aAAa,CAAC,WAAW,EAAE,EAAE,EAAE,MAAM,CAAC,CAAA;IACxC,CAAC;AACH,CAAC;AAED,MAAM,UAAU,aAAa;IAC3B,MAAM,MAAM,GAAG,UAAU,EAAE,CAAA;IAC3B,MAAM,KAAK,GAAG,YAAY,CAAC,MAAM,CAAC,CAAA;IAClC,IAAI,CAAC,KAAK,EAAE,CAAC;QACX,OAAO,CAAC,KAAK,CAAC,mCAAmC,CAAC,CAAA;QAClD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;IACD,OAAO,EAAE,GAAG,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,aAAa,CAAC,MAAM,CAAC,EAAE,CAAA;AAC5D,CAAC;AAED,OAAO,EAAE,eAAe,EAAE,eAAe,EAAE,CAAA"}
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":""}
package/dist/index.js ADDED
@@ -0,0 +1,47 @@
1
+ #!/usr/bin/env node
2
+ import { Command } from 'commander';
3
+ import { createCheck } from './commands/checks/create.js';
4
+ import { listChecks } from './commands/checks/list.js';
5
+ import { link } from './commands/link.js';
6
+ import { login } from './commands/login.js';
7
+ import { logout } from './commands/logout.js';
8
+ import { whoami } from './commands/whoami.js';
9
+ import { startMcpServer } from './mcp.js';
10
+ const program = new Command();
11
+ program
12
+ .name('alertee')
13
+ .description('Alertee CLI — manage database monitoring checks')
14
+ .version('0.1.0')
15
+ .addHelpText('after', '\nDocs: https://docs.alertee.io');
16
+ program
17
+ .command('login')
18
+ .description('Authenticate via your browser')
19
+ .option('--no-browser', 'print the authorization URL instead of opening a browser')
20
+ .action((opts) => login(opts));
21
+ program
22
+ .command('logout')
23
+ .description('Remove stored credentials')
24
+ .action(logout);
25
+ program
26
+ .command('whoami')
27
+ .description('Show current authentication status')
28
+ .action(whoami);
29
+ program
30
+ .command('link')
31
+ .description('Link to an organization')
32
+ .action(link);
33
+ const checks = program.command('checks').description('Manage checks');
34
+ checks
35
+ .command('list')
36
+ .description('List checks in the linked organization')
37
+ .action(listChecks);
38
+ checks
39
+ .command('create')
40
+ .description('Create a new check interactively')
41
+ .action(createCheck);
42
+ program
43
+ .command('mcp')
44
+ .description('Start the MCP server (for Claude Code integration)')
45
+ .action(startMcpServer);
46
+ program.parseAsync();
47
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,WAAW,EAAE,MAAM,6BAA6B,CAAA;AACzD,OAAO,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAA;AACtD,OAAO,EAAE,IAAI,EAAE,MAAM,oBAAoB,CAAA;AACzC,OAAO,EAAE,KAAK,EAAE,MAAM,qBAAqB,CAAA;AAC3C,OAAO,EAAE,MAAM,EAAE,MAAM,sBAAsB,CAAA;AAC7C,OAAO,EAAE,MAAM,EAAE,MAAM,sBAAsB,CAAA;AAC7C,OAAO,EAAE,cAAc,EAAE,MAAM,UAAU,CAAA;AAEzC,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAA;AAE7B,OAAO;KACJ,IAAI,CAAC,SAAS,CAAC;KACf,WAAW,CAAC,iDAAiD,CAAC;KAC9D,OAAO,CAAC,OAAO,CAAC;KAChB,WAAW,CAAC,OAAO,EAAE,iCAAiC,CAAC,CAAA;AAE1D,OAAO;KACJ,OAAO,CAAC,OAAO,CAAC;KAChB,WAAW,CAAC,+BAA+B,CAAC;KAC5C,MAAM,CAAC,cAAc,EAAE,0DAA0D,CAAC;KAClF,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAA;AAEhC,OAAO;KACJ,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CAAC,2BAA2B,CAAC;KACxC,MAAM,CAAC,MAAM,CAAC,CAAA;AAEjB,OAAO;KACJ,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CAAC,oCAAoC,CAAC;KACjD,MAAM,CAAC,MAAM,CAAC,CAAA;AAEjB,OAAO;KACJ,OAAO,CAAC,MAAM,CAAC;KACf,WAAW,CAAC,yBAAyB,CAAC;KACtC,MAAM,CAAC,IAAI,CAAC,CAAA;AAEf,MAAM,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,WAAW,CAAC,eAAe,CAAC,CAAA;AAErE,MAAM;KACH,OAAO,CAAC,MAAM,CAAC;KACf,WAAW,CAAC,wCAAwC,CAAC;KACrD,MAAM,CAAC,UAAU,CAAC,CAAA;AAErB,MAAM;KACH,OAAO,CAAC,QAAQ,CAAC;KACjB,WAAW,CAAC,kCAAkC,CAAC;KAC/C,MAAM,CAAC,WAAW,CAAC,CAAA;AAEtB,OAAO;KACJ,OAAO,CAAC,KAAK,CAAC;KACd,WAAW,CAAC,oDAAoD,CAAC;KACjE,MAAM,CAAC,cAAc,CAAC,CAAA;AAEzB,OAAO,CAAC,UAAU,EAAE,CAAA"}
@@ -0,0 +1,15 @@
1
+ /**
2
+ * Mapping between user-facing minute choices and the backend `check_interval`
3
+ * enum (backend/check/db/migrations/008_add_check_interval.up.sql).
4
+ */
5
+ export interface IntervalChoice {
6
+ name: string;
7
+ /** backend check_interval enum value */
8
+ value: string;
9
+ }
10
+ export declare const INTERVAL_CHOICES: IntervalChoice[];
11
+ /** Map a minute count (as used by the MCP tool input) to the backend enum. */
12
+ export declare const MINUTES_TO_INTERVAL: Record<number, string>;
13
+ /** Human-readable label for a backend interval enum value. */
14
+ export declare function formatInterval(enumValue: string | null | undefined): string;
15
+ //# sourceMappingURL=intervals.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"intervals.d.ts","sourceRoot":"","sources":["../src/intervals.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,MAAM,CAAA;IACZ,wCAAwC;IACxC,KAAK,EAAE,MAAM,CAAA;CACd;AAED,eAAO,MAAM,gBAAgB,EAAE,cAAc,EAM5C,CAAA;AAaD,8EAA8E;AAC9E,eAAO,MAAM,mBAAmB,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAMtD,CAAA;AAED,8DAA8D;AAC9D,wBAAgB,cAAc,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS,GAAG,MAAM,CAG3E"}
@@ -0,0 +1,36 @@
1
+ /**
2
+ * Mapping between user-facing minute choices and the backend `check_interval`
3
+ * enum (backend/check/db/migrations/008_add_check_interval.up.sql).
4
+ */
5
+ export const INTERVAL_CHOICES = [
6
+ { name: '1 minute', value: 'minute' },
7
+ { name: '5 minutes', value: 'five_minutes' },
8
+ { name: '15 minutes', value: 'fifteen_minutes' },
9
+ { name: '30 minutes', value: 'thirty_minutes' },
10
+ { name: '1 hour', value: 'hourly' },
11
+ ];
12
+ const INTERVAL_LABELS = {
13
+ minute: '1 min',
14
+ five_minutes: '5 min',
15
+ fifteen_minutes: '15 min',
16
+ thirty_minutes: '30 min',
17
+ hourly: '1 hr',
18
+ daily: '1 day',
19
+ weekly: '1 wk',
20
+ custom: 'custom',
21
+ };
22
+ /** Map a minute count (as used by the MCP tool input) to the backend enum. */
23
+ export const MINUTES_TO_INTERVAL = {
24
+ 1: 'minute',
25
+ 5: 'five_minutes',
26
+ 15: 'fifteen_minutes',
27
+ 30: 'thirty_minutes',
28
+ 60: 'hourly',
29
+ };
30
+ /** Human-readable label for a backend interval enum value. */
31
+ export function formatInterval(enumValue) {
32
+ if (!enumValue)
33
+ return '—';
34
+ return INTERVAL_LABELS[enumValue] ?? enumValue;
35
+ }
36
+ //# sourceMappingURL=intervals.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"intervals.js","sourceRoot":"","sources":["../src/intervals.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAQH,MAAM,CAAC,MAAM,gBAAgB,GAAqB;IAChD,EAAE,IAAI,EAAE,UAAU,EAAE,KAAK,EAAE,QAAQ,EAAE;IACrC,EAAE,IAAI,EAAE,WAAW,EAAE,KAAK,EAAE,cAAc,EAAE;IAC5C,EAAE,IAAI,EAAE,YAAY,EAAE,KAAK,EAAE,iBAAiB,EAAE;IAChD,EAAE,IAAI,EAAE,YAAY,EAAE,KAAK,EAAE,gBAAgB,EAAE;IAC/C,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,QAAQ,EAAE;CACpC,CAAA;AAED,MAAM,eAAe,GAA2B;IAC9C,MAAM,EAAE,OAAO;IACf,YAAY,EAAE,OAAO;IACrB,eAAe,EAAE,QAAQ;IACzB,cAAc,EAAE,QAAQ;IACxB,MAAM,EAAE,MAAM;IACd,KAAK,EAAE,OAAO;IACd,MAAM,EAAE,MAAM;IACd,MAAM,EAAE,QAAQ;CACjB,CAAA;AAED,8EAA8E;AAC9E,MAAM,CAAC,MAAM,mBAAmB,GAA2B;IACzD,CAAC,EAAE,QAAQ;IACX,CAAC,EAAE,cAAc;IACjB,EAAE,EAAE,iBAAiB;IACrB,EAAE,EAAE,gBAAgB;IACpB,EAAE,EAAE,QAAQ;CACb,CAAA;AAED,8DAA8D;AAC9D,MAAM,UAAU,cAAc,CAAC,SAAoC;IACjE,IAAI,CAAC,SAAS;QAAE,OAAO,GAAG,CAAA;IAC1B,OAAO,eAAe,CAAC,SAAS,CAAC,IAAI,SAAS,CAAA;AAChD,CAAC"}
package/dist/mcp.d.ts ADDED
@@ -0,0 +1,7 @@
1
+ /**
2
+ * Alertee MCP server — exposes Alertee as tools for Claude Code sessions.
3
+ * Communicates over stdio using the Model Context Protocol.
4
+ * Start via: alertee mcp (or npx @alertee/cli mcp)
5
+ */
6
+ export declare function startMcpServer(): void;
7
+ //# sourceMappingURL=mcp.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mcp.d.ts","sourceRoot":"","sources":["../src/mcp.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAuLH,wBAAgB,cAAc,IAAI,IAAI,CAuBrC"}
package/dist/mcp.js ADDED
@@ -0,0 +1,191 @@
1
+ /**
2
+ * Alertee MCP server — exposes Alertee as tools for Claude Code sessions.
3
+ * Communicates over stdio using the Model Context Protocol.
4
+ * Start via: alertee mcp (or npx @alertee/cli mcp)
5
+ */
6
+ import { createClient } from './api.js';
7
+ import { loadConfig, resolveOrgId, usingEnvToken } from './config.js';
8
+ import { MINUTES_TO_INTERVAL } from './intervals.js';
9
+ /** Org is required unless credentials come from the env (default-org fallback). */
10
+ function needsOrg(config) {
11
+ return !resolveOrgId(config) && !usingEnvToken()
12
+ ? 'No organization linked. Run `alertee link` (or set ALERTEE_ORG).'
13
+ : null;
14
+ }
15
+ // ---- Tool definitions ----
16
+ const TOOLS = [
17
+ {
18
+ name: 'list_checks',
19
+ description: 'List all Alertee checks in the linked organization.',
20
+ inputSchema: { type: 'object', properties: {}, required: [] },
21
+ },
22
+ {
23
+ name: 'get_check',
24
+ description: 'Get details of a specific Alertee check by ID.',
25
+ inputSchema: {
26
+ type: 'object',
27
+ properties: { id: { type: 'string', description: 'Check ID' } },
28
+ required: ['id'],
29
+ },
30
+ },
31
+ {
32
+ name: 'create_check',
33
+ description: 'Create a new Alertee database monitoring check.',
34
+ inputSchema: {
35
+ type: 'object',
36
+ properties: {
37
+ name: { type: 'string', description: 'Human-readable name for the check' },
38
+ connection_id: { type: 'string', description: 'ID of the database connection to use' },
39
+ query: { type: 'string', description: 'SQL query that returns a single numeric value' },
40
+ condition_type: {
41
+ type: 'string',
42
+ enum: ['greater_than', 'less_than', 'equals', 'not_equals'],
43
+ description: 'How to evaluate the query result',
44
+ },
45
+ threshold: { type: 'number', description: 'Value to compare the result against' },
46
+ interval_minutes: {
47
+ type: 'number',
48
+ enum: [1, 5, 15, 30, 60],
49
+ description: 'How often to run the check (minutes)',
50
+ },
51
+ },
52
+ required: ['name', 'connection_id', 'query', 'condition_type', 'threshold', 'interval_minutes'],
53
+ },
54
+ },
55
+ {
56
+ name: 'list_connections',
57
+ description: 'List all database connections available in the linked organization.',
58
+ inputSchema: { type: 'object', properties: {}, required: [] },
59
+ },
60
+ {
61
+ name: 'list_organizations',
62
+ description: 'List organizations the authenticated user belongs to.',
63
+ inputSchema: { type: 'object', properties: {}, required: [] },
64
+ },
65
+ ];
66
+ // ---- Dispatch ----
67
+ async function callTool(name, args) {
68
+ const config = loadConfig();
69
+ if (!config?.token) {
70
+ return 'Not logged in. Run `alertee login` to authenticate.';
71
+ }
72
+ const client = createClient(config);
73
+ switch (name) {
74
+ case 'list_checks': {
75
+ {
76
+ const m = needsOrg(config);
77
+ if (m)
78
+ return m;
79
+ }
80
+ const data = await client.listChecks();
81
+ return JSON.stringify(data.checks, null, 2);
82
+ }
83
+ case 'list_connections': {
84
+ {
85
+ const m = needsOrg(config);
86
+ if (m)
87
+ return m;
88
+ }
89
+ const data = await client.listConnections();
90
+ return JSON.stringify(data.connections, null, 2);
91
+ }
92
+ case 'list_organizations': {
93
+ const data = await client.listOrganizations();
94
+ return JSON.stringify(data.organizations, null, 2);
95
+ }
96
+ case 'create_check': {
97
+ {
98
+ const m = needsOrg(config);
99
+ if (m)
100
+ return m;
101
+ }
102
+ const interval = MINUTES_TO_INTERVAL[args.interval_minutes];
103
+ if (!interval) {
104
+ return `Invalid interval_minutes: ${args.interval_minutes}. Allowed: 1, 5, 15, 30, 60.`;
105
+ }
106
+ const resp = await client.createCheck({
107
+ name: args.name,
108
+ connection_id: args.connection_id,
109
+ query: args.query,
110
+ condition: {
111
+ type: args.condition_type,
112
+ value: String(args.threshold),
113
+ },
114
+ interval,
115
+ });
116
+ return JSON.stringify(resp.check, null, 2);
117
+ }
118
+ default:
119
+ return `Unknown tool: ${name}`;
120
+ }
121
+ }
122
+ // ---- MCP stdio server ----
123
+ function send(msg) {
124
+ process.stdout.write(JSON.stringify(msg) + '\n');
125
+ }
126
+ function respond(id, result) {
127
+ send({ jsonrpc: '2.0', id, result });
128
+ }
129
+ function error(id, code, message) {
130
+ send({ jsonrpc: '2.0', id, error: { code, message } });
131
+ }
132
+ async function handleRequest(req) {
133
+ if (req.method === 'initialize') {
134
+ respond(req.id, {
135
+ protocolVersion: '2024-11-05',
136
+ capabilities: { tools: {} },
137
+ serverInfo: { name: 'alertee', version: '0.1.0' },
138
+ });
139
+ return;
140
+ }
141
+ if (req.method === 'tools/list') {
142
+ respond(req.id, { tools: TOOLS });
143
+ return;
144
+ }
145
+ if (req.method === 'tools/call') {
146
+ const params = req.params;
147
+ try {
148
+ const result = await callTool(params.name, params.arguments ?? {});
149
+ respond(req.id, {
150
+ content: [{ type: 'text', text: result }],
151
+ });
152
+ }
153
+ catch (err) {
154
+ respond(req.id, {
155
+ content: [{ type: 'text', text: `Error: ${err.message}` }],
156
+ isError: true,
157
+ });
158
+ }
159
+ return;
160
+ }
161
+ if (req.method === 'notifications/initialized') {
162
+ // no response needed
163
+ return;
164
+ }
165
+ error(req.id, -32601, `Method not found: ${req.method}`);
166
+ }
167
+ export function startMcpServer() {
168
+ let buffer = '';
169
+ process.stdin.setEncoding('utf8');
170
+ process.stdin.on('data', (chunk) => {
171
+ buffer += chunk;
172
+ const lines = buffer.split('\n');
173
+ buffer = lines.pop() ?? '';
174
+ for (const line of lines) {
175
+ const trimmed = line.trim();
176
+ if (!trimmed)
177
+ continue;
178
+ try {
179
+ const req = JSON.parse(trimmed);
180
+ handleRequest(req).catch((err) => {
181
+ error(req.id ?? null, -32603, err.message);
182
+ });
183
+ }
184
+ catch {
185
+ // malformed JSON — ignore
186
+ }
187
+ }
188
+ });
189
+ process.stdin.on('end', () => process.exit(0));
190
+ }
191
+ //# sourceMappingURL=mcp.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mcp.js","sourceRoot":"","sources":["../src/mcp.ts"],"names":[],"mappings":"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"}
package/package.json ADDED
@@ -0,0 +1,27 @@
1
+ {
2
+ "name": "@alertee/cli",
3
+ "version": "0.1.0",
4
+ "description": "Alertee CLI — create and manage database monitoring checks",
5
+ "type": "module",
6
+ "bin": {
7
+ "alertee": "./dist/index.js"
8
+ },
9
+ "files": [
10
+ "dist"
11
+ ],
12
+ "scripts": {
13
+ "build": "tsc",
14
+ "dev": "tsx src/index.ts",
15
+ "build:check": "tsc --noEmit",
16
+ "prepublishOnly": "npm run build"
17
+ },
18
+ "dependencies": {
19
+ "@inquirer/prompts": "^7.5.0",
20
+ "commander": "^12.1.0"
21
+ },
22
+ "devDependencies": {
23
+ "@types/node": "^22.0.0",
24
+ "tsx": "^4.19.2",
25
+ "typescript": "^5.5.4"
26
+ }
27
+ }