Compare commits

...

275 Commits

Author SHA1 Message Date
dependabot[bot]
1e3c1d8a4c chore(deps): bump axios from 1.13.4 to 1.13.5 in /ui
Bumps [axios](https://github.com/axios/axios) from 1.13.4 to 1.13.5.
- [Release notes](https://github.com/axios/axios/releases)
- [Changelog](https://github.com/axios/axios/blob/v1.x/CHANGELOG.md)
- [Commits](https://github.com/axios/axios/compare/v1.13.4...v1.13.5)

---
updated-dependencies:
- dependency-name: axios
  dependency-version: 1.13.5
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-02-11 06:01:19 +00:00
public-glueops-renovatebot[bot]
1c740da56d chore(patch): update @types/node to 25.2.2 #patch (#652)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-11 06:00:17 +00:00
public-glueops-renovatebot[bot]
0136c8ef78 chore(patch): update shadcn to 3.8.3 #patch (#642)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-07 17:45:19 +00:00
public-glueops-renovatebot[bot]
d4fdd85671 chore(patch): update @types/react to 19.2.11 #patch (#645)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-07 15:00:28 +00:00
public-glueops-renovatebot[bot]
5d3f0bfaf6 chore: lock file maintenance (#624)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:06:43 +00:00
public-glueops-renovatebot[bot]
3926bafa5c feat: update docker/login-action to v3.7.0 #minor (#623)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:03:13 +00:00
public-glueops-renovatebot[bot]
210a056fe6 feat: update github.com/aws/aws-sdk-go-v2/service/s3 to v1.96.0 #minor (#627)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:03:00 +00:00
public-glueops-renovatebot[bot]
b864187af5 feat: update typescript-eslint to 8.54.0 #minor (#618)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:02:44 +00:00
public-glueops-renovatebot[bot]
10725d9263 chore(lockfile): update motion-lockfile #patch (#633)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:02:30 +00:00
public-glueops-renovatebot[bot]
84d5575ea8 feat: update eslint-plugin-react-refresh to 0.5.0 #minor (#629)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:02:23 +00:00
public-glueops-renovatebot[bot]
b7b2c3c65d chore(patch): update motion to 12.29.3 #patch (#632)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:02:13 +00:00
public-glueops-renovatebot[bot]
94cd1ca2df chore(patch): update github.com/golang-jwt/jwt/v5 to v5.3.1 #patch (#626)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:01:59 +00:00
public-glueops-renovatebot[bot]
9379e8dd05 chore(patch): update golang to 1.25.7 #patch (#639)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:01:48 +00:00
public-glueops-renovatebot[bot]
e0b15f6b9e chore(patch): update github.com/go-chi/chi/v5 to v5.2.5 #patch (#641)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:01:42 +00:00
public-glueops-renovatebot[bot]
accf590d24 chore(patch): update @vitejs/plugin-react to 5.1.3 #patch (#631)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 23:01:21 +00:00
public-glueops-renovatebot[bot]
b910ff52ab feat: update @types/node to 25.2.1 #minor (#630)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 22:48:50 +00:00
public-glueops-renovatebot[bot]
1e498b309b chore(patch): update @types/react to 19.2.10 #patch (#619)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 22:40:45 +00:00
public-glueops-renovatebot[bot]
85601bcb84 chore(patch): update shadcn to 3.8.2 #patch (#635)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-05 11:32:21 +00:00
public-glueops-renovatebot[bot]
ce348a65ea chore(patch): update shadcn to 3.8.1 #patch (#634)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-03 11:59:38 +00:00
public-glueops-renovatebot[bot]
37153a6eed feat: update shadcn to 3.8.0 #minor (#628)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-02-03 00:52:13 +00:00
public-glueops-renovatebot[bot]
936891d110 chore(patch): update typescript-eslint to 8.53.1 #patch (#608)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:49:07 +00:00
public-glueops-renovatebot[bot]
965a5ed88b chore: lock file maintenance (#620)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:23:14 +00:00
public-glueops-renovatebot[bot]
c2b76f1dea chore(patch): update prettier to 3.8.1 #patch (#611)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:22:37 +00:00
public-glueops-renovatebot[bot]
5c9768b0b2 chore(patch): update @tanstack/react-query to 5.90.20 #patch (#598)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:22:22 +00:00
public-glueops-renovatebot[bot]
a02c29f333 chore(fallback): update golang (#607)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:22:16 +00:00
public-glueops-renovatebot[bot]
223d89bdd1 chore(patch): update @types/node to 25.0.10 #patch (#613)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:22:09 +00:00
public-glueops-renovatebot[bot]
411c98174a chore(lockfile): update motion-lockfile #patch (#614)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:22:03 +00:00
public-glueops-renovatebot[bot]
a7657368ed chore: lock file maintenance (#605)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:21:14 +00:00
public-glueops-renovatebot[bot]
134153c197 feat: update shadcn to 3.7.0 #minor (#603)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:20:44 +00:00
public-glueops-renovatebot[bot]
b4905b8c59 feat: update lucide-react to 0.563.0 #minor (#616)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:20:23 +00:00
public-glueops-renovatebot[bot]
f9dc0d4db5 chore(lockfile): update react-router-dom-lockfile #patch (#617)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:20:11 +00:00
public-glueops-renovatebot[bot]
3d6e53d24d chore(lockfile): update motion-lockfile #patch (#610)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:19:38 +00:00
public-glueops-renovatebot[bot]
2f6a382733 chore(lockfile): update motion-lockfile #patch (#606)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:19:27 +00:00
public-glueops-renovatebot[bot]
8261b5d702 chore(patch): update @types/react to 19.2.9 #patch (#609)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-27 18:01:27 +00:00
public-glueops-renovatebot[bot]
23415ead6d chore(patch): update @types/node to 25.0.9 #patch (#604)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-22 01:15:32 +00:00
public-glueops-renovatebot[bot]
ba8098acac feat: update prettier to 3.8.0 #minor (#600)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-21 18:51:23 +00:00
public-glueops-renovatebot[bot]
da5801cc6b chore: lock file maintenance (#596)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-16 17:33:44 +00:00
public-glueops-renovatebot[bot]
809c0930ae chore(patch): update golang to 1.25.6 #patch (#601)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-16 17:33:10 +00:00
public-glueops-renovatebot[bot]
17af4e8da4 chore(patch): update motion to 12.26.2 #patch (#592)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-16 17:33:05 +00:00
public-glueops-renovatebot[bot]
039fb04c97 chore(patch): update github.com/go-chi/chi/v5 to v5.2.4 #patch (#599)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-16 17:32:52 +00:00
public-glueops-renovatebot[bot]
335fd10fab chore(patch): update @types/react to 19.2.8 #patch (#590)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-16 17:32:43 +00:00
public-glueops-renovatebot[bot]
a3ec862e12 feat: update typescript-eslint to 8.53.0 #minor (#594)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-16 17:31:14 +00:00
public-glueops-renovatebot[bot]
66595daa4b chore(patch): update @types/node to 25.0.8 #patch (#602)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-16 17:16:31 +00:00
public-glueops-renovatebot[bot]
d6d1806907 chore(patch): update @types/node to 25.0.7 #patch (#597)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-16 08:30:02 +00:00
public-glueops-renovatebot[bot]
3c61f66c9a chore(patch): update @types/node to 25.0.6 #patch (#595)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-13 18:14:04 +00:00
public-glueops-renovatebot[bot]
0fb6fa3389 feat: update golang.org/x/crypto to v0.47.0 #minor (#593)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-13 04:35:28 +00:00
public-glueops-renovatebot[bot]
4cd9f77694 chore(patch): update github.com/aws/aws-sdk-go-v2 to v1.41.1 #patch (#588)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-13 04:23:26 +00:00
public-glueops-renovatebot[bot]
f6af0d970f chore(patch): update vite to 7.3.1 #patch (#578)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-13 04:02:47 +00:00
public-glueops-renovatebot[bot]
1138b346e3 chore: lock file maintenance (#587)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-13 04:02:17 +00:00
public-glueops-renovatebot[bot]
4e612652a2 chore(patch): update @types/node to 25.0.5 #patch (#589)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-13 03:24:39 +00:00
public-glueops-renovatebot[bot]
4127c0dd06 chore: lock file maintenance (#586)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-09 10:45:20 +00:00
public-glueops-renovatebot[bot]
8e97df134a chore(patch): update github.com/swaggo/swag/v2 to v2.0.0-rc5 #patch (#584)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-09 10:44:46 +00:00
public-glueops-renovatebot[bot]
636b500108 chore(patch): update shadcn to 3.6.3 #patch (#572)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-09 10:43:54 +00:00
public-glueops-renovatebot[bot]
2e3fd44b34 chore: lock file maintenance (#583)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-08 18:28:09 +00:00
public-glueops-renovatebot[bot]
2bfd8b0a78 chore: lock file maintenance (#581)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-08 17:14:27 +00:00
public-glueops-renovatebot[bot]
c7fb0bcf18 feat: update typescript-eslint to 8.52.0 #minor (#570)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-08 17:13:05 +00:00
public-glueops-renovatebot[bot]
c4a0fbd7b8 chore: lock file maintenance (#580)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-07 09:46:32 +00:00
public-glueops-renovatebot[bot]
8616336279 chore: lock file maintenance (#579)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-07 09:45:20 +00:00
public-glueops-renovatebot[bot]
d1ea3667e6 chore: lock file maintenance (#577)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-06 17:29:30 +00:00
allanice001
0f562ac5f4 ui fixes 2026-01-06 17:05:52 +00:00
allanice001
810218124e revert, but increase httprate 2026-01-06 10:11:42 +00:00
allanice001
5aff256377 fix import issue 2026-01-06 09:59:23 +00:00
Alanis
bdd6b61859 Remove rate limiting by IP from routes
Removed rate limiting middleware from the API routes.
2026-01-06 09:50:10 +00:00
public-glueops-renovatebot[bot]
42a86b22dd chore: lock file maintenance (#567)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-05 10:45:19 +00:00
public-glueops-renovatebot[bot]
b8cb1e1a2a chore: lock file maintenance (#566)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-05 10:11:13 +00:00
public-glueops-renovatebot[bot]
5a4ae19900 chore: lock file maintenance (#564)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-04 10:51:50 +00:00
public-glueops-renovatebot[bot]
d9db293894 chore: lock file maintenance (#563)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-04 08:27:53 +00:00
public-glueops-renovatebot[bot]
19d5ee7251 chore: lock file maintenance (#562)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-04 04:12:39 +00:00
public-glueops-renovatebot[bot]
6b91a5760b chore: lock file maintenance (#560)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-03 13:32:05 +00:00
public-glueops-renovatebot[bot]
bbd4c86013 chore: lock file maintenance (#559)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-02 14:40:46 +00:00
public-glueops-renovatebot[bot]
99ebcb11a3 chore: lock file maintenance (#558)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-02 13:44:37 +00:00
public-glueops-renovatebot[bot]
be1b35da3c feat: update typescript-eslint to 8.51.0 #minor (#540)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2026-01-01 17:09:21 +00:00
public-glueops-renovatebot[bot]
a6a296f283 chore: lock file maintenance (#556)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-31 23:27:07 +00:00
public-glueops-renovatebot[bot]
341ecf8b0a chore: lock file maintenance (#555)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-31 19:37:14 +00:00
public-glueops-renovatebot[bot]
92998015ec chore: lock file maintenance (#554)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-31 16:10:12 +00:00
public-glueops-renovatebot[bot]
9345c2761c chore: lock file maintenance (#553)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-31 15:08:55 +00:00
public-glueops-renovatebot[bot]
6944e5d027 chore: lock file maintenance (#552)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-31 06:14:14 +00:00
public-glueops-renovatebot[bot]
48b3bf5d3c chore: lock file maintenance (#551)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-31 06:13:11 +00:00
public-glueops-renovatebot[bot]
4c595db85e chore: lock file maintenance (#550)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-31 05:42:43 +00:00
allanice001
79f3259bd6 fix: ensure only a single instance is fired
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-30 17:30:38 +00:00
allanice001
e0d163181a Merge branch 'main' of github.com:GlueOps/autoglue 2025-12-30 16:35:18 +00:00
allanice001
e8d568eba7 fix: ensure only a single instance is fired
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-30 16:35:00 +00:00
public-glueops-renovatebot[bot]
c21a766dab chore: lock file maintenance (#548)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-30 15:09:36 +00:00
public-glueops-renovatebot[bot]
495c1551b4 chore: lock file maintenance (#547)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-30 08:45:47 +00:00
public-glueops-renovatebot[bot]
4a5c0df481 chore: lock file maintenance (#545)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 22:09:22 +00:00
public-glueops-renovatebot[bot]
c92bba5518 chore: lock file maintenance (#544)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 22:08:16 +00:00
public-glueops-renovatebot[bot]
823088e294 chore: lock file maintenance (#543)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 19:52:02 +00:00
public-glueops-renovatebot[bot]
938689fda3 chore: lock file maintenance (#542)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 18:46:56 +00:00
public-glueops-renovatebot[bot]
77332f208f chore: lock file maintenance (#541)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 17:26:24 +00:00
public-glueops-renovatebot[bot]
711488492c breaking: the dependency actions/checkout has been updated to a new major version (v6), which may include breaking changes. #major (#536)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 17:03:09 +00:00
public-glueops-renovatebot[bot]
27b89722a4 chore: lock file maintenance (#539)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 16:27:51 +00:00
public-glueops-renovatebot[bot]
c8a537e30f chore(fallback): update postgres (#535)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 12:34:44 +00:00
public-glueops-renovatebot[bot]
98de70b96b chore: lock file maintenance (#538)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 12:34:10 +00:00
public-glueops-renovatebot[bot]
63c4574f9c chore(fallback): update axllent/mailpit (#534)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 12:33:13 +00:00
public-glueops-renovatebot[bot]
5e85cad5b7 chore(pin): update typescript to #patch (#533)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-29 12:32:35 +00:00
allanice001
53725bb834 chore: add org id to org table 2025-12-29 11:59:27 +00:00
public-glueops-renovatebot[bot]
6611dc4950 chore(patch): update typescript-eslint to 8.50.1 #patch (#511)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-28 01:26:48 +00:00
public-glueops-renovatebot[bot]
49665ffc9c feat: update github.com/aws/aws-sdk-go-v2/service/s3 to v1.95.0 #minor (#516)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-28 01:26:33 +00:00
public-glueops-renovatebot[bot]
ac14ef8fff chore: lock file maintenance (#528)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-28 01:25:13 +00:00
allanice001
f8e543b595 fix: improve dns error logging 2025-12-28 00:08:42 +00:00
allanice001
8cc81e52b7 fix: add get record for dns 2025-12-27 23:21:59 +00:00
public-glueops-renovatebot[bot]
d6e28c7fa2 chore(patch): update @types/node to 25.0.3 #patch (#507)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 15:30:04 +00:00
public-glueops-renovatebot[bot]
9832229194 chore(patch): update eslint-plugin-react-refresh to 0.4.26 #patch (#508)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 15:29:07 +00:00
public-glueops-renovatebot[bot]
da82998754 chore(fallback): update alpine (#487)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 15:28:34 +00:00
public-glueops-renovatebot[bot]
bca32fe784 chore(fallback): update golang (#486)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 15:28:18 +00:00
public-glueops-renovatebot[bot]
848e8d5179 chore(patch): update shadcn to 3.6.2 #patch (#510)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 15:28:03 +00:00
public-glueops-renovatebot[bot]
d3ee38881c feat: update docker/setup-buildx-action to v3.12.0 #minor (#515)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 15:27:20 +00:00
public-glueops-renovatebot[bot]
d39db44aa7 feat: update lucide-react to 0.562.0 #minor (#518)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 15:26:54 +00:00
public-glueops-renovatebot[bot]
01b29a4706 feat: update vite to 7.3.0 #minor (#519)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 15:26:38 +00:00
allanice001
bc3bd92d54 fix: improve job tracking
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-26 15:14:48 +00:00
allanice001
2057f92b82 fix: improve job tracking 2025-12-26 15:04:31 +00:00
allanice001
169283b6c7 fix: improve job tracking
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-26 15:04:15 +00:00
allanice001
865270312c fix: update jobs
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-26 04:47:08 +00:00
public-glueops-renovatebot[bot]
7cc447c0f5 chore(lockfile): update react-hook-form-lockfile #patch (#496)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 01:12:10 +00:00
public-glueops-renovatebot[bot]
8a0345f7f5 chore: lock file maintenance (#520)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 01:11:47 +00:00
public-glueops-renovatebot[bot]
bb7114efe9 feat: update github.com/go-playground/validator/v10 to v10.30.1 #minor (#517)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 00:45:14 +00:00
public-glueops-renovatebot[bot]
9dd0148764 chore(lockfile): update react-router-dom-lockfile #patch (#514)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 00:45:00 +00:00
public-glueops-renovatebot[bot]
bcc69e1c86 chore(lockfile): update react-day-picker-lockfile #patch (#513)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 00:44:27 +00:00
public-glueops-renovatebot[bot]
a7bf6b43b4 chore(patch): update zod to 4.2.1 #patch (#512)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 00:44:17 +00:00
public-glueops-renovatebot[bot]
ced0a0663f chore(patch): update github.com/aws/aws-sdk-go-v2/config to v1.32.6 #patch (#509)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-26 00:43:51 +00:00
allanice001
dac28d3ea5 feat: move jobs to action based
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-26 00:30:46 +00:00
allanice001
dd0cefc08a fix: bugfix jobs
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-16 01:15:00 +00:00
allanice001
842f7c9be6 fix: bugfix jobs
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-16 00:52:16 +00:00
public-glueops-renovatebot[bot]
c15311a5a1 chore(patch): update @eslint/js to 9.39.2 #patch (#456)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-15 22:26:54 +00:00
public-glueops-renovatebot[bot]
25ced343c4 feat: update shadcn to 3.6.0 #minor (#454)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-15 20:23:28 +00:00
public-glueops-renovatebot[bot]
b72a8d384d feat: update github.com/aws/aws-sdk-go-v2/service/s3 to v1.94.0 #minor (#470)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-15 20:22:48 +00:00
public-glueops-renovatebot[bot]
c786a79b60 chore: lock file maintenance (#469)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-15 19:39:22 +00:00
public-glueops-renovatebot[bot]
01b1434842 chore: lock file maintenance (#468)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-15 19:38:13 +00:00
public-glueops-renovatebot[bot]
e8c9cde474 chore: lock file maintenance (#467)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-15 19:09:53 +00:00
public-glueops-renovatebot[bot]
ae92d05cd4 feat: update typescript-eslint to 8.50.0 #minor (#465)
* chore: lock file maintenance (#452)

Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>

* feat: update github.com/go-playground/validator/v10 to v10.29.0 #minor (#453)

Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>

* chore: lock file maintenance (#455)

Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>

* chore: lock file maintenance (#457)

Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>

* chore: lock file maintenance (#462)

Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>

* chore: lock file maintenance (#464)

Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>

* chore: lock file maintenance (#466)

Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>

* feat: update typescript-eslint to 8.50.0 #minor

---------

Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-15 18:08:04 +00:00
allanice001
67d50d2b15 fix: bugfix in responding with correct label ids 2025-12-15 18:04:22 +00:00
allanice001
e5a664b812 Merge remote-tracking branch 'origin/main' 2025-12-12 11:36:33 +00:00
allanice001
f722ba8dca chore: update dependencies
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-12 11:36:25 +00:00
public-glueops-renovatebot[bot]
20e6d8d186 chore: lock file maintenance (#449)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-12 07:40:12 +00:00
allanice001
85f37cd113 fix: ui updates for org api keys
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-12 02:05:31 +00:00
allanice001
fd1a81ecd8 fix: api keys form bugfix and org key sweeper job
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-12 01:37:42 +00:00
allanice001
793daf3ac3 Merge remote-tracking branch 'origin/main' 2025-12-12 00:20:34 +00:00
allanice001
7bef4ef6f1 feat: add org_key and org_secret to payload on bastion
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-12 00:20:27 +00:00
public-glueops-renovatebot[bot]
9fa9cd169b chore: lock file maintenance (#448)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-11 23:26:33 +00:00
public-glueops-renovatebot[bot]
8812b43346 chore: lock file maintenance (#447)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-11 20:39:59 +00:00
public-glueops-renovatebot[bot]
21a6d7d5a1 chore: lock file maintenance (#445)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-11 19:37:53 +00:00
public-glueops-renovatebot[bot]
da332c89dd chore: lock file maintenance (#443)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-11 17:12:09 +00:00
public-glueops-renovatebot[bot]
fd25825f34 chore: lock file maintenance (#441)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-11 15:54:18 +00:00
allanice001
de3740e974 Merge remote-tracking branch 'origin/main' 2025-12-11 13:08:47 +00:00
allanice001
21dd26503f feat: add kubeconfig to payload if available
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-11 13:08:39 +00:00
public-glueops-renovatebot[bot]
e1da229c30 chore: lock file maintenance (#439)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-10 14:43:04 +00:00
allanice001
5377e521e9 fix: fix build error
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-10 14:19:10 +00:00
allanice001
a929561bc8 fix: bg jobs sequencing 2025-12-10 13:25:12 +00:00
allanice001
c63f9f1cf3 Merge remote-tracking branch 'origin/main' 2025-12-10 12:35:10 +00:00
allanice001
4c02179b70 fix: fix payload shape
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-10 12:34:11 +00:00
public-glueops-renovatebot[bot]
c8289c6936 chore: lock file maintenance (#435)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-10 11:38:00 +00:00
allanice001
c17caf22a2 fix: ui typo fix 2025-12-10 09:51:38 +00:00
allanice001
986eeb9bf9 fix: ui typo fix
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-10 09:51:13 +00:00
allanice001
b0bbc13946 fix: ui typo fix
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-10 09:51:07 +00:00
public-glueops-renovatebot[bot]
f50dcae823 feat: update github.com/aws/aws-sdk-go-v2/service/route53 to v1.62.0 #minor (#433)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-09 21:20:27 +00:00
public-glueops-renovatebot[bot]
ab9a77e1f5 chore(patch): update github.com/aws/aws-sdk-go-v2/config to v1.32.5 #patch (#432)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-09 20:41:11 +00:00
allanice001
416b2ff4e2 Merge remote-tracking branch 'origin/main' 2025-12-09 18:11:01 +00:00
allanice001
20bef7545c chore: log background jobs
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-09 18:10:50 +00:00
public-glueops-renovatebot[bot]
15e101439b chore: lock file maintenance (#430)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-09 17:05:07 +00:00
public-glueops-renovatebot[bot]
fb0901a812 chore(patch): update github.com/aws/aws-sdk-go-v2/config to v1.32.4 #patch (#428)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-09 16:56:56 +00:00
allanice001
fee4c64551 fix: fix background jobs
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-09 15:49:31 +00:00
allanice001
4d37a6363f feat: add docker_image and docker_tag to cluster api
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-08 17:04:10 +00:00
allanice001
1dbdd04808 Merge remote-tracking branch 'origin/main' 2025-12-08 16:19:03 +00:00
allanice001
45b55015ac fix: ensure jobs are running
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-08 16:18:54 +00:00
public-glueops-renovatebot[bot]
6b191089a5 chore: lock file maintenance (#418)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-08 14:42:04 +00:00
public-glueops-renovatebot[bot]
d2e6ff9812 feat: update lucide-react to 0.556.0 #minor (#408)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-08 13:46:35 +00:00
public-glueops-renovatebot[bot]
98a6cf7e51 feat: update golang.org/x/oauth2 to v0.34.0 #minor (#417)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-08 12:31:38 +00:00
public-glueops-renovatebot[bot]
fb4af74e3c chore: lock file maintenance (#414)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-07 14:38:05 +00:00
public-glueops-renovatebot[bot]
1021e06655 chore: lock file maintenance (#413)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-06 18:42:45 +00:00
public-glueops-renovatebot[bot]
c6be7bf8eb chore: lock file maintenance (#411)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-06 14:37:41 +00:00
public-glueops-renovatebot[bot]
1429c40b2b chore: lock file maintenance (#410)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-05 16:43:39 +00:00
public-glueops-renovatebot[bot]
73c4904a42 chore: lock file maintenance (#409)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-05 13:54:39 +00:00
allanice001
40df22c166 Merge remote-tracking branch 'origin/main' 2025-12-05 12:37:32 +00:00
allanice001
500a8d1095 chore: ensure build succeeds locally
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-05 12:37:22 +00:00
public-glueops-renovatebot[bot]
eff69ff4ce chore(pin): update typescript to #patch (#407)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-05 12:32:31 +00:00
allanice001
2cd6ee91eb fix: cluster page references
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-05 12:31:16 +00:00
allanice001
2d3800b576 chore: update dependencies
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-05 12:20:47 +00:00
allanice001
eb86f2ad3c Merge remote-tracking branch 'origin/main'
# Conflicts:
#	docker-compose.yml
#	go.sum
2025-12-05 12:18:18 +00:00
allanice001
0b342f2c65 fis: updates to remove Terraform Provider reserved word collisions
Signed-off-by: allanice001 <allanice001@gmail.com>
2025-12-05 12:17:36 +00:00
public-glueops-renovatebot[bot]
e8725b1a7c chore(patch): update typescript-eslint to 8.48.1 #patch (#373)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-05 09:28:03 +00:00
public-glueops-renovatebot[bot]
5ec1d3bb0c chore: lock file maintenance (#406)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-05 07:26:59 +00:00
public-glueops-renovatebot[bot]
35efd1c0b9 chore: lock file maintenance (#404)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-04 19:25:02 +00:00
public-glueops-renovatebot[bot]
8febd35998 chore: lock file maintenance (#402)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-04 18:41:49 +00:00
public-glueops-renovatebot[bot]
94f668583e chore(patch): update prettier-plugin-tailwindcss to 0.7.2 #patch (#368)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-04 18:40:43 +00:00
public-glueops-renovatebot[bot]
9e1bca3dc3 chore: lock file maintenance (#401)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-04 14:02:27 +00:00
public-glueops-renovatebot[bot]
a9eb8cebd6 chore(patch): update vite to 7.2.6 #patch (#365)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-04 08:01:32 +00:00
public-glueops-renovatebot[bot]
fa5bbbe7b9 chore(fallback): update golang (#399)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-04 04:24:02 +00:00
public-glueops-renovatebot[bot]
8468317cf9 chore(patch): update github.com/spf13/cobra to v1.10.2 #patch (#398)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-04 00:41:00 +00:00
public-glueops-renovatebot[bot]
d315536956 chore: lock file maintenance (#397)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 23:26:28 +00:00
public-glueops-renovatebot[bot]
165fcb51ff chore: lock file maintenance (#396)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 23:25:21 +00:00
public-glueops-renovatebot[bot]
6f195aa0e6 chore: lock file maintenance (#395)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 22:49:35 +00:00
public-glueops-renovatebot[bot]
b07d56c93c chore: lock file maintenance (#393)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 22:06:05 +00:00
public-glueops-renovatebot[bot]
01fb6bfe61 feat: update alpine to 3.23 #minor (#392)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 20:44:33 +00:00
public-glueops-renovatebot[bot]
06bd37f8d4 chore: lock file maintenance (#391)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 16:58:04 +00:00
public-glueops-renovatebot[bot]
4f005b541d chore: lock file maintenance (#390)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 16:19:55 +00:00
public-glueops-renovatebot[bot]
8426f43c5e chore: lock file maintenance (#389)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 16:18:40 +00:00
public-glueops-renovatebot[bot]
963477a348 chore: lock file maintenance (#388)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 15:39:17 +00:00
public-glueops-renovatebot[bot]
cdec3896a7 chore: lock file maintenance (#387)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 14:24:17 +00:00
public-glueops-renovatebot[bot]
ba39f70e21 chore: lock file maintenance (#386)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 13:47:15 +00:00
public-glueops-renovatebot[bot]
571aa67f39 chore: lock file maintenance (#385)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-03 07:03:42 +00:00
public-glueops-renovatebot[bot]
8b01dfb8f0 chore: lock file maintenance (#383)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 19:02:33 +00:00
public-glueops-renovatebot[bot]
e177a07c94 chore(patch): update golang to 1.25.5 #patch (#382)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 19:01:22 +00:00
public-glueops-renovatebot[bot]
3ea6de756f chore(patch): update prettier to 3.7.3 #patch (#378)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 18:19:56 +00:00
public-glueops-renovatebot[bot]
be197a4ec5 feat: update github.com/aws/aws-sdk-go-v2/service/s3 to v1.93.0 #minor (#381)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 17:38:01 +00:00
public-glueops-renovatebot[bot]
fb92033555 chore(patch): update github.com/aws/aws-sdk-go-v2 to v1.40.1 #patch (#380)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 17:37:13 +00:00
public-glueops-renovatebot[bot]
4420ea8ffe chore: lock file maintenance (#379)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 16:42:41 +00:00
public-glueops-renovatebot[bot]
e1c59e2dbe chore(patch): update prettier to 3.7.2 #patch (#364)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 16:04:34 +00:00
public-glueops-renovatebot[bot]
d269f8fa52 chore: lock file maintenance (#377)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 14:06:49 +00:00
public-glueops-renovatebot[bot]
3ee9c0cddb chore: lock file maintenance (#376)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 09:51:28 +00:00
public-glueops-renovatebot[bot]
fa97e9411a chore: lock file maintenance (#375)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 09:17:34 +00:00
public-glueops-renovatebot[bot]
e2f91ffc8c chore: lock file maintenance (#374)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 09:16:25 +00:00
public-glueops-renovatebot[bot]
9bc47b7fdc chore: lock file maintenance (#372)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-02 07:25:20 +00:00
public-glueops-renovatebot[bot]
3d2f98bf7c chore: lock file maintenance (#371)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-01 21:04:18 +00:00
public-glueops-renovatebot[bot]
1c875f2634 chore: lock file maintenance (#370)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-01 16:48:00 +00:00
public-glueops-renovatebot[bot]
b752cf2aa9 chore: lock file maintenance (#369)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-01 16:13:19 +00:00
public-glueops-renovatebot[bot]
a52166af4a chore: lock file maintenance (#367)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-12-01 11:55:03 +00:00
public-glueops-renovatebot[bot]
83abb08534 chore(patch): update shadcn to 3.5.1 #patch (#356)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-30 17:17:55 +00:00
public-glueops-renovatebot[bot]
fefad47ab4 feat: update prettier to 3.7.1 #minor (#354)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-30 16:29:21 +00:00
public-glueops-renovatebot[bot]
125c896ef5 chore: lock file maintenance (#363)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-29 21:22:59 +00:00
public-glueops-renovatebot[bot]
bc04f4ed8e chore: lock file maintenance (#362)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-29 11:41:17 +00:00
public-glueops-renovatebot[bot]
25f2da417d feat: update lucide-react to 0.555.0 #minor (#349)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-29 08:48:38 +00:00
public-glueops-renovatebot[bot]
79e16c8bf7 chore: lock file maintenance (#360)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-29 08:00:20 +00:00
public-glueops-renovatebot[bot]
56a4899d2b chore: lock file maintenance (#359)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-28 20:56:37 +00:00
public-glueops-renovatebot[bot]
6e86da8939 chore: lock file maintenance (#358)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-28 16:09:59 +00:00
public-glueops-renovatebot[bot]
75dc2689c8 chore: lock file maintenance (#357)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-28 14:50:12 +00:00
public-glueops-renovatebot[bot]
2fcfa04a3f feat: update typescript-eslint to 8.48.0 #minor (#338)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-27 17:11:41 +00:00
public-glueops-renovatebot[bot]
78ec2744f1 feat: update docker/metadata-action to v5.10.0 #minor (#355)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-27 14:01:03 +00:00
public-glueops-renovatebot[bot]
6948fcfaec chore(patch): update @types/react to 19.2.7 #patch (#336)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-27 10:01:25 +00:00
public-glueops-renovatebot[bot]
4ac43b38d5 chore: lock file maintenance (#353)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-27 07:04:08 +00:00
public-glueops-renovatebot[bot]
590d3980be chore: lock file maintenance (#352)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-26 23:07:17 +00:00
public-glueops-renovatebot[bot]
e569b90fcf chore: lock file maintenance (#351)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-26 19:03:32 +00:00
public-glueops-renovatebot[bot]
49eb568990 chore: lock file maintenance (#350)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-26 17:57:41 +00:00
public-glueops-renovatebot[bot]
698c8263ca chore: lock file maintenance (#347)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-25 22:58:06 +00:00
public-glueops-renovatebot[bot]
b73f78dd74 chore: lock file maintenance (#346)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-25 21:51:54 +00:00
public-glueops-renovatebot[bot]
b250f1d8c2 feat: update github.com/aws/aws-sdk-go-v2/service/route53 to v1.61.0 #minor (#345)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-25 20:52:18 +00:00
public-glueops-renovatebot[bot]
1764cfa03d chore(patch): update github.com/aws/aws-sdk-go-v2/config to v1.32.2 #patch (#344)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-25 20:51:16 +00:00
public-glueops-renovatebot[bot]
7e33ae3e38 chore: lock file maintenance (#343)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-25 17:34:34 +00:00
public-glueops-renovatebot[bot]
590a39ef14 chore: lock file maintenance (#341)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-25 14:00:53 +00:00
public-glueops-renovatebot[bot]
154bd738ff chore: lock file maintenance (#340)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-24 23:51:08 +00:00
public-glueops-renovatebot[bot]
831c29a774 chore: lock file maintenance (#339)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-24 19:24:00 +00:00
public-glueops-renovatebot[bot]
8a5afc358c chore: lock file maintenance (#337)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-24 17:14:49 +00:00
public-glueops-renovatebot[bot]
93f4189885 chore: lock file maintenance (#335)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-24 08:01:15 +00:00
public-glueops-renovatebot[bot]
e1a53b122b chore: lock file maintenance (#334)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-24 03:06:41 +00:00
public-glueops-renovatebot[bot]
2fafe2d752 chore: lock file maintenance (#332)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-23 15:24:02 +00:00
public-glueops-renovatebot[bot]
1d82e562f4 chore: lock file maintenance (#331)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-23 14:40:27 +00:00
public-glueops-renovatebot[bot]
a6a4315b7c chore: lock file maintenance (#330)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-23 11:00:23 +00:00
public-glueops-renovatebot[bot]
f7aa67f522 chore(patch): update vite to 7.2.4 #patch (#316)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-23 07:45:30 +00:00
public-glueops-renovatebot[bot]
ddcba7e4e8 chore: lock file maintenance (#329)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-23 04:10:22 +00:00
public-glueops-renovatebot[bot]
f44ac86010 chore: lock file maintenance (#328)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-22 22:30:47 +00:00
public-glueops-renovatebot[bot]
c02eb401a9 feat: update github.com/sosedoff/pgweb to v0.17.0 #minor (#327)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-22 16:10:35 +00:00
public-glueops-renovatebot[bot]
bc24ae2553 chore(fallback): update sosedoff/pgweb (#326)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-22 16:09:46 +00:00
public-glueops-renovatebot[bot]
f423a53854 chore: lock file maintenance (#325)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-21 21:11:01 +00:00
public-glueops-renovatebot[bot]
f9ca5a85ae chore(patch): update github.com/aws/aws-sdk-go-v2/config to v1.32.1 #patch (#324)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-21 21:09:50 +00:00
public-glueops-renovatebot[bot]
a815cb8131 feat: update github.com/coreos/go-oidc/v3 to v3.17.0 #minor (#323)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-21 03:41:52 +00:00
public-glueops-renovatebot[bot]
e488974ca8 chore(patch): update @types/react to 19.2.6 #patch (#301)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-21 02:54:49 +00:00
public-glueops-renovatebot[bot]
55b5459854 chore: lock file maintenance (#322)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-20 23:17:56 +00:00
public-glueops-renovatebot[bot]
76e02ac8e0 feat: update github.com/aws/aws-sdk-go-v2/service/s3 to v1.92.0 #minor (#321)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-20 20:39:04 +00:00
public-glueops-renovatebot[bot]
af19648fe9 chore: lock file maintenance (#320)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-20 19:26:41 +00:00
public-glueops-renovatebot[bot]
28c8151b2c feat: update typescript-eslint to 8.47.0 #minor (#296)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-20 17:39:32 +00:00
public-glueops-renovatebot[bot]
fa831a74ce chore: lock file maintenance (#318)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-20 15:17:30 +00:00
public-glueops-renovatebot[bot]
3c2b7dade5 chore: lock file maintenance (#317)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-20 11:33:14 +00:00
public-glueops-renovatebot[bot]
78b9c97de1 feat: update lucide-react to 0.554.0 #minor (#295)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-20 09:17:36 +00:00
public-glueops-renovatebot[bot]
ae1aa591a2 chore: lock file maintenance (#315)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-20 03:03:01 +00:00
public-glueops-renovatebot[bot]
7cae40b00b feat: update github.com/aws/aws-sdk-go-v2/config to v1.32.0 #minor (#313)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-19 23:39:30 +00:00
public-glueops-renovatebot[bot]
59b158ca0a chore(patch): update github.com/aws/aws-sdk-go-v2/service/route53 to v1.60.1 #patch (#311)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-19 23:38:44 +00:00
public-glueops-renovatebot[bot]
915a9a4342 feat: update github.com/aws/aws-sdk-go-v2/service/s3 to v1.91.0 #minor (#309)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-19 20:42:54 +00:00
public-glueops-renovatebot[bot]
ffa59e66e1 chore: lock file maintenance (#306)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-19 20:36:23 +00:00
public-glueops-renovatebot[bot]
1e8d2e8410 feat: update golang.org/x/crypto to v0.45.0 #minor (#310)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-19 20:35:48 +00:00
public-glueops-renovatebot[bot]
686511e21b feat: update github.com/aws/aws-sdk-go-v2/service/route53 to v1.60.0 #minor (#308)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-19 20:35:32 +00:00
public-glueops-renovatebot[bot]
8cb1901227 chore(patch): update github.com/aws/aws-sdk-go-v2/config to v1.31.21 #patch (#307)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-19 20:34:24 +00:00
public-glueops-renovatebot[bot]
388eec726e chore: lock file maintenance (#305)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-18 23:46:13 +00:00
public-glueops-renovatebot[bot]
6f696b4e94 chore: lock file maintenance (#304)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-18 17:04:13 +00:00
public-glueops-renovatebot[bot]
5c07732b42 chore: lock file maintenance (#303)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-18 15:35:40 +00:00
public-glueops-renovatebot[bot]
7949a544a4 chore: lock file maintenance (#302)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-18 11:02:01 +00:00
public-glueops-renovatebot[bot]
3f0f6579ef chore: lock file maintenance (#300)
Co-authored-by: public-glueops-renovatebot[bot] <186083205+public-glueops-renovatebot[bot]@users.noreply.github.com>
2025-11-17 20:48:03 +00:00
271 changed files with 39400 additions and 7685 deletions

View File

@@ -33,7 +33,7 @@ jobs:
steps:
- name: Checkout repository
uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # v5
uses: actions/checkout@8e8c483db84b4bee98b60c0593521ed34d9990e8 # v6
# Install the cosign tool except on PR
# https://github.com/sigstore/cosign-installer
@@ -47,13 +47,13 @@ jobs:
# multi-platform images and export cache
# https://github.com/docker/setup-buildx-action
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@e468171a9de216ec08956ac3ada2f0791b6bd435 # v3.11.1
uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f # v3.12.0
# Login against a Docker registry except on PR
# https://github.com/docker/login-action
- name: Log into registry ${{ env.REGISTRY }}
if: github.event_name != 'pull_request'
uses: docker/login-action@5e57cd118135c172c3672efd75eb46360885c0ef # v3.6.0
uses: docker/login-action@c94ce9fb468520275223c153574b00df6fe4bcc9 # v3.7.0
with:
registry: ${{ env.REGISTRY }}
username: ${{ github.actor }}
@@ -63,7 +63,7 @@ jobs:
# https://github.com/docker/metadata-action
- name: Extract Docker metadata
id: meta
uses: docker/metadata-action@318604b99e75e41977312d83839a89be02ca4893 # v5.9.0
uses: docker/metadata-action@c299e40c65443455700f0fdfc63efafe5b349051 # v5.10.0
with:
images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
tags: |

View File

@@ -1,7 +1,7 @@
#################################
# Builder: Go + Node in one
#################################
FROM golang:1.25.4-alpine@sha256:d3f0cf7723f3429e3f9ed846243970b20a2de7bae6a5b66fc5914e228d831bbb AS builder
FROM golang:1.25.7-alpine@sha256:81d49e1de26fa223b9ae0b4d5a4065ff8176a7d80aa5ef0bd9f2eee430afe4d7 AS builder
RUN apk add --no-cache \
bash git ca-certificates tzdata \
@@ -24,7 +24,7 @@ RUN make build
#################################
# Runtime
#################################
FROM alpine:3.22@sha256:4b7ce07002c69e8f3d704a9c5d6fd3053be500b7f1c69fc0d80990c2ad8dd412
FROM alpine:3.23@sha256:865b95f46d98cf867a156fe4a135ad3fe50d2056aa3f25ed31662dff6da4eb62
RUN apk add --no-cache ca-certificates tzdata postgresql17-client \
&& addgroup -S app && adduser -S app -G app

View File

@@ -204,6 +204,7 @@ swagger: $(DOCS_JSON) ## Generate Swagger docs if stale
# --- build ---
build: prepare ui swagger sdk-all ## Build everything: Go hygiene, UI, Swagger, SDKs, then Go binary
@echo ">> Building Go binary: $(BIN)"
@$(GOCMD) get github.com/swaggo/swag/v2@v2.0.0-rc4
@$(GOCMD) build -trimpath -ldflags "$(LDFLAGS)" -o $(BIN) $(MAIN)
# Handy: print resolved version metadata

View File

@@ -115,6 +115,64 @@ var serveCmd = &cobra.Command{
if err != nil {
log.Printf("failed to enqueue bootstrap_bastion: %v", err)
}
/*
_, err = jobs.Enqueue(
context.Background(),
uuid.NewString(),
"prepare_cluster",
bg.ClusterPrepareArgs{IntervalS: 120},
archer.WithMaxRetries(3),
archer.WithScheduleTime(time.Now().Add(60*time.Second)),
)
if err != nil {
log.Printf("failed to enqueue prepare_cluster: %v", err)
}
_, err = jobs.Enqueue(
context.Background(),
uuid.NewString(),
"cluster_setup",
bg.ClusterSetupArgs{
IntervalS: 120,
},
archer.WithMaxRetries(3),
archer.WithScheduleTime(time.Now().Add(60*time.Second)),
)
if err != nil {
log.Printf("failed to enqueue cluster setup: %v", err)
}
_, err = jobs.Enqueue(
context.Background(),
uuid.NewString(),
"cluster_bootstrap",
bg.ClusterBootstrapArgs{
IntervalS: 120,
},
archer.WithMaxRetries(3),
archer.WithScheduleTime(time.Now().Add(60*time.Second)),
)
if err != nil {
log.Printf("failed to enqueue cluster bootstrap: %v", err)
}
*/
_, err = jobs.Enqueue(
context.Background(),
uuid.NewString(),
"org_key_sweeper",
bg.OrgKeySweeperArgs{
IntervalS: 3600,
RetentionDays: 10,
},
archer.WithMaxRetries(1),
archer.WithScheduleTime(time.Now()),
)
if err != nil {
log.Printf("failed to enqueue org_key_sweeper: %v", err)
}
}
_ = auth.Refresh(rt.DB, rt.Cfg.JWTPrivateEncKey)

View File

@@ -1,18 +1,4 @@
services:
autoglue:
# image: ghcr.io/glueops/autoglue:latest
build: .
ports:
- 8080:8080
expose:
- 8080
env_file: .env
environment:
AUTOGLUE_DATABASE_DSN: postgres://$DB_USER:$DB_PASSWORD@postgres:5432/$DB_NAME
AUTOGLUE_BIND_ADDRESS: 0.0.0.0
depends_on:
- postgres
postgres:
build:
context: postgres
@@ -28,21 +14,8 @@ services:
volumes:
- postgres_data:/var/lib/postgresql/data
pgweb:
image: sosedoff/pgweb@sha256:8f1ed22e10c9da0912169b98b62ddc54930dc39a5ae07b0f1354d2a93d44c6ed
restart: always
ports:
- "8081:8081"
links:
- postgres:postgres
env_file: .env
environment:
PGWEB_DATABASE_URL: postgres://$DB_USER:$DB_PASSWORD@postgres:5432/$DB_NAME
depends_on:
- postgres
mailpit:
image: axllent/mailpit@sha256:e22dce5b36f93c77082e204a3942fb6b283b7896e057458400a4c88344c3df68
image: axllent/mailpit@sha256:c076638db1e15662150be4fb62b8a6e96ef6ba5bde90c838a0239225854830f7
restart: always
ports:
- "1025:1025"

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@@ -1,5 +1,23 @@
components:
schemas:
dto.ActionResponse:
properties:
created_at:
format: date-time
type: string
description:
type: string
id:
format: uuid
type: string
label:
type: string
make_target:
type: string
updated_at:
format: date-time
type: string
type: object
dto.AnnotationResponse:
properties:
created_at:
@@ -88,14 +106,24 @@ components:
$ref: '#/components/schemas/dto.DomainResponse'
certificate_key:
type: string
cluster_provider:
type: string
control_plane_fqdn:
type: string
control_plane_record_set:
$ref: '#/components/schemas/dto.RecordSetResponse'
created_at:
type: string
docker_image:
type: string
docker_tag:
type: string
glueops_load_balancer:
$ref: '#/components/schemas/dto.LoadBalancerResponse'
id:
type: string
kubeconfig:
type: string
last_error:
type: string
name:
@@ -105,7 +133,9 @@ components:
$ref: '#/components/schemas/dto.NodePoolResponse'
type: array
uniqueItems: false
provider:
org_key:
type: string
org_secret:
type: string
random_token:
type: string
@@ -116,6 +146,42 @@ components:
updated_at:
type: string
type: object
dto.ClusterRunResponse:
properties:
action:
type: string
cluster_id:
format: uuid
type: string
created_at:
format: date-time
type: string
error:
type: string
finished_at:
format: date-time
type: string
id:
format: uuid
type: string
organization_id:
format: uuid
type: string
status:
type: string
updated_at:
format: date-time
type: string
type: object
dto.CreateActionRequest:
properties:
description:
type: string
label:
type: string
make_target:
type: string
type: object
dto.CreateAnnotationRequest:
properties:
key:
@@ -125,9 +191,13 @@ components:
type: object
dto.CreateClusterRequest:
properties:
name:
cluster_provider:
type: string
provider:
docker_image:
type: string
docker_tag:
type: string
name:
type: string
region:
type: string
@@ -137,14 +207,7 @@ components:
account_id:
maxLength: 32
type: string
kind:
description: aws_access_key, api_token, basic_auth, oauth2
type: string
name:
description: human label
maxLength: 100
type: string
provider:
credential_provider:
enum:
- aws
- cloudflare
@@ -152,6 +215,13 @@ components:
- digitalocean
- generic
type: string
kind:
description: aws_access_key, api_token, basic_auth, oauth2
type: string
name:
description: human label
maxLength: 100
type: string
region:
maxLength: 32
type: string
@@ -164,7 +234,7 @@ components:
type: object
scope_kind:
enum:
- provider
- credential_provider
- service
- resource
type: string
@@ -176,8 +246,8 @@ components:
description: encrypted later
type: object
required:
- credential_provider
- kind
- provider
- schema_version
- scope
- scope_kind
@@ -312,14 +382,14 @@ components:
type: string
created_at:
type: string
credential_provider:
type: string
id:
type: string
kind:
type: string
name:
type: string
provider:
type: string
region:
type: string
schema_version:
@@ -700,6 +770,15 @@ components:
example: Bearer
type: string
type: object
dto.UpdateActionRequest:
properties:
description:
type: string
label:
type: string
make_target:
type: string
type: object
dto.UpdateAnnotationRequest:
properties:
key:
@@ -709,9 +788,13 @@ components:
type: object
dto.UpdateClusterRequest:
properties:
name:
cluster_provider:
type: string
provider:
docker_image:
type: string
docker_tag:
type: string
name:
type: string
region:
type: string
@@ -1023,6 +1106,8 @@ components:
type: object
models.APIKey:
properties:
cluster_id:
type: string
created_at:
format: date-time
type: string
@@ -1032,6 +1117,8 @@ components:
id:
format: uuid
type: string
is_ephemeral:
type: boolean
last_used_at:
format: date-time
type: string
@@ -1042,6 +1129,8 @@ components:
type: string
prefix:
type: string
purpose:
type: string
revoked:
type: boolean
scope:
@@ -1159,7 +1248,7 @@ info:
name: GlueOps
description: API for managing K3s clusters across cloud providers
title: AutoGlue API
version: ""
version: dev
openapi: 3.1.0
paths:
/.well-known/jwks.json:
@@ -1176,6 +1265,222 @@ paths:
summary: Get JWKS
tags:
- Auth
/admin/actions:
get:
description: Returns all admin-configured actions.
operationId: ListActions
responses:
"200":
content:
application/json:
schema:
items:
$ref: '#/components/schemas/dto.ActionResponse'
type: array
description: OK
"401":
content:
application/json:
schema:
type: string
description: Unauthorized
"500":
content:
application/json:
schema:
type: string
description: db error
security:
- BearerAuth: []
summary: List available actions
tags:
- Actions
post:
description: Creates a new admin-configured action.
operationId: CreateAction
requestBody:
content:
application/json:
schema:
$ref: '#/components/schemas/dto.CreateActionRequest'
description: payload
required: true
responses:
"201":
content:
application/json:
schema:
$ref: '#/components/schemas/dto.ActionResponse'
description: Created
"400":
content:
application/json:
schema:
type: string
description: bad request
"401":
content:
application/json:
schema:
type: string
description: Unauthorized
"500":
content:
application/json:
schema:
type: string
description: db error
security:
- BearerAuth: []
summary: Create an action
tags:
- Actions
/admin/actions/{actionID}:
delete:
description: Deletes an action.
operationId: DeleteAction
parameters:
- description: Action ID
in: path
name: actionID
required: true
schema:
type: string
responses:
"204":
content:
application/json:
schema:
type: string
description: deleted
"400":
content:
application/json:
schema:
type: string
description: bad request
"401":
content:
application/json:
schema:
type: string
description: Unauthorized
"404":
content:
application/json:
schema:
type: string
description: not found
"500":
content:
application/json:
schema:
type: string
description: db error
security:
- BearerAuth: []
summary: Delete an action
tags:
- Actions
get:
description: Returns a single action.
operationId: GetAction
parameters:
- description: Action ID
in: path
name: actionID
required: true
schema:
type: string
responses:
"200":
content:
application/json:
schema:
$ref: '#/components/schemas/dto.ActionResponse'
description: OK
"400":
content:
application/json:
schema:
type: string
description: bad request
"401":
content:
application/json:
schema:
type: string
description: Unauthorized
"404":
content:
application/json:
schema:
type: string
description: not found
"500":
content:
application/json:
schema:
type: string
description: db error
security:
- BearerAuth: []
summary: Get a single action by ID
tags:
- Actions
patch:
description: Updates an action. Only provided fields are modified.
operationId: UpdateAction
parameters:
- description: Action ID
in: path
name: actionID
required: true
schema:
type: string
requestBody:
content:
application/json:
schema:
$ref: '#/components/schemas/dto.UpdateActionRequest'
description: payload
required: true
responses:
"200":
content:
application/json:
schema:
$ref: '#/components/schemas/dto.ActionResponse'
description: OK
"400":
content:
application/json:
schema:
type: string
description: bad request
"401":
content:
application/json:
schema:
type: string
description: Unauthorized
"404":
content:
application/json:
schema:
type: string
description: not found
"500":
content:
application/json:
schema:
type: string
description: db error
security:
- BearerAuth: []
summary: Update an action
tags:
- Actions
/admin/archer/jobs:
get:
description: Paginated background jobs with optional filters. Search `q` may
@@ -2098,6 +2403,73 @@ paths:
summary: Update basic cluster details (org scoped)
tags:
- Clusters
/clusters/{clusterID}/actions/{actionID}/runs:
post:
description: Creates a ClusterRun record for the cluster/action. Execution is
handled asynchronously by workers.
operationId: RunClusterAction
parameters:
- description: Organization UUID
in: header
name: X-Org-ID
schema:
type: string
- description: Cluster ID
in: path
name: clusterID
required: true
schema:
type: string
- description: Action ID
in: path
name: actionID
required: true
schema:
type: string
responses:
"201":
content:
application/json:
schema:
$ref: '#/components/schemas/dto.ClusterRunResponse'
description: Created
"400":
content:
application/json:
schema:
type: string
description: bad request
"401":
content:
application/json:
schema:
type: string
description: Unauthorized
"403":
content:
application/json:
schema:
type: string
description: organization required
"404":
content:
application/json:
schema:
type: string
description: cluster or action not found
"500":
content:
application/json:
schema:
type: string
description: db error
security:
- BearerAuth: []
- OrgKeyAuth: []
- OrgSecretAuth: []
summary: Run an admin-configured action on a cluster (org scoped)
tags:
- ClusterRuns
/clusters/{clusterID}/apps-load-balancer:
delete:
description: Clears apps_load_balancer_id on the cluster.
@@ -2991,6 +3363,128 @@ paths:
summary: Detach a node pool from a cluster
tags:
- Clusters
/clusters/{clusterID}/runs:
get:
description: Returns runs for a cluster within the organization in X-Org-ID.
operationId: ListClusterRuns
parameters:
- description: Organization UUID
in: header
name: X-Org-ID
schema:
type: string
- description: Cluster ID
in: path
name: clusterID
required: true
schema:
type: string
responses:
"200":
content:
application/json:
schema:
items:
$ref: '#/components/schemas/dto.ClusterRunResponse'
type: array
description: OK
"401":
content:
application/json:
schema:
type: string
description: Unauthorized
"403":
content:
application/json:
schema:
type: string
description: organization required
"404":
content:
application/json:
schema:
type: string
description: cluster not found
"500":
content:
application/json:
schema:
type: string
description: db error
security:
- BearerAuth: []
- OrgKeyAuth: []
- OrgSecretAuth: []
summary: List cluster runs (org scoped)
tags:
- ClusterRuns
/clusters/{clusterID}/runs/{runID}:
get:
description: Returns a single run for a cluster within the organization in X-Org-ID.
operationId: GetClusterRun
parameters:
- description: Organization UUID
in: header
name: X-Org-ID
schema:
type: string
- description: Cluster ID
in: path
name: clusterID
required: true
schema:
type: string
- description: Run ID
in: path
name: runID
required: true
schema:
type: string
responses:
"200":
content:
application/json:
schema:
$ref: '#/components/schemas/dto.ClusterRunResponse'
description: OK
"400":
content:
application/json:
schema:
type: string
description: bad request
"401":
content:
application/json:
schema:
type: string
description: Unauthorized
"403":
content:
application/json:
schema:
type: string
description: organization required
"404":
content:
application/json:
schema:
type: string
description: not found
"500":
content:
application/json:
schema:
type: string
description: db error
security:
- BearerAuth: []
- OrgKeyAuth: []
- OrgSecretAuth: []
summary: Get a cluster run (org scoped)
tags:
- ClusterRuns
/credentials:
get:
description: Returns credential metadata for the current org. Secrets are never
@@ -3004,7 +3498,7 @@ paths:
type: string
- description: Filter by provider (e.g., aws)
in: query
name: provider
name: credential_provider
schema:
type: string
- description: Filter by kind (e.g., aws_access_key)
@@ -3012,7 +3506,7 @@ paths:
name: kind
schema:
type: string
- description: Filter by scope kind (provider/service/resource)
- description: Filter by scope kind (credential_provider/service/resource)
in: query
name: scope_kind
schema:
@@ -3670,6 +4164,42 @@ paths:
external deletion policy)
tags:
- DNS
get:
operationId: GetRecordSet
parameters:
- description: Organization UUID
in: header
name: X-Org-ID
schema:
type: string
- description: Record Set ID (UUID)
in: path
name: id
required: true
schema:
type: string
responses:
"200":
content:
application/json:
schema:
$ref: '#/components/schemas/dto.RecordSetResponse'
description: OK
"403":
content:
application/json:
schema:
type: string
description: organization required
"404":
content:
application/json:
schema:
type: string
description: not found
summary: Get a record set (org scoped)
tags:
- DNS
patch:
operationId: UpdateRecordSet
parameters:
@@ -6695,7 +7225,9 @@ paths:
- Meta
servers:
- description: Production API
url: https://autoglue.onglueops.rocks/api/v1
url: https://autoglue.glueopshosted.com/api/v1
- description: Pre-Production API
url: https://autoglue.glueopshosted.rocks/api/v1
- description: Staging API
url: https://autoglue.apps.nonprod.earth.onglueops.rocks/api/v1
- description: Local dev

124
go.mod
View File

@@ -3,31 +3,31 @@ module github.com/glueops/autoglue
go 1.25.4
require (
ariga.io/atlas-provider-gorm v0.6.0
github.com/alexedwards/argon2id v1.0.0
github.com/aws/aws-sdk-go-v2 v1.39.6
github.com/aws/aws-sdk-go-v2/config v1.31.20
github.com/aws/aws-sdk-go-v2/credentials v1.18.24
github.com/aws/aws-sdk-go-v2/service/route53 v1.59.5
github.com/aws/aws-sdk-go-v2/service/s3 v1.90.2
github.com/coreos/go-oidc/v3 v3.16.0
github.com/aws/aws-sdk-go-v2 v1.41.1
github.com/aws/aws-sdk-go-v2/config v1.32.7
github.com/aws/aws-sdk-go-v2/credentials v1.19.7
github.com/aws/aws-sdk-go-v2/service/route53 v1.62.1
github.com/aws/aws-sdk-go-v2/service/s3 v1.96.0
github.com/aws/smithy-go v1.24.0
github.com/coreos/go-oidc/v3 v3.17.0
github.com/dyaksa/archer v1.1.5
github.com/fergusstrange/embedded-postgres v1.33.0
github.com/gin-gonic/gin v1.11.0
github.com/go-chi/chi/v5 v5.2.3
github.com/go-chi/chi/v5 v5.2.5
github.com/go-chi/cors v1.2.2
github.com/go-chi/httprate v0.15.0
github.com/go-playground/validator/v10 v10.28.0
github.com/golang-jwt/jwt/v5 v5.3.0
github.com/go-playground/validator/v10 v10.30.1
github.com/golang-jwt/jwt/v5 v5.3.1
github.com/google/uuid v1.6.0
github.com/joho/godotenv v1.5.1
github.com/rs/zerolog v1.34.0
github.com/sosedoff/pgweb v0.16.2
github.com/spf13/cobra v1.10.1
github.com/sosedoff/pgweb v0.17.0
github.com/spf13/cobra v1.10.2
github.com/spf13/viper v1.21.0
github.com/swaggo/swag/v2 v2.0.0-rc4
golang.org/x/crypto v0.44.0
golang.org/x/oauth2 v0.33.0
github.com/swaggo/swag/v2 v2.0.0-rc5
golang.org/x/crypto v0.47.0
golang.org/x/oauth2 v0.34.0
gopkg.in/yaml.v3 v3.0.1
gorm.io/datatypes v1.2.7
gorm.io/driver/postgres v1.6.0
@@ -35,52 +35,35 @@ require (
)
require (
ariga.io/atlas v0.36.2-0.20250806044935-5bb51a0a956e // indirect
cel.dev/expr v0.24.0 // indirect
cloud.google.com/go v0.121.6 // indirect
cloud.google.com/go/auth v0.16.4 // indirect
cloud.google.com/go/auth/oauth2adapt v0.2.8 // indirect
cloud.google.com/go/compute/metadata v0.8.0 // indirect
cloud.google.com/go/iam v1.5.2 // indirect
cloud.google.com/go/longrunning v0.6.7 // indirect
cloud.google.com/go/monitoring v1.24.2 // indirect
cloud.google.com/go/spanner v1.84.1 // indirect
filippo.io/edwards25519 v1.1.0 // indirect
github.com/BurntSushi/toml v1.1.0 // indirect
github.com/GoogleCloudPlatform/grpc-gcp-go/grpcgcp v1.5.3 // indirect
github.com/GoogleCloudPlatform/opentelemetry-operations-go/detectors/gcp v1.29.0 // indirect
github.com/KyleBanks/depth v1.2.1 // indirect
github.com/ScaleFT/sshkeys v0.0.0-20200327173127-6142f742bca5 // indirect
github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.7.3 // indirect
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.18.13 // indirect
github.com/aws/aws-sdk-go-v2/internal/configsources v1.4.13 // indirect
github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.7.13 // indirect
github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.7.4 // indirect
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.18.17 // indirect
github.com/aws/aws-sdk-go-v2/internal/configsources v1.4.17 // indirect
github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.7.17 // indirect
github.com/aws/aws-sdk-go-v2/internal/ini v1.8.4 // indirect
github.com/aws/aws-sdk-go-v2/internal/v4a v1.4.13 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.13.3 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.9.4 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.13.13 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/s3shared v1.19.13 // indirect
github.com/aws/aws-sdk-go-v2/service/sso v1.30.3 // indirect
github.com/aws/aws-sdk-go-v2/service/ssooidc v1.35.7 // indirect
github.com/aws/aws-sdk-go-v2/service/sts v1.40.2 // indirect
github.com/aws/smithy-go v1.23.2 // indirect
github.com/aws/aws-sdk-go-v2/internal/v4a v1.4.17 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.13.4 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.9.8 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.13.17 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/s3shared v1.19.17 // indirect
github.com/aws/aws-sdk-go-v2/service/signin v1.0.5 // indirect
github.com/aws/aws-sdk-go-v2/service/sso v1.30.9 // indirect
github.com/aws/aws-sdk-go-v2/service/ssooidc v1.35.13 // indirect
github.com/aws/aws-sdk-go-v2/service/sts v1.41.6 // indirect
github.com/beorn7/perks v1.0.1 // indirect
github.com/bytedance/sonic v1.14.0 // indirect
github.com/bytedance/sonic/loader v0.3.0 // indirect
github.com/cespare/xxhash/v2 v2.3.0 // indirect
github.com/cloudwego/base64x v0.1.6 // indirect
github.com/cncf/xds/go v0.0.0-20250501225837-2ac532fd4443 // indirect
github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect
github.com/dchest/bcrypt_pbkdf v0.0.0-20150205184540-83f37f9c154a // indirect
github.com/envoyproxy/go-control-plane/envoy v1.32.4 // indirect
github.com/envoyproxy/protoc-gen-validate v1.2.1 // indirect
github.com/felixge/httpsnoop v1.0.4 // indirect
github.com/fsnotify/fsnotify v1.9.0 // indirect
github.com/gabriel-vasile/mimetype v1.4.10 // indirect
github.com/gabriel-vasile/mimetype v1.4.12 // indirect
github.com/gin-contrib/sse v1.1.0 // indirect
github.com/go-jose/go-jose/v4 v4.1.3 // indirect
github.com/go-logr/logr v1.4.3 // indirect
github.com/go-logr/stdr v1.2.2 // indirect
github.com/go-openapi/jsonpointer v0.19.6 // indirect
github.com/go-openapi/jsonreference v0.20.2 // indirect
github.com/go-openapi/spec v0.20.9 // indirect
@@ -91,15 +74,6 @@ require (
github.com/go-viper/mapstructure/v2 v2.4.0 // indirect
github.com/goccy/go-json v0.10.5 // indirect
github.com/goccy/go-yaml v1.18.0 // indirect
github.com/golang-sql/civil v0.0.0-20220223132316-b832511892a9 // indirect
github.com/golang-sql/sqlexp v0.1.0 // indirect
github.com/golang/groupcache v0.0.0-20241129210726-2c02b8208cf8 // indirect
github.com/google/s2a-go v0.1.9 // indirect
github.com/googleapis/enterprise-certificate-proxy v0.3.6 // indirect
github.com/googleapis/gax-go/v2 v2.15.0 // indirect
github.com/googleapis/go-gorm-spanner v1.8.6 // indirect
github.com/googleapis/go-sql-spanner v1.17.0 // indirect
github.com/hashicorp/golang-lru/v2 v2.0.7 // indirect
github.com/inconshreveable/mousetrap v1.1.0 // indirect
github.com/jackc/pgpassfile v1.0.0 // indirect
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761 // indirect
@@ -118,63 +92,43 @@ require (
github.com/mattn/go-colorable v0.1.13 // indirect
github.com/mattn/go-isatty v0.0.20 // indirect
github.com/mattn/go-sqlite3 v1.14.28 // indirect
github.com/microsoft/go-mssqldb v1.7.2 // indirect
github.com/mitchellh/go-homedir v1.1.0 // indirect
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
github.com/modern-go/reflect2 v1.0.2 // indirect
github.com/mr-tron/base58 v1.2.0 // indirect
github.com/pelletier/go-toml/v2 v2.2.4 // indirect
github.com/pkg/errors v0.9.1 // indirect
github.com/planetscale/vtprotobuf v0.6.1-0.20240319094008-0393e58bdf10 // indirect
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect
github.com/prometheus/client_golang v1.19.1 // indirect
github.com/prometheus/client_model v0.6.1 // indirect
github.com/prometheus/common v0.48.0 // indirect
github.com/prometheus/procfs v0.12.0 // indirect
github.com/quic-go/qpack v0.5.1 // indirect
github.com/quic-go/quic-go v0.54.0 // indirect
github.com/rogpeppe/go-internal v1.13.1 // indirect
github.com/sagikazarmark/locafero v0.11.0 // indirect
github.com/sirupsen/logrus v1.9.0 // indirect
github.com/sourcegraph/conc v0.3.1-0.20240121214520-5f936abd7ae8 // indirect
github.com/spf13/afero v1.15.0 // indirect
github.com/spf13/cast v1.10.0 // indirect
github.com/spf13/pflag v1.0.10 // indirect
github.com/spiffe/go-spiffe/v2 v2.5.0 // indirect
github.com/subosito/gotenv v1.6.0 // indirect
github.com/sv-tools/openapi v0.2.1 // indirect
github.com/sv-tools/openapi v0.4.0 // indirect
github.com/tuvistavie/securerandom v0.0.0-20140719024926-15512123a948 // indirect
github.com/twitchyliquid64/golang-asm v0.15.1 // indirect
github.com/ugorji/go/codec v1.3.0 // indirect
github.com/xi2/xz v0.0.0-20171230120015-48954b6210f8 // indirect
github.com/zeebo/errs v1.4.0 // indirect
github.com/zeebo/xxh3 v1.0.2 // indirect
go.opencensus.io v0.24.0 // indirect
go.opentelemetry.io/auto/sdk v1.1.0 // indirect
go.opentelemetry.io/contrib/detectors/gcp v1.37.0 // indirect
go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.62.0 // indirect
go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.62.0 // indirect
go.opentelemetry.io/otel v1.37.0 // indirect
go.opentelemetry.io/otel/metric v1.37.0 // indirect
go.opentelemetry.io/otel/sdk v1.37.0 // indirect
go.opentelemetry.io/otel/sdk/metric v1.37.0 // indirect
go.opentelemetry.io/otel/trace v1.37.0 // indirect
go.uber.org/mock v0.5.0 // indirect
go.yaml.in/yaml/v3 v3.0.4 // indirect
golang.org/x/arch v0.20.0 // indirect
golang.org/x/mod v0.29.0 // indirect
golang.org/x/net v0.46.0 // indirect
golang.org/x/sync v0.18.0 // indirect
golang.org/x/sys v0.38.0 // indirect
golang.org/x/text v0.31.0 // indirect
golang.org/x/time v0.12.0 // indirect
golang.org/x/tools v0.38.0 // indirect
google.golang.org/api v0.247.0 // indirect
google.golang.org/genproto v0.0.0-20250804133106-a7a43d27e69b // indirect
google.golang.org/genproto/googleapis/api v0.0.0-20250804133106-a7a43d27e69b // indirect
google.golang.org/genproto/googleapis/rpc v0.0.0-20250811230008-5f3141c8851a // indirect
google.golang.org/grpc v1.74.2 // indirect
golang.org/x/mod v0.31.0 // indirect
golang.org/x/net v0.48.0 // indirect
golang.org/x/sync v0.19.0 // indirect
golang.org/x/sys v0.40.0 // indirect
golang.org/x/text v0.33.0 // indirect
golang.org/x/tools v0.40.0 // indirect
google.golang.org/protobuf v1.36.9 // indirect
gopkg.in/yaml.v2 v2.4.0 // indirect
gorm.io/driver/mysql v1.5.7 // indirect
gorm.io/driver/sqlite v1.6.0 // indirect
gorm.io/driver/sqlserver v1.6.0 // indirect
)

1835
go.sum

File diff suppressed because it is too large Load Diff

View File

@@ -22,5 +22,16 @@ func mountAdminRoutes(r chi.Router, db *gorm.DB, jobs *bg.Jobs, authUser func(ht
archer.Post("/jobs/{id}/cancel", handlers.AdminCancelArcherJob(db))
archer.Get("/queues", handlers.AdminListArcherQueues(db))
})
admin.Route("/actions", func(action chi.Router) {
action.Use(authUser)
action.Use(httpmiddleware.RequirePlatformAdmin())
action.Get("/", handlers.ListActions(db))
action.Post("/", handlers.CreateAction(db))
action.Get("/{actionID}", handlers.GetAction(db))
action.Patch("/{actionID}", handlers.UpdateAction(db))
action.Delete("/{actionID}", handlers.DeleteAction(db))
})
})
}

View File

@@ -33,7 +33,7 @@ func mountAPIRoutes(r chi.Router, db *gorm.DB, jobs *bg.Jobs) {
mountNodePoolRoutes(v1, db, authOrg)
mountDNSRoutes(v1, db, authOrg)
mountLoadBalancerRoutes(v1, db, authOrg)
mountClusterRoutes(v1, db, authOrg)
mountClusterRoutes(v1, db, jobs, authOrg)
})
})
}

View File

@@ -3,12 +3,13 @@ package api
import (
"net/http"
"github.com/glueops/autoglue/internal/bg"
"github.com/glueops/autoglue/internal/handlers"
"github.com/go-chi/chi/v5"
"gorm.io/gorm"
)
func mountClusterRoutes(r chi.Router, db *gorm.DB, authOrg func(http.Handler) http.Handler) {
func mountClusterRoutes(r chi.Router, db *gorm.DB, jobs *bg.Jobs, authOrg func(http.Handler) http.Handler) {
r.Route("/clusters", func(c chi.Router) {
c.Use(authOrg)
c.Get("/", handlers.ListClusters(db))
@@ -36,6 +37,10 @@ func mountClusterRoutes(r chi.Router, db *gorm.DB, authOrg func(http.Handler) ht
c.Delete("/{clusterID}/kubeconfig", handlers.ClearClusterKubeconfig(db))
c.Post("/{clusterID}/node-pools", handlers.AttachNodePool(db))
c.Delete("/{clusterID}/node-pools/{nodePoolID}", handlers.DeleteNodePool(db))
c.Delete("/{clusterID}/node-pools/{nodePoolID}", handlers.DetachNodePool(db))
c.Get("/{clusterID}/runs", handlers.ListClusterRuns(db))
c.Get("/{clusterID}/runs/{runID}", handlers.GetClusterRun(db))
c.Post("/{clusterID}/actions/{actionID}/runs", handlers.RunClusterAction(db, jobs))
})
}

View File

@@ -20,6 +20,7 @@ func mountDNSRoutes(r chi.Router, db *gorm.DB, authOrg func(http.Handler) http.H
d.Get("/domains/{domain_id}/records", handlers.ListRecordSets(db))
d.Post("/domains/{domain_id}/records", handlers.CreateRecordSet(db))
d.Get("/records/{id}", handlers.GetRecordSet(db))
d.Patch("/records/{id}", handlers.UpdateRecordSet(db))
d.Delete("/records/{id}", handlers.DeleteRecordSet(db))
})

View File

@@ -37,7 +37,7 @@ func NewRouter(db *gorm.DB, jobs *bg.Jobs, studio http.Handler) http.Handler {
r.Use(middleware.Recoverer)
r.Use(SecurityHeaders)
r.Use(requestBodyLimit(10 << 20))
r.Use(httprate.LimitByIP(100, 1*time.Minute))
r.Use(httprate.LimitByIP(1000, 1*time.Minute))
r.Use(middleware.StripSlashes)
allowed := getAllowedOrigins()

View File

@@ -44,6 +44,9 @@ func NewRuntime() *Runtime {
&models.RecordSet{},
&models.LoadBalancer{},
&models.Cluster{},
&models.Action{},
&models.Cluster{},
&models.ClusterRun{},
)
if err != nil {

View File

@@ -107,6 +107,42 @@ func NewJobs(gdb *gorm.DB, dbUrl string) (*Jobs, error) {
archer.WithInstances(1),
archer.WithTimeout(2*time.Minute),
)
/*
c.Register(
"prepare_cluster",
ClusterPrepareWorker(gdb, jobs),
archer.WithInstances(1),
archer.WithTimeout(2*time.Minute),
)
c.Register(
"cluster_setup",
ClusterSetupWorker(gdb, jobs),
archer.WithInstances(1),
archer.WithTimeout(2*time.Minute),
)
c.Register(
"cluster_bootstrap",
ClusterBootstrapWorker(gdb, jobs),
archer.WithInstances(1),
archer.WithTimeout(60*time.Minute),
)
*/
c.Register(
"org_key_sweeper",
OrgKeySweeperWorker(gdb, jobs),
archer.WithInstances(1),
archer.WithTimeout(5*time.Minute),
)
c.Register(
"cluster_action",
ClusterActionWorker(gdb),
archer.WithInstances(1),
)
return jobs, nil
}

View File

@@ -0,0 +1,195 @@
package bg
import (
"context"
"encoding/json"
"fmt"
"time"
"github.com/dyaksa/archer"
"github.com/dyaksa/archer/job"
"github.com/glueops/autoglue/internal/mapper"
"github.com/glueops/autoglue/internal/models"
"github.com/glueops/autoglue/internal/utils"
"github.com/google/uuid"
"github.com/rs/zerolog/log"
"gorm.io/gorm"
)
type ClusterActionArgs struct {
OrgID uuid.UUID `json:"org_id"`
ClusterID uuid.UUID `json:"cluster_id"`
Action string `json:"action"`
MakeTarget string `json:"make_target"`
}
type ClusterActionResult struct {
Status string `json:"status"`
Action string `json:"action"`
ClusterID string `json:"cluster_id"`
ElapsedMs int `json:"elapsed_ms"`
}
func ClusterActionWorker(db *gorm.DB) archer.WorkerFn {
return func(ctx context.Context, j job.Job) (any, error) {
start := time.Now()
var args ClusterActionArgs
_ = j.ParseArguments(&args)
runID, _ := uuid.Parse(j.ID)
updateRun := func(status string, errMsg string) {
updates := map[string]any{
"status": status,
"error": errMsg,
}
if status == "succeeded" || status == "failed" {
updates["finished_at"] = time.Now().UTC().Format(time.RFC3339)
}
db.Model(&models.ClusterRun{}).Where("id = ?", runID).Updates(updates)
}
updateRun("running", "")
logger := log.With().
Str("job", j.ID).
Str("cluster_id", args.ClusterID.String()).
Str("action", args.Action).
Logger()
var c models.Cluster
if err := db.
Preload("BastionServer.SshKey").
Preload("CaptainDomain").
Preload("ControlPlaneRecordSet").
Preload("AppsLoadBalancer").
Preload("GlueOpsLoadBalancer").
Preload("NodePools").
Preload("NodePools.Labels").
Preload("NodePools.Annotations").
Preload("NodePools.Taints").
Preload("NodePools.Servers.SshKey").
Where("id = ? AND organization_id = ?", args.ClusterID, args.OrgID).
First(&c).Error; err != nil {
updateRun("failed", fmt.Errorf("load cluster: %w", err).Error())
return nil, fmt.Errorf("load cluster: %w", err)
}
// ---- Step 1: Prepare (mostly lifted from ClusterPrepareWorker)
if err := setClusterStatus(db, c.ID, clusterStatusBootstrapping, ""); err != nil {
updateRun("failed", err.Error())
return nil, fmt.Errorf("mark bootstrapping: %w", err)
}
c.Status = clusterStatusBootstrapping
if err := validateClusterForPrepare(&c); err != nil {
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
updateRun("failed", err.Error())
return nil, fmt.Errorf("validate: %w", err)
}
allServers := flattenClusterServers(&c)
keyPayloads, sshConfig, err := buildSSHAssetsForCluster(db, &c, allServers)
if err != nil {
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
updateRun("failed", err.Error())
return nil, fmt.Errorf("build ssh assets: %w", err)
}
dtoCluster := mapper.ClusterToDTO(c)
if c.EncryptedKubeconfig != "" && c.KubeIV != "" && c.KubeTag != "" {
kubeconfig, err := utils.DecryptForOrg(
c.OrganizationID,
c.EncryptedKubeconfig,
c.KubeIV,
c.KubeTag,
db,
)
if err != nil {
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
return nil, fmt.Errorf("decrypt kubeconfig: %w", err)
}
dtoCluster.Kubeconfig = &kubeconfig
}
orgKey, orgSecret, err := findOrCreateClusterAutomationKey(db, c.OrganizationID, c.ID, 24*time.Hour)
if err != nil {
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
updateRun("failed", err.Error())
return nil, fmt.Errorf("org key: %w", err)
}
dtoCluster.OrgKey = &orgKey
dtoCluster.OrgSecret = &orgSecret
payloadJSON, err := json.MarshalIndent(dtoCluster, "", " ")
if err != nil {
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
updateRun("failed", err.Error())
return nil, fmt.Errorf("marshal payload: %w", err)
}
{
runCtx, cancel := context.WithTimeout(ctx, 8*time.Minute)
err := pushAssetsToBastion(runCtx, db, &c, sshConfig, keyPayloads, payloadJSON)
cancel()
if err != nil {
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
updateRun("failed", err.Error())
return nil, fmt.Errorf("push assets: %w", err)
}
}
if err := setClusterStatus(db, c.ID, clusterStatusPending, ""); err != nil {
updateRun("failed", err.Error())
return nil, fmt.Errorf("mark pending: %w", err)
}
c.Status = clusterStatusPending
// ---- Step 2: Setup (ping-servers)
{
runCtx, cancel := context.WithTimeout(ctx, 30*time.Minute)
out, err := runMakeOnBastion(runCtx, db, &c, "ping-servers")
cancel()
if err != nil {
logger.Error().Err(err).Str("output", out).Msg("ping-servers failed")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, fmt.Sprintf("make ping-servers: %v", err))
updateRun("failed", err.Error())
return nil, fmt.Errorf("ping-servers: %w", err)
}
}
if err := setClusterStatus(db, c.ID, clusterStatusProvisioning, ""); err != nil {
updateRun("failed", err.Error())
return nil, fmt.Errorf("mark provisioning: %w", err)
}
c.Status = clusterStatusProvisioning
// ---- Step 3: Bootstrap (parameterized target)
{
runCtx, cancel := context.WithTimeout(ctx, 60*time.Minute)
out, err := runMakeOnBastion(runCtx, db, &c, args.MakeTarget)
cancel()
if err != nil {
logger.Error().Err(err).Str("output", out).Msg("bootstrap target failed")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, fmt.Sprintf("make %s: %v", args.MakeTarget, err))
updateRun("failed", err.Error())
return nil, fmt.Errorf("make %s: %w", args.MakeTarget, err)
}
}
if err := setClusterStatus(db, c.ID, clusterStatusReady, ""); err != nil {
updateRun("failed", err.Error())
return nil, fmt.Errorf("mark ready: %w", err)
}
updateRun("succeeded", "")
return ClusterActionResult{
Status: "ok",
Action: args.Action,
ClusterID: c.ID.String(),
ElapsedMs: int(time.Since(start).Milliseconds()),
}, nil
}
}

View File

@@ -0,0 +1,121 @@
package bg
import (
"context"
"fmt"
"time"
"github.com/dyaksa/archer"
"github.com/dyaksa/archer/job"
"github.com/glueops/autoglue/internal/models"
"github.com/google/uuid"
"github.com/rs/zerolog/log"
"gorm.io/gorm"
)
type ClusterBootstrapArgs struct {
IntervalS int `json:"interval_seconds,omitempty"`
}
type ClusterBootstrapResult struct {
Status string `json:"status"`
Processed int `json:"processed"`
Ready int `json:"ready"`
Failed int `json:"failed"`
ElapsedMs int `json:"elapsed_ms"`
FailedIDs []uuid.UUID `json:"failed_cluster_ids"`
}
func ClusterBootstrapWorker(db *gorm.DB, jobs *Jobs) archer.WorkerFn {
return func(ctx context.Context, j job.Job) (any, error) {
args := ClusterBootstrapArgs{IntervalS: 120}
jobID := j.ID
start := time.Now()
_ = j.ParseArguments(&args)
if args.IntervalS <= 0 {
args.IntervalS = 120
}
var clusters []models.Cluster
if err := db.
Preload("BastionServer.SshKey").
Where("status = ?", clusterStatusProvisioning).
Find(&clusters).Error; err != nil {
log.Error().Err(err).Msg("[cluster_bootstrap] query clusters failed")
return nil, err
}
proc, ready, failCount := 0, 0, 0
var failedIDs []uuid.UUID
perClusterTimeout := 60 * time.Minute
for i := range clusters {
c := &clusters[i]
proc++
if c.BastionServer.ID == uuid.Nil || c.BastionServer.Status != "ready" {
continue
}
logger := log.With().
Str("job", jobID).
Str("cluster_id", c.ID.String()).
Str("cluster_name", c.Name).
Logger()
logger.Info().Msg("[cluster_bootstrap] running make bootstrap")
runCtx, cancel := context.WithTimeout(ctx, perClusterTimeout)
out, err := runMakeOnBastion(runCtx, db, c, "setup")
cancel()
if err != nil {
failCount++
failedIDs = append(failedIDs, c.ID)
logger.Error().Err(err).Str("output", out).Msg("[cluster_bootstrap] make setup failed")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, fmt.Sprintf("make setup: %v", err))
continue
}
// you can choose a different terminal status here if you like
if err := setClusterStatus(db, c.ID, clusterStatusReady, ""); err != nil {
failCount++
failedIDs = append(failedIDs, c.ID)
logger.Error().Err(err).Msg("[cluster_bootstrap] failed to mark cluster ready")
continue
}
ready++
logger.Info().Msg("[cluster_bootstrap] cluster marked ready")
}
res := ClusterBootstrapResult{
Status: "ok",
Processed: proc,
Ready: ready,
Failed: failCount,
ElapsedMs: int(time.Since(start).Milliseconds()),
FailedIDs: failedIDs,
}
log.Info().
Int("processed", proc).
Int("ready", ready).
Int("failed", failCount).
Msg("[cluster_bootstrap] reconcile tick ok")
// self-reschedule
next := time.Now().Add(time.Duration(args.IntervalS) * time.Second)
_, _ = jobs.Enqueue(
ctx,
uuid.NewString(),
"cluster_bootstrap",
args,
archer.WithScheduleTime(next),
archer.WithMaxRetries(1),
)
return res, nil
}
}

View File

@@ -0,0 +1,120 @@
package bg
import (
"context"
"fmt"
"time"
"github.com/dyaksa/archer"
"github.com/dyaksa/archer/job"
"github.com/glueops/autoglue/internal/models"
"github.com/google/uuid"
"github.com/rs/zerolog/log"
"gorm.io/gorm"
)
type ClusterSetupArgs struct {
IntervalS int `json:"interval_seconds,omitempty"`
}
type ClusterSetupResult struct {
Status string `json:"status"`
Processed int `json:"processed"`
Provisioning int `json:"provisioning"`
Failed int `json:"failed"`
ElapsedMs int `json:"elapsed_ms"`
FailedCluster []uuid.UUID `json:"failed_cluster_ids"`
}
func ClusterSetupWorker(db *gorm.DB, jobs *Jobs) archer.WorkerFn {
return func(ctx context.Context, j job.Job) (any, error) {
args := ClusterSetupArgs{IntervalS: 120}
jobID := j.ID
start := time.Now()
_ = j.ParseArguments(&args)
if args.IntervalS <= 0 {
args.IntervalS = 120
}
var clusters []models.Cluster
if err := db.
Preload("BastionServer.SshKey").
Where("status = ?", clusterStatusPending).
Find(&clusters).Error; err != nil {
log.Error().Err(err).Msg("[cluster_setup] query clusters failed")
return nil, err
}
proc, prov, failCount := 0, 0, 0
var failedIDs []uuid.UUID
perClusterTimeout := 30 * time.Minute
for i := range clusters {
c := &clusters[i]
proc++
if c.BastionServer.ID == uuid.Nil || c.BastionServer.Status != "ready" {
continue
}
logger := log.With().
Str("job", jobID).
Str("cluster_id", c.ID.String()).
Str("cluster_name", c.Name).
Logger()
logger.Info().Msg("[cluster_setup] running make setup")
runCtx, cancel := context.WithTimeout(ctx, perClusterTimeout)
out, err := runMakeOnBastion(runCtx, db, c, "ping-servers")
cancel()
if err != nil {
failCount++
failedIDs = append(failedIDs, c.ID)
logger.Error().Err(err).Str("output", out).Msg("[cluster_setup] make ping-servers failed")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, fmt.Sprintf("make ping-servers: %v", err))
continue
}
if err := setClusterStatus(db, c.ID, clusterStatusProvisioning, ""); err != nil {
failCount++
failedIDs = append(failedIDs, c.ID)
logger.Error().Err(err).Msg("[cluster_setup] failed to mark cluster provisioning")
continue
}
prov++
logger.Info().Msg("[cluster_setup] cluster moved to provisioning")
}
res := ClusterSetupResult{
Status: "ok",
Processed: proc,
Provisioning: prov,
Failed: failCount,
ElapsedMs: int(time.Since(start).Milliseconds()),
FailedCluster: failedIDs,
}
log.Info().
Int("processed", proc).
Int("provisioning", prov).
Int("failed", failCount).
Msg("[cluster_setup] reconcile tick ok")
// self-reschedule
next := time.Now().Add(time.Duration(args.IntervalS) * time.Second)
_, _ = jobs.Enqueue(
ctx,
uuid.NewString(),
"cluster_setup",
args,
archer.WithScheduleTime(next),
archer.WithMaxRetries(1),
)
return res, nil
}
}

View File

@@ -15,6 +15,7 @@ import (
"github.com/glueops/autoglue/internal/models"
"github.com/glueops/autoglue/internal/utils"
"github.com/google/uuid"
"github.com/rs/zerolog"
"github.com/rs/zerolog/log"
"gorm.io/gorm"
@@ -23,6 +24,8 @@ import (
"github.com/aws/aws-sdk-go-v2/credentials"
r53 "github.com/aws/aws-sdk-go-v2/service/route53"
r53types "github.com/aws/aws-sdk-go-v2/service/route53/types"
"github.com/aws/smithy-go"
smithyhttp "github.com/aws/smithy-go/transport/http"
)
/************* args & small DTOs *************/
@@ -47,6 +50,9 @@ const externalDNSPoisonOwner = "autoglue-lock"
// ExternalDNS poison content fake owner so real external-dns skips it.
const externalDNSPoisonValue = "heritage=external-dns,external-dns/owner=" + externalDNSPoisonOwner + ",external-dns/resource=manual/autoglue"
// Default TTL for non-alias records (alias not supported in this reconciler)
const defaultRecordTTLSeconds int64 = 300
/************* entrypoint worker *************/
func DNSReconsileWorker(db *gorm.DB, jobs *Jobs) archer.WorkerFn {
@@ -225,7 +231,14 @@ func processPendingRecordsForDomain(ctx context.Context, db *gorm.DB, d *models.
applied := 0
for i := range records {
if err := applyRecord(ctx, db, r53c, d, &records[i]); err != nil {
log.Error().Err(err).Str("rr", records[i].Name).Msg("[dns] apply record failed")
log.Error().
Err(err).
Str("zone_id", d.ZoneID).
Str("domain", d.DomainName).
Str("record_id", records[i].ID.String()).
Str("name", records[i].Name).
Str("type", strings.ToUpper(records[i].Type)).
Msg("[dns] apply record failed")
_ = setRecordFailed(db, &records[i], err)
continue
}
@@ -249,12 +262,24 @@ func applyRecord(ctx context.Context, db *gorm.DB, r53c *r53.Client, d *models.D
mname := markerName(fq)
expected := buildMarkerValue(d.OrganizationID.String(), r.ID.String(), r.Fingerprint)
logCtx := log.With().
Str("zone_id", zoneID).
Str("domain", d.DomainName).
Str("fqdn", fq).
Str("rr_type", rt).
Str("record_id", r.ID.String()).
Str("org_id", d.OrganizationID.String()).
Logger()
start := time.Now()
// ---- ExternalDNS preflight ----
extOwned, err := hasExternalDNSOwnership(ctx, r53c, zoneID, fq, rt)
if err != nil {
return fmt.Errorf("external_dns_lookup: %w", err)
}
if extOwned {
logCtx.Warn().Msg("[dns] ownership conflict: external-dns claims this record")
r.Owner = "external"
_ = db.Save(r).Error
return fmt.Errorf("ownership_conflict: external-dns claims %s; refusing to modify", strings.TrimSuffix(fq, "."))
@@ -265,6 +290,7 @@ func applyRecord(ctx context.Context, db *gorm.DB, r53c *r53.Client, d *models.D
if err != nil {
return fmt.Errorf("marker lookup: %w", err)
}
hasForeignOwner := false
hasOurExact := false
for _, v := range markerVals {
@@ -279,25 +305,26 @@ func applyRecord(ctx context.Context, db *gorm.DB, r53c *r53.Client, d *models.D
hasForeignOwner = true
}
}
logCtx.Debug().
Bool("externaldns_owned", extOwned).
Int("marker_txt_count", len(markerVals)).
Bool("marker_has_our_exact", hasOurExact).
Bool("marker_has_foreign", hasForeignOwner).
Msg("[dns] ownership preflight")
if hasForeignOwner {
logCtx.Warn().Msg("[dns] ownership conflict: foreign _autoglue marker")
r.Owner = "external"
_ = db.Save(r).Error
return fmt.Errorf("ownership_conflict: marker for %s is owned by another controller; refusing to modify", strings.TrimSuffix(fq, "."))
}
// Build RR change (UPSERT)
rrChange := r53types.Change{
Action: r53types.ChangeActionUpsert,
ResourceRecordSet: &r53types.ResourceRecordSet{
Name: aws.String(fq),
Type: r53types.RRType(rt),
},
}
// Decode user values
var userVals []string
if len(r.Values) > 0 {
if err := jsonUnmarshalStrict([]byte(r.Values), &userVals); err != nil {
rawVals := strings.TrimSpace(string(r.Values))
if rawVals != "" && rawVals != "null" {
if err := jsonUnmarshalStrict([]byte(rawVals), &userVals); err != nil {
return fmt.Errorf("values decode: %w", err)
}
}
@@ -306,15 +333,38 @@ func applyRecord(ctx context.Context, db *gorm.DB, r53c *r53.Client, d *models.D
recs := make([]r53types.ResourceRecord, 0, len(userVals))
for _, v := range userVals {
v = strings.TrimSpace(v)
if v == "" {
continue
}
if rt == "TXT" && !(strings.HasPrefix(v, `"`) && strings.HasSuffix(v, `"`)) {
v = strconv.Quote(v)
}
recs = append(recs, r53types.ResourceRecord{Value: aws.String(v)})
}
rrChange.ResourceRecordSet.ResourceRecords = recs
if r.TTL != nil {
ttl := int64(*r.TTL)
rrChange.ResourceRecordSet.TTL = aws.Int64(ttl)
// Alias is NOT supported - enforce at least one value for all record types we manage
if len(recs) == 0 {
logCtx.Warn().
Str("raw_values", truncateForLog(string(r.Values), 240)).
Int("decoded_value_count", len(userVals)).
Msg("[dns] invalid record: no values (alias not supported)")
return fmt.Errorf("invalid_record: %s %s requires at least one value (alias not supported)", strings.TrimSuffix(fq, "."), rt)
}
ttl := defaultRecordTTLSeconds
if r.TTL != nil && *r.TTL > 0 {
ttl = int64(*r.TTL)
}
// Build RR change (UPSERT)
rrChange := r53types.Change{
Action: r53types.ChangeActionUpsert,
ResourceRecordSet: &r53types.ResourceRecordSet{
Name: aws.String(fq),
Type: r53types.RRType(rt),
TTL: aws.Int64(ttl),
ResourceRecords: recs,
},
}
// Build marker TXT change (UPSERT)
@@ -323,7 +373,7 @@ func applyRecord(ctx context.Context, db *gorm.DB, r53c *r53.Client, d *models.D
ResourceRecordSet: &r53types.ResourceRecordSet{
Name: aws.String(mname),
Type: r53types.RRTypeTxt,
TTL: aws.Int64(300),
TTL: aws.Int64(defaultRecordTTLSeconds),
ResourceRecords: []r53types.ResourceRecord{
{Value: aws.String(strconv.Quote(expected))},
},
@@ -337,14 +387,26 @@ func applyRecord(ctx context.Context, db *gorm.DB, r53c *r53.Client, d *models.D
changes := []r53types.Change{rrChange, markerChange}
changes = append(changes, poisonChanges...)
// Log what we are about to send
logCtx.Debug().
Interface("route53_change_batch", toLogChangeBatch(zoneID, changes)).
Msg("[dns] route53 request preview")
_, err = r53c.ChangeResourceRecordSets(ctx, &r53.ChangeResourceRecordSetsInput{
HostedZoneId: aws.String(zoneID),
ChangeBatch: &r53types.ChangeBatch{Changes: changes},
})
if err != nil {
logAWSError(logCtx, err)
logCtx.Info().Dur("elapsed", time.Since(start)).Msg("[dns] apply failed")
return err
}
logCtx.Info().
Dur("elapsed", time.Since(start)).
Int("change_count", len(changes)).
Msg("[dns] apply ok")
// Success → mark ready & ownership
r.Status = "ready"
r.LastError = ""
@@ -352,6 +414,7 @@ func applyRecord(ctx context.Context, db *gorm.DB, r53c *r53.Client, d *models.D
if err := db.Save(r).Error; err != nil {
return err
}
_ = hasOurExact // could be used to skip marker write in future
return nil
}
@@ -568,7 +631,7 @@ func buildExternalDNSPoisonTXTChanges(fqdn, rrType string) []r53types.Change {
ResourceRecordSet: &r53types.ResourceRecordSet{
Name: aws.String(n),
Type: r53types.RRTypeTxt,
TTL: aws.Int64(300),
TTL: aws.Int64(defaultRecordTTLSeconds),
ResourceRecords: []r53types.ResourceRecord{
{Value: aws.String(val)},
},
@@ -595,3 +658,125 @@ func jsonUnmarshalStrict(b []byte, dst any) error {
}
return json.Unmarshal(b, dst)
}
/************* logging DTOs & helpers *************/
type logRR struct {
Value string `json:"value"`
}
type logRRSet struct {
Action string `json:"action"`
Name string `json:"name"`
Type string `json:"type"`
TTL *int64 `json:"ttl,omitempty"`
Records []logRR `json:"records,omitempty"`
RecordCount int `json:"record_count"`
HasAliasTarget bool `json:"has_alias_target"`
SetIdentifier *string `json:"set_identifier,omitempty"`
}
type logChangeBatch struct {
HostedZoneID string `json:"hosted_zone_id"`
ChangeCount int `json:"change_count"`
Changes []logRRSet `json:"changes"`
}
func truncateForLog(s string, max int) string {
s = strings.TrimSpace(s)
if max <= 0 || len(s) <= max {
return s
}
return s[:max] + "…"
}
func toLogChangeBatch(zoneID string, changes []r53types.Change) logChangeBatch {
out := logChangeBatch{
HostedZoneID: zoneID,
ChangeCount: len(changes),
Changes: make([]logRRSet, 0, len(changes)),
}
for _, ch := range changes {
if ch.ResourceRecordSet == nil {
continue
}
rrs := ch.ResourceRecordSet
lc := logRRSet{
Action: string(ch.Action),
Name: aws.ToString(rrs.Name),
Type: string(rrs.Type),
TTL: rrs.TTL,
HasAliasTarget: rrs.AliasTarget != nil,
SetIdentifier: rrs.SetIdentifier,
RecordCount: len(rrs.ResourceRecords),
Records: make([]logRR, 0, min(len(rrs.ResourceRecords), 5)),
}
// Log up to first 5 values (truncate each) to avoid log bloat / secrets
for i, rr := range rrs.ResourceRecords {
if i >= 5 {
break
}
lc.Records = append(lc.Records, logRR{Value: truncateForLog(aws.ToString(rr.Value), 160)})
}
out.Changes = append(out.Changes, lc)
}
return out
}
func min(a, b int) int {
if a < b {
return a
}
return b
}
// logAWSError extracts useful smithy/HTTP metadata (status code + request id + api code) into logs.
// logAWSError extracts useful smithy/HTTP metadata (status code + request id + api code) into logs.
func logAWSError(l zerolog.Logger, err error) {
// Add operation context if present
var opErr *smithy.OperationError
if errors.As(err, &opErr) {
l = l.With().
Str("aws_service", opErr.ServiceID).
Str("aws_operation", opErr.OperationName).
Logger()
err = opErr.Unwrap()
}
// HTTP status + request id (smithy-go transport/http)
var re *smithyhttp.ResponseError
if errors.As(err, &re) {
status := re.HTTPStatusCode()
reqID := ""
if resp := re.HTTPResponse(); resp != nil && resp.Header != nil {
reqID = resp.Header.Get("x-amzn-RequestId")
if reqID == "" {
reqID = resp.Header.Get("x-amz-request-id")
}
}
ev := l.Error().Int("http_status", status).Err(err)
if reqID != "" {
ev = ev.Str("aws_request_id", reqID)
}
ev.Msg("[dns] aws route53 call failed")
return
}
// API error code/message (best-effort)
var apiErr smithy.APIError
if errors.As(err, &apiErr) {
l.Error().
Str("aws_error_code", apiErr.ErrorCode()).
Str("aws_error_message", apiErr.ErrorMessage()).
Err(err).
Msg("[dns] aws route53 api error")
return
}
l.Error().Err(err).Msg("[dns] aws route53 error")
}

View File

@@ -0,0 +1,95 @@
package bg
import (
"context"
"time"
"github.com/dyaksa/archer"
"github.com/dyaksa/archer/job"
"github.com/glueops/autoglue/internal/models"
"github.com/google/uuid"
"github.com/rs/zerolog/log"
"gorm.io/gorm"
)
type OrgKeySweeperArgs struct {
IntervalS int `json:"interval_seconds,omitempty"`
RetentionDays int `json:"retention_days,omitempty"`
}
type OrgKeySweeperResult struct {
Status string `json:"status"`
MarkedRevoked int `json:"marked_revoked"`
DeletedEphemeral int `json:"deleted_ephemeral"`
ElapsedMs int `json:"elapsed_ms"`
}
func OrgKeySweeperWorker(db *gorm.DB, jobs *Jobs) archer.WorkerFn {
return func(ctx context.Context, j job.Job) (any, error) {
args := OrgKeySweeperArgs{
IntervalS: 3600,
RetentionDays: 10,
}
start := time.Now()
_ = j.ParseArguments(&args)
if args.IntervalS <= 0 {
args.IntervalS = 3600
}
if args.RetentionDays <= 0 {
args.RetentionDays = 10
}
now := time.Now()
// 1) Mark expired keys as revoked
res1 := db.Model(&models.APIKey{}).
Where("expires_at IS NOT NULL AND expires_at <= ? AND revoked = false", now).
Updates(map[string]any{
"revoked": true,
"updated_at": now,
})
if res1.Error != nil {
log.Error().Err(res1.Error).Msg("[org_key_sweeper] mark expired revoked failed")
return nil, res1.Error
}
markedRevoked := int(res1.RowsAffected)
// 2) Hard-delete ephemeral keys that are revoked and older than retention
cutoff := now.Add(-time.Duration(args.RetentionDays) * 24 * time.Hour)
res2 := db.
Where("is_ephemeral = ? AND revoked = ? AND updated_at <= ?", true, true, cutoff).
Delete(&models.APIKey{})
if res2.Error != nil {
log.Error().Err(res2.Error).Msg("[org_key_sweeper] delete revoked ephemeral keys failed")
return nil, res2.Error
}
deletedEphemeral := int(res2.RowsAffected)
out := OrgKeySweeperResult{
Status: "ok",
MarkedRevoked: markedRevoked,
DeletedEphemeral: deletedEphemeral,
ElapsedMs: int(time.Since(start).Milliseconds()),
}
log.Info().
Int("marked_revoked", markedRevoked).
Int("deleted_ephemeral", deletedEphemeral).
Msg("[org_key_sweeper] cleanup tick ok")
// Re-enqueue the sweeper
next := time.Now().Add(time.Duration(args.IntervalS) * time.Second)
_, _ = jobs.Enqueue(
ctx,
uuid.NewString(),
"org_key_sweeper",
args,
archer.WithScheduleTime(next),
archer.WithMaxRetries(1),
)
return out, nil
}
}

View File

@@ -0,0 +1,658 @@
package bg
import (
"bytes"
"context"
"crypto/rand"
"encoding/base64"
"encoding/json"
"fmt"
"net"
"strings"
"time"
"github.com/dyaksa/archer"
"github.com/dyaksa/archer/job"
"github.com/glueops/autoglue/internal/auth"
"github.com/glueops/autoglue/internal/mapper"
"github.com/glueops/autoglue/internal/models"
"github.com/glueops/autoglue/internal/utils"
"github.com/google/uuid"
"github.com/rs/zerolog/log"
"golang.org/x/crypto/ssh"
"gorm.io/gorm"
)
type ClusterPrepareArgs struct {
IntervalS int `json:"interval_seconds,omitempty"`
}
type ClusterPrepareFailure struct {
ClusterID uuid.UUID `json:"cluster_id"`
Step string `json:"step"`
Reason string `json:"reason"`
}
type ClusterPrepareResult struct {
Status string `json:"status"`
Processed int `json:"processed"`
MarkedPending int `json:"marked_pending"`
Failed int `json:"failed"`
ElapsedMs int `json:"elapsed_ms"`
FailedIDs []uuid.UUID `json:"failed_cluster_ids"`
Failures []ClusterPrepareFailure `json:"failures"`
}
// Alias the status constants from models to avoid string drift.
const (
clusterStatusPrePending = models.ClusterStatusPrePending
clusterStatusPending = models.ClusterStatusPending
clusterStatusProvisioning = models.ClusterStatusProvisioning
clusterStatusReady = models.ClusterStatusReady
clusterStatusFailed = models.ClusterStatusFailed
clusterStatusBootstrapping = models.ClusterStatusBootstrapping
)
func ClusterPrepareWorker(db *gorm.DB, jobs *Jobs) archer.WorkerFn {
return func(ctx context.Context, j job.Job) (any, error) {
args := ClusterPrepareArgs{IntervalS: 120}
jobID := j.ID
start := time.Now()
_ = j.ParseArguments(&args)
if args.IntervalS <= 0 {
args.IntervalS = 120
}
// Load all clusters that are pre_pending; well filter for bastion.ready in memory.
var clusters []models.Cluster
if err := db.
Preload("BastionServer.SshKey").
Preload("CaptainDomain").
Preload("ControlPlaneRecordSet").
Preload("AppsLoadBalancer").
Preload("GlueOpsLoadBalancer").
Preload("NodePools").
Preload("NodePools.Labels").
Preload("NodePools.Annotations").
Preload("NodePools.Taints").
Preload("NodePools.Servers.SshKey").
Where("status = ?", clusterStatusPrePending).
Find(&clusters).Error; err != nil {
log.Error().Err(err).Msg("[cluster_prepare] query clusters failed")
return nil, err
}
proc, ok, fail := 0, 0, 0
var failedIDs []uuid.UUID
var failures []ClusterPrepareFailure
perClusterTimeout := 8 * time.Minute
for i := range clusters {
c := &clusters[i]
proc++
// bastion must exist and be ready
if c.BastionServer == nil || c.BastionServerID == nil || *c.BastionServerID == uuid.Nil || c.BastionServer.Status != "ready" {
continue
}
if err := setClusterStatus(db, c.ID, clusterStatusBootstrapping, ""); err != nil {
log.Error().Err(err).Msg("[cluster_prepare] failed to mark cluster bootstrapping")
continue
}
c.Status = clusterStatusBootstrapping
clusterLog := log.With().
Str("job", jobID).
Str("cluster_id", c.ID.String()).
Str("cluster_name", c.Name).
Logger()
clusterLog.Info().Msg("[cluster_prepare] starting")
if err := validateClusterForPrepare(c); err != nil {
fail++
failedIDs = append(failedIDs, c.ID)
failures = append(failures, ClusterPrepareFailure{
ClusterID: c.ID,
Step: "validate",
Reason: err.Error(),
})
clusterLog.Error().Err(err).Msg("[cluster_prepare] validation failed")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
continue
}
allServers := flattenClusterServers(c)
keyPayloads, sshConfig, err := buildSSHAssetsForCluster(db, c, allServers)
if err != nil {
fail++
failedIDs = append(failedIDs, c.ID)
failures = append(failures, ClusterPrepareFailure{
ClusterID: c.ID,
Step: "build_ssh_assets",
Reason: err.Error(),
})
clusterLog.Error().Err(err).Msg("[cluster_prepare] build ssh assets failed")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
continue
}
dtoCluster := mapper.ClusterToDTO(*c)
if c.EncryptedKubeconfig != "" && c.KubeIV != "" && c.KubeTag != "" {
kubeconfig, err := utils.DecryptForOrg(
c.OrganizationID,
c.EncryptedKubeconfig,
c.KubeIV,
c.KubeTag,
db,
)
if err != nil {
fail++
failedIDs = append(failedIDs, c.ID)
failures = append(failures, ClusterPrepareFailure{
ClusterID: c.ID,
Step: "decrypt_kubeconfig",
Reason: err.Error(),
})
clusterLog.Error().Err(err).Msg("[cluster_prepare] decrypt kubeconfig failed")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
continue
}
dtoCluster.Kubeconfig = &kubeconfig
}
orgKey, orgSecret, err := findOrCreateClusterAutomationKey(
db,
c.OrganizationID,
c.ID,
24*time.Hour,
)
if err != nil {
fail++
failedIDs = append(failedIDs, c.ID)
failures = append(failures, ClusterPrepareFailure{
ClusterID: c.ID,
Step: "create_org_key",
Reason: err.Error(),
})
clusterLog.Error().Err(err).Msg("[cluster_prepare] create org key for payload failed")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
continue
}
dtoCluster.OrgKey = &orgKey
dtoCluster.OrgSecret = &orgSecret
payloadJSON, err := json.MarshalIndent(dtoCluster, "", " ")
if err != nil {
fail++
failedIDs = append(failedIDs, c.ID)
failures = append(failures, ClusterPrepareFailure{
ClusterID: c.ID,
Step: "marshal_payload",
Reason: err.Error(),
})
clusterLog.Error().Err(err).Msg("[cluster_prepare] json marshal failed")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
continue
}
runCtx, cancel := context.WithTimeout(ctx, perClusterTimeout)
err = pushAssetsToBastion(runCtx, db, c, sshConfig, keyPayloads, payloadJSON)
cancel()
if err != nil {
fail++
failedIDs = append(failedIDs, c.ID)
failures = append(failures, ClusterPrepareFailure{
ClusterID: c.ID,
Step: "ssh_push",
Reason: err.Error(),
})
clusterLog.Error().Err(err).Msg("[cluster_prepare] failed to push assets to bastion")
_ = setClusterStatus(db, c.ID, clusterStatusFailed, err.Error())
continue
}
if err := setClusterStatus(db, c.ID, clusterStatusPending, ""); err != nil {
fail++
failedIDs = append(failedIDs, c.ID)
failures = append(failures, ClusterPrepareFailure{
ClusterID: c.ID,
Step: "set_pending",
Reason: err.Error(),
})
clusterLog.Error().Err(err).Msg("[cluster_prepare] failed to mark cluster pending")
continue
}
ok++
clusterLog.Info().Msg("[cluster_prepare] cluster marked pending")
}
res := ClusterPrepareResult{
Status: "ok",
Processed: proc,
MarkedPending: ok,
Failed: fail,
ElapsedMs: int(time.Since(start).Milliseconds()),
FailedIDs: failedIDs,
Failures: failures,
}
log.Info().
Int("processed", proc).
Int("pending", ok).
Int("failed", fail).
Msg("[cluster_prepare] reconcile tick ok")
next := time.Now().Add(time.Duration(args.IntervalS) * time.Second)
_, _ = jobs.Enqueue(
ctx,
uuid.NewString(),
"prepare_cluster",
args,
archer.WithScheduleTime(next),
archer.WithMaxRetries(1),
)
return res, nil
}
}
// ---------- helpers ----------
func validateClusterForPrepare(c *models.Cluster) error {
if c.BastionServer == nil || c.BastionServerID == nil || *c.BastionServerID == uuid.Nil {
return fmt.Errorf("missing bastion server")
}
if c.BastionServer.Status != "ready" {
return fmt.Errorf("bastion server not ready (status=%s)", c.BastionServer.Status)
}
// CaptainDomain is a value type; presence is via *ID
if c.CaptainDomainID == nil || *c.CaptainDomainID == uuid.Nil {
return fmt.Errorf("missing captain domain for cluster")
}
// ControlPlaneRecordSet is a pointer; presence is via *ID + non-nil struct
if c.ControlPlaneRecordSetID == nil || *c.ControlPlaneRecordSetID == uuid.Nil || c.ControlPlaneRecordSet == nil {
return fmt.Errorf("missing control_plane_record_set for cluster")
}
if len(c.NodePools) == 0 {
return fmt.Errorf("cluster has no node pools")
}
hasServer := false
for i := range c.NodePools {
if len(c.NodePools[i].Servers) > 0 {
hasServer = true
break
}
}
if !hasServer {
return fmt.Errorf("cluster has no servers attached to node pools")
}
return nil
}
func flattenClusterServers(c *models.Cluster) []*models.Server {
var out []*models.Server
for i := range c.NodePools {
for j := range c.NodePools[i].Servers {
s := &c.NodePools[i].Servers[j]
out = append(out, s)
}
}
return out
}
type keyPayload struct {
FileName string
PrivateKeyB64 string
}
// build ssh-config for all servers + decrypt keys.
// ssh-config is intended to live on the bastion and connect via *private* IPs.
func buildSSHAssetsForCluster(db *gorm.DB, c *models.Cluster, servers []*models.Server) (map[uuid.UUID]keyPayload, string, error) {
var sb strings.Builder
keys := make(map[uuid.UUID]keyPayload)
for _, s := range servers {
// Defensive checks
if strings.TrimSpace(s.PrivateIPAddress) == "" {
return nil, "", fmt.Errorf("server %s missing private ip", s.ID)
}
if s.SshKeyID == uuid.Nil {
return nil, "", fmt.Errorf("server %s missing ssh key relation", s.ID)
}
// de-dupe keys: many servers may share the same ssh key
if _, ok := keys[s.SshKeyID]; !ok {
priv, err := utils.DecryptForOrg(
s.OrganizationID,
s.SshKey.EncryptedPrivateKey,
s.SshKey.PrivateIV,
s.SshKey.PrivateTag,
db,
)
if err != nil {
return nil, "", fmt.Errorf("decrypt key for server %s: %w", s.ID, err)
}
fname := fmt.Sprintf("%s.pem", s.SshKeyID.String())
keys[s.SshKeyID] = keyPayload{
FileName: fname,
PrivateKeyB64: base64.StdEncoding.EncodeToString([]byte(priv)),
}
}
// ssh config entry per server
keyFile := keys[s.SshKeyID].FileName
hostAlias := s.Hostname
if hostAlias == "" {
hostAlias = s.ID.String()
}
sb.WriteString(fmt.Sprintf("Host %s\n", hostAlias))
sb.WriteString(fmt.Sprintf(" HostName %s\n", s.PrivateIPAddress))
sb.WriteString(fmt.Sprintf(" User %s\n", s.SSHUser))
sb.WriteString(fmt.Sprintf(" IdentityFile ~/.ssh/autoglue/keys/%s\n", keyFile))
sb.WriteString(" IdentitiesOnly yes\n")
sb.WriteString(" StrictHostKeyChecking accept-new\n\n")
}
return keys, sb.String(), nil
}
func pushAssetsToBastion(
ctx context.Context,
db *gorm.DB,
c *models.Cluster,
sshConfig string,
keyPayloads map[uuid.UUID]keyPayload,
payloadJSON []byte,
) error {
bastion := c.BastionServer
if bastion == nil {
return fmt.Errorf("bastion server is nil")
}
if bastion.PublicIPAddress == nil || strings.TrimSpace(*bastion.PublicIPAddress) == "" {
return fmt.Errorf("bastion server missing public ip")
}
privKey, err := utils.DecryptForOrg(
bastion.OrganizationID,
bastion.SshKey.EncryptedPrivateKey,
bastion.SshKey.PrivateIV,
bastion.SshKey.PrivateTag,
db,
)
if err != nil {
return fmt.Errorf("decrypt bastion key: %w", err)
}
signer, err := ssh.ParsePrivateKey([]byte(privKey))
if err != nil {
return fmt.Errorf("parse bastion private key: %w", err)
}
hkcb := makeDBHostKeyCallback(db, bastion)
config := &ssh.ClientConfig{
User: bastion.SSHUser,
Auth: []ssh.AuthMethod{ssh.PublicKeys(signer)},
HostKeyCallback: hkcb,
Timeout: 30 * time.Second,
}
host := net.JoinHostPort(*bastion.PublicIPAddress, "22")
dialer := &net.Dialer{}
conn, err := dialer.DialContext(ctx, "tcp", host)
if err != nil {
return fmt.Errorf("dial bastion: %w", err)
}
defer conn.Close()
cconn, chans, reqs, err := ssh.NewClientConn(conn, host, config)
if err != nil {
return fmt.Errorf("ssh handshake bastion: %w", err)
}
client := ssh.NewClient(cconn, chans, reqs)
defer client.Close()
sess, err := client.NewSession()
if err != nil {
return fmt.Errorf("ssh session: %w", err)
}
defer sess.Close()
// build one shot script to:
// - mkdir ~/.ssh/autoglue/keys
// - write cluster-specific ssh-config
// - write all private keys
// - write payload.json
clusterDir := fmt.Sprintf("$HOME/autoglue/clusters/%s", c.ID.String())
configPath := fmt.Sprintf("$HOME/.ssh/autoglue/cluster-%s.config", c.ID.String())
var script bytes.Buffer
script.WriteString("set -euo pipefail\n")
script.WriteString("mkdir -p \"$HOME/.ssh/autoglue/keys\"\n")
script.WriteString("mkdir -p " + clusterDir + "\n")
script.WriteString("chmod 700 \"$HOME/.ssh\" || true\n")
// ssh-config
script.WriteString("cat > " + configPath + " <<'EOF_CFG'\n")
script.WriteString(sshConfig)
script.WriteString("EOF_CFG\n")
script.WriteString("chmod 600 " + configPath + "\n")
// keys
for id, kp := range keyPayloads {
tag := "KEY_" + id.String()
target := fmt.Sprintf("$HOME/.ssh/autoglue/keys/%s", kp.FileName)
script.WriteString("cat <<'" + tag + "' | base64 -d > " + target + "\n")
script.WriteString(kp.PrivateKeyB64 + "\n")
script.WriteString(tag + "\n")
script.WriteString("chmod 600 " + target + "\n")
}
// payload.json
payloadPath := clusterDir + "/payload.json"
script.WriteString("cat > " + payloadPath + " <<'EOF_PAYLOAD'\n")
script.Write(payloadJSON)
script.WriteString("\nEOF_PAYLOAD\n")
script.WriteString("chmod 600 " + payloadPath + "\n")
// If you later want to always include cluster configs automatically, you can
// optionally manage ~/.ssh/config here (kept simple for now).
sess.Stdin = strings.NewReader(script.String())
out, runErr := sess.CombinedOutput("bash -s")
if runErr != nil {
return wrapSSHError(runErr, string(out))
}
return nil
}
func setClusterStatus(db *gorm.DB, id uuid.UUID, status, lastError string) error {
updates := map[string]any{
"status": status,
"updated_at": time.Now(),
}
if lastError != "" {
updates["last_error"] = lastError
}
return db.Model(&models.Cluster{}).
Where("id = ?", id).
Updates(updates).Error
}
// runMakeOnBastion runs `make <target>` from the cluster's directory on the bastion.
func runMakeOnBastion(
ctx context.Context,
db *gorm.DB,
c *models.Cluster,
target string,
) (string, error) {
logger := log.With().
Str("cluster_id", c.ID.String()).
Str("cluster_name", c.Name).
Logger()
bastion := c.BastionServer
if bastion == nil {
return "", fmt.Errorf("bastion server is nil")
}
if bastion.PublicIPAddress == nil || strings.TrimSpace(*bastion.PublicIPAddress) == "" {
return "", fmt.Errorf("bastion server missing public ip")
}
privKey, err := utils.DecryptForOrg(
bastion.OrganizationID,
bastion.SshKey.EncryptedPrivateKey,
bastion.SshKey.PrivateIV,
bastion.SshKey.PrivateTag,
db,
)
if err != nil {
return "", fmt.Errorf("decrypt bastion key: %w", err)
}
signer, err := ssh.ParsePrivateKey([]byte(privKey))
if err != nil {
return "", fmt.Errorf("parse bastion private key: %w", err)
}
hkcb := makeDBHostKeyCallback(db, bastion)
config := &ssh.ClientConfig{
User: bastion.SSHUser,
Auth: []ssh.AuthMethod{ssh.PublicKeys(signer)},
HostKeyCallback: hkcb,
Timeout: 30 * time.Second,
}
host := net.JoinHostPort(*bastion.PublicIPAddress, "22")
dialer := &net.Dialer{}
conn, err := dialer.DialContext(ctx, "tcp", host)
if err != nil {
return "", fmt.Errorf("dial bastion: %w", err)
}
defer conn.Close()
cconn, chans, reqs, err := ssh.NewClientConn(conn, host, config)
if err != nil {
return "", fmt.Errorf("ssh handshake bastion: %w", err)
}
client := ssh.NewClient(cconn, chans, reqs)
defer client.Close()
sess, err := client.NewSession()
if err != nil {
return "", fmt.Errorf("ssh session: %w", err)
}
defer sess.Close()
clusterDir := fmt.Sprintf("$HOME/autoglue/clusters/%s", c.ID.String())
sshDir := fmt.Sprintf("$HOME/.ssh")
cmd := fmt.Sprintf("cd %s && docker run -v %s:/root/.ssh -v ./payload.json:/opt/gluekube/platform.json %s:%s make %s", clusterDir, sshDir, c.DockerImage, c.DockerTag, target)
logger.Info().
Str("cmd", cmd).
Msg("[runMakeOnBastion] executing remote command")
out, runErr := sess.CombinedOutput(cmd)
if runErr != nil {
return string(out), wrapSSHError(runErr, string(out))
}
return string(out), nil
}
func randomB64URL(n int) (string, error) {
b := make([]byte, n)
if _, err := rand.Read(b); err != nil {
return "", err
}
return base64.RawURLEncoding.EncodeToString(b), nil
}
func findOrCreateClusterAutomationKey(
db *gorm.DB,
orgID uuid.UUID,
clusterID uuid.UUID,
ttl time.Duration,
) (orgKey string, orgSecret string, err error) {
now := time.Now()
name := fmt.Sprintf("cluster-%s-bastion", clusterID.String())
// 1) Delete any existing ephemeral cluster-bastion key for this org+cluster
if err := db.Where(
"org_id = ? AND scope = ? AND purpose = ? AND cluster_id = ? AND is_ephemeral = ?",
orgID, "org", "cluster_bastion", clusterID, true,
).Delete(&models.APIKey{}).Error; err != nil {
return "", "", fmt.Errorf("delete existing cluster key: %w", err)
}
// 2) Mint a fresh keypair
keySuffix, err := randomB64URL(16)
if err != nil {
return "", "", fmt.Errorf("entropy_error: %w", err)
}
sec, err := randomB64URL(32)
if err != nil {
return "", "", fmt.Errorf("entropy_error: %w", err)
}
orgKey = "org_" + keySuffix
orgSecret = sec
keyHash := auth.SHA256Hex(orgKey)
secretHash, err := auth.HashSecretArgon2id(orgSecret)
if err != nil {
return "", "", fmt.Errorf("hash_error: %w", err)
}
exp := now.Add(ttl)
prefix := orgKey
if len(prefix) > 12 {
prefix = prefix[:12]
}
rec := models.APIKey{
OrgID: &orgID,
Scope: "org",
Purpose: "cluster_bastion",
ClusterID: &clusterID,
IsEphemeral: true,
Name: name,
KeyHash: keyHash,
SecretHash: &secretHash,
ExpiresAt: &exp,
Revoked: false,
Prefix: &prefix,
}
if err := db.Create(&rec).Error; err != nil {
return "", "", fmt.Errorf("db_error: %w", err)
}
return orgKey, orgSecret, nil
}

View File

@@ -0,0 +1,256 @@
package handlers
import (
"encoding/json"
"errors"
"net/http"
"strings"
"github.com/glueops/autoglue/internal/handlers/dto"
"github.com/glueops/autoglue/internal/models"
"github.com/glueops/autoglue/internal/utils"
"github.com/go-chi/chi/v5"
"github.com/google/uuid"
"gorm.io/gorm"
)
// ListActions godoc
//
// @ID ListActions
// @Summary List available actions
// @Description Returns all admin-configured actions.
// @Tags Actions
// @Produce json
// @Success 200 {array} dto.ActionResponse
// @Failure 401 {string} string "Unauthorized"
// @Failure 500 {string} string "db error"
// @Router /admin/actions [get]
// @Security BearerAuth
func ListActions(db *gorm.DB) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
var rows []models.Action
if err := db.Order("label ASC").Find(&rows).Error; err != nil {
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
out := make([]dto.ActionResponse, 0, len(rows))
for _, a := range rows {
out = append(out, actionToDTO(a))
}
utils.WriteJSON(w, http.StatusOK, out)
}
}
// GetAction godoc
//
// @ID GetAction
// @Summary Get a single action by ID
// @Description Returns a single action.
// @Tags Actions
// @Produce json
// @Param actionID path string true "Action ID"
// @Success 200 {object} dto.ActionResponse
// @Failure 400 {string} string "bad request"
// @Failure 401 {string} string "Unauthorized"
// @Failure 404 {string} string "not found"
// @Failure 500 {string} string "db error"
// @Router /admin/actions/{actionID} [get]
// @Security BearerAuth
func GetAction(db *gorm.DB) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
actionID, err := uuid.Parse(chi.URLParam(r, "actionID"))
if err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_action_id", "invalid action id")
return
}
var row models.Action
if err := db.Where("id = ?", actionID).First(&row).Error; err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
utils.WriteError(w, http.StatusNotFound, "not_found", "action not found")
return
}
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
utils.WriteJSON(w, http.StatusOK, actionToDTO(row))
}
}
// CreateAction godoc
//
// @ID CreateAction
// @Summary Create an action
// @Description Creates a new admin-configured action.
// @Tags Actions
// @Accept json
// @Produce json
// @Param body body dto.CreateActionRequest true "payload"
// @Success 201 {object} dto.ActionResponse
// @Failure 400 {string} string "bad request"
// @Failure 401 {string} string "Unauthorized"
// @Failure 500 {string} string "db error"
// @Router /admin/actions [post]
// @Security BearerAuth
func CreateAction(db *gorm.DB) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
var in dto.CreateActionRequest
if err := json.NewDecoder(r.Body).Decode(&in); err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_json", err.Error())
return
}
label := strings.TrimSpace(in.Label)
desc := strings.TrimSpace(in.Description)
target := strings.TrimSpace(in.MakeTarget)
if label == "" {
utils.WriteError(w, http.StatusBadRequest, "validation_error", "label is required")
return
}
if desc == "" {
utils.WriteError(w, http.StatusBadRequest, "validation_error", "description is required")
return
}
if target == "" {
utils.WriteError(w, http.StatusBadRequest, "validation_error", "make_target is required")
return
}
row := models.Action{
Label: label,
Description: desc,
MakeTarget: target,
}
if err := db.Create(&row).Error; err != nil {
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
utils.WriteJSON(w, http.StatusCreated, actionToDTO(row))
}
}
// UpdateAction godoc
//
// @ID UpdateAction
// @Summary Update an action
// @Description Updates an action. Only provided fields are modified.
// @Tags Actions
// @Accept json
// @Produce json
// @Param actionID path string true "Action ID"
// @Param body body dto.UpdateActionRequest true "payload"
// @Success 200 {object} dto.ActionResponse
// @Failure 400 {string} string "bad request"
// @Failure 401 {string} string "Unauthorized"
// @Failure 404 {string} string "not found"
// @Failure 500 {string} string "db error"
// @Router /admin/actions/{actionID} [patch]
// @Security BearerAuth
func UpdateAction(db *gorm.DB) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
actionID, err := uuid.Parse(chi.URLParam(r, "actionID"))
if err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_action_id", "invalid action id")
return
}
var in dto.UpdateActionRequest
if err := json.NewDecoder(r.Body).Decode(&in); err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_json", err.Error())
return
}
var row models.Action
if err := db.Where("id = ?", actionID).First(&row).Error; err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
utils.WriteError(w, http.StatusNotFound, "not_found", "action not found")
return
}
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
if in.Label != nil {
v := strings.TrimSpace(*in.Label)
if v == "" {
utils.WriteError(w, http.StatusBadRequest, "validation_error", "label cannot be empty")
return
}
row.Label = v
}
if in.Description != nil {
v := strings.TrimSpace(*in.Description)
if v == "" {
utils.WriteError(w, http.StatusBadRequest, "validation_error", "description cannot be empty")
return
}
row.Description = v
}
if in.MakeTarget != nil {
v := strings.TrimSpace(*in.MakeTarget)
if v == "" {
utils.WriteError(w, http.StatusBadRequest, "validation_error", "make_target cannot be empty")
return
}
row.MakeTarget = v
}
if err := db.Save(&row).Error; err != nil {
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
utils.WriteJSON(w, http.StatusOK, actionToDTO(row))
}
}
// DeleteAction godoc
//
// @ID DeleteAction
// @Summary Delete an action
// @Description Deletes an action.
// @Tags Actions
// @Produce json
// @Param actionID path string true "Action ID"
// @Success 204 {string} string "deleted"
// @Failure 400 {string} string "bad request"
// @Failure 401 {string} string "Unauthorized"
// @Failure 404 {string} string "not found"
// @Failure 500 {string} string "db error"
// @Router /admin/actions/{actionID} [delete]
// @Security BearerAuth
func DeleteAction(db *gorm.DB) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
actionID, err := uuid.Parse(chi.URLParam(r, "actionID"))
if err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_action_id", "invalid action id")
return
}
tx := db.Where("id = ?", actionID).Delete(&models.Action{})
if tx.Error != nil {
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
if tx.RowsAffected == 0 {
utils.WriteError(w, http.StatusNotFound, "not_found", "action not found")
return
}
w.WriteHeader(http.StatusNoContent)
}
}
func actionToDTO(a models.Action) dto.ActionResponse {
return dto.ActionResponse{
ID: a.ID,
Label: a.Label,
Description: a.Description,
MakeTarget: a.MakeTarget,
CreatedAt: a.CreatedAt,
UpdatedAt: a.UpdatedAt,
}
}

View File

@@ -0,0 +1,263 @@
package handlers
import (
"errors"
"net/http"
"time"
"github.com/dyaksa/archer"
"github.com/glueops/autoglue/internal/api/httpmiddleware"
"github.com/glueops/autoglue/internal/bg"
"github.com/glueops/autoglue/internal/handlers/dto"
"github.com/glueops/autoglue/internal/models"
"github.com/glueops/autoglue/internal/utils"
"github.com/go-chi/chi/v5"
"github.com/google/uuid"
"gorm.io/gorm"
)
// ListClusterRuns godoc
//
// @ID ListClusterRuns
// @Summary List cluster runs (org scoped)
// @Description Returns runs for a cluster within the organization in X-Org-ID.
// @Tags ClusterRuns
// @Produce json
// @Param X-Org-ID header string false "Organization UUID"
// @Param clusterID path string true "Cluster ID"
// @Success 200 {array} dto.ClusterRunResponse
// @Failure 401 {string} string "Unauthorized"
// @Failure 403 {string} string "organization required"
// @Failure 404 {string} string "cluster not found"
// @Failure 500 {string} string "db error"
// @Router /clusters/{clusterID}/runs [get]
// @Security BearerAuth
// @Security OrgKeyAuth
// @Security OrgSecretAuth
func ListClusterRuns(db *gorm.DB) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
orgID, ok := httpmiddleware.OrgIDFrom(r.Context())
if !ok {
utils.WriteError(w, http.StatusForbidden, "org_required", "specify X-Org-ID")
return
}
clusterID, err := uuid.Parse(chi.URLParam(r, "clusterID"))
if err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_cluster_id", "invalid cluster id")
return
}
// Ensure cluster exists + org scoped
if err := db.Select("id").
Where("id = ? AND organization_id = ?", clusterID, orgID).
First(&models.Cluster{}).Error; err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
utils.WriteError(w, http.StatusNotFound, "not_found", "cluster not found")
return
}
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
var rows []models.ClusterRun
if err := db.
Where("organization_id = ? AND cluster_id = ?", orgID, clusterID).
Order("created_at DESC").
Find(&rows).Error; err != nil {
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
out := make([]dto.ClusterRunResponse, 0, len(rows))
for _, cr := range rows {
out = append(out, clusterRunToDTO(cr))
}
utils.WriteJSON(w, http.StatusOK, out)
}
}
// GetClusterRun godoc
//
// @ID GetClusterRun
// @Summary Get a cluster run (org scoped)
// @Description Returns a single run for a cluster within the organization in X-Org-ID.
// @Tags ClusterRuns
// @Produce json
// @Param X-Org-ID header string false "Organization UUID"
// @Param clusterID path string true "Cluster ID"
// @Param runID path string true "Run ID"
// @Success 200 {object} dto.ClusterRunResponse
// @Failure 400 {string} string "bad request"
// @Failure 401 {string} string "Unauthorized"
// @Failure 403 {string} string "organization required"
// @Failure 404 {string} string "not found"
// @Failure 500 {string} string "db error"
// @Router /clusters/{clusterID}/runs/{runID} [get]
// @Security BearerAuth
// @Security OrgKeyAuth
// @Security OrgSecretAuth
func GetClusterRun(db *gorm.DB) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
orgID, ok := httpmiddleware.OrgIDFrom(r.Context())
if !ok {
utils.WriteError(w, http.StatusForbidden, "org_required", "specify X-Org-ID")
return
}
clusterID, err := uuid.Parse(chi.URLParam(r, "clusterID"))
if err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_cluster_id", "invalid cluster id")
return
}
runID, err := uuid.Parse(chi.URLParam(r, "runID"))
if err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_run_id", "invalid run id")
return
}
var row models.ClusterRun
if err := db.
Where("id = ? AND organization_id = ? AND cluster_id = ?", runID, orgID, clusterID).
First(&row).Error; err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
utils.WriteError(w, http.StatusNotFound, "not_found", "run not found")
return
}
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
utils.WriteJSON(w, http.StatusOK, clusterRunToDTO(row))
}
}
// RunClusterAction godoc
//
// @ID RunClusterAction
// @Summary Run an admin-configured action on a cluster (org scoped)
// @Description Creates a ClusterRun record for the cluster/action. Execution is handled asynchronously by workers.
// @Tags ClusterRuns
// @Produce json
// @Param X-Org-ID header string false "Organization UUID"
// @Param clusterID path string true "Cluster ID"
// @Param actionID path string true "Action ID"
// @Success 201 {object} dto.ClusterRunResponse
// @Failure 400 {string} string "bad request"
// @Failure 401 {string} string "Unauthorized"
// @Failure 403 {string} string "organization required"
// @Failure 404 {string} string "cluster or action not found"
// @Failure 500 {string} string "db error"
// @Router /clusters/{clusterID}/actions/{actionID}/runs [post]
// @Security BearerAuth
// @Security OrgKeyAuth
// @Security OrgSecretAuth
func RunClusterAction(db *gorm.DB, jobs *bg.Jobs) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
orgID, ok := httpmiddleware.OrgIDFrom(r.Context())
if !ok {
utils.WriteError(w, http.StatusForbidden, "org_required", "specify X-Org-ID")
return
}
clusterID, err := uuid.Parse(chi.URLParam(r, "clusterID"))
if err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_cluster_id", "invalid cluster id")
return
}
actionID, err := uuid.Parse(chi.URLParam(r, "actionID"))
if err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_action_id", "invalid action id")
return
}
// cluster must exist + org scoped
var cluster models.Cluster
if err := db.Select("id", "organization_id").
Where("id = ? AND organization_id = ?", clusterID, orgID).
First(&cluster).Error; err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
utils.WriteError(w, http.StatusNotFound, "not_found", "cluster not found")
return
}
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
// action is global/admin-configured (not org scoped)
var action models.Action
if err := db.Where("id = ?", actionID).First(&action).Error; err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
utils.WriteError(w, http.StatusNotFound, "action_not_found", "action not found")
return
}
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
run := models.ClusterRun{
OrganizationID: orgID,
ClusterID: clusterID,
Action: action.MakeTarget, // this is what you actually execute
Status: models.ClusterRunStatusQueued,
Error: "",
FinishedAt: time.Time{},
}
if err := db.Create(&run).Error; err != nil {
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
}
args := bg.ClusterActionArgs{
OrgID: orgID,
ClusterID: clusterID,
Action: action.MakeTarget,
MakeTarget: action.MakeTarget,
}
// Enqueue with run.ID as the job ID so the worker can look it up.
_, enqueueErr := jobs.Enqueue(
r.Context(),
run.ID.String(),
"cluster_action",
args,
archer.WithMaxRetries(0),
)
if enqueueErr != nil {
_ = db.Model(&models.ClusterRun{}).
Where("id = ?", run.ID).
Updates(map[string]any{
"status": models.ClusterRunStatusFailed,
"error": "failed to enqueue job: " + enqueueErr.Error(),
"finished_at": time.Now().UTC(),
}).Error
utils.WriteError(w, http.StatusInternalServerError, "job_error", "failed to enqueue cluster action")
return
}
utils.WriteJSON(w, http.StatusCreated, clusterRunToDTO(run))
}
}
func clusterRunToDTO(cr models.ClusterRun) dto.ClusterRunResponse {
var finished *time.Time
if !cr.FinishedAt.IsZero() {
t := cr.FinishedAt
finished = &t
}
return dto.ClusterRunResponse{
ID: cr.ID,
OrganizationID: cr.OrganizationID,
ClusterID: cr.ClusterID,
Action: cr.Action,
Status: cr.Status,
Error: cr.Error,
CreatedAt: cr.CreatedAt,
UpdatedAt: cr.UpdatedAt,
FinishedAt: finished,
}
}

View File

@@ -69,7 +69,17 @@ func ListClusters(db *gorm.DB) http.HandlerFunc {
out := make([]dto.ClusterResponse, 0, len(rows))
for _, row := range rows {
out = append(out, clusterToDTO(row))
cr := clusterToDTO(row)
if row.EncryptedKubeconfig != "" && row.KubeIV != "" && row.KubeTag != "" {
kubeconfig, err := utils.DecryptForOrg(orgID, row.EncryptedKubeconfig, row.KubeIV, row.KubeTag, db)
if err != nil {
utils.WriteError(w, http.StatusInternalServerError, "kubeconfig_decrypt_failed", "failed to decrypt kubeconfig")
return
}
cr.Kubeconfig = &kubeconfig
}
out = append(out, cr)
}
utils.WriteJSON(w, http.StatusOK, out)
}
@@ -131,7 +141,18 @@ func GetCluster(db *gorm.DB) http.HandlerFunc {
return
}
utils.WriteJSON(w, http.StatusOK, clusterToDTO(cluster))
resp := clusterToDTO(cluster)
if cluster.EncryptedKubeconfig != "" && cluster.KubeIV != "" && cluster.KubeTag != "" {
kubeconfig, err := utils.DecryptForOrg(orgID, cluster.EncryptedKubeconfig, cluster.KubeIV, cluster.KubeTag, db)
if err != nil {
utils.WriteError(w, http.StatusInternalServerError, "kubeconfig_decrypt_failed", "failed to decrypt kubeconfig")
return
}
resp.Kubeconfig = &kubeconfig
}
utils.WriteJSON(w, http.StatusOK, resp)
}
}
@@ -183,12 +204,14 @@ func CreateCluster(db *gorm.DB) http.HandlerFunc {
c := models.Cluster{
OrganizationID: orgID,
Name: in.Name,
Provider: in.Provider,
Provider: in.ClusterProvider,
Region: in.Region,
Status: models.ClusterStatusPrePending,
LastError: "",
CertificateKey: certificateKey,
RandomToken: randomToken,
DockerImage: in.DockerImage,
DockerTag: in.DockerTag,
}
if err := db.Create(&c).Error; err != nil {
@@ -255,13 +278,21 @@ func UpdateCluster(db *gorm.DB) http.HandlerFunc {
if in.Name != nil {
cluster.Name = *in.Name
}
if in.Provider != nil {
cluster.Provider = *in.Provider
if in.ClusterProvider != nil {
cluster.Provider = *in.ClusterProvider
}
if in.Region != nil {
cluster.Region = *in.Region
}
if in.DockerImage != nil {
cluster.DockerImage = *in.DockerImage
}
if in.DockerTag != nil {
cluster.DockerTag = *in.DockerTag
}
if err := db.Save(&cluster).Error; err != nil {
utils.WriteError(w, http.StatusInternalServerError, "db_error", "db error")
return
@@ -1508,6 +1539,12 @@ func clusterToDTO(c models.Cluster) dto.ClusterResponse {
controlPlane = &rr
}
var cfqdn *string
if captainDomain != nil && controlPlane != nil {
fq := fmt.Sprintf("%s.%s", controlPlane.Name, captainDomain.DomainName)
cfqdn = &fq
}
var appsLB *dto.LoadBalancerResponse
if c.AppsLoadBalancer != nil {
lr := loadBalancerToDTO(*c.AppsLoadBalancer)
@@ -1530,6 +1567,7 @@ func clusterToDTO(c models.Cluster) dto.ClusterResponse {
Name: c.Name,
CaptainDomain: captainDomain,
ControlPlaneRecordSet: controlPlane,
ControlPlaneFQDN: cfqdn,
AppsLoadBalancer: appsLB,
GlueOpsLoadBalancer: glueOpsLB,
BastionServer: bastion,
@@ -1540,6 +1578,8 @@ func clusterToDTO(c models.Cluster) dto.ClusterResponse {
RandomToken: c.RandomToken,
CertificateKey: c.CertificateKey,
NodePools: nps,
DockerImage: c.DockerImage,
DockerTag: c.DockerTag,
CreatedAt: c.CreatedAt,
UpdatedAt: c.UpdatedAt,
}

View File

@@ -29,14 +29,14 @@ import (
// @Description Returns credential metadata for the current org. Secrets are never returned.
// @Tags Credentials
// @Produce json
// @Param X-Org-ID header string false "Organization ID (UUID)"
// @Param provider query string false "Filter by provider (e.g., aws)"
// @Param kind query string false "Filter by kind (e.g., aws_access_key)"
// @Param scope_kind query string false "Filter by scope kind (provider/service/resource)"
// @Success 200 {array} dto.CredentialOut
// @Failure 401 {string} string "Unauthorized"
// @Failure 403 {string} string "organization required"
// @Failure 500 {string} string "internal server error"
// @Param X-Org-ID header string false "Organization ID (UUID)"
// @Param credential_provider query string false "Filter by provider (e.g., aws)"
// @Param kind query string false "Filter by kind (e.g., aws_access_key)"
// @Param scope_kind query string false "Filter by scope kind (credential_provider/service/resource)"
// @Success 200 {array} dto.CredentialOut
// @Failure 401 {string} string "Unauthorized"
// @Failure 403 {string} string "organization required"
// @Failure 500 {string} string "internal server error"
// @Router /credentials [get]
// @Security BearerAuth
// @Security OrgKeyAuth
@@ -49,7 +49,7 @@ func ListCredentials(db *gorm.DB) http.HandlerFunc {
return
}
q := db.Where("organization_id = ?", orgID)
if v := r.URL.Query().Get("provider"); v != "" {
if v := r.URL.Query().Get("credential_provider"); v != "" {
q = q.Where("provider = ?", v)
}
if v := r.URL.Query().Get("kind"); v != "" {
@@ -154,7 +154,7 @@ func CreateCredential(db *gorm.DB) http.HandlerFunc {
cred, err := SaveCredentialWithScope(
r.Context(), db, orgID,
in.Provider, in.Kind, in.SchemaVersion,
in.CredentialProvider, in.Kind, in.SchemaVersion,
in.ScopeKind, in.ScopeVersion, json.RawMessage(in.Scope), json.RawMessage(in.Secret),
in.Name, in.AccountID, in.Region,
)
@@ -548,17 +548,17 @@ func SaveCredentialWithScope(
// credOut converts model → response DTO
func credOut(c *models.Credential) dto.CredentialOut {
return dto.CredentialOut{
ID: c.ID.String(),
Provider: c.Provider,
Kind: c.Kind,
SchemaVersion: c.SchemaVersion,
Name: c.Name,
ScopeKind: c.ScopeKind,
ScopeVersion: c.ScopeVersion,
Scope: dto.RawJSON(c.Scope),
AccountID: c.AccountID,
Region: c.Region,
CreatedAt: c.CreatedAt.UTC().Format(time.RFC3339),
UpdatedAt: c.UpdatedAt.UTC().Format(time.RFC3339),
ID: c.ID.String(),
CredentialProvider: c.Provider,
Kind: c.Kind,
SchemaVersion: c.SchemaVersion,
Name: c.Name,
ScopeKind: c.ScopeKind,
ScopeVersion: c.ScopeVersion,
Scope: dto.RawJSON(c.Scope),
AccountID: c.AccountID,
Region: c.Region,
CreatedAt: c.CreatedAt.UTC().Format(time.RFC3339),
UpdatedAt: c.UpdatedAt.UTC().Format(time.RFC3339),
}
}

View File

@@ -503,6 +503,50 @@ func ListRecordSets(db *gorm.DB) http.HandlerFunc {
}
}
// GetRecordSet godoc
//
// @ID GetRecordSet
// @Summary Get a record set (org scoped)
// @Tags DNS
// @Produce json
// @Param X-Org-ID header string false "Organization UUID"
// @Param id path string true "Record Set ID (UUID)"
// @Success 200 {object} dto.RecordSetResponse
// @Failure 403 {string} string "organization required"
// @Failure 404 {string} string "not found"
// @Router /dns/records/{id} [get]
func GetRecordSet(db *gorm.DB) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
orgID, ok := httpmiddleware.OrgIDFrom(r.Context())
if !ok {
utils.WriteError(w, http.StatusForbidden, "org_required", "specify X-Org-ID")
return
}
id, err := uuid.Parse(chi.URLParam(r, "id"))
if err != nil {
utils.WriteError(w, http.StatusBadRequest, "bad_id", "invalid UUID")
return
}
var row models.RecordSet
if err := db.
Joins("Domain").
Where(`record_sets.id = ? AND "Domain"."organization_id" = ?`, id, orgID).
First(&row).Error; err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
utils.WriteError(w, http.StatusNotFound, "not_found", "record set not found")
return
}
utils.WriteError(w, http.StatusInternalServerError, "db_error", err.Error())
return
}
utils.WriteJSON(w, http.StatusOK, recordOut(&row))
}
}
// CreateRecordSet godoc
//
// @ID CreateRecordSet

View File

@@ -0,0 +1,28 @@
package dto
import (
"time"
"github.com/google/uuid"
)
type ActionResponse struct {
ID uuid.UUID `json:"id" format:"uuid"`
Label string `json:"label"`
Description string `json:"description"`
MakeTarget string `json:"make_target"`
CreatedAt time.Time `json:"created_at" format:"date-time"`
UpdatedAt time.Time `json:"updated_at" format:"date-time"`
}
type CreateActionRequest struct {
Label string `json:"label"`
Description string `json:"description"`
MakeTarget string `json:"make_target"`
}
type UpdateActionRequest struct {
Label *string `json:"label,omitempty"`
Description *string `json:"description,omitempty"`
MakeTarget *string `json:"make_target,omitempty"`
}

View File

@@ -0,0 +1,19 @@
package dto
import (
"time"
"github.com/google/uuid"
)
type ClusterRunResponse struct {
ID uuid.UUID `json:"id" format:"uuid"`
OrganizationID uuid.UUID `json:"organization_id" format:"uuid"`
ClusterID uuid.UUID `json:"cluster_id" format:"uuid"`
Action string `json:"action"`
Status string `json:"status"`
Error string `json:"error"`
CreatedAt time.Time `json:"created_at" format:"date-time"`
UpdatedAt time.Time `json:"updated_at" format:"date-time"`
FinishedAt *time.Time `json:"finished_at,omitempty" format:"date-time"`
}

View File

@@ -11,30 +11,40 @@ type ClusterResponse struct {
Name string `json:"name"`
CaptainDomain *DomainResponse `json:"captain_domain,omitempty"`
ControlPlaneRecordSet *RecordSetResponse `json:"control_plane_record_set,omitempty"`
ControlPlaneFQDN *string `json:"control_plane_fqdn,omitempty"`
AppsLoadBalancer *LoadBalancerResponse `json:"apps_load_balancer,omitempty"`
GlueOpsLoadBalancer *LoadBalancerResponse `json:"glueops_load_balancer,omitempty"`
BastionServer *ServerResponse `json:"bastion_server,omitempty"`
Provider string `json:"provider"`
Provider string `json:"cluster_provider"`
Region string `json:"region"`
Status string `json:"status"`
LastError string `json:"last_error"`
RandomToken string `json:"random_token"`
CertificateKey string `json:"certificate_key"`
NodePools []NodePoolResponse `json:"node_pools,omitempty"`
DockerImage string `json:"docker_image"`
DockerTag string `json:"docker_tag"`
Kubeconfig *string `json:"kubeconfig,omitempty"`
OrgKey *string `json:"org_key,omitempty"`
OrgSecret *string `json:"org_secret,omitempty"`
CreatedAt time.Time `json:"created_at"`
UpdatedAt time.Time `json:"updated_at"`
}
type CreateClusterRequest struct {
Name string `json:"name"`
Provider string `json:"provider"`
Region string `json:"region"`
Name string `json:"name"`
ClusterProvider string `json:"cluster_provider"`
Region string `json:"region"`
DockerImage string `json:"docker_image"`
DockerTag string `json:"docker_tag"`
}
type UpdateClusterRequest struct {
Name *string `json:"name,omitempty"`
Provider *string `json:"provider,omitempty"`
Region *string `json:"region,omitempty"`
Name *string `json:"name,omitempty"`
ClusterProvider *string `json:"cluster_provider,omitempty"`
Region *string `json:"region,omitempty"`
DockerImage *string `json:"docker_image,omitempty"`
DockerTag *string `json:"docker_tag,omitempty"`
}
type AttachCaptainDomainRequest struct {

View File

@@ -97,16 +97,16 @@ var ScopeRegistry = map[string]map[string]map[int]ScopeDef{
// CreateCredentialRequest represents the POST /credentials payload
type CreateCredentialRequest struct {
Provider string `json:"provider" validate:"required,oneof=aws cloudflare hetzner digitalocean generic"`
Kind string `json:"kind" validate:"required"` // aws_access_key, api_token, basic_auth, oauth2
SchemaVersion int `json:"schema_version" validate:"required,gte=1"` // secret schema version
Name string `json:"name" validate:"omitempty,max=100"` // human label
ScopeKind string `json:"scope_kind" validate:"required,oneof=provider service resource"`
ScopeVersion int `json:"scope_version" validate:"required,gte=1"` // scope schema version
Scope RawJSON `json:"scope" validate:"required" swaggertype:"object"` // {"service":"route53"} or {"arn":"..."}
AccountID string `json:"account_id,omitempty" validate:"omitempty,max=32"`
Region string `json:"region,omitempty" validate:"omitempty,max=32"`
Secret RawJSON `json:"secret" validate:"required" swaggertype:"object"` // encrypted later
CredentialProvider string `json:"credential_provider" validate:"required,oneof=aws cloudflare hetzner digitalocean generic"`
Kind string `json:"kind" validate:"required"` // aws_access_key, api_token, basic_auth, oauth2
SchemaVersion int `json:"schema_version" validate:"required,gte=1"` // secret schema version
Name string `json:"name" validate:"omitempty,max=100"` // human label
ScopeKind string `json:"scope_kind" validate:"required,oneof=credential_provider service resource"`
ScopeVersion int `json:"scope_version" validate:"required,gte=1"` // scope schema version
Scope RawJSON `json:"scope" validate:"required" swaggertype:"object"` // {"service":"route53"} or {"arn":"..."}
AccountID string `json:"account_id,omitempty" validate:"omitempty,max=32"`
Region string `json:"region,omitempty" validate:"omitempty,max=32"`
Secret RawJSON `json:"secret" validate:"required" swaggertype:"object"` // encrypted later
}
// UpdateCredentialRequest represents PATCH /credentials/{id}
@@ -123,16 +123,16 @@ type UpdateCredentialRequest struct {
// CredentialOut is what we return (no secrets)
type CredentialOut struct {
ID string `json:"id"`
Provider string `json:"provider"`
Kind string `json:"kind"`
SchemaVersion int `json:"schema_version"`
Name string `json:"name"`
ScopeKind string `json:"scope_kind"`
ScopeVersion int `json:"scope_version"`
Scope RawJSON `json:"scope" swaggertype:"object"`
AccountID string `json:"account_id,omitempty"`
Region string `json:"region,omitempty"`
CreatedAt string `json:"created_at"`
UpdatedAt string `json:"updated_at"`
ID string `json:"id"`
CredentialProvider string `json:"credential_provider"`
Kind string `json:"kind"`
SchemaVersion int `json:"schema_version"`
Name string `json:"name"`
ScopeKind string `json:"scope_kind"`
ScopeVersion int `json:"scope_version"`
Scope RawJSON `json:"scope" swaggertype:"object"`
AccountID string `json:"account_id,omitempty"`
Region string `json:"region,omitempty"`
CreatedAt string `json:"created_at"`
UpdatedAt string `json:"updated_at"`
}

View File

@@ -828,16 +828,16 @@ func ListNodePoolLabels(db *gorm.DB) http.HandlerFunc {
}
out := make([]dto.LabelResponse, 0, len(np.Taints))
for _, taint := range np.Taints {
for _, label := range np.Labels {
out = append(out, dto.LabelResponse{
AuditFields: common.AuditFields{
ID: taint.ID,
OrganizationID: taint.OrganizationID,
CreatedAt: taint.CreatedAt,
UpdatedAt: taint.UpdatedAt,
ID: label.ID,
OrganizationID: label.OrganizationID,
CreatedAt: label.CreatedAt,
UpdatedAt: label.UpdatedAt,
},
Key: taint.Key,
Value: taint.Value,
Key: label.Key,
Value: label.Value,
})
}
utils.WriteJSON(w, http.StatusOK, out)

View File

@@ -585,13 +585,22 @@ func CreateOrgKey(db *gorm.DB) http.HandlerFunc {
exp = &e
}
prefix := orgKey
if len(prefix) > 12 {
prefix = prefix[:12]
}
rec := models.APIKey{
OrgID: &oid,
Scope: "org",
Name: req.Name,
KeyHash: keyHash,
SecretHash: &secretHash,
ExpiresAt: exp,
OrgID: &oid,
Scope: "org",
Purpose: "user",
IsEphemeral: false,
Name: req.Name,
KeyHash: keyHash,
SecretHash: &secretHash,
ExpiresAt: exp,
Revoked: false,
Prefix: &prefix,
}
if err := db.Create(&rec).Error; err != nil {
utils.WriteError(w, 500, "db_error", err.Error())

182
internal/mapper/cluster.go Normal file
View File

@@ -0,0 +1,182 @@
package mapper
import (
"fmt"
"time"
"github.com/glueops/autoglue/internal/common"
"github.com/glueops/autoglue/internal/handlers/dto"
"github.com/glueops/autoglue/internal/models"
"github.com/google/uuid"
)
func ClusterToDTO(c models.Cluster) dto.ClusterResponse {
var bastion *dto.ServerResponse
if c.BastionServer != nil {
b := ServerToDTO(*c.BastionServer)
bastion = &b
}
var captainDomain *dto.DomainResponse
if c.CaptainDomainID != nil && c.CaptainDomain.ID != uuid.Nil {
dr := DomainToDTO(c.CaptainDomain)
captainDomain = &dr
}
var controlPlane *dto.RecordSetResponse
if c.ControlPlaneRecordSet != nil {
rr := RecordSetToDTO(*c.ControlPlaneRecordSet)
controlPlane = &rr
}
var cfqdn *string
if captainDomain != nil && controlPlane != nil {
fq := fmt.Sprintf("%s.%s", controlPlane.Name, captainDomain.DomainName)
cfqdn = &fq
}
var appsLB *dto.LoadBalancerResponse
if c.AppsLoadBalancer != nil {
lr := LoadBalancerToDTO(*c.AppsLoadBalancer)
appsLB = &lr
}
var glueOpsLB *dto.LoadBalancerResponse
if c.GlueOpsLoadBalancer != nil {
lr := LoadBalancerToDTO(*c.GlueOpsLoadBalancer)
glueOpsLB = &lr
}
nps := make([]dto.NodePoolResponse, 0, len(c.NodePools))
for _, np := range c.NodePools {
nps = append(nps, NodePoolToDTO(np))
}
return dto.ClusterResponse{
ID: c.ID,
Name: c.Name,
CaptainDomain: captainDomain,
ControlPlaneRecordSet: controlPlane,
ControlPlaneFQDN: cfqdn,
AppsLoadBalancer: appsLB,
GlueOpsLoadBalancer: glueOpsLB,
BastionServer: bastion,
Provider: c.Provider,
Region: c.Region,
Status: c.Status,
LastError: c.LastError,
RandomToken: c.RandomToken,
CertificateKey: c.CertificateKey,
NodePools: nps,
DockerImage: c.DockerImage,
DockerTag: c.DockerTag,
CreatedAt: c.CreatedAt,
UpdatedAt: c.UpdatedAt,
}
}
func NodePoolToDTO(np models.NodePool) dto.NodePoolResponse {
labels := make([]dto.LabelResponse, 0, len(np.Labels))
for _, l := range np.Labels {
labels = append(labels, dto.LabelResponse{
Key: l.Key,
Value: l.Value,
})
}
annotations := make([]dto.AnnotationResponse, 0, len(np.Annotations))
for _, a := range np.Annotations {
annotations = append(annotations, dto.AnnotationResponse{
Key: a.Key,
Value: a.Value,
})
}
taints := make([]dto.TaintResponse, 0, len(np.Taints))
for _, t := range np.Taints {
taints = append(taints, dto.TaintResponse{
Key: t.Key,
Value: t.Value,
Effect: t.Effect,
})
}
servers := make([]dto.ServerResponse, 0, len(np.Servers))
for _, s := range np.Servers {
servers = append(servers, ServerToDTO(s))
}
return dto.NodePoolResponse{
AuditFields: common.AuditFields{
ID: np.ID,
OrganizationID: np.OrganizationID,
CreatedAt: np.CreatedAt,
UpdatedAt: np.UpdatedAt,
},
Name: np.Name,
Role: dto.NodeRole(np.Role),
Labels: labels,
Annotations: annotations,
Taints: taints,
Servers: servers,
}
}
func ServerToDTO(s models.Server) dto.ServerResponse {
return dto.ServerResponse{
ID: s.ID,
Hostname: s.Hostname,
PrivateIPAddress: s.PrivateIPAddress,
PublicIPAddress: s.PublicIPAddress,
Role: s.Role,
Status: s.Status,
SSHUser: s.SSHUser,
SshKeyID: s.SshKeyID,
CreatedAt: s.CreatedAt.UTC().Format(time.RFC3339),
UpdatedAt: s.UpdatedAt.UTC().Format(time.RFC3339),
}
}
func DomainToDTO(d models.Domain) dto.DomainResponse {
return dto.DomainResponse{
ID: d.ID.String(),
OrganizationID: d.OrganizationID.String(),
DomainName: d.DomainName,
ZoneID: d.ZoneID,
Status: d.Status,
LastError: d.LastError,
CredentialID: d.CredentialID.String(),
CreatedAt: d.CreatedAt.UTC().Format(time.RFC3339),
UpdatedAt: d.UpdatedAt.UTC().Format(time.RFC3339),
}
}
func RecordSetToDTO(rs models.RecordSet) dto.RecordSetResponse {
return dto.RecordSetResponse{
ID: rs.ID.String(),
DomainID: rs.DomainID.String(),
Name: rs.Name,
Type: rs.Type,
TTL: rs.TTL,
Values: []byte(rs.Values),
Fingerprint: rs.Fingerprint,
Status: rs.Status,
Owner: rs.Owner,
LastError: rs.LastError,
CreatedAt: rs.CreatedAt.UTC().Format(time.RFC3339),
UpdatedAt: rs.UpdatedAt.UTC().Format(time.RFC3339),
}
}
func LoadBalancerToDTO(lb models.LoadBalancer) dto.LoadBalancerResponse {
return dto.LoadBalancerResponse{
ID: lb.ID,
OrganizationID: lb.OrganizationID,
Name: lb.Name,
Kind: lb.Kind,
PublicIPAddress: lb.PublicIPAddress,
PrivateIPAddress: lb.PrivateIPAddress,
CreatedAt: lb.CreatedAt,
UpdatedAt: lb.UpdatedAt,
}
}

16
internal/models/action.go Normal file
View File

@@ -0,0 +1,16 @@
package models
import (
"time"
"github.com/google/uuid"
)
type Action struct {
ID uuid.UUID `gorm:"type:uuid;primaryKey;default:gen_random_uuid()" json:"id" format:"uuid"`
Label string `gorm:"type:varchar(255);not null;uniqueIndex" json:"label"`
Description string `gorm:"type:text;not null" json:"description"`
MakeTarget string `gorm:"type:varchar(255);not null;uniqueIndex" json:"make_target"`
CreatedAt time.Time `json:"created_at,omitempty" gorm:"type:timestamptz;column:created_at;not null;default:now()" format:"date-time"`
UpdatedAt time.Time `json:"updated_at,omitempty" gorm:"type:timestamptz;autoUpdateTime;column:updated_at;not null;default:now()" format:"date-time"`
}

View File

@@ -7,17 +7,20 @@ import (
)
type APIKey struct {
ID uuid.UUID `gorm:"type:uuid;primaryKey;default:gen_random_uuid()" json:"id" format:"uuid"`
Name string `gorm:"not null;default:''" json:"name"`
KeyHash string `gorm:"uniqueIndex;not null" json:"-"`
Scope string `gorm:"not null;default:''" json:"scope"`
UserID *uuid.UUID `json:"user_id,omitempty" format:"uuid"`
OrgID *uuid.UUID `json:"org_id,omitempty" format:"uuid"`
SecretHash *string `json:"-"`
ExpiresAt *time.Time `json:"expires_at,omitempty" format:"date-time"`
Revoked bool `gorm:"not null;default:false" json:"revoked"`
Prefix *string `json:"prefix,omitempty"`
LastUsedAt *time.Time `json:"last_used_at,omitempty" format:"date-time"`
CreatedAt time.Time `json:"created_at,omitempty" gorm:"type:timestamptz;column:created_at;not null;default:now()" format:"date-time"`
UpdatedAt time.Time `json:"updated_at,omitempty" gorm:"type:timestamptz;autoUpdateTime;column:updated_at;not null;default:now()" format:"date-time"`
ID uuid.UUID `gorm:"type:uuid;primaryKey;default:gen_random_uuid()" json:"id" format:"uuid"`
OrgID *uuid.UUID `json:"org_id,omitempty" format:"uuid"`
Scope string `gorm:"not null;default:''" json:"scope"`
Purpose string `json:"purpose"`
ClusterID *uuid.UUID `json:"cluster_id,omitempty"`
IsEphemeral bool `json:"is_ephemeral"`
Name string `gorm:"not null;default:''" json:"name"`
KeyHash string `gorm:"uniqueIndex;not null" json:"-"`
SecretHash *string `json:"-"`
UserID *uuid.UUID `json:"user_id,omitempty" format:"uuid"`
ExpiresAt *time.Time `json:"expires_at,omitempty" format:"date-time"`
Revoked bool `gorm:"not null;default:false" json:"revoked"`
Prefix *string `json:"prefix,omitempty"`
LastUsedAt *time.Time `json:"last_used_at,omitempty" format:"date-time"`
CreatedAt time.Time `json:"created_at,omitempty" gorm:"type:timestamptz;column:created_at;not null;default:now()" format:"date-time"`
UpdatedAt time.Time `json:"updated_at,omitempty" gorm:"type:timestamptz;autoUpdateTime;column:updated_at;not null;default:now()" format:"date-time"`
}

View File

@@ -7,12 +7,13 @@ import (
)
const (
ClusterStatusPrePending = "pre_pending" // needs validation
ClusterStatusIncomplete = "incomplete" // invalid/missing shape
ClusterStatusPending = "pending" // valid shape, waiting for provisioning
ClusterStatusProvisioning = "provisioning"
ClusterStatusReady = "ready"
ClusterStatusFailed = "failed" // provisioning/runtime failure
ClusterStatusPrePending = "pre_pending" // needs validation
ClusterStatusIncomplete = "incomplete" // invalid/missing shape
ClusterStatusPending = "pending" // valid shape, waiting for provisioning
ClusterStatusProvisioning = "provisioning"
ClusterStatusReady = "ready"
ClusterStatusFailed = "failed" // provisioning/runtime failure
ClusterStatusBootstrapping = "bootstrapping"
)
type Cluster struct {
@@ -40,6 +41,8 @@ type Cluster struct {
EncryptedKubeconfig string `gorm:"type:text" json:"-"`
KubeIV string `json:"-"`
KubeTag string `json:"-"`
DockerImage string `json:"docker_image"`
DockerTag string `json:"docker_tag"`
CreatedAt time.Time `json:"created_at,omitempty" gorm:"type:timestamptz;column:created_at;not null;default:now()"`
UpdatedAt time.Time `json:"updated_at,omitempty" gorm:"type:timestamptz;autoUpdateTime;column:updated_at;not null;default:now()"`
}

View File

@@ -0,0 +1,27 @@
package models
import (
"time"
"github.com/google/uuid"
)
const (
ClusterRunStatusQueued = "queued"
ClusterRunStatusRunning = "running"
ClusterRunStatusSuccess = "success"
ClusterRunStatusFailed = "failed"
ClusterRunStatusCanceled = "canceled"
)
type ClusterRun struct {
ID uuid.UUID `gorm:"type:uuid;primaryKey;default:gen_random_uuid()" json:"id" format:"uuid"`
OrganizationID uuid.UUID `json:"organization_id" gorm:"type:uuid;index"`
ClusterID uuid.UUID `json:"cluster_id" gorm:"type:uuid;index"`
Action string `json:"action" gorm:"type:text;not null"`
Status string `json:"status" gorm:"type:text;not null"`
Error string `json:"error" gorm:"type:text;not null"`
CreatedAt time.Time `json:"created_at,omitempty" gorm:"type:timestamptz;column:created_at;not null;default:now()" format:"date-time"`
UpdatedAt time.Time `json:"updated_at,omitempty" gorm:"type:timestamptz;autoUpdateTime;column:updated_at;not null;default:now()" format:"date-time"`
FinishedAt time.Time `json:"finished_at,omitempty" gorm:"type:timestamptz" format:"date-time"`
}

File diff suppressed because one or more lines are too long

Binary file not shown.

Binary file not shown.

File diff suppressed because one or more lines are too long

4186
internal/web/dist/assets/index-GteqH5KT.js vendored Normal file

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

Binary file not shown.

Binary file not shown.

File diff suppressed because one or more lines are too long

Binary file not shown.

Binary file not shown.

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@@ -5,9 +5,9 @@
<link rel="icon" type="image/svg+xml" href="/vite.svg" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>AutoGlue</title>
<script type="module" crossorigin src="/assets/index-BRRMZeeQ.js"></script>
<link rel="modulepreload" crossorigin href="/assets/react-B7S5QDrv.js">
<link rel="stylesheet" crossorigin href="/assets/index-VHZG0dIU.css">
<script type="module" crossorigin src="/assets/index-GteqH5KT.js"></script>
<link rel="modulepreload" crossorigin href="/assets/react-v1TLhXpT.js">
<link rel="stylesheet" crossorigin href="/assets/index-Cdjh6IZW.css">
</head>
<body>
<div id="root"></div>

Binary file not shown.

Binary file not shown.

View File

@@ -1,2 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" role="img" class="iconify iconify--logos" width="31.88"
height="32" preserveAspectRatio="xMidYMid meet" viewBox="0 0 256 257"><defs><linearGradient id="IconifyId1813088fe1fbc01fb466" x1="-.828%" x2="57.636%" y1="7.652%" y2="78.411%"><stop offset="0%" stop-color="#41D1FF"></stop><stop offset="100%" stop-color="#BD34FE"></stop></linearGradient><linearGradient id="IconifyId1813088fe1fbc01fb467" x1="43.376%" x2="50.316%" y1="2.242%" y2="89.03%"><stop offset="0%" stop-color="#FFEA83"></stop><stop offset="8.333%" stop-color="#FFDD35"></stop><stop offset="100%" stop-color="#FFA800"></stop></linearGradient></defs><path fill="url(#IconifyId1813088fe1fbc01fb466)" d="M255.153 37.938L134.897 252.976c-2.483 4.44-8.862 4.466-11.382.048L.875 37.958c-2.746-4.814 1.371-10.646 6.827-9.67l120.385 21.517a6.537 6.537 0 0 0 2.322-.004l117.867-21.483c5.438-.991 9.574 4.796 6.877 9.62Z"></path><path fill="url(#IconifyId1813088fe1fbc01fb467)" d="M185.432.063L96.44 17.501a3.268 3.268 0 0 0-2.634 3.014l-5.474 92.456a3.268 3.268 0 0 0 3.997 3.378l24.777-5.718c2.318-.535 4.413 1.507 3.936 3.838l-7.361 36.047c-.495 2.426 1.782 4.5 4.151 3.78l15.304-4.649c2.372-.72 4.652 1.36 4.15 3.788l-11.698 56.621c-.732 3.542 3.979 5.473 5.943 2.437l1.313-2.028l72.516-144.72c1.215-2.423-.88-5.186-3.54-4.672l-25.505 4.922c-2.396.462-4.435-1.77-3.759-4.114l16.646-57.705c.677-2.35-1.37-4.583-3.769-4.113Z"></path></svg>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" aria-hidden="true" role="img" class="iconify iconify--logos" width="31.88" height="32" preserveAspectRatio="xMidYMid meet" viewBox="0 0 256 257"><defs><linearGradient id="IconifyId1813088fe1fbc01fb466" x1="-.828%" x2="57.636%" y1="7.652%" y2="78.411%"><stop offset="0%" stop-color="#41D1FF"></stop><stop offset="100%" stop-color="#BD34FE"></stop></linearGradient><linearGradient id="IconifyId1813088fe1fbc01fb467" x1="43.376%" x2="50.316%" y1="2.242%" y2="89.03%"><stop offset="0%" stop-color="#FFEA83"></stop><stop offset="8.333%" stop-color="#FFDD35"></stop><stop offset="100%" stop-color="#FFA800"></stop></linearGradient></defs><path fill="url(#IconifyId1813088fe1fbc01fb466)" d="M255.153 37.938L134.897 252.976c-2.483 4.44-8.862 4.466-11.382.048L.875 37.958c-2.746-4.814 1.371-10.646 6.827-9.67l120.385 21.517a6.537 6.537 0 0 0 2.322-.004l117.867-21.483c5.438-.991 9.574 4.796 6.877 9.62Z"></path><path fill="url(#IconifyId1813088fe1fbc01fb467)" d="M185.432.063L96.44 17.501a3.268 3.268 0 0 0-2.634 3.014l-5.474 92.456a3.268 3.268 0 0 0 3.997 3.378l24.777-5.718c2.318-.535 4.413 1.507 3.936 3.838l-7.361 36.047c-.495 2.426 1.782 4.5 4.151 3.78l15.304-4.649c2.372-.72 4.652 1.36 4.15 3.788l-11.698 56.621c-.732 3.542 3.979 5.473 5.943 2.437l1.313-2.028l72.516-144.72c1.215-2.423-.88-5.186-3.54-4.672l-25.505 4.922c-2.396.462-4.435-1.77-3.759-4.114l16.646-57.705c.677-2.35-1.37-4.583-3.769-4.113Z"></path></svg>

Before

Width:  |  Height:  |  Size: 1.4 KiB

After

Width:  |  Height:  |  Size: 1.5 KiB

View File

@@ -11,8 +11,10 @@ import (
// @description API for managing K3s clusters across cloud providers
// @contact.name GlueOps
// @servers.url https://autoglue.onglueops.rocks/api/v1
// @servers.url https://autoglue.glueopshosted.com/api/v1
// @servers.description Production API
// @servers.url https://autoglue.glueopshosted.rocks/api/v1
// @servers.description Pre-Production API
// @servers.url https://autoglue.apps.nonprod.earth.onglueops.rocks/api/v1
// @servers.description Staging API
// @servers.url http://localhost:8080/api/v1

View File

@@ -1,4 +1,4 @@
FROM postgres:17.7@sha256:44640f16641cf36716cabd011e2f7eb4742b6b6b19f4488ddcbb7c250e5c9753
FROM postgres:17.7@sha256:dca7512acaa113409df7e40d977d801e53c0c8088e45d4311a45b4065ccfdcd3
RUN cd /var/lib/postgresql/ && \
openssl req -new -text -passout pass:abcd -subj /CN=localhost -out server.req -keyout privkey.pem && \
@@ -6,5 +6,4 @@ RUN cd /var/lib/postgresql/ && \
openssl req -x509 -in server.req -text -key server.key -out server.crt && \
chmod 600 server.key && \
chown postgres:postgres server.key
USER non-root
CMD ["postgres", "-c", "ssl=on", "-c", "ssl_cert_file=/var/lib/postgresql/server.crt", "-c", "ssl_key_file=/var/lib/postgresql/server.key" ]

4
sdk/ts/.gitignore vendored Normal file
View File

@@ -0,0 +1,4 @@
wwwroot/*.js
node_modules
typings
dist

1
sdk/ts/.npmignore Normal file
View File

@@ -0,0 +1 @@
README.md

View File

@@ -0,0 +1,23 @@
# OpenAPI Generator Ignore
# Generated by openapi-generator https://github.com/openapitools/openapi-generator
# Use this file to prevent files from being overwritten by the generator.
# The patterns follow closely to .gitignore or .dockerignore.
# As an example, the C# client generator defines ApiClient.cs.
# You can make changes and tell OpenAPI Generator to ignore just this file by uncommenting the following line:
#ApiClient.cs
# You can match any string of characters against a directory, file or extension with a single asterisk (*):
#foo/*/qux
# The above matches foo/bar/qux and foo/baz/qux, but not foo/bar/baz/qux
# You can recursively match patterns against a directory, file or extension with a double asterisk (**):
#foo/**/qux
# This matches foo/bar/qux, foo/baz/qux, and foo/bar/baz/qux
# You can also negate patterns with an exclamation (!).
# For example, you can ignore all files in a docs folder with the file extension .md:
#docs/*.md
# Then explicitly reverse the ignore rule for a single file:
#!docs/README.md

View File

@@ -0,0 +1,189 @@
.gitignore
.npmignore
.openapi-generator-ignore
README.md
docs/AnnotationsApi.md
docs/ArcherAdminApi.md
docs/AuthApi.md
docs/ClustersApi.md
docs/CredentialsApi.md
docs/DNSApi.md
docs/DtoAnnotationResponse.md
docs/DtoAttachAnnotationsRequest.md
docs/DtoAttachBastionRequest.md
docs/DtoAttachCaptainDomainRequest.md
docs/DtoAttachLabelsRequest.md
docs/DtoAttachLoadBalancerRequest.md
docs/DtoAttachNodePoolRequest.md
docs/DtoAttachRecordSetRequest.md
docs/DtoAttachServersRequest.md
docs/DtoAttachTaintsRequest.md
docs/DtoAuthStartResponse.md
docs/DtoClusterResponse.md
docs/DtoCreateAnnotationRequest.md
docs/DtoCreateClusterRequest.md
docs/DtoCreateCredentialRequest.md
docs/DtoCreateDomainRequest.md
docs/DtoCreateLabelRequest.md
docs/DtoCreateLoadBalancerRequest.md
docs/DtoCreateNodePoolRequest.md
docs/DtoCreateRecordSetRequest.md
docs/DtoCreateSSHRequest.md
docs/DtoCreateServerRequest.md
docs/DtoCreateTaintRequest.md
docs/DtoCredentialOut.md
docs/DtoDomainResponse.md
docs/DtoEnqueueRequest.md
docs/DtoJWK.md
docs/DtoJWKS.md
docs/DtoJob.md
docs/DtoJobStatus.md
docs/DtoLabelResponse.md
docs/DtoLoadBalancerResponse.md
docs/DtoLogoutRequest.md
docs/DtoNodePoolResponse.md
docs/DtoPageJob.md
docs/DtoQueueInfo.md
docs/DtoRecordSetResponse.md
docs/DtoRefreshRequest.md
docs/DtoServerResponse.md
docs/DtoSetKubeconfigRequest.md
docs/DtoSshResponse.md
docs/DtoSshRevealResponse.md
docs/DtoTaintResponse.md
docs/DtoTokenPair.md
docs/DtoUpdateAnnotationRequest.md
docs/DtoUpdateClusterRequest.md
docs/DtoUpdateCredentialRequest.md
docs/DtoUpdateDomainRequest.md
docs/DtoUpdateLabelRequest.md
docs/DtoUpdateLoadBalancerRequest.md
docs/DtoUpdateNodePoolRequest.md
docs/DtoUpdateRecordSetRequest.md
docs/DtoUpdateServerRequest.md
docs/DtoUpdateTaintRequest.md
docs/GetSSHKey200Response.md
docs/HandlersCreateUserKeyRequest.md
docs/HandlersHealthStatus.md
docs/HandlersMeResponse.md
docs/HandlersMemberOut.md
docs/HandlersMemberUpsertReq.md
docs/HandlersOrgCreateReq.md
docs/HandlersOrgKeyCreateReq.md
docs/HandlersOrgKeyCreateResp.md
docs/HandlersOrgUpdateReq.md
docs/HandlersUpdateMeRequest.md
docs/HandlersUserAPIKeyOut.md
docs/HandlersVersionResponse.md
docs/HealthApi.md
docs/LabelsApi.md
docs/LoadBalancersApi.md
docs/MeAPIKeysApi.md
docs/MeApi.md
docs/MetaApi.md
docs/ModelsAPIKey.md
docs/ModelsOrganization.md
docs/ModelsUser.md
docs/ModelsUserEmail.md
docs/NodePoolsApi.md
docs/OrgsApi.md
docs/ServersApi.md
docs/SshApi.md
docs/TaintsApi.md
docs/UtilsErrorResponse.md
package.json
src/apis/AnnotationsApi.ts
src/apis/ArcherAdminApi.ts
src/apis/AuthApi.ts
src/apis/ClustersApi.ts
src/apis/CredentialsApi.ts
src/apis/DNSApi.ts
src/apis/HealthApi.ts
src/apis/LabelsApi.ts
src/apis/LoadBalancersApi.ts
src/apis/MeAPIKeysApi.ts
src/apis/MeApi.ts
src/apis/MetaApi.ts
src/apis/NodePoolsApi.ts
src/apis/OrgsApi.ts
src/apis/ServersApi.ts
src/apis/SshApi.ts
src/apis/TaintsApi.ts
src/apis/index.ts
src/index.ts
src/models/DtoAnnotationResponse.ts
src/models/DtoAttachAnnotationsRequest.ts
src/models/DtoAttachBastionRequest.ts
src/models/DtoAttachCaptainDomainRequest.ts
src/models/DtoAttachLabelsRequest.ts
src/models/DtoAttachLoadBalancerRequest.ts
src/models/DtoAttachNodePoolRequest.ts
src/models/DtoAttachRecordSetRequest.ts
src/models/DtoAttachServersRequest.ts
src/models/DtoAttachTaintsRequest.ts
src/models/DtoAuthStartResponse.ts
src/models/DtoClusterResponse.ts
src/models/DtoCreateAnnotationRequest.ts
src/models/DtoCreateClusterRequest.ts
src/models/DtoCreateCredentialRequest.ts
src/models/DtoCreateDomainRequest.ts
src/models/DtoCreateLabelRequest.ts
src/models/DtoCreateLoadBalancerRequest.ts
src/models/DtoCreateNodePoolRequest.ts
src/models/DtoCreateRecordSetRequest.ts
src/models/DtoCreateSSHRequest.ts
src/models/DtoCreateServerRequest.ts
src/models/DtoCreateTaintRequest.ts
src/models/DtoCredentialOut.ts
src/models/DtoDomainResponse.ts
src/models/DtoEnqueueRequest.ts
src/models/DtoJWK.ts
src/models/DtoJWKS.ts
src/models/DtoJob.ts
src/models/DtoJobStatus.ts
src/models/DtoLabelResponse.ts
src/models/DtoLoadBalancerResponse.ts
src/models/DtoLogoutRequest.ts
src/models/DtoNodePoolResponse.ts
src/models/DtoPageJob.ts
src/models/DtoQueueInfo.ts
src/models/DtoRecordSetResponse.ts
src/models/DtoRefreshRequest.ts
src/models/DtoServerResponse.ts
src/models/DtoSetKubeconfigRequest.ts
src/models/DtoSshResponse.ts
src/models/DtoSshRevealResponse.ts
src/models/DtoTaintResponse.ts
src/models/DtoTokenPair.ts
src/models/DtoUpdateAnnotationRequest.ts
src/models/DtoUpdateClusterRequest.ts
src/models/DtoUpdateCredentialRequest.ts
src/models/DtoUpdateDomainRequest.ts
src/models/DtoUpdateLabelRequest.ts
src/models/DtoUpdateLoadBalancerRequest.ts
src/models/DtoUpdateNodePoolRequest.ts
src/models/DtoUpdateRecordSetRequest.ts
src/models/DtoUpdateServerRequest.ts
src/models/DtoUpdateTaintRequest.ts
src/models/GetSSHKey200Response.ts
src/models/HandlersCreateUserKeyRequest.ts
src/models/HandlersHealthStatus.ts
src/models/HandlersMeResponse.ts
src/models/HandlersMemberOut.ts
src/models/HandlersMemberUpsertReq.ts
src/models/HandlersOrgCreateReq.ts
src/models/HandlersOrgKeyCreateReq.ts
src/models/HandlersOrgKeyCreateResp.ts
src/models/HandlersOrgUpdateReq.ts
src/models/HandlersUpdateMeRequest.ts
src/models/HandlersUserAPIKeyOut.ts
src/models/HandlersVersionResponse.ts
src/models/ModelsAPIKey.ts
src/models/ModelsOrganization.ts
src/models/ModelsUser.ts
src/models/ModelsUserEmail.ts
src/models/UtilsErrorResponse.ts
src/models/index.ts
src/runtime.ts
tsconfig.esm.json
tsconfig.json

View File

@@ -0,0 +1 @@
7.17.0

325
sdk/ts/README.md Normal file
View File

@@ -0,0 +1,325 @@
# @glueops/autoglue-sdk-go@0.1.0
A TypeScript SDK client for the autoglue.glueopshosted.com API.
## Usage
First, install the SDK from npm.
```bash
npm install @glueops/autoglue-sdk-go --save
```
Next, try it out.
```ts
import {
Configuration,
AnnotationsApi,
} from '@glueops/autoglue-sdk-go';
import type { CreateAnnotationRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new AnnotationsApi(config);
const body = {
// DtoCreateAnnotationRequest | Annotation payload
dtoCreateAnnotationRequest: ...,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies CreateAnnotationRequest;
try {
const data = await api.createAnnotation(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
## Documentation
### API Endpoints
All URIs are relative to *https://autoglue.glueopshosted.com/api/v1*
| Class | Method | HTTP request | Description |
| ------------------ | ---------------------------------------------------------------------------------- | --------------------------------------------------------- | -------------------------------------------------------------------------------------------- |
| _AnnotationsApi_ | [**createAnnotation**](docs/AnnotationsApi.md#createannotation) | **POST** /annotations | Create annotation (org scoped) |
| _AnnotationsApi_ | [**deleteAnnotation**](docs/AnnotationsApi.md#deleteannotation) | **DELETE** /annotations/{id} | Delete annotation (org scoped) |
| _AnnotationsApi_ | [**getAnnotation**](docs/AnnotationsApi.md#getannotation) | **GET** /annotations/{id} | Get annotation by ID (org scoped) |
| _AnnotationsApi_ | [**listAnnotations**](docs/AnnotationsApi.md#listannotations) | **GET** /annotations | List annotations (org scoped) |
| _AnnotationsApi_ | [**updateAnnotation**](docs/AnnotationsApi.md#updateannotation) | **PATCH** /annotations/{id} | Update annotation (org scoped) |
| _ArcherAdminApi_ | [**adminCancelArcherJob**](docs/ArcherAdminApi.md#admincancelarcherjob) | **POST** /admin/archer/jobs/{id}/cancel | Cancel an Archer job (admin) |
| _ArcherAdminApi_ | [**adminEnqueueArcherJob**](docs/ArcherAdminApi.md#adminenqueuearcherjob) | **POST** /admin/archer/jobs | Enqueue a new Archer job (admin) |
| _ArcherAdminApi_ | [**adminListArcherJobs**](docs/ArcherAdminApi.md#adminlistarcherjobs) | **GET** /admin/archer/jobs | List Archer jobs (admin) |
| _ArcherAdminApi_ | [**adminListArcherQueues**](docs/ArcherAdminApi.md#adminlistarcherqueues) | **GET** /admin/archer/queues | List Archer queues (admin) |
| _ArcherAdminApi_ | [**adminRetryArcherJob**](docs/ArcherAdminApi.md#adminretryarcherjob) | **POST** /admin/archer/jobs/{id}/retry | Retry a failed/canceled Archer job (admin) |
| _AuthApi_ | [**authCallback**](docs/AuthApi.md#authcallback) | **GET** /auth/{provider}/callback | Handle social login callback |
| _AuthApi_ | [**authStart**](docs/AuthApi.md#authstart) | **POST** /auth/{provider}/start | Begin social login |
| _AuthApi_ | [**getJWKS**](docs/AuthApi.md#getjwks) | **GET** /.well-known/jwks.json | Get JWKS |
| _AuthApi_ | [**logout**](docs/AuthApi.md#logout) | **POST** /auth/logout | Revoke refresh token family (logout everywhere) |
| _AuthApi_ | [**refresh**](docs/AuthApi.md#refresh) | **POST** /auth/refresh | Rotate refresh token |
| _ClustersApi_ | [**attachAppsLoadBalancer**](docs/ClustersApi.md#attachappsloadbalancer) | **POST** /clusters/{clusterID}/apps-load-balancer | Attach an apps load balancer to a cluster |
| _ClustersApi_ | [**attachBastionServer**](docs/ClustersApi.md#attachbastionserver) | **POST** /clusters/{clusterID}/bastion | Attach a bastion server to a cluster |
| _ClustersApi_ | [**attachCaptainDomain**](docs/ClustersApi.md#attachcaptaindomain) | **POST** /clusters/{clusterID}/captain-domain | Attach a captain domain to a cluster |
| _ClustersApi_ | [**attachControlPlaneRecordSet**](docs/ClustersApi.md#attachcontrolplanerecordset) | **POST** /clusters/{clusterID}/control-plane-record-set | Attach a control plane record set to a cluster |
| _ClustersApi_ | [**attachGlueOpsLoadBalancer**](docs/ClustersApi.md#attachglueopsloadbalancer) | **POST** /clusters/{clusterID}/glueops-load-balancer | Attach a GlueOps/control-plane load balancer to a cluster |
| _ClustersApi_ | [**attachNodePool**](docs/ClustersApi.md#attachnodepool) | **POST** /clusters/{clusterID}/node-pools | Attach a node pool to a cluster |
| _ClustersApi_ | [**clearClusterKubeconfig**](docs/ClustersApi.md#clearclusterkubeconfig) | **DELETE** /clusters/{clusterID}/kubeconfig | Clear the kubeconfig for a cluster |
| _ClustersApi_ | [**createCluster**](docs/ClustersApi.md#createcluster) | **POST** /clusters | Create cluster (org scoped) |
| _ClustersApi_ | [**deleteCluster**](docs/ClustersApi.md#deletecluster) | **DELETE** /clusters/{clusterID} | Delete a cluster (org scoped) |
| _ClustersApi_ | [**detachAppsLoadBalancer**](docs/ClustersApi.md#detachappsloadbalancer) | **DELETE** /clusters/{clusterID}/apps-load-balancer | Detach the apps load balancer from a cluster |
| _ClustersApi_ | [**detachBastionServer**](docs/ClustersApi.md#detachbastionserver) | **DELETE** /clusters/{clusterID}/bastion | Detach the bastion server from a cluster |
| _ClustersApi_ | [**detachCaptainDomain**](docs/ClustersApi.md#detachcaptaindomain) | **DELETE** /clusters/{clusterID}/captain-domain | Detach the captain domain from a cluster |
| _ClustersApi_ | [**detachControlPlaneRecordSet**](docs/ClustersApi.md#detachcontrolplanerecordset) | **DELETE** /clusters/{clusterID}/control-plane-record-set | Detach the control plane record set from a cluster |
| _ClustersApi_ | [**detachGlueOpsLoadBalancer**](docs/ClustersApi.md#detachglueopsloadbalancer) | **DELETE** /clusters/{clusterID}/glueops-load-balancer | Detach the GlueOps/control-plane load balancer from a cluster |
| _ClustersApi_ | [**detachNodePool**](docs/ClustersApi.md#detachnodepool) | **DELETE** /clusters/{clusterID}/node-pools/{nodePoolID} | Detach a node pool from a cluster |
| _ClustersApi_ | [**getCluster**](docs/ClustersApi.md#getcluster) | **GET** /clusters/{clusterID} | Get a single cluster by ID (org scoped) |
| _ClustersApi_ | [**listClusters**](docs/ClustersApi.md#listclusters) | **GET** /clusters | List clusters (org scoped) |
| _ClustersApi_ | [**setClusterKubeconfig**](docs/ClustersApi.md#setclusterkubeconfig) | **POST** /clusters/{clusterID}/kubeconfig | Set (or replace) the kubeconfig for a cluster |
| _ClustersApi_ | [**updateCluster**](docs/ClustersApi.md#updatecluster) | **PATCH** /clusters/{clusterID} | Update basic cluster details (org scoped) |
| _CredentialsApi_ | [**createCredential**](docs/CredentialsApi.md#createcredential) | **POST** /credentials | Create a credential (encrypts secret) |
| _CredentialsApi_ | [**deleteCredential**](docs/CredentialsApi.md#deletecredential) | **DELETE** /credentials/{id} | Delete credential |
| _CredentialsApi_ | [**getCredential**](docs/CredentialsApi.md#getcredential) | **GET** /credentials/{id} | Get credential by ID (metadata only) |
| _CredentialsApi_ | [**listCredentials**](docs/CredentialsApi.md#listcredentials) | **GET** /credentials | List credentials (metadata only) |
| _CredentialsApi_ | [**revealCredential**](docs/CredentialsApi.md#revealcredential) | **POST** /credentials/{id}/reveal | Reveal decrypted secret (one-time read) |
| _CredentialsApi_ | [**updateCredential**](docs/CredentialsApi.md#updatecredential) | **PATCH** /credentials/{id} | Update credential metadata and/or rotate secret |
| _DNSApi_ | [**createDomain**](docs/DNSApi.md#createdomain) | **POST** /dns/domains | Create a domain (org scoped) |
| _DNSApi_ | [**createRecordSet**](docs/DNSApi.md#createrecordset) | **POST** /dns/domains/{domain_id}/records | Create a record set (pending; Archer will UPSERT to Route 53) |
| _DNSApi_ | [**deleteDomain**](docs/DNSApi.md#deletedomain) | **DELETE** /dns/domains/{id} | Delete a domain |
| _DNSApi_ | [**deleteRecordSet**](docs/DNSApi.md#deleterecordset) | **DELETE** /dns/records/{id} | Delete a record set (API removes row; worker can optionally handle external deletion policy) |
| _DNSApi_ | [**getDomain**](docs/DNSApi.md#getdomain) | **GET** /dns/domains/{id} | Get a domain (org scoped) |
| _DNSApi_ | [**listDomains**](docs/DNSApi.md#listdomains) | **GET** /dns/domains | List domains (org scoped) |
| _DNSApi_ | [**listRecordSets**](docs/DNSApi.md#listrecordsets) | **GET** /dns/domains/{domain_id}/records | List record sets for a domain |
| _DNSApi_ | [**updateDomain**](docs/DNSApi.md#updatedomain) | **PATCH** /dns/domains/{id} | Update a domain (org scoped) |
| _DNSApi_ | [**updateRecordSet**](docs/DNSApi.md#updaterecordset) | **PATCH** /dns/records/{id} | Update a record set (flips to pending for reconciliation) |
| _HealthApi_ | [**healthCheckOperationId**](docs/HealthApi.md#healthcheckoperationid) | **GET** /healthz | Basic health check |
| _LabelsApi_ | [**createLabel**](docs/LabelsApi.md#createlabel) | **POST** /labels | Create label (org scoped) |
| _LabelsApi_ | [**deleteLabel**](docs/LabelsApi.md#deletelabel) | **DELETE** /labels/{id} | Delete label (org scoped) |
| _LabelsApi_ | [**getLabel**](docs/LabelsApi.md#getlabel) | **GET** /labels/{id} | Get label by ID (org scoped) |
| _LabelsApi_ | [**listLabels**](docs/LabelsApi.md#listlabels) | **GET** /labels | List node labels (org scoped) |
| _LabelsApi_ | [**updateLabel**](docs/LabelsApi.md#updatelabel) | **PATCH** /labels/{id} | Update label (org scoped) |
| _LoadBalancersApi_ | [**createLoadBalancer**](docs/LoadBalancersApi.md#createloadbalancer) | **POST** /load-balancers | Create a load balancer |
| _LoadBalancersApi_ | [**deleteLoadBalancer**](docs/LoadBalancersApi.md#deleteloadbalancer) | **DELETE** /load-balancers/{id} | Delete a load balancer |
| _LoadBalancersApi_ | [**getLoadBalancers**](docs/LoadBalancersApi.md#getloadbalancers) | **GET** /load-balancers/{id} | Get a load balancer (org scoped) |
| _LoadBalancersApi_ | [**listLoadBalancers**](docs/LoadBalancersApi.md#listloadbalancers) | **GET** /load-balancers | List load balancers (org scoped) |
| _LoadBalancersApi_ | [**updateLoadBalancer**](docs/LoadBalancersApi.md#updateloadbalancer) | **PATCH** /load-balancers/{id} | Update a load balancer (org scoped) |
| _MeApi_ | [**getMe**](docs/MeApi.md#getme) | **GET** /me | Get current user profile |
| _MeApi_ | [**updateMe**](docs/MeApi.md#updateme) | **PATCH** /me | Update current user profile |
| _MeAPIKeysApi_ | [**createUserAPIKey**](docs/MeAPIKeysApi.md#createuserapikey) | **POST** /me/api-keys | Create a new user API key |
| _MeAPIKeysApi_ | [**deleteUserAPIKey**](docs/MeAPIKeysApi.md#deleteuserapikey) | **DELETE** /me/api-keys/{id} | Delete a user API key |
| _MeAPIKeysApi_ | [**listUserAPIKeys**](docs/MeAPIKeysApi.md#listuserapikeys) | **GET** /me/api-keys | List my API keys |
| _MetaApi_ | [**versionOperationId**](docs/MetaApi.md#versionoperationid) | **GET** /version | Service version information |
| _NodePoolsApi_ | [**attachNodePoolAnnotations**](docs/NodePoolsApi.md#attachnodepoolannotations) | **POST** /node-pools/{id}/annotations | Attach annotation to a node pool (org scoped) |
| _NodePoolsApi_ | [**attachNodePoolLabels**](docs/NodePoolsApi.md#attachnodepoollabels) | **POST** /node-pools/{id}/labels | Attach labels to a node pool (org scoped) |
| _NodePoolsApi_ | [**attachNodePoolServers**](docs/NodePoolsApi.md#attachnodepoolservers) | **POST** /node-pools/{id}/servers | Attach servers to a node pool (org scoped) |
| _NodePoolsApi_ | [**attachNodePoolTaints**](docs/NodePoolsApi.md#attachnodepooltaints) | **POST** /node-pools/{id}/taints | Attach taints to a node pool (org scoped) |
| _NodePoolsApi_ | [**createNodePool**](docs/NodePoolsApi.md#createnodepool) | **POST** /node-pools | Create node pool (org scoped) |
| _NodePoolsApi_ | [**deleteNodePool**](docs/NodePoolsApi.md#deletenodepool) | **DELETE** /node-pools/{id} | Delete node pool (org scoped) |
| _NodePoolsApi_ | [**detachNodePoolAnnotation**](docs/NodePoolsApi.md#detachnodepoolannotation) | **DELETE** /node-pools/{id}/annotations/{annotationId} | Detach one annotation from a node pool (org scoped) |
| _NodePoolsApi_ | [**detachNodePoolLabel**](docs/NodePoolsApi.md#detachnodepoollabel) | **DELETE** /node-pools/{id}/labels/{labelId} | Detach one label from a node pool (org scoped) |
| _NodePoolsApi_ | [**detachNodePoolServer**](docs/NodePoolsApi.md#detachnodepoolserver) | **DELETE** /node-pools/{id}/servers/{serverId} | Detach one server from a node pool (org scoped) |
| _NodePoolsApi_ | [**detachNodePoolTaint**](docs/NodePoolsApi.md#detachnodepooltaint) | **DELETE** /node-pools/{id}/taints/{taintId} | Detach one taint from a node pool (org scoped) |
| _NodePoolsApi_ | [**getNodePool**](docs/NodePoolsApi.md#getnodepool) | **GET** /node-pools/{id} | Get node pool by ID (org scoped) |
| _NodePoolsApi_ | [**listNodePoolAnnotations**](docs/NodePoolsApi.md#listnodepoolannotations) | **GET** /node-pools/{id}/annotations | List annotations attached to a node pool (org scoped) |
| _NodePoolsApi_ | [**listNodePoolLabels**](docs/NodePoolsApi.md#listnodepoollabels) | **GET** /node-pools/{id}/labels | List labels attached to a node pool (org scoped) |
| _NodePoolsApi_ | [**listNodePoolServers**](docs/NodePoolsApi.md#listnodepoolservers) | **GET** /node-pools/{id}/servers | List servers attached to a node pool (org scoped) |
| _NodePoolsApi_ | [**listNodePoolTaints**](docs/NodePoolsApi.md#listnodepooltaints) | **GET** /node-pools/{id}/taints | List taints attached to a node pool (org scoped) |
| _NodePoolsApi_ | [**listNodePools**](docs/NodePoolsApi.md#listnodepools) | **GET** /node-pools | List node pools (org scoped) |
| _NodePoolsApi_ | [**updateNodePool**](docs/NodePoolsApi.md#updatenodepool) | **PATCH** /node-pools/{id} | Update node pool (org scoped) |
| _OrgsApi_ | [**addOrUpdateMember**](docs/OrgsApi.md#addorupdatemember) | **POST** /orgs/{id}/members | Add or update a member (owner/admin) |
| _OrgsApi_ | [**createOrg**](docs/OrgsApi.md#createorg) | **POST** /orgs | Create organization |
| _OrgsApi_ | [**createOrgKey**](docs/OrgsApi.md#createorgkey) | **POST** /orgs/{id}/api-keys | Create org key/secret pair (owner/admin) |
| _OrgsApi_ | [**deleteOrg**](docs/OrgsApi.md#deleteorg) | **DELETE** /orgs/{id} | Delete organization (owner) |
| _OrgsApi_ | [**deleteOrgKey**](docs/OrgsApi.md#deleteorgkey) | **DELETE** /orgs/{id}/api-keys/{key_id} | Delete org key (owner/admin) |
| _OrgsApi_ | [**getOrg**](docs/OrgsApi.md#getorg) | **GET** /orgs/{id} | Get organization |
| _OrgsApi_ | [**listMembers**](docs/OrgsApi.md#listmembers) | **GET** /orgs/{id}/members | List members in org |
| _OrgsApi_ | [**listMyOrgs**](docs/OrgsApi.md#listmyorgs) | **GET** /orgs | List organizations I belong to |
| _OrgsApi_ | [**listOrgKeys**](docs/OrgsApi.md#listorgkeys) | **GET** /orgs/{id}/api-keys | List org-scoped API keys (no secrets) |
| _OrgsApi_ | [**removeMember**](docs/OrgsApi.md#removemember) | **DELETE** /orgs/{id}/members/{user_id} | Remove a member (owner/admin) |
| _OrgsApi_ | [**updateOrg**](docs/OrgsApi.md#updateorg) | **PATCH** /orgs/{id} | Update organization (owner/admin) |
| _ServersApi_ | [**createServer**](docs/ServersApi.md#createserver) | **POST** /servers | Create server (org scoped) |
| _ServersApi_ | [**deleteServer**](docs/ServersApi.md#deleteserver) | **DELETE** /servers/{id} | Delete server (org scoped) |
| _ServersApi_ | [**getServer**](docs/ServersApi.md#getserver) | **GET** /servers/{id} | Get server by ID (org scoped) |
| _ServersApi_ | [**listServers**](docs/ServersApi.md#listservers) | **GET** /servers | List servers (org scoped) |
| _ServersApi_ | [**resetServerHostKey**](docs/ServersApi.md#resetserverhostkey) | **POST** /servers/{id}/reset-hostkey | Reset SSH host key (org scoped) |
| _ServersApi_ | [**updateServer**](docs/ServersApi.md#updateserver) | **PATCH** /servers/{id} | Update server (org scoped) |
| _SshApi_ | [**createSSHKey**](docs/SshApi.md#createsshkey) | **POST** /ssh | Create ssh keypair (org scoped) |
| _SshApi_ | [**deleteSSHKey**](docs/SshApi.md#deletesshkey) | **DELETE** /ssh/{id} | Delete ssh keypair (org scoped) |
| _SshApi_ | [**downloadSSHKey**](docs/SshApi.md#downloadsshkey) | **GET** /ssh/{id}/download | Download ssh key files by ID (org scoped) |
| _SshApi_ | [**getSSHKey**](docs/SshApi.md#getsshkey) | **GET** /ssh/{id} | Get ssh key by ID (org scoped) |
| _SshApi_ | [**listPublicSshKeys**](docs/SshApi.md#listpublicsshkeys) | **GET** /ssh | List ssh keys (org scoped) |
| _TaintsApi_ | [**createTaint**](docs/TaintsApi.md#createtaint) | **POST** /taints | Create node taint (org scoped) |
| _TaintsApi_ | [**deleteTaint**](docs/TaintsApi.md#deletetaint) | **DELETE** /taints/{id} | Delete taint (org scoped) |
| _TaintsApi_ | [**getTaint**](docs/TaintsApi.md#gettaint) | **GET** /taints/{id} | Get node taint by ID (org scoped) |
| _TaintsApi_ | [**listTaints**](docs/TaintsApi.md#listtaints) | **GET** /taints | List node pool taints (org scoped) |
| _TaintsApi_ | [**updateTaint**](docs/TaintsApi.md#updatetaint) | **PATCH** /taints/{id} | Update node taint (org scoped) |
### Models
- [DtoAnnotationResponse](docs/DtoAnnotationResponse.md)
- [DtoAttachAnnotationsRequest](docs/DtoAttachAnnotationsRequest.md)
- [DtoAttachBastionRequest](docs/DtoAttachBastionRequest.md)
- [DtoAttachCaptainDomainRequest](docs/DtoAttachCaptainDomainRequest.md)
- [DtoAttachLabelsRequest](docs/DtoAttachLabelsRequest.md)
- [DtoAttachLoadBalancerRequest](docs/DtoAttachLoadBalancerRequest.md)
- [DtoAttachNodePoolRequest](docs/DtoAttachNodePoolRequest.md)
- [DtoAttachRecordSetRequest](docs/DtoAttachRecordSetRequest.md)
- [DtoAttachServersRequest](docs/DtoAttachServersRequest.md)
- [DtoAttachTaintsRequest](docs/DtoAttachTaintsRequest.md)
- [DtoAuthStartResponse](docs/DtoAuthStartResponse.md)
- [DtoClusterResponse](docs/DtoClusterResponse.md)
- [DtoCreateAnnotationRequest](docs/DtoCreateAnnotationRequest.md)
- [DtoCreateClusterRequest](docs/DtoCreateClusterRequest.md)
- [DtoCreateCredentialRequest](docs/DtoCreateCredentialRequest.md)
- [DtoCreateDomainRequest](docs/DtoCreateDomainRequest.md)
- [DtoCreateLabelRequest](docs/DtoCreateLabelRequest.md)
- [DtoCreateLoadBalancerRequest](docs/DtoCreateLoadBalancerRequest.md)
- [DtoCreateNodePoolRequest](docs/DtoCreateNodePoolRequest.md)
- [DtoCreateRecordSetRequest](docs/DtoCreateRecordSetRequest.md)
- [DtoCreateSSHRequest](docs/DtoCreateSSHRequest.md)
- [DtoCreateServerRequest](docs/DtoCreateServerRequest.md)
- [DtoCreateTaintRequest](docs/DtoCreateTaintRequest.md)
- [DtoCredentialOut](docs/DtoCredentialOut.md)
- [DtoDomainResponse](docs/DtoDomainResponse.md)
- [DtoEnqueueRequest](docs/DtoEnqueueRequest.md)
- [DtoJWK](docs/DtoJWK.md)
- [DtoJWKS](docs/DtoJWKS.md)
- [DtoJob](docs/DtoJob.md)
- [DtoJobStatus](docs/DtoJobStatus.md)
- [DtoLabelResponse](docs/DtoLabelResponse.md)
- [DtoLoadBalancerResponse](docs/DtoLoadBalancerResponse.md)
- [DtoLogoutRequest](docs/DtoLogoutRequest.md)
- [DtoNodePoolResponse](docs/DtoNodePoolResponse.md)
- [DtoPageJob](docs/DtoPageJob.md)
- [DtoQueueInfo](docs/DtoQueueInfo.md)
- [DtoRecordSetResponse](docs/DtoRecordSetResponse.md)
- [DtoRefreshRequest](docs/DtoRefreshRequest.md)
- [DtoServerResponse](docs/DtoServerResponse.md)
- [DtoSetKubeconfigRequest](docs/DtoSetKubeconfigRequest.md)
- [DtoSshResponse](docs/DtoSshResponse.md)
- [DtoSshRevealResponse](docs/DtoSshRevealResponse.md)
- [DtoTaintResponse](docs/DtoTaintResponse.md)
- [DtoTokenPair](docs/DtoTokenPair.md)
- [DtoUpdateAnnotationRequest](docs/DtoUpdateAnnotationRequest.md)
- [DtoUpdateClusterRequest](docs/DtoUpdateClusterRequest.md)
- [DtoUpdateCredentialRequest](docs/DtoUpdateCredentialRequest.md)
- [DtoUpdateDomainRequest](docs/DtoUpdateDomainRequest.md)
- [DtoUpdateLabelRequest](docs/DtoUpdateLabelRequest.md)
- [DtoUpdateLoadBalancerRequest](docs/DtoUpdateLoadBalancerRequest.md)
- [DtoUpdateNodePoolRequest](docs/DtoUpdateNodePoolRequest.md)
- [DtoUpdateRecordSetRequest](docs/DtoUpdateRecordSetRequest.md)
- [DtoUpdateServerRequest](docs/DtoUpdateServerRequest.md)
- [DtoUpdateTaintRequest](docs/DtoUpdateTaintRequest.md)
- [GetSSHKey200Response](docs/GetSSHKey200Response.md)
- [HandlersCreateUserKeyRequest](docs/HandlersCreateUserKeyRequest.md)
- [HandlersHealthStatus](docs/HandlersHealthStatus.md)
- [HandlersMeResponse](docs/HandlersMeResponse.md)
- [HandlersMemberOut](docs/HandlersMemberOut.md)
- [HandlersMemberUpsertReq](docs/HandlersMemberUpsertReq.md)
- [HandlersOrgCreateReq](docs/HandlersOrgCreateReq.md)
- [HandlersOrgKeyCreateReq](docs/HandlersOrgKeyCreateReq.md)
- [HandlersOrgKeyCreateResp](docs/HandlersOrgKeyCreateResp.md)
- [HandlersOrgUpdateReq](docs/HandlersOrgUpdateReq.md)
- [HandlersUpdateMeRequest](docs/HandlersUpdateMeRequest.md)
- [HandlersUserAPIKeyOut](docs/HandlersUserAPIKeyOut.md)
- [HandlersVersionResponse](docs/HandlersVersionResponse.md)
- [ModelsAPIKey](docs/ModelsAPIKey.md)
- [ModelsOrganization](docs/ModelsOrganization.md)
- [ModelsUser](docs/ModelsUser.md)
- [ModelsUserEmail](docs/ModelsUserEmail.md)
- [UtilsErrorResponse](docs/UtilsErrorResponse.md)
### Authorization
Authentication schemes defined for the API:
<a id="ApiKeyAuth"></a>
#### ApiKeyAuth
- **Type**: API key
- **API key parameter name**: `X-API-KEY`
- **Location**: HTTP header
<a id="BearerAuth"></a>
#### BearerAuth
- **Type**: API key
- **API key parameter name**: `Authorization`
- **Location**: HTTP header
<a id="OrgKeyAuth"></a>
#### OrgKeyAuth
- **Type**: API key
- **API key parameter name**: `X-ORG-KEY`
- **Location**: HTTP header
<a id="OrgSecretAuth"></a>
#### OrgSecretAuth
- **Type**: API key
- **API key parameter name**: `X-ORG-SECRET`
- **Location**: HTTP header
## About
This TypeScript SDK client supports the [Fetch API](https://fetch.spec.whatwg.org/)
and is automatically generated by the
[OpenAPI Generator](https://openapi-generator.tech) project:
- API version: `dev`
- Package version: `0.1.0`
- Generator version: `7.17.0`
- Build package: `org.openapitools.codegen.languages.TypeScriptFetchClientCodegen`
The generated npm module supports the following:
- Environments
- Node.js
- Webpack
- Browserify
- Language levels
- ES5 - you must have a Promises/A+ library installed
- ES6
- Module systems
- CommonJS
- ES6 module system
## Development
### Building
To build the TypeScript source code, you need to have Node.js and npm installed.
After cloning the repository, navigate to the project directory and run:
```bash
npm install
npm run build
```
### Publishing
Once you've built the package, you can publish it to npm:
```bash
npm publish
```
## License
[]()

View File

@@ -0,0 +1,412 @@
# AnnotationsApi
All URIs are relative to *https://autoglue.glueopshosted.com/api/v1*
| Method | HTTP request | Description |
| ---------------------------------------------------------- | ---------------------------- | --------------------------------- |
| [**createAnnotation**](AnnotationsApi.md#createannotation) | **POST** /annotations | Create annotation (org scoped) |
| [**deleteAnnotation**](AnnotationsApi.md#deleteannotation) | **DELETE** /annotations/{id} | Delete annotation (org scoped) |
| [**getAnnotation**](AnnotationsApi.md#getannotation) | **GET** /annotations/{id} | Get annotation by ID (org scoped) |
| [**listAnnotations**](AnnotationsApi.md#listannotations) | **GET** /annotations | List annotations (org scoped) |
| [**updateAnnotation**](AnnotationsApi.md#updateannotation) | **PATCH** /annotations/{id} | Update annotation (org scoped) |
## createAnnotation
> DtoAnnotationResponse createAnnotation(dtoCreateAnnotationRequest, xOrgID)
Create annotation (org scoped)
Creates an annotation.
### Example
```ts
import {
Configuration,
AnnotationsApi,
} from '@glueops/autoglue-sdk-go';
import type { CreateAnnotationRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new AnnotationsApi(config);
const body = {
// DtoCreateAnnotationRequest | Annotation payload
dtoCreateAnnotationRequest: ...,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies CreateAnnotationRequest;
try {
const data = await api.createAnnotation(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ------------------------------ | ----------------------------------------------------------- | ------------------ | ------------------------------------ |
| **dtoCreateAnnotationRequest** | [DtoCreateAnnotationRequest](DtoCreateAnnotationRequest.md) | Annotation payload | |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoAnnotationResponse**](DtoAnnotationResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ----------------------------- | ---------------- |
| **201** | Created | - |
| **400** | invalid json / missing fields | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **500** | create failed | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## deleteAnnotation
> deleteAnnotation(id, xOrgID)
Delete annotation (org scoped)
Permanently deletes the annotation.
### Example
```ts
import { Configuration, AnnotationsApi } from "@glueops/autoglue-sdk-go";
import type { DeleteAnnotationRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new AnnotationsApi(config);
const body = {
// string | Annotation ID (UUID)
id: id_example,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies DeleteAnnotationRequest;
try {
const data = await api.deleteAnnotation(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------- | -------- | -------------------- | ------------------------------------ |
| **id** | `string` | Annotation ID (UUID) | [Defaults to `undefined`] |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
`void` (Empty response body)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **204** | No Content | - |
| **400** | invalid id | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **500** | delete failed | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## getAnnotation
> DtoAnnotationResponse getAnnotation(id, xOrgID)
Get annotation by ID (org scoped)
Returns one annotation. Add &#x60;include&#x3D;node_pools&#x60; to include node pools.
### Example
```ts
import { Configuration, AnnotationsApi } from "@glueops/autoglue-sdk-go";
import type { GetAnnotationRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new AnnotationsApi(config);
const body = {
// string | Annotation ID (UUID)
id: id_example,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies GetAnnotationRequest;
try {
const data = await api.getAnnotation(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------- | -------- | -------------------- | ------------------------------------ |
| **id** | `string` | Annotation ID (UUID) | [Defaults to `undefined`] |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoAnnotationResponse**](DtoAnnotationResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **200** | OK | - |
| **400** | invalid id | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **404** | not found | - |
| **500** | fetch failed | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## listAnnotations
> Array&lt;DtoAnnotationResponse&gt; listAnnotations(xOrgID, key, value, q)
List annotations (org scoped)
Returns annotations for the organization in X-Org-ID. Filters: &#x60;key&#x60;, &#x60;value&#x60;, and &#x60;q&#x60; (key contains). Add &#x60;include&#x3D;node_pools&#x60; to include linked node pools.
### Example
```ts
import { Configuration, AnnotationsApi } from "@glueops/autoglue-sdk-go";
import type { ListAnnotationsRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new AnnotationsApi(config);
const body = {
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
// string | Exact key (optional)
key: key_example,
// string | Exact value (optional)
value: value_example,
// string | key contains (case-insensitive) (optional)
q: q_example,
} satisfies ListAnnotationsRequest;
try {
const data = await api.listAnnotations(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------- | -------- | ------------------------------- | ------------------------------------ |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
| **key** | `string` | Exact key | [Optional] [Defaults to `undefined`] |
| **value** | `string` | Exact value | [Optional] [Defaults to `undefined`] |
| **q** | `string` | key contains (case-insensitive) | [Optional] [Defaults to `undefined`] |
### Return type
[**Array&lt;DtoAnnotationResponse&gt;**](DtoAnnotationResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | -------------------------- | ---------------- |
| **200** | OK | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **500** | failed to list annotations | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## updateAnnotation
> DtoAnnotationResponse updateAnnotation(id, dtoUpdateAnnotationRequest, xOrgID)
Update annotation (org scoped)
Partially update annotation fields.
### Example
```ts
import {
Configuration,
AnnotationsApi,
} from '@glueops/autoglue-sdk-go';
import type { UpdateAnnotationRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new AnnotationsApi(config);
const body = {
// string | Annotation ID (UUID)
id: id_example,
// DtoUpdateAnnotationRequest | Fields to update
dtoUpdateAnnotationRequest: ...,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies UpdateAnnotationRequest;
try {
const data = await api.updateAnnotation(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ------------------------------ | ----------------------------------------------------------- | -------------------- | ------------------------------------ |
| **id** | `string` | Annotation ID (UUID) | [Defaults to `undefined`] |
| **dtoUpdateAnnotationRequest** | [DtoUpdateAnnotationRequest](DtoUpdateAnnotationRequest.md) | Fields to update | |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoAnnotationResponse**](DtoAnnotationResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ------------------------- | ---------------- |
| **200** | OK | - |
| **400** | invalid id / invalid json | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **404** | not found | - |
| **500** | update failed | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,373 @@
# ArcherAdminApi
All URIs are relative to *https://autoglue.glueopshosted.com/api/v1*
| Method | HTTP request | Description |
| -------------------------------------------------------------------- | --------------------------------------- | ------------------------------------------ |
| [**adminCancelArcherJob**](ArcherAdminApi.md#admincancelarcherjob) | **POST** /admin/archer/jobs/{id}/cancel | Cancel an Archer job (admin) |
| [**adminEnqueueArcherJob**](ArcherAdminApi.md#adminenqueuearcherjob) | **POST** /admin/archer/jobs | Enqueue a new Archer job (admin) |
| [**adminListArcherJobs**](ArcherAdminApi.md#adminlistarcherjobs) | **GET** /admin/archer/jobs | List Archer jobs (admin) |
| [**adminListArcherQueues**](ArcherAdminApi.md#adminlistarcherqueues) | **GET** /admin/archer/queues | List Archer queues (admin) |
| [**adminRetryArcherJob**](ArcherAdminApi.md#adminretryarcherjob) | **POST** /admin/archer/jobs/{id}/retry | Retry a failed/canceled Archer job (admin) |
## adminCancelArcherJob
> DtoJob adminCancelArcherJob(id, body)
Cancel an Archer job (admin)
Set job status to canceled if cancellable. For running jobs, this only affects future picks; wire to Archer if you need active kill.
### Example
```ts
import { Configuration, ArcherAdminApi } from "@glueops/autoglue-sdk-go";
import type { AdminCancelArcherJobRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new ArcherAdminApi(config);
const body = {
// string | Job ID
id: id_example,
// object (optional)
body: Object,
} satisfies AdminCancelArcherJobRequest;
try {
const data = await api.adminCancelArcherJob(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| -------- | -------- | ----------- | ------------------------- |
| **id** | `string` | Job ID | [Defaults to `undefined`] |
| **body** | `object` | | [Optional] |
### Return type
[**DtoJob**](DtoJob.md)
### Authorization
[BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ------------------------------ | ---------------- |
| **200** | OK | - |
| **400** | invalid job or not cancellable | - |
| **401** | Unauthorized | - |
| **403** | forbidden | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## adminEnqueueArcherJob
> DtoJob adminEnqueueArcherJob(dtoEnqueueRequest)
Enqueue a new Archer job (admin)
Create a job immediately or schedule it for the future via &#x60;run_at&#x60;.
### Example
```ts
import {
Configuration,
ArcherAdminApi,
} from '@glueops/autoglue-sdk-go';
import type { AdminEnqueueArcherJobRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new ArcherAdminApi(config);
const body = {
// DtoEnqueueRequest | Job parameters
dtoEnqueueRequest: ...,
} satisfies AdminEnqueueArcherJobRequest;
try {
const data = await api.adminEnqueueArcherJob(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| --------------------- | ----------------------------------------- | -------------- | ----- |
| **dtoEnqueueRequest** | [DtoEnqueueRequest](DtoEnqueueRequest.md) | Job parameters | |
### Return type
[**DtoJob**](DtoJob.md)
### Authorization
[BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ------------------------------ | ---------------- |
| **200** | OK | - |
| **400** | invalid json or missing fields | - |
| **401** | Unauthorized | - |
| **403** | forbidden | - |
| **500** | internal error | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## adminListArcherJobs
> DtoPageJob adminListArcherJobs(status, queue, q, page, pageSize)
List Archer jobs (admin)
Paginated background jobs with optional filters. Search &#x60;q&#x60; may match id, type, error, payload (implementation-dependent).
### Example
```ts
import { Configuration, ArcherAdminApi } from "@glueops/autoglue-sdk-go";
import type { AdminListArcherJobsRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new ArcherAdminApi(config);
const body = {
// 'queued' | 'running' | 'succeeded' | 'failed' | 'canceled' | 'retrying' | 'scheduled' | Filter by status (optional)
status: status_example,
// string | Filter by queue name / worker name (optional)
queue: queue_example,
// string | Free-text search (optional)
q: q_example,
// number | Page number (optional)
page: 56,
// number | Items per page (optional)
pageSize: 56,
} satisfies AdminListArcherJobsRequest;
try {
const data = await api.adminListArcherJobs(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ------------ | ------------------------------------------------------------------------------- | ---------------------------------- | -------------------------------------------------------------------------------------------------------------- |
| **status** | `queued`, `running`, `succeeded`, `failed`, `canceled`, `retrying`, `scheduled` | Filter by status | [Optional] [Defaults to `undefined`] [Enum: queued, running, succeeded, failed, canceled, retrying, scheduled] |
| **queue** | `string` | Filter by queue name / worker name | [Optional] [Defaults to `undefined`] |
| **q** | `string` | Free-text search | [Optional] [Defaults to `undefined`] |
| **page** | `number` | Page number | [Optional] [Defaults to `1`] |
| **pageSize** | `number` | Items per page | [Optional] [Defaults to `25`] |
### Return type
[**DtoPageJob**](DtoPageJob.md)
### Authorization
[BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | -------------- | ---------------- |
| **200** | OK | - |
| **401** | Unauthorized | - |
| **403** | forbidden | - |
| **500** | internal error | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## adminListArcherQueues
> Array&lt;DtoQueueInfo&gt; adminListArcherQueues()
List Archer queues (admin)
Summary metrics per queue (pending, running, failed, scheduled).
### Example
```ts
import { Configuration, ArcherAdminApi } from "@glueops/autoglue-sdk-go";
import type { AdminListArcherQueuesRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new ArcherAdminApi(config);
try {
const data = await api.adminListArcherQueues();
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
This endpoint does not need any parameter.
### Return type
[**Array&lt;DtoQueueInfo&gt;**](DtoQueueInfo.md)
### Authorization
[BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | -------------- | ---------------- |
| **200** | OK | - |
| **401** | Unauthorized | - |
| **403** | forbidden | - |
| **500** | internal error | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## adminRetryArcherJob
> DtoJob adminRetryArcherJob(id, body)
Retry a failed/canceled Archer job (admin)
Marks the job retriable (DB flip). Swap this for an Archer admin call if you expose one.
### Example
```ts
import { Configuration, ArcherAdminApi } from "@glueops/autoglue-sdk-go";
import type { AdminRetryArcherJobRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new ArcherAdminApi(config);
const body = {
// string | Job ID
id: id_example,
// object (optional)
body: Object,
} satisfies AdminRetryArcherJobRequest;
try {
const data = await api.adminRetryArcherJob(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| -------- | -------- | ----------- | ------------------------- |
| **id** | `string` | Job ID | [Defaults to `undefined`] |
| **body** | `object` | | [Optional] |
### Return type
[**DtoJob**](DtoJob.md)
### Authorization
[BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------------- | ---------------- |
| **200** | OK | - |
| **400** | invalid job or not eligible | - |
| **401** | Unauthorized | - |
| **403** | forbidden | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

314
sdk/ts/docs/AuthApi.md Normal file
View File

@@ -0,0 +1,314 @@
# AuthApi
All URIs are relative to *https://autoglue.glueopshosted.com/api/v1*
| Method | HTTP request | Description |
| ------------------------------------------- | --------------------------------- | ----------------------------------------------- |
| [**authCallback**](AuthApi.md#authcallback) | **GET** /auth/{provider}/callback | Handle social login callback |
| [**authStart**](AuthApi.md#authstart) | **POST** /auth/{provider}/start | Begin social login |
| [**getJWKS**](AuthApi.md#getjwks) | **GET** /.well-known/jwks.json | Get JWKS |
| [**logout**](AuthApi.md#logout) | **POST** /auth/logout | Revoke refresh token family (logout everywhere) |
| [**refresh**](AuthApi.md#refresh) | **POST** /auth/refresh | Rotate refresh token |
## authCallback
> DtoTokenPair authCallback(provider)
Handle social login callback
### Example
```ts
import { Configuration, AuthApi } from "@glueops/autoglue-sdk-go";
import type { AuthCallbackRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const api = new AuthApi();
const body = {
// string | google|github
provider: provider_example,
} satisfies AuthCallbackRequest;
try {
const data = await api.authCallback(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ------------ | -------- | ----------- | ------ | ------------------------- |
| **provider** | `string` | google | github | [Defaults to `undefined`] |
### Return type
[**DtoTokenPair**](DtoTokenPair.md)
### Authorization
No authorization required
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ----------- | ---------------- |
| **200** | OK | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## authStart
> DtoAuthStartResponse authStart(provider)
Begin social login
Returns provider authorization URL for the frontend to redirect
### Example
```ts
import { Configuration, AuthApi } from "@glueops/autoglue-sdk-go";
import type { AuthStartRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const api = new AuthApi();
const body = {
// string | google|github
provider: provider_example,
} satisfies AuthStartRequest;
try {
const data = await api.authStart(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ------------ | -------- | ----------- | ------ | ------------------------- |
| **provider** | `string` | google | github | [Defaults to `undefined`] |
### Return type
[**DtoAuthStartResponse**](DtoAuthStartResponse.md)
### Authorization
No authorization required
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ----------- | ---------------- |
| **200** | OK | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## getJWKS
> DtoJWKS getJWKS()
Get JWKS
Returns the JSON Web Key Set for token verification
### Example
```ts
import { Configuration, AuthApi } from "@glueops/autoglue-sdk-go";
import type { GetJWKSRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const api = new AuthApi();
try {
const data = await api.getJWKS();
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
This endpoint does not need any parameter.
### Return type
[**DtoJWKS**](DtoJWKS.md)
### Authorization
No authorization required
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ----------- | ---------------- |
| **200** | OK | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## logout
> logout(dtoLogoutRequest)
Revoke refresh token family (logout everywhere)
### Example
```ts
import {
Configuration,
AuthApi,
} from '@glueops/autoglue-sdk-go';
import type { LogoutRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const api = new AuthApi();
const body = {
// DtoLogoutRequest | Refresh token
dtoLogoutRequest: ...,
} satisfies LogoutRequest;
try {
const data = await api.logout(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| -------------------- | --------------------------------------- | ------------- | ----- |
| **dtoLogoutRequest** | [DtoLogoutRequest](DtoLogoutRequest.md) | Refresh token | |
### Return type
`void` (Empty response body)
### Authorization
No authorization required
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: Not defined
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ----------- | ---------------- |
| **204** | No Content | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## refresh
> DtoTokenPair refresh(dtoRefreshRequest)
Rotate refresh token
### Example
```ts
import {
Configuration,
AuthApi,
} from '@glueops/autoglue-sdk-go';
import type { RefreshRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const api = new AuthApi();
const body = {
// DtoRefreshRequest | Refresh token
dtoRefreshRequest: ...,
} satisfies RefreshRequest;
try {
const data = await api.refresh(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| --------------------- | ----------------------------------------- | ------------- | ----- |
| **dtoRefreshRequest** | [DtoRefreshRequest](DtoRefreshRequest.md) | Refresh token | |
### Return type
[**DtoTokenPair**](DtoTokenPair.md)
### Authorization
No authorization required
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ----------- | ---------------- |
| **200** | OK | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

1558
sdk/ts/docs/ClustersApi.md Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,472 @@
# CredentialsApi
All URIs are relative to *https://autoglue.glueopshosted.com/api/v1*
| Method | HTTP request | Description |
| ---------------------------------------------------------- | --------------------------------- | ----------------------------------------------- |
| [**createCredential**](CredentialsApi.md#createcredential) | **POST** /credentials | Create a credential (encrypts secret) |
| [**deleteCredential**](CredentialsApi.md#deletecredential) | **DELETE** /credentials/{id} | Delete credential |
| [**getCredential**](CredentialsApi.md#getcredential) | **GET** /credentials/{id} | Get credential by ID (metadata only) |
| [**listCredentials**](CredentialsApi.md#listcredentials) | **GET** /credentials | List credentials (metadata only) |
| [**revealCredential**](CredentialsApi.md#revealcredential) | **POST** /credentials/{id}/reveal | Reveal decrypted secret (one-time read) |
| [**updateCredential**](CredentialsApi.md#updatecredential) | **PATCH** /credentials/{id} | Update credential metadata and/or rotate secret |
## createCredential
> DtoCredentialOut createCredential(dtoCreateCredentialRequest, xOrgID)
Create a credential (encrypts secret)
### Example
```ts
import {
Configuration,
CredentialsApi,
} from '@glueops/autoglue-sdk-go';
import type { CreateCredentialRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new CredentialsApi(config);
const body = {
// DtoCreateCredentialRequest | Credential payload
dtoCreateCredentialRequest: ...,
// string | Organization ID (UUID) (optional)
xOrgID: xOrgID_example,
} satisfies CreateCredentialRequest;
try {
const data = await api.createCredential(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ------------------------------ | ----------------------------------------------------------- | ---------------------- | ------------------------------------ |
| **dtoCreateCredentialRequest** | [DtoCreateCredentialRequest](DtoCreateCredentialRequest.md) | Credential payload | |
| **xOrgID** | `string` | Organization ID (UUID) | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoCredentialOut**](DtoCredentialOut.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **201** | Created | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **500** | internal server error | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## deleteCredential
> deleteCredential(id, xOrgID)
Delete credential
### Example
```ts
import { Configuration, CredentialsApi } from "@glueops/autoglue-sdk-go";
import type { DeleteCredentialRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new CredentialsApi(config);
const body = {
// string | Credential ID (UUID)
id: id_example,
// string | Organization ID (UUID) (optional)
xOrgID: xOrgID_example,
} satisfies DeleteCredentialRequest;
try {
const data = await api.deleteCredential(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------- | -------- | ---------------------- | ------------------------------------ |
| **id** | `string` | Credential ID (UUID) | [Defaults to `undefined`] |
| **xOrgID** | `string` | Organization ID (UUID) | [Optional] [Defaults to `undefined`] |
### Return type
`void` (Empty response body)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ----------- | ---------------- |
| **204** | No Content | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## getCredential
> DtoCredentialOut getCredential(id, xOrgID)
Get credential by ID (metadata only)
### Example
```ts
import { Configuration, CredentialsApi } from "@glueops/autoglue-sdk-go";
import type { GetCredentialRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new CredentialsApi(config);
const body = {
// string | Credential ID (UUID)
id: id_example,
// string | Organization ID (UUID) (optional)
xOrgID: xOrgID_example,
} satisfies GetCredentialRequest;
try {
const data = await api.getCredential(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------- | -------- | ---------------------- | ------------------------------------ |
| **id** | `string` | Credential ID (UUID) | [Defaults to `undefined`] |
| **xOrgID** | `string` | Organization ID (UUID) | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoCredentialOut**](DtoCredentialOut.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **200** | OK | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **500** | internal server error | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## listCredentials
> Array&lt;DtoCredentialOut&gt; listCredentials(xOrgID, credentialProvider, kind, scopeKind)
List credentials (metadata only)
Returns credential metadata for the current org. Secrets are never returned.
### Example
```ts
import { Configuration, CredentialsApi } from "@glueops/autoglue-sdk-go";
import type { ListCredentialsRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new CredentialsApi(config);
const body = {
// string | Organization ID (UUID) (optional)
xOrgID: xOrgID_example,
// string | Filter by provider (e.g., aws) (optional)
credentialProvider: credentialProvider_example,
// string | Filter by kind (e.g., aws_access_key) (optional)
kind: kind_example,
// string | Filter by scope kind (credential_provider/service/resource) (optional)
scopeKind: scopeKind_example,
} satisfies ListCredentialsRequest;
try {
const data = await api.listCredentials(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------------------- | -------- | ----------------------------------------------------------- | ------------------------------------ |
| **xOrgID** | `string` | Organization ID (UUID) | [Optional] [Defaults to `undefined`] |
| **credentialProvider** | `string` | Filter by provider (e.g., aws) | [Optional] [Defaults to `undefined`] |
| **kind** | `string` | Filter by kind (e.g., aws_access_key) | [Optional] [Defaults to `undefined`] |
| **scopeKind** | `string` | Filter by scope kind (credential_provider/service/resource) | [Optional] [Defaults to `undefined`] |
### Return type
[**Array&lt;DtoCredentialOut&gt;**](DtoCredentialOut.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **200** | OK | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **500** | internal server error | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## revealCredential
> { [key: string]: any; } revealCredential(id, xOrgID, body)
Reveal decrypted secret (one-time read)
### Example
```ts
import { Configuration, CredentialsApi } from "@glueops/autoglue-sdk-go";
import type { RevealCredentialRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new CredentialsApi(config);
const body = {
// string | Credential ID (UUID)
id: id_example,
// string | Organization ID (UUID) (optional)
xOrgID: xOrgID_example,
// object (optional)
body: Object,
} satisfies RevealCredentialRequest;
try {
const data = await api.revealCredential(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------- | -------- | ---------------------- | ------------------------------------ |
| **id** | `string` | Credential ID (UUID) | [Defaults to `undefined`] |
| **xOrgID** | `string` | Organization ID (UUID) | [Optional] [Defaults to `undefined`] |
| **body** | `object` | | [Optional] |
### Return type
**{ [key: string]: any; }**
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **200** | OK | - |
| **403** | organization required | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## updateCredential
> DtoCredentialOut updateCredential(id, dtoUpdateCredentialRequest, xOrgID)
Update credential metadata and/or rotate secret
### Example
```ts
import {
Configuration,
CredentialsApi,
} from '@glueops/autoglue-sdk-go';
import type { UpdateCredentialRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new CredentialsApi(config);
const body = {
// string | Credential ID (UUID)
id: id_example,
// DtoUpdateCredentialRequest | Fields to update
dtoUpdateCredentialRequest: ...,
// string | Organization ID (UUID) (optional)
xOrgID: xOrgID_example,
} satisfies UpdateCredentialRequest;
try {
const data = await api.updateCredential(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ------------------------------ | ----------------------------------------------------------- | ---------------------- | ------------------------------------ |
| **id** | `string` | Credential ID (UUID) | [Defaults to `undefined`] |
| **dtoUpdateCredentialRequest** | [DtoUpdateCredentialRequest](DtoUpdateCredentialRequest.md) | Fields to update | |
| **xOrgID** | `string` | Organization ID (UUID) | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoCredentialOut**](DtoCredentialOut.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | ----------------- | ---------------- |
| **200** | OK | - |
| **403** | X-Org-ID required | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

721
sdk/ts/docs/DNSApi.md Normal file
View File

@@ -0,0 +1,721 @@
# DNSApi
All URIs are relative to *https://autoglue.glueopshosted.com/api/v1*
| Method | HTTP request | Description |
| ------------------------------------------------ | ----------------------------------------- | -------------------------------------------------------------------------------------------- |
| [**createDomain**](DNSApi.md#createdomain) | **POST** /dns/domains | Create a domain (org scoped) |
| [**createRecordSet**](DNSApi.md#createrecordset) | **POST** /dns/domains/{domain_id}/records | Create a record set (pending; Archer will UPSERT to Route 53) |
| [**deleteDomain**](DNSApi.md#deletedomain) | **DELETE** /dns/domains/{id} | Delete a domain |
| [**deleteRecordSet**](DNSApi.md#deleterecordset) | **DELETE** /dns/records/{id} | Delete a record set (API removes row; worker can optionally handle external deletion policy) |
| [**getDomain**](DNSApi.md#getdomain) | **GET** /dns/domains/{id} | Get a domain (org scoped) |
| [**listDomains**](DNSApi.md#listdomains) | **GET** /dns/domains | List domains (org scoped) |
| [**listRecordSets**](DNSApi.md#listrecordsets) | **GET** /dns/domains/{domain_id}/records | List record sets for a domain |
| [**updateDomain**](DNSApi.md#updatedomain) | **PATCH** /dns/domains/{id} | Update a domain (org scoped) |
| [**updateRecordSet**](DNSApi.md#updaterecordset) | **PATCH** /dns/records/{id} | Update a record set (flips to pending for reconciliation) |
## createDomain
> DtoDomainResponse createDomain(dtoCreateDomainRequest, xOrgID)
Create a domain (org scoped)
Creates a domain bound to a Route 53 scoped credential. Archer will backfill ZoneID if omitted.
### Example
```ts
import {
Configuration,
DNSApi,
} from '@glueops/autoglue-sdk-go';
import type { CreateDomainRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new DNSApi(config);
const body = {
// DtoCreateDomainRequest | Domain payload
dtoCreateDomainRequest: ...,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies CreateDomainRequest;
try {
const data = await api.createDomain(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| -------------------------- | --------------------------------------------------- | ----------------- | ------------------------------------ |
| **dtoCreateDomainRequest** | [DtoCreateDomainRequest](DtoCreateDomainRequest.md) | Domain payload | |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoDomainResponse**](DtoDomainResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **201** | Created | - |
| **400** | validation error | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **500** | db error | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## createRecordSet
> DtoRecordSetResponse createRecordSet(domainId, dtoCreateRecordSetRequest, xOrgID)
Create a record set (pending; Archer will UPSERT to Route 53)
### Example
```ts
import {
Configuration,
DNSApi,
} from '@glueops/autoglue-sdk-go';
import type { CreateRecordSetRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new DNSApi(config);
const body = {
// string | Domain ID (UUID)
domainId: domainId_example,
// DtoCreateRecordSetRequest | Record set payload
dtoCreateRecordSetRequest: ...,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies CreateRecordSetRequest;
try {
const data = await api.createRecordSet(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ----------------------------- | --------------------------------------------------------- | ------------------ | ------------------------------------ |
| **domainId** | `string` | Domain ID (UUID) | [Defaults to `undefined`] |
| **dtoCreateRecordSetRequest** | [DtoCreateRecordSetRequest](DtoCreateRecordSetRequest.md) | Record set payload | |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoRecordSetResponse**](DtoRecordSetResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **201** | Created | - |
| **400** | validation error | - |
| **403** | organization required | - |
| **404** | domain not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## deleteDomain
> deleteDomain(id, xOrgID)
Delete a domain
### Example
```ts
import { Configuration, DNSApi } from "@glueops/autoglue-sdk-go";
import type { DeleteDomainRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new DNSApi(config);
const body = {
// string | Domain ID (UUID)
id: id_example,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies DeleteDomainRequest;
try {
const data = await api.deleteDomain(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------- | -------- | ----------------- | ------------------------------------ |
| **id** | `string` | Domain ID (UUID) | [Defaults to `undefined`] |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
`void` (Empty response body)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **204** | No Content | - |
| **403** | organization required | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## deleteRecordSet
> deleteRecordSet(id, xOrgID)
Delete a record set (API removes row; worker can optionally handle external deletion policy)
### Example
```ts
import { Configuration, DNSApi } from "@glueops/autoglue-sdk-go";
import type { DeleteRecordSetRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new DNSApi(config);
const body = {
// string | Record Set ID (UUID)
id: id_example,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies DeleteRecordSetRequest;
try {
const data = await api.deleteRecordSet(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------- | -------- | -------------------- | ------------------------------------ |
| **id** | `string` | Record Set ID (UUID) | [Defaults to `undefined`] |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
`void` (Empty response body)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **204** | No Content | - |
| **403** | organization required | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## getDomain
> DtoDomainResponse getDomain(id, xOrgID)
Get a domain (org scoped)
### Example
```ts
import { Configuration, DNSApi } from "@glueops/autoglue-sdk-go";
import type { GetDomainRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new DNSApi(config);
const body = {
// string | Domain ID (UUID)
id: id_example,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies GetDomainRequest;
try {
const data = await api.getDomain(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ---------- | -------- | ----------------- | ------------------------------------ |
| **id** | `string` | Domain ID (UUID) | [Defaults to `undefined`] |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoDomainResponse**](DtoDomainResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **200** | OK | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## listDomains
> Array&lt;DtoDomainResponse&gt; listDomains(xOrgID, domainName, status, q)
List domains (org scoped)
Returns domains for X-Org-ID. Filters: &#x60;domain_name&#x60;, &#x60;status&#x60;, &#x60;q&#x60; (contains).
### Example
```ts
import { Configuration, DNSApi } from "@glueops/autoglue-sdk-go";
import type { ListDomainsRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new DNSApi(config);
const body = {
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
// string | Exact domain name (lowercase, no trailing dot) (optional)
domainName: domainName_example,
// string | pending|provisioning|ready|failed (optional)
status: status_example,
// string | Domain contains (case-insensitive) (optional)
q: q_example,
} satisfies ListDomainsRequest;
try {
const data = await api.listDomains(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| -------------- | -------- | ---------------------------------------------- | ------------------------------------ | ----- | ------ | ------------------------------------ |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
| **domainName** | `string` | Exact domain name (lowercase, no trailing dot) | [Optional] [Defaults to `undefined`] |
| **status** | `string` | pending | provisioning | ready | failed | [Optional] [Defaults to `undefined`] |
| **q** | `string` | Domain contains (case-insensitive) | [Optional] [Defaults to `undefined`] |
### Return type
[**Array&lt;DtoDomainResponse&gt;**](DtoDomainResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **200** | OK | - |
| **401** | Unauthorized | - |
| **403** | organization required | - |
| **500** | db error | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## listRecordSets
> Array&lt;DtoRecordSetResponse&gt; listRecordSets(domainId, xOrgID, name, type, status)
List record sets for a domain
Filters: &#x60;name&#x60;, &#x60;type&#x60;, &#x60;status&#x60;.
### Example
```ts
import { Configuration, DNSApi } from "@glueops/autoglue-sdk-go";
import type { ListRecordSetsRequest } from "@glueops/autoglue-sdk-go";
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new DNSApi(config);
const body = {
// string | Domain ID (UUID)
domainId: domainId_example,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
// string | Exact relative name or FQDN (server normalizes) (optional)
name: name_example,
// string | RR type (A, AAAA, CNAME, TXT, MX, NS, SRV, CAA) (optional)
type: type_example,
// string | pending|provisioning|ready|failed (optional)
status: status_example,
} satisfies ListRecordSetsRequest;
try {
const data = await api.listRecordSets(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ------------ | -------- | ----------------------------------------------- | ------------------------------------ | ----- | ------ | ------------------------------------ |
| **domainId** | `string` | Domain ID (UUID) | [Defaults to `undefined`] |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
| **name** | `string` | Exact relative name or FQDN (server normalizes) | [Optional] [Defaults to `undefined`] |
| **type** | `string` | RR type (A, AAAA, CNAME, TXT, MX, NS, SRV, CAA) | [Optional] [Defaults to `undefined`] |
| **status** | `string` | pending | provisioning | ready | failed | [Optional] [Defaults to `undefined`] |
### Return type
[**Array&lt;DtoRecordSetResponse&gt;**](DtoRecordSetResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: Not defined
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **200** | OK | - |
| **403** | organization required | - |
| **404** | domain not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## updateDomain
> DtoDomainResponse updateDomain(id, dtoUpdateDomainRequest, xOrgID)
Update a domain (org scoped)
### Example
```ts
import {
Configuration,
DNSApi,
} from '@glueops/autoglue-sdk-go';
import type { UpdateDomainRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new DNSApi(config);
const body = {
// string | Domain ID (UUID)
id: id_example,
// DtoUpdateDomainRequest | Fields to update
dtoUpdateDomainRequest: ...,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies UpdateDomainRequest;
try {
const data = await api.updateDomain(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| -------------------------- | --------------------------------------------------- | ----------------- | ------------------------------------ |
| **id** | `string` | Domain ID (UUID) | [Defaults to `undefined`] |
| **dtoUpdateDomainRequest** | [DtoUpdateDomainRequest](DtoUpdateDomainRequest.md) | Fields to update | |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoDomainResponse**](DtoDomainResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **200** | OK | - |
| **400** | validation error | - |
| **403** | organization required | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)
## updateRecordSet
> DtoRecordSetResponse updateRecordSet(id, dtoUpdateRecordSetRequest, xOrgID)
Update a record set (flips to pending for reconciliation)
### Example
```ts
import {
Configuration,
DNSApi,
} from '@glueops/autoglue-sdk-go';
import type { UpdateRecordSetRequest } from '@glueops/autoglue-sdk-go';
async function example() {
console.log("🚀 Testing @glueops/autoglue-sdk-go SDK...");
const config = new Configuration({
// To configure API key authorization: OrgKeyAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: OrgSecretAuth
apiKey: "YOUR API KEY",
// To configure API key authorization: BearerAuth
apiKey: "YOUR API KEY",
});
const api = new DNSApi(config);
const body = {
// string | Record Set ID (UUID)
id: id_example,
// DtoUpdateRecordSetRequest | Fields to update
dtoUpdateRecordSetRequest: ...,
// string | Organization UUID (optional)
xOrgID: xOrgID_example,
} satisfies UpdateRecordSetRequest;
try {
const data = await api.updateRecordSet(body);
console.log(data);
} catch (error) {
console.error(error);
}
}
// Run the test
example().catch(console.error);
```
### Parameters
| Name | Type | Description | Notes |
| ----------------------------- | --------------------------------------------------------- | -------------------- | ------------------------------------ |
| **id** | `string` | Record Set ID (UUID) | [Defaults to `undefined`] |
| **dtoUpdateRecordSetRequest** | [DtoUpdateRecordSetRequest](DtoUpdateRecordSetRequest.md) | Fields to update | |
| **xOrgID** | `string` | Organization UUID | [Optional] [Defaults to `undefined`] |
### Return type
[**DtoRecordSetResponse**](DtoRecordSetResponse.md)
### Authorization
[OrgKeyAuth](../README.md#OrgKeyAuth), [OrgSecretAuth](../README.md#OrgSecretAuth), [BearerAuth](../README.md#BearerAuth)
### HTTP request headers
- **Content-Type**: `application/json`
- **Accept**: `application/json`
### HTTP response details
| Status code | Description | Response headers |
| ----------- | --------------------- | ---------------- |
| **200** | OK | - |
| **400** | validation error | - |
| **403** | organization required | - |
| **404** | not found | - |
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,40 @@
# DtoAnnotationResponse
## Properties
| Name | Type |
| ----------------- | ------ |
| `created_at` | string |
| `id` | string |
| `key` | string |
| `organization_id` | string |
| `updated_at` | string |
| `value` | string |
## Example
```typescript
import type { DtoAnnotationResponse } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
created_at: null,
id: null,
key: null,
organization_id: null,
updated_at: null,
value: null,
} satisfies DtoAnnotationResponse;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAnnotationResponse;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAttachAnnotationsRequest
## Properties
| Name | Type |
| ---------------- | ------------------- |
| `annotation_ids` | Array&lt;string&gt; |
## Example
```typescript
import type { DtoAttachAnnotationsRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
annotation_ids: null,
} satisfies DtoAttachAnnotationsRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAttachAnnotationsRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAttachBastionRequest
## Properties
| Name | Type |
| ----------- | ------ |
| `server_id` | string |
## Example
```typescript
import type { DtoAttachBastionRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
server_id: null,
} satisfies DtoAttachBastionRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAttachBastionRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAttachCaptainDomainRequest
## Properties
| Name | Type |
| ----------- | ------ |
| `domain_id` | string |
## Example
```typescript
import type { DtoAttachCaptainDomainRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
domain_id: null,
} satisfies DtoAttachCaptainDomainRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAttachCaptainDomainRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAttachLabelsRequest
## Properties
| Name | Type |
| ----------- | ------------------- |
| `label_ids` | Array&lt;string&gt; |
## Example
```typescript
import type { DtoAttachLabelsRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
label_ids: null,
} satisfies DtoAttachLabelsRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAttachLabelsRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAttachLoadBalancerRequest
## Properties
| Name | Type |
| ------------------ | ------ |
| `load_balancer_id` | string |
## Example
```typescript
import type { DtoAttachLoadBalancerRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
load_balancer_id: null,
} satisfies DtoAttachLoadBalancerRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAttachLoadBalancerRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAttachNodePoolRequest
## Properties
| Name | Type |
| -------------- | ------ |
| `node_pool_id` | string |
## Example
```typescript
import type { DtoAttachNodePoolRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
node_pool_id: null,
} satisfies DtoAttachNodePoolRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAttachNodePoolRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAttachRecordSetRequest
## Properties
| Name | Type |
| --------------- | ------ |
| `record_set_id` | string |
## Example
```typescript
import type { DtoAttachRecordSetRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
record_set_id: null,
} satisfies DtoAttachRecordSetRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAttachRecordSetRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAttachServersRequest
## Properties
| Name | Type |
| ------------ | ------------------- |
| `server_ids` | Array&lt;string&gt; |
## Example
```typescript
import type { DtoAttachServersRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
server_ids: null,
} satisfies DtoAttachServersRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAttachServersRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAttachTaintsRequest
## Properties
| Name | Type |
| ----------- | ------------------- |
| `taint_ids` | Array&lt;string&gt; |
## Example
```typescript
import type { DtoAttachTaintsRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
taint_ids: null,
} satisfies DtoAttachTaintsRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAttachTaintsRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,30 @@
# DtoAuthStartResponse
## Properties
| Name | Type |
| ---------- | ------ |
| `auth_url` | string |
## Example
```typescript
import type { DtoAuthStartResponse } from '@glueops/autoglue-sdk-go'
// TODO: Update the object below with actual values
const example = {
"auth_url": https://accounts.google.com/o/oauth2/v2/auth?client_id=...,
} satisfies DtoAuthStartResponse
console.log(example)
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example)
console.log(exampleJSON)
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoAuthStartResponse
console.log(exampleParsed)
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,66 @@
# DtoClusterResponse
## Properties
| Name | Type |
| -------------------------- | ---------------------------------------------------------- |
| `apps_load_balancer` | [DtoLoadBalancerResponse](DtoLoadBalancerResponse.md) |
| `bastion_server` | [DtoServerResponse](DtoServerResponse.md) |
| `captain_domain` | [DtoDomainResponse](DtoDomainResponse.md) |
| `certificate_key` | string |
| `cluster_provider` | string |
| `control_plane_fqdn` | string |
| `control_plane_record_set` | [DtoRecordSetResponse](DtoRecordSetResponse.md) |
| `created_at` | string |
| `docker_image` | string |
| `docker_tag` | string |
| `glueops_load_balancer` | [DtoLoadBalancerResponse](DtoLoadBalancerResponse.md) |
| `id` | string |
| `last_error` | string |
| `name` | string |
| `node_pools` | [Array&lt;DtoNodePoolResponse&gt;](DtoNodePoolResponse.md) |
| `random_token` | string |
| `region` | string |
| `status` | string |
| `updated_at` | string |
## Example
```typescript
import type { DtoClusterResponse } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
apps_load_balancer: null,
bastion_server: null,
captain_domain: null,
certificate_key: null,
cluster_provider: null,
control_plane_fqdn: null,
control_plane_record_set: null,
created_at: null,
docker_image: null,
docker_tag: null,
glueops_load_balancer: null,
id: null,
last_error: null,
name: null,
node_pools: null,
random_token: null,
region: null,
status: null,
updated_at: null,
} satisfies DtoClusterResponse;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoClusterResponse;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,32 @@
# DtoCreateAnnotationRequest
## Properties
| Name | Type |
| ------- | ------ |
| `key` | string |
| `value` | string |
## Example
```typescript
import type { DtoCreateAnnotationRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
key: null,
value: null,
} satisfies DtoCreateAnnotationRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateAnnotationRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,38 @@
# DtoCreateClusterRequest
## Properties
| Name | Type |
| ------------------ | ------ |
| `cluster_provider` | string |
| `docker_image` | string |
| `docker_tag` | string |
| `name` | string |
| `region` | string |
## Example
```typescript
import type { DtoCreateClusterRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
cluster_provider: null,
docker_image: null,
docker_tag: null,
name: null,
region: null,
} satisfies DtoCreateClusterRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateClusterRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,48 @@
# DtoCreateCredentialRequest
## Properties
| Name | Type |
| --------------------- | ------ |
| `account_id` | string |
| `credential_provider` | string |
| `kind` | string |
| `name` | string |
| `region` | string |
| `schema_version` | number |
| `scope` | object |
| `scope_kind` | string |
| `scope_version` | number |
| `secret` | object |
## Example
```typescript
import type { DtoCreateCredentialRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
account_id: null,
credential_provider: null,
kind: null,
name: null,
region: null,
schema_version: null,
scope: null,
scope_kind: null,
scope_version: null,
secret: null,
} satisfies DtoCreateCredentialRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateCredentialRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,34 @@
# DtoCreateDomainRequest
## Properties
| Name | Type |
| --------------- | ------ |
| `credential_id` | string |
| `domain_name` | string |
| `zone_id` | string |
## Example
```typescript
import type { DtoCreateDomainRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
credential_id: null,
domain_name: null,
zone_id: null,
} satisfies DtoCreateDomainRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateDomainRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,32 @@
# DtoCreateLabelRequest
## Properties
| Name | Type |
| ------- | ------ |
| `key` | string |
| `value` | string |
## Example
```typescript
import type { DtoCreateLabelRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
key: null,
value: null,
} satisfies DtoCreateLabelRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateLabelRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,36 @@
# DtoCreateLoadBalancerRequest
## Properties
| Name | Type |
| -------------------- | ------ |
| `kind` | string |
| `name` | string |
| `private_ip_address` | string |
| `public_ip_address` | string |
## Example
```typescript
import type { DtoCreateLoadBalancerRequest } from '@glueops/autoglue-sdk-go'
// TODO: Update the object below with actual values
const example = {
"kind": public,
"name": glueops,
"private_ip_address": 192.168.0.2,
"public_ip_address": 8.8.8.8,
} satisfies DtoCreateLoadBalancerRequest
console.log(example)
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example)
console.log(exampleJSON)
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateLoadBalancerRequest
console.log(exampleParsed)
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,32 @@
# DtoCreateNodePoolRequest
## Properties
| Name | Type |
| ------ | ------ |
| `name` | string |
| `role` | string |
## Example
```typescript
import type { DtoCreateNodePoolRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
name: null,
role: null,
} satisfies DtoCreateNodePoolRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateNodePoolRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,36 @@
# DtoCreateRecordSetRequest
## Properties
| Name | Type |
| -------- | ------------------- |
| `name` | string |
| `ttl` | number |
| `type` | string |
| `values` | Array&lt;string&gt; |
## Example
```typescript
import type { DtoCreateRecordSetRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
name: null,
ttl: null,
type: null,
values: null,
} satisfies DtoCreateRecordSetRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateRecordSetRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,36 @@
# DtoCreateSSHRequest
## Properties
| Name | Type |
| --------- | ------ |
| `bits` | number |
| `comment` | string |
| `name` | string |
| `type` | string |
## Example
```typescript
import type { DtoCreateSSHRequest } from '@glueops/autoglue-sdk-go'
// TODO: Update the object below with actual values
const example = {
"bits": null,
"comment": deploy@autoglue,
"name": null,
"type": null,
} satisfies DtoCreateSSHRequest
console.log(example)
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example)
console.log(exampleJSON)
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateSSHRequest
console.log(exampleParsed)
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,42 @@
# DtoCreateServerRequest
## Properties
| Name | Type |
| -------------------- | ------ |
| `hostname` | string |
| `private_ip_address` | string |
| `public_ip_address` | string |
| `role` | string |
| `ssh_key_id` | string |
| `ssh_user` | string |
| `status` | string |
## Example
```typescript
import type { DtoCreateServerRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
hostname: null,
private_ip_address: null,
public_ip_address: null,
role: master | worker | bastion,
ssh_key_id: null,
ssh_user: null,
status: pending | provisioning | ready | failed,
} satisfies DtoCreateServerRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateServerRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,34 @@
# DtoCreateTaintRequest
## Properties
| Name | Type |
| -------- | ------ |
| `effect` | string |
| `key` | string |
| `value` | string |
## Example
```typescript
import type { DtoCreateTaintRequest } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
effect: null,
key: null,
value: null,
} satisfies DtoCreateTaintRequest;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCreateTaintRequest;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,52 @@
# DtoCredentialOut
## Properties
| Name | Type |
| --------------------- | ------ |
| `account_id` | string |
| `created_at` | string |
| `credential_provider` | string |
| `id` | string |
| `kind` | string |
| `name` | string |
| `region` | string |
| `schema_version` | number |
| `scope` | object |
| `scope_kind` | string |
| `scope_version` | number |
| `updated_at` | string |
## Example
```typescript
import type { DtoCredentialOut } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
account_id: null,
created_at: null,
credential_provider: null,
id: null,
kind: null,
name: null,
region: null,
schema_version: null,
scope: null,
scope_kind: null,
scope_version: null,
updated_at: null,
} satisfies DtoCredentialOut;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoCredentialOut;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,46 @@
# DtoDomainResponse
## Properties
| Name | Type |
| ----------------- | ------ |
| `created_at` | string |
| `credential_id` | string |
| `domain_name` | string |
| `id` | string |
| `last_error` | string |
| `organization_id` | string |
| `status` | string |
| `updated_at` | string |
| `zone_id` | string |
## Example
```typescript
import type { DtoDomainResponse } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
created_at: null,
credential_id: null,
domain_name: null,
id: null,
last_error: null,
organization_id: null,
status: null,
updated_at: null,
zone_id: null,
} satisfies DtoDomainResponse;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoDomainResponse;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

View File

@@ -0,0 +1,36 @@
# DtoEnqueueRequest
## Properties
| Name | Type |
| --------- | ------ |
| `payload` | object |
| `queue` | string |
| `run_at` | string |
| `type` | string |
## Example
```typescript
import type { DtoEnqueueRequest } from '@glueops/autoglue-sdk-go'
// TODO: Update the object below with actual values
const example = {
"payload": null,
"queue": default,
"run_at": 2025-11-05T08:00:00Z,
"type": email.send,
} satisfies DtoEnqueueRequest
console.log(example)
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example)
console.log(exampleJSON)
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoEnqueueRequest
console.log(exampleParsed)
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

42
sdk/ts/docs/DtoJWK.md Normal file
View File

@@ -0,0 +1,42 @@
# DtoJWK
## Properties
| Name | Type |
| ----- | ------ |
| `alg` | string |
| `e` | string |
| `kid` | string |
| `kty` | string |
| `n` | string |
| `use` | string |
| `x` | string |
## Example
```typescript
import type { DtoJWK } from '@glueops/autoglue-sdk-go'
// TODO: Update the object below with actual values
const example = {
"alg": RS256,
"e": AQAB,
"kid": 7c6f1d0a-7a98-4e6a-9dbf-6b1af4b9f345,
"kty": RSA,
"n": null,
"use": sig,
"x": null,
} satisfies DtoJWK
console.log(example)
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example)
console.log(exampleJSON)
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoJWK
console.log(exampleParsed)
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

30
sdk/ts/docs/DtoJWKS.md Normal file
View File

@@ -0,0 +1,30 @@
# DtoJWKS
## Properties
| Name | Type |
| ------ | -------------------------------- |
| `keys` | [Array&lt;DtoJWK&gt;](DtoJWK.md) |
## Example
```typescript
import type { DtoJWKS } from "@glueops/autoglue-sdk-go";
// TODO: Update the object below with actual values
const example = {
keys: null,
} satisfies DtoJWKS;
console.log(example);
// Convert the instance to a JSON string
const exampleJSON: string = JSON.stringify(example);
console.log(exampleJSON);
// Parse the JSON string back to an object
const exampleParsed = JSON.parse(exampleJSON) as DtoJWKS;
console.log(exampleParsed);
```
[[Back to top]](#) [[Back to API list]](../README.md#api-endpoints) [[Back to Model list]](../README.md#models) [[Back to README]](../README.md)

Some files were not shown because too many files have changed in this diff Show More