@tinybirdco/sdk 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +518 -0
- package/bin/tinybird.js +7 -0
- package/dist/api/branches.d.ts +98 -0
- package/dist/api/branches.d.ts.map +1 -0
- package/dist/api/branches.js +203 -0
- package/dist/api/branches.js.map +1 -0
- package/dist/api/branches.test.d.ts +2 -0
- package/dist/api/branches.test.d.ts.map +1 -0
- package/dist/api/branches.test.js +286 -0
- package/dist/api/branches.test.js.map +1 -0
- package/dist/api/build.d.ts +130 -0
- package/dist/api/build.d.ts.map +1 -0
- package/dist/api/build.js +143 -0
- package/dist/api/build.js.map +1 -0
- package/dist/api/build.test.d.ts +2 -0
- package/dist/api/build.test.d.ts.map +1 -0
- package/dist/api/build.test.js +138 -0
- package/dist/api/build.test.js.map +1 -0
- package/dist/api/deploy.d.ts +39 -0
- package/dist/api/deploy.d.ts.map +1 -0
- package/dist/api/deploy.js +135 -0
- package/dist/api/deploy.js.map +1 -0
- package/dist/api/deploy.test.d.ts +2 -0
- package/dist/api/deploy.test.d.ts.map +1 -0
- package/dist/api/deploy.test.js +118 -0
- package/dist/api/deploy.test.js.map +1 -0
- package/dist/api/workspaces.d.ts +46 -0
- package/dist/api/workspaces.d.ts.map +1 -0
- package/dist/api/workspaces.js +39 -0
- package/dist/api/workspaces.js.map +1 -0
- package/dist/api/workspaces.test.d.ts +2 -0
- package/dist/api/workspaces.test.d.ts.map +1 -0
- package/dist/api/workspaces.test.js +65 -0
- package/dist/api/workspaces.test.js.map +1 -0
- package/dist/cli/auth.d.ts +86 -0
- package/dist/cli/auth.d.ts.map +1 -0
- package/dist/cli/auth.js +284 -0
- package/dist/cli/auth.js.map +1 -0
- package/dist/cli/branch-store.d.ts +53 -0
- package/dist/cli/branch-store.d.ts.map +1 -0
- package/dist/cli/branch-store.js +91 -0
- package/dist/cli/branch-store.js.map +1 -0
- package/dist/cli/branch-store.test.d.ts +2 -0
- package/dist/cli/branch-store.test.d.ts.map +1 -0
- package/dist/cli/branch-store.test.js +115 -0
- package/dist/cli/branch-store.test.js.map +1 -0
- package/dist/cli/commands/branch.d.ts +82 -0
- package/dist/cli/commands/branch.d.ts.map +1 -0
- package/dist/cli/commands/branch.js +215 -0
- package/dist/cli/commands/branch.js.map +1 -0
- package/dist/cli/commands/build.d.ts +43 -0
- package/dist/cli/commands/build.d.ts.map +1 -0
- package/dist/cli/commands/build.js +138 -0
- package/dist/cli/commands/build.js.map +1 -0
- package/dist/cli/commands/dev.d.ts +78 -0
- package/dist/cli/commands/dev.d.ts.map +1 -0
- package/dist/cli/commands/dev.js +226 -0
- package/dist/cli/commands/dev.js.map +1 -0
- package/dist/cli/commands/init.d.ts +45 -0
- package/dist/cli/commands/init.d.ts.map +1 -0
- package/dist/cli/commands/init.js +277 -0
- package/dist/cli/commands/init.js.map +1 -0
- package/dist/cli/commands/init.test.d.ts +2 -0
- package/dist/cli/commands/init.test.d.ts.map +1 -0
- package/dist/cli/commands/init.test.js +158 -0
- package/dist/cli/commands/init.test.js.map +1 -0
- package/dist/cli/commands/login.d.ts +37 -0
- package/dist/cli/commands/login.d.ts.map +1 -0
- package/dist/cli/commands/login.js +64 -0
- package/dist/cli/commands/login.js.map +1 -0
- package/dist/cli/config.d.ts +114 -0
- package/dist/cli/config.d.ts.map +1 -0
- package/dist/cli/config.js +258 -0
- package/dist/cli/config.js.map +1 -0
- package/dist/cli/config.test.d.ts +2 -0
- package/dist/cli/config.test.d.ts.map +1 -0
- package/dist/cli/config.test.js +243 -0
- package/dist/cli/config.test.js.map +1 -0
- package/dist/cli/env.d.ts +29 -0
- package/dist/cli/env.d.ts.map +1 -0
- package/dist/cli/env.js +66 -0
- package/dist/cli/env.js.map +1 -0
- package/dist/cli/git.d.ts +29 -0
- package/dist/cli/git.d.ts.map +1 -0
- package/dist/cli/git.js +114 -0
- package/dist/cli/git.js.map +1 -0
- package/dist/cli/git.test.d.ts +2 -0
- package/dist/cli/git.test.d.ts.map +1 -0
- package/dist/cli/git.test.js +125 -0
- package/dist/cli/git.test.js.map +1 -0
- package/dist/cli/index.d.ts +7 -0
- package/dist/cli/index.d.ts.map +1 -0
- package/dist/cli/index.js +337 -0
- package/dist/cli/index.js.map +1 -0
- package/dist/cli/utils/schema-validation.d.ts +95 -0
- package/dist/cli/utils/schema-validation.d.ts.map +1 -0
- package/dist/cli/utils/schema-validation.js +175 -0
- package/dist/cli/utils/schema-validation.js.map +1 -0
- package/dist/cli/utils/schema-validation.test.d.ts +5 -0
- package/dist/cli/utils/schema-validation.test.d.ts.map +1 -0
- package/dist/cli/utils/schema-validation.test.js +173 -0
- package/dist/cli/utils/schema-validation.test.js.map +1 -0
- package/dist/client/base.d.ts +116 -0
- package/dist/client/base.d.ts.map +1 -0
- package/dist/client/base.js +328 -0
- package/dist/client/base.js.map +1 -0
- package/dist/client/types.d.ts +137 -0
- package/dist/client/types.d.ts.map +1 -0
- package/dist/client/types.js +43 -0
- package/dist/client/types.js.map +1 -0
- package/dist/generator/client.d.ts +44 -0
- package/dist/generator/client.d.ts.map +1 -0
- package/dist/generator/client.js +144 -0
- package/dist/generator/client.js.map +1 -0
- package/dist/generator/datasource.d.ts +57 -0
- package/dist/generator/datasource.d.ts.map +1 -0
- package/dist/generator/datasource.js +169 -0
- package/dist/generator/datasource.js.map +1 -0
- package/dist/generator/datasource.test.d.ts +2 -0
- package/dist/generator/datasource.test.d.ts.map +1 -0
- package/dist/generator/datasource.test.js +254 -0
- package/dist/generator/datasource.test.js.map +1 -0
- package/dist/generator/index.d.ts +131 -0
- package/dist/generator/index.d.ts.map +1 -0
- package/dist/generator/index.js +121 -0
- package/dist/generator/index.js.map +1 -0
- package/dist/generator/index.test.d.ts +2 -0
- package/dist/generator/index.test.d.ts.map +1 -0
- package/dist/generator/index.test.js +175 -0
- package/dist/generator/index.test.js.map +1 -0
- package/dist/generator/loader.d.ts +156 -0
- package/dist/generator/loader.d.ts.map +1 -0
- package/dist/generator/loader.js +295 -0
- package/dist/generator/loader.js.map +1 -0
- package/dist/generator/pipe.d.ts +72 -0
- package/dist/generator/pipe.d.ts.map +1 -0
- package/dist/generator/pipe.js +174 -0
- package/dist/generator/pipe.js.map +1 -0
- package/dist/generator/pipe.test.d.ts +2 -0
- package/dist/generator/pipe.test.d.ts.map +1 -0
- package/dist/generator/pipe.test.js +393 -0
- package/dist/generator/pipe.test.js.map +1 -0
- package/dist/index.d.ts +74 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +73 -0
- package/dist/index.js.map +1 -0
- package/dist/infer/index.d.ts +202 -0
- package/dist/infer/index.d.ts.map +1 -0
- package/dist/infer/index.js +5 -0
- package/dist/infer/index.js.map +1 -0
- package/dist/schema/datasource.d.ts +135 -0
- package/dist/schema/datasource.d.ts.map +1 -0
- package/dist/schema/datasource.js +105 -0
- package/dist/schema/datasource.js.map +1 -0
- package/dist/schema/datasource.test.d.ts +2 -0
- package/dist/schema/datasource.test.d.ts.map +1 -0
- package/dist/schema/datasource.test.js +142 -0
- package/dist/schema/datasource.test.js.map +1 -0
- package/dist/schema/engines.d.ts +157 -0
- package/dist/schema/engines.d.ts.map +1 -0
- package/dist/schema/engines.js +155 -0
- package/dist/schema/engines.js.map +1 -0
- package/dist/schema/engines.test.d.ts +2 -0
- package/dist/schema/engines.test.d.ts.map +1 -0
- package/dist/schema/engines.test.js +221 -0
- package/dist/schema/engines.test.js.map +1 -0
- package/dist/schema/params.d.ts +106 -0
- package/dist/schema/params.d.ts.map +1 -0
- package/dist/schema/params.js +138 -0
- package/dist/schema/params.js.map +1 -0
- package/dist/schema/params.test.d.ts +2 -0
- package/dist/schema/params.test.d.ts.map +1 -0
- package/dist/schema/params.test.js +175 -0
- package/dist/schema/params.test.js.map +1 -0
- package/dist/schema/pipe.d.ts +436 -0
- package/dist/schema/pipe.d.ts.map +1 -0
- package/dist/schema/pipe.js +484 -0
- package/dist/schema/pipe.js.map +1 -0
- package/dist/schema/pipe.test.d.ts +2 -0
- package/dist/schema/pipe.test.d.ts.map +1 -0
- package/dist/schema/pipe.test.js +488 -0
- package/dist/schema/pipe.test.js.map +1 -0
- package/dist/schema/project.d.ts +202 -0
- package/dist/schema/project.d.ts.map +1 -0
- package/dist/schema/project.js +188 -0
- package/dist/schema/project.js.map +1 -0
- package/dist/schema/project.test.d.ts +2 -0
- package/dist/schema/project.test.d.ts.map +1 -0
- package/dist/schema/project.test.js +180 -0
- package/dist/schema/project.test.js.map +1 -0
- package/dist/schema/types.d.ts +140 -0
- package/dist/schema/types.d.ts.map +1 -0
- package/dist/schema/types.js +174 -0
- package/dist/schema/types.js.map +1 -0
- package/dist/schema/types.test.d.ts +2 -0
- package/dist/schema/types.test.d.ts.map +1 -0
- package/dist/schema/types.test.js +176 -0
- package/dist/schema/types.test.js.map +1 -0
- package/dist/test/handlers.d.ts +58 -0
- package/dist/test/handlers.d.ts.map +1 -0
- package/dist/test/handlers.js +62 -0
- package/dist/test/handlers.js.map +1 -0
- package/dist/test/setup.d.ts +5 -0
- package/dist/test/setup.d.ts.map +1 -0
- package/dist/test/setup.js +11 -0
- package/dist/test/setup.js.map +1 -0
- package/package.json +57 -0
- package/src/api/branches.test.ts +377 -0
- package/src/api/branches.ts +334 -0
- package/src/api/build.test.ts +216 -0
- package/src/api/build.ts +266 -0
- package/src/api/deploy.test.ts +193 -0
- package/src/api/deploy.ts +163 -0
- package/src/api/workspaces.test.ts +81 -0
- package/src/api/workspaces.ts +77 -0
- package/src/cli/auth.ts +358 -0
- package/src/cli/branch-store.test.ts +139 -0
- package/src/cli/branch-store.ts +137 -0
- package/src/cli/commands/branch.ts +306 -0
- package/src/cli/commands/build.ts +183 -0
- package/src/cli/commands/dev.ts +334 -0
- package/src/cli/commands/init.test.ts +249 -0
- package/src/cli/commands/init.ts +323 -0
- package/src/cli/commands/login.ts +98 -0
- package/src/cli/config.test.ts +359 -0
- package/src/cli/config.ts +335 -0
- package/src/cli/env.ts +86 -0
- package/src/cli/git.test.ts +147 -0
- package/src/cli/git.ts +125 -0
- package/src/cli/index.ts +382 -0
- package/src/cli/utils/schema-validation.test.ts +222 -0
- package/src/cli/utils/schema-validation.ts +272 -0
- package/src/client/base.ts +414 -0
- package/src/client/types.ts +165 -0
- package/src/generator/client.ts +194 -0
- package/src/generator/datasource.test.ts +297 -0
- package/src/generator/datasource.ts +217 -0
- package/src/generator/index.test.ts +209 -0
- package/src/generator/index.ts +203 -0
- package/src/generator/loader.ts +406 -0
- package/src/generator/pipe.test.ts +441 -0
- package/src/generator/pipe.ts +220 -0
- package/src/index.ts +191 -0
- package/src/infer/index.ts +247 -0
- package/src/schema/datasource.test.ts +187 -0
- package/src/schema/datasource.ts +195 -0
- package/src/schema/engines.test.ts +247 -0
- package/src/schema/engines.ts +271 -0
- package/src/schema/params.test.ts +208 -0
- package/src/schema/params.ts +249 -0
- package/src/schema/pipe.test.ts +588 -0
- package/src/schema/pipe.ts +832 -0
- package/src/schema/project.test.ts +236 -0
- package/src/schema/project.ts +394 -0
- package/src/schema/types.test.ts +212 -0
- package/src/schema/types.ts +366 -0
- package/src/test/handlers.ts +79 -0
- package/src/test/setup.ts +13 -0
|
@@ -0,0 +1,203 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Tinybird Branch (Environment) API client
|
|
3
|
+
* Uses the /v1/environments endpoints (Forward API)
|
|
4
|
+
*/
|
|
5
|
+
/**
|
|
6
|
+
* Error thrown by branch API operations
|
|
7
|
+
*/
|
|
8
|
+
export class BranchApiError extends Error {
|
|
9
|
+
status;
|
|
10
|
+
body;
|
|
11
|
+
constructor(message, status, body) {
|
|
12
|
+
super(message);
|
|
13
|
+
this.status = status;
|
|
14
|
+
this.body = body;
|
|
15
|
+
this.name = "BranchApiError";
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Poll a job until it completes
|
|
20
|
+
*
|
|
21
|
+
* @param config - API configuration
|
|
22
|
+
* @param jobId - Job ID to poll
|
|
23
|
+
* @param maxAttempts - Maximum polling attempts (default: 120, i.e. 2 minutes)
|
|
24
|
+
* @param intervalMs - Polling interval in milliseconds (default: 1000)
|
|
25
|
+
* @returns Job status when complete
|
|
26
|
+
*/
|
|
27
|
+
async function pollJob(config, jobId, maxAttempts = 120, intervalMs = 1000) {
|
|
28
|
+
for (let attempt = 0; attempt < maxAttempts; attempt++) {
|
|
29
|
+
const url = new URL(`/v0/jobs/${jobId}`, config.baseUrl);
|
|
30
|
+
const response = await fetch(url.toString(), {
|
|
31
|
+
method: "GET",
|
|
32
|
+
headers: {
|
|
33
|
+
Authorization: `Bearer ${config.token}`,
|
|
34
|
+
},
|
|
35
|
+
});
|
|
36
|
+
if (!response.ok) {
|
|
37
|
+
const body = await response.text();
|
|
38
|
+
throw new BranchApiError(`Failed to poll job '${jobId}': ${response.status} ${response.statusText}\nAPI response: ${body}`, response.status, body);
|
|
39
|
+
}
|
|
40
|
+
const jobStatus = (await response.json());
|
|
41
|
+
if (jobStatus.status === "done") {
|
|
42
|
+
return jobStatus;
|
|
43
|
+
}
|
|
44
|
+
if (jobStatus.status === "error") {
|
|
45
|
+
throw new BranchApiError(`Job '${jobId}' failed: ${jobStatus.error ?? "Unknown error"}`, 500, jobStatus);
|
|
46
|
+
}
|
|
47
|
+
// Wait before next poll
|
|
48
|
+
await new Promise((resolve) => setTimeout(resolve, intervalMs));
|
|
49
|
+
}
|
|
50
|
+
throw new BranchApiError(`Job '${jobId}' timed out after ${maxAttempts} attempts`, 408);
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Create a new branch
|
|
54
|
+
* POST /v1/environments?name={name}
|
|
55
|
+
*
|
|
56
|
+
* This is an async operation that returns a job. We poll the job until
|
|
57
|
+
* it completes, then fetch the branch with its token.
|
|
58
|
+
*
|
|
59
|
+
* @param config - API configuration
|
|
60
|
+
* @param name - Branch name to create
|
|
61
|
+
* @returns The created branch with token
|
|
62
|
+
*/
|
|
63
|
+
export async function createBranch(config, name) {
|
|
64
|
+
const url = new URL("/v1/environments", config.baseUrl);
|
|
65
|
+
url.searchParams.set("name", name);
|
|
66
|
+
const response = await fetch(url.toString(), {
|
|
67
|
+
method: "POST",
|
|
68
|
+
headers: {
|
|
69
|
+
Authorization: `Bearer ${config.token}`,
|
|
70
|
+
},
|
|
71
|
+
});
|
|
72
|
+
if (!response.ok) {
|
|
73
|
+
const body = await response.text();
|
|
74
|
+
// Provide helpful error message for common cases, but include raw response for debugging
|
|
75
|
+
let message = `Failed to create branch '${name}': ${response.status} ${response.statusText}`;
|
|
76
|
+
if (response.status === 403) {
|
|
77
|
+
message = `Permission denied creating branch '${name}'. ` +
|
|
78
|
+
`Make sure TINYBIRD_TOKEN is a workspace admin token (not a branch token). ` +
|
|
79
|
+
`Branch tokens cannot create new branches.\n` +
|
|
80
|
+
`API response: ${body}`;
|
|
81
|
+
}
|
|
82
|
+
else if (response.status === 409) {
|
|
83
|
+
message = `Branch '${name}' already exists.`;
|
|
84
|
+
}
|
|
85
|
+
else {
|
|
86
|
+
message += `\nAPI response: ${body}`;
|
|
87
|
+
}
|
|
88
|
+
throw new BranchApiError(message, response.status, body);
|
|
89
|
+
}
|
|
90
|
+
// Parse the job response
|
|
91
|
+
const jobResponse = (await response.json());
|
|
92
|
+
if (!jobResponse.job?.id) {
|
|
93
|
+
throw new BranchApiError(`Unexpected response from branch creation: no job ID returned`, 500, jobResponse);
|
|
94
|
+
}
|
|
95
|
+
// Poll the job until it completes
|
|
96
|
+
await pollJob(config, jobResponse.job.id);
|
|
97
|
+
// Now fetch the branch with its token using the branch name
|
|
98
|
+
const branch = await getBranch(config, name);
|
|
99
|
+
return branch;
|
|
100
|
+
}
|
|
101
|
+
/**
|
|
102
|
+
* List all branches in the workspace
|
|
103
|
+
* GET /v1/environments
|
|
104
|
+
*
|
|
105
|
+
* @param config - API configuration
|
|
106
|
+
* @returns Array of branches
|
|
107
|
+
*/
|
|
108
|
+
export async function listBranches(config) {
|
|
109
|
+
const url = new URL("/v1/environments", config.baseUrl);
|
|
110
|
+
const response = await fetch(url.toString(), {
|
|
111
|
+
method: "GET",
|
|
112
|
+
headers: {
|
|
113
|
+
Authorization: `Bearer ${config.token}`,
|
|
114
|
+
},
|
|
115
|
+
});
|
|
116
|
+
if (!response.ok) {
|
|
117
|
+
const body = await response.text();
|
|
118
|
+
throw new BranchApiError(`Failed to list branches: ${response.status} ${response.statusText}`, response.status, body);
|
|
119
|
+
}
|
|
120
|
+
const data = (await response.json());
|
|
121
|
+
return data.environments ?? [];
|
|
122
|
+
}
|
|
123
|
+
/**
|
|
124
|
+
* Get a branch by name with its token
|
|
125
|
+
* GET /v0/environments/{name}?with_token=true
|
|
126
|
+
*
|
|
127
|
+
* @param config - API configuration
|
|
128
|
+
* @param name - Branch name
|
|
129
|
+
* @returns Branch with token
|
|
130
|
+
*/
|
|
131
|
+
export async function getBranch(config, name) {
|
|
132
|
+
const url = new URL(`/v0/environments/${encodeURIComponent(name)}`, config.baseUrl);
|
|
133
|
+
url.searchParams.set("with_token", "true");
|
|
134
|
+
const response = await fetch(url.toString(), {
|
|
135
|
+
method: "GET",
|
|
136
|
+
headers: {
|
|
137
|
+
Authorization: `Bearer ${config.token}`,
|
|
138
|
+
},
|
|
139
|
+
});
|
|
140
|
+
if (!response.ok) {
|
|
141
|
+
const body = await response.text();
|
|
142
|
+
throw new BranchApiError(`Failed to get branch '${name}': ${response.status} ${response.statusText}`, response.status, body);
|
|
143
|
+
}
|
|
144
|
+
const data = (await response.json());
|
|
145
|
+
return data;
|
|
146
|
+
}
|
|
147
|
+
/**
|
|
148
|
+
* Delete a branch
|
|
149
|
+
* DELETE /v1/environments/{name}
|
|
150
|
+
*
|
|
151
|
+
* @param config - API configuration
|
|
152
|
+
* @param name - Branch name to delete
|
|
153
|
+
*/
|
|
154
|
+
export async function deleteBranch(config, name) {
|
|
155
|
+
const url = new URL(`/v1/environments/${encodeURIComponent(name)}`, config.baseUrl);
|
|
156
|
+
const response = await fetch(url.toString(), {
|
|
157
|
+
method: "DELETE",
|
|
158
|
+
headers: {
|
|
159
|
+
Authorization: `Bearer ${config.token}`,
|
|
160
|
+
},
|
|
161
|
+
});
|
|
162
|
+
if (!response.ok) {
|
|
163
|
+
const body = await response.text();
|
|
164
|
+
throw new BranchApiError(`Failed to delete branch '${name}': ${response.status} ${response.statusText}`, response.status, body);
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
/**
|
|
168
|
+
* Check if a branch exists
|
|
169
|
+
*
|
|
170
|
+
* @param config - API configuration
|
|
171
|
+
* @param name - Branch name to check
|
|
172
|
+
* @returns true if branch exists, false if not
|
|
173
|
+
* @throws BranchApiError on API/network/auth failures
|
|
174
|
+
*/
|
|
175
|
+
export async function branchExists(config, name) {
|
|
176
|
+
const branches = await listBranches(config);
|
|
177
|
+
return branches.some((b) => b.name === name);
|
|
178
|
+
}
|
|
179
|
+
/**
|
|
180
|
+
* Get or create a branch
|
|
181
|
+
* If the branch exists, returns it with token.
|
|
182
|
+
* If it doesn't exist, creates it.
|
|
183
|
+
*
|
|
184
|
+
* @param config - API configuration
|
|
185
|
+
* @param name - Branch name
|
|
186
|
+
* @returns Branch with token
|
|
187
|
+
*/
|
|
188
|
+
export async function getOrCreateBranch(config, name) {
|
|
189
|
+
// First try to get the existing branch
|
|
190
|
+
try {
|
|
191
|
+
const branch = await getBranch(config, name);
|
|
192
|
+
return { ...branch, wasCreated: false };
|
|
193
|
+
}
|
|
194
|
+
catch (error) {
|
|
195
|
+
// If it's a 404, create the branch
|
|
196
|
+
if (error instanceof BranchApiError && error.status === 404) {
|
|
197
|
+
const branch = await createBranch(config, name);
|
|
198
|
+
return { ...branch, wasCreated: true };
|
|
199
|
+
}
|
|
200
|
+
throw error;
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
//# sourceMappingURL=branches.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"branches.js","sourceRoot":"","sources":["../../src/api/branches.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"branches.test.d.ts","sourceRoot":"","sources":["../../src/api/branches.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,286 @@
|
|
|
1
|
+
import { describe, it, expect, vi, beforeEach, afterEach } from "vitest";
|
|
2
|
+
import { BranchApiError, createBranch, listBranches, getBranch, deleteBranch, branchExists, getOrCreateBranch, } from "./branches.js";
|
|
3
|
+
// Mock fetch globally
|
|
4
|
+
const mockFetch = vi.fn();
|
|
5
|
+
global.fetch = mockFetch;
|
|
6
|
+
describe("Branch API client", () => {
|
|
7
|
+
const config = {
|
|
8
|
+
baseUrl: "https://api.tinybird.co",
|
|
9
|
+
token: "p.test-token",
|
|
10
|
+
};
|
|
11
|
+
beforeEach(() => {
|
|
12
|
+
mockFetch.mockReset();
|
|
13
|
+
vi.useFakeTimers();
|
|
14
|
+
});
|
|
15
|
+
afterEach(() => {
|
|
16
|
+
vi.useRealTimers();
|
|
17
|
+
});
|
|
18
|
+
describe("createBranch", () => {
|
|
19
|
+
it("creates a branch and returns it", async () => {
|
|
20
|
+
const mockBranch = {
|
|
21
|
+
id: "branch-123",
|
|
22
|
+
name: "my-feature",
|
|
23
|
+
token: "p.branch-token",
|
|
24
|
+
created_at: "2024-01-01T00:00:00Z",
|
|
25
|
+
};
|
|
26
|
+
// 1. POST to /v1/environments returns a job
|
|
27
|
+
mockFetch.mockResolvedValueOnce({
|
|
28
|
+
ok: true,
|
|
29
|
+
json: () => Promise.resolve({
|
|
30
|
+
job: { id: "job-123", status: "waiting" },
|
|
31
|
+
workspace: { id: "ws-123" },
|
|
32
|
+
}),
|
|
33
|
+
});
|
|
34
|
+
// 2. Poll job - returns done
|
|
35
|
+
mockFetch.mockResolvedValueOnce({
|
|
36
|
+
ok: true,
|
|
37
|
+
json: () => Promise.resolve({ id: "job-123", status: "done" }),
|
|
38
|
+
});
|
|
39
|
+
// 3. Get branch with token
|
|
40
|
+
mockFetch.mockResolvedValueOnce({
|
|
41
|
+
ok: true,
|
|
42
|
+
json: () => Promise.resolve(mockBranch),
|
|
43
|
+
});
|
|
44
|
+
const result = await createBranch(config, "my-feature");
|
|
45
|
+
expect(mockFetch).toHaveBeenCalledTimes(3);
|
|
46
|
+
expect(mockFetch).toHaveBeenNthCalledWith(1, "https://api.tinybird.co/v1/environments?name=my-feature", {
|
|
47
|
+
method: "POST",
|
|
48
|
+
headers: {
|
|
49
|
+
Authorization: "Bearer p.test-token",
|
|
50
|
+
},
|
|
51
|
+
});
|
|
52
|
+
expect(mockFetch).toHaveBeenNthCalledWith(2, "https://api.tinybird.co/v0/jobs/job-123", {
|
|
53
|
+
method: "GET",
|
|
54
|
+
headers: {
|
|
55
|
+
Authorization: "Bearer p.test-token",
|
|
56
|
+
},
|
|
57
|
+
});
|
|
58
|
+
expect(mockFetch).toHaveBeenNthCalledWith(3, "https://api.tinybird.co/v0/environments/my-feature?with_token=true", {
|
|
59
|
+
method: "GET",
|
|
60
|
+
headers: {
|
|
61
|
+
Authorization: "Bearer p.test-token",
|
|
62
|
+
},
|
|
63
|
+
});
|
|
64
|
+
expect(result).toEqual(mockBranch);
|
|
65
|
+
});
|
|
66
|
+
it("polls job until done", async () => {
|
|
67
|
+
const mockBranch = {
|
|
68
|
+
id: "branch-123",
|
|
69
|
+
name: "my-feature",
|
|
70
|
+
token: "p.branch-token",
|
|
71
|
+
created_at: "2024-01-01T00:00:00Z",
|
|
72
|
+
};
|
|
73
|
+
// 1. POST to /v1/environments returns a job
|
|
74
|
+
mockFetch.mockResolvedValueOnce({
|
|
75
|
+
ok: true,
|
|
76
|
+
json: () => Promise.resolve({
|
|
77
|
+
job: { id: "job-123", status: "waiting" },
|
|
78
|
+
workspace: { id: "ws-123" },
|
|
79
|
+
}),
|
|
80
|
+
});
|
|
81
|
+
// 2. Poll job - waiting
|
|
82
|
+
mockFetch.mockResolvedValueOnce({
|
|
83
|
+
ok: true,
|
|
84
|
+
json: () => Promise.resolve({ id: "job-123", status: "waiting" }),
|
|
85
|
+
});
|
|
86
|
+
// 3. Poll job - working
|
|
87
|
+
mockFetch.mockResolvedValueOnce({
|
|
88
|
+
ok: true,
|
|
89
|
+
json: () => Promise.resolve({ id: "job-123", status: "working" }),
|
|
90
|
+
});
|
|
91
|
+
// 4. Poll job - done
|
|
92
|
+
mockFetch.mockResolvedValueOnce({
|
|
93
|
+
ok: true,
|
|
94
|
+
json: () => Promise.resolve({ id: "job-123", status: "done" }),
|
|
95
|
+
});
|
|
96
|
+
// 5. Get branch with token
|
|
97
|
+
mockFetch.mockResolvedValueOnce({
|
|
98
|
+
ok: true,
|
|
99
|
+
json: () => Promise.resolve(mockBranch),
|
|
100
|
+
});
|
|
101
|
+
// Start the async operation
|
|
102
|
+
const promise = createBranch(config, "my-feature");
|
|
103
|
+
// Advance timers and run all pending promises
|
|
104
|
+
await vi.runAllTimersAsync();
|
|
105
|
+
const result = await promise;
|
|
106
|
+
expect(mockFetch).toHaveBeenCalledTimes(5);
|
|
107
|
+
expect(result).toEqual(mockBranch);
|
|
108
|
+
});
|
|
109
|
+
it("throws BranchApiError on job error", async () => {
|
|
110
|
+
// 1. POST to /v1/environments returns a job
|
|
111
|
+
mockFetch.mockResolvedValueOnce({
|
|
112
|
+
ok: true,
|
|
113
|
+
json: () => Promise.resolve({
|
|
114
|
+
job: { id: "job-123", status: "waiting" },
|
|
115
|
+
}),
|
|
116
|
+
});
|
|
117
|
+
// 2. Poll job - error
|
|
118
|
+
mockFetch.mockResolvedValueOnce({
|
|
119
|
+
ok: true,
|
|
120
|
+
json: () => Promise.resolve({ id: "job-123", status: "error", error: "Something went wrong" }),
|
|
121
|
+
});
|
|
122
|
+
await expect(createBranch(config, "my-feature")).rejects.toThrow(BranchApiError);
|
|
123
|
+
});
|
|
124
|
+
it("throws BranchApiError on failure", async () => {
|
|
125
|
+
mockFetch.mockResolvedValueOnce({
|
|
126
|
+
ok: false,
|
|
127
|
+
status: 400,
|
|
128
|
+
statusText: "Bad Request",
|
|
129
|
+
text: () => Promise.resolve("Branch already exists"),
|
|
130
|
+
});
|
|
131
|
+
await expect(createBranch(config, "existing")).rejects.toThrow(BranchApiError);
|
|
132
|
+
});
|
|
133
|
+
});
|
|
134
|
+
describe("listBranches", () => {
|
|
135
|
+
it("returns array of branches", async () => {
|
|
136
|
+
const mockBranches = [
|
|
137
|
+
{ id: "1", name: "feature-a", created_at: "2024-01-01T00:00:00Z" },
|
|
138
|
+
{ id: "2", name: "feature-b", created_at: "2024-01-02T00:00:00Z" },
|
|
139
|
+
];
|
|
140
|
+
mockFetch.mockResolvedValueOnce({
|
|
141
|
+
ok: true,
|
|
142
|
+
json: () => Promise.resolve({ environments: mockBranches }),
|
|
143
|
+
});
|
|
144
|
+
const result = await listBranches(config);
|
|
145
|
+
expect(mockFetch).toHaveBeenCalledWith("https://api.tinybird.co/v1/environments", {
|
|
146
|
+
method: "GET",
|
|
147
|
+
headers: {
|
|
148
|
+
Authorization: "Bearer p.test-token",
|
|
149
|
+
},
|
|
150
|
+
});
|
|
151
|
+
expect(result).toEqual(mockBranches);
|
|
152
|
+
});
|
|
153
|
+
it("returns empty array when no branches", async () => {
|
|
154
|
+
mockFetch.mockResolvedValueOnce({
|
|
155
|
+
ok: true,
|
|
156
|
+
json: () => Promise.resolve({ environments: undefined }),
|
|
157
|
+
});
|
|
158
|
+
const result = await listBranches(config);
|
|
159
|
+
expect(result).toEqual([]);
|
|
160
|
+
});
|
|
161
|
+
});
|
|
162
|
+
describe("getBranch", () => {
|
|
163
|
+
it("returns branch with token", async () => {
|
|
164
|
+
const mockBranch = {
|
|
165
|
+
id: "branch-123",
|
|
166
|
+
name: "my-feature",
|
|
167
|
+
token: "p.branch-token",
|
|
168
|
+
created_at: "2024-01-01T00:00:00Z",
|
|
169
|
+
};
|
|
170
|
+
mockFetch.mockResolvedValueOnce({
|
|
171
|
+
ok: true,
|
|
172
|
+
json: () => Promise.resolve(mockBranch),
|
|
173
|
+
});
|
|
174
|
+
const result = await getBranch(config, "my-feature");
|
|
175
|
+
expect(mockFetch).toHaveBeenCalledWith("https://api.tinybird.co/v0/environments/my-feature?with_token=true", {
|
|
176
|
+
method: "GET",
|
|
177
|
+
headers: {
|
|
178
|
+
Authorization: "Bearer p.test-token",
|
|
179
|
+
},
|
|
180
|
+
});
|
|
181
|
+
expect(result).toEqual(mockBranch);
|
|
182
|
+
});
|
|
183
|
+
it("throws BranchApiError when branch not found", async () => {
|
|
184
|
+
mockFetch.mockResolvedValueOnce({
|
|
185
|
+
ok: false,
|
|
186
|
+
status: 404,
|
|
187
|
+
statusText: "Not Found",
|
|
188
|
+
text: () => Promise.resolve("Branch not found"),
|
|
189
|
+
});
|
|
190
|
+
await expect(getBranch(config, "nonexistent")).rejects.toThrow(BranchApiError);
|
|
191
|
+
});
|
|
192
|
+
});
|
|
193
|
+
describe("deleteBranch", () => {
|
|
194
|
+
it("deletes a branch successfully", async () => {
|
|
195
|
+
mockFetch.mockResolvedValueOnce({
|
|
196
|
+
ok: true,
|
|
197
|
+
});
|
|
198
|
+
await deleteBranch(config, "my-feature");
|
|
199
|
+
expect(mockFetch).toHaveBeenCalledWith("https://api.tinybird.co/v1/environments/my-feature", {
|
|
200
|
+
method: "DELETE",
|
|
201
|
+
headers: {
|
|
202
|
+
Authorization: "Bearer p.test-token",
|
|
203
|
+
},
|
|
204
|
+
});
|
|
205
|
+
});
|
|
206
|
+
});
|
|
207
|
+
describe("branchExists", () => {
|
|
208
|
+
it("returns true when branch exists", async () => {
|
|
209
|
+
mockFetch.mockResolvedValueOnce({
|
|
210
|
+
ok: true,
|
|
211
|
+
json: () => Promise.resolve({
|
|
212
|
+
environments: [
|
|
213
|
+
{ id: "1", name: "my-feature", created_at: "2024-01-01" },
|
|
214
|
+
],
|
|
215
|
+
}),
|
|
216
|
+
});
|
|
217
|
+
const result = await branchExists(config, "my-feature");
|
|
218
|
+
expect(result).toBe(true);
|
|
219
|
+
});
|
|
220
|
+
it("returns false when branch does not exist", async () => {
|
|
221
|
+
mockFetch.mockResolvedValueOnce({
|
|
222
|
+
ok: true,
|
|
223
|
+
json: () => Promise.resolve({ environments: [] }),
|
|
224
|
+
});
|
|
225
|
+
const result = await branchExists(config, "nonexistent");
|
|
226
|
+
expect(result).toBe(false);
|
|
227
|
+
});
|
|
228
|
+
it("throws on API error", async () => {
|
|
229
|
+
mockFetch.mockRejectedValueOnce(new Error("Network error"));
|
|
230
|
+
await expect(branchExists(config, "any")).rejects.toThrow("Network error");
|
|
231
|
+
});
|
|
232
|
+
});
|
|
233
|
+
describe("getOrCreateBranch", () => {
|
|
234
|
+
it("returns existing branch if found", async () => {
|
|
235
|
+
const mockBranch = {
|
|
236
|
+
id: "branch-123",
|
|
237
|
+
name: "existing-feature",
|
|
238
|
+
token: "p.branch-token",
|
|
239
|
+
created_at: "2024-01-01T00:00:00Z",
|
|
240
|
+
};
|
|
241
|
+
mockFetch.mockResolvedValueOnce({
|
|
242
|
+
ok: true,
|
|
243
|
+
json: () => Promise.resolve(mockBranch),
|
|
244
|
+
});
|
|
245
|
+
const result = await getOrCreateBranch(config, "existing-feature");
|
|
246
|
+
expect(result).toEqual({ ...mockBranch, wasCreated: false });
|
|
247
|
+
});
|
|
248
|
+
it("creates branch if not found", async () => {
|
|
249
|
+
const newBranch = {
|
|
250
|
+
id: "branch-456",
|
|
251
|
+
name: "new-feature",
|
|
252
|
+
token: "p.new-token",
|
|
253
|
+
created_at: "2024-01-02T00:00:00Z",
|
|
254
|
+
};
|
|
255
|
+
// 1. getBranch returns 404
|
|
256
|
+
mockFetch.mockResolvedValueOnce({
|
|
257
|
+
ok: false,
|
|
258
|
+
status: 404,
|
|
259
|
+
statusText: "Not Found",
|
|
260
|
+
text: () => Promise.resolve("Not found"),
|
|
261
|
+
});
|
|
262
|
+
// 2. createBranch: POST to /v1/environments returns a job
|
|
263
|
+
mockFetch.mockResolvedValueOnce({
|
|
264
|
+
ok: true,
|
|
265
|
+
json: () => Promise.resolve({
|
|
266
|
+
job: { id: "job-456", status: "waiting" },
|
|
267
|
+
workspace: { id: "ws-456" },
|
|
268
|
+
}),
|
|
269
|
+
});
|
|
270
|
+
// 3. Poll job - done
|
|
271
|
+
mockFetch.mockResolvedValueOnce({
|
|
272
|
+
ok: true,
|
|
273
|
+
json: () => Promise.resolve({ id: "job-456", status: "done" }),
|
|
274
|
+
});
|
|
275
|
+
// 4. Get branch with token
|
|
276
|
+
mockFetch.mockResolvedValueOnce({
|
|
277
|
+
ok: true,
|
|
278
|
+
json: () => Promise.resolve(newBranch),
|
|
279
|
+
});
|
|
280
|
+
const result = await getOrCreateBranch(config, "new-feature");
|
|
281
|
+
expect(result).toEqual({ ...newBranch, wasCreated: true });
|
|
282
|
+
expect(mockFetch).toHaveBeenCalledTimes(4);
|
|
283
|
+
});
|
|
284
|
+
});
|
|
285
|
+
});
|
|
286
|
+
//# sourceMappingURL=branches.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"branches.test.js","sourceRoot":"","sources":["../../src/api/branches.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Build and deploy resources to Tinybird API
|
|
3
|
+
* Uses the /v1/build endpoint to deploy all resources at once
|
|
4
|
+
*/
|
|
5
|
+
import type { GeneratedResources } from "../generator/index.js";
|
|
6
|
+
/**
|
|
7
|
+
* Configuration for building/deploying to Tinybird
|
|
8
|
+
*/
|
|
9
|
+
export interface BuildConfig {
|
|
10
|
+
/** Tinybird API base URL */
|
|
11
|
+
baseUrl: string;
|
|
12
|
+
/** API token for authentication */
|
|
13
|
+
token: string;
|
|
14
|
+
}
|
|
15
|
+
/**
|
|
16
|
+
* Resource info in the build response
|
|
17
|
+
*/
|
|
18
|
+
export interface ResourceInfo {
|
|
19
|
+
name: string;
|
|
20
|
+
type: string;
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Error details from the build endpoint
|
|
24
|
+
*/
|
|
25
|
+
export interface BuildError {
|
|
26
|
+
filename?: string;
|
|
27
|
+
type?: string;
|
|
28
|
+
error: string;
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Build response from the /v1/build endpoint
|
|
32
|
+
*/
|
|
33
|
+
export interface BuildResponse {
|
|
34
|
+
/** Result status */
|
|
35
|
+
result: "success" | "failed" | "no_changes";
|
|
36
|
+
/** Error message if failed (simple error) */
|
|
37
|
+
error?: string;
|
|
38
|
+
/** Array of errors if multiple (validation errors) */
|
|
39
|
+
errors?: BuildError[];
|
|
40
|
+
/** Build details */
|
|
41
|
+
build?: {
|
|
42
|
+
id: string;
|
|
43
|
+
datasources?: ResourceInfo[];
|
|
44
|
+
pipes?: ResourceInfo[];
|
|
45
|
+
/** Names of pipes that were changed in this build */
|
|
46
|
+
changed_pipe_names?: string[];
|
|
47
|
+
/** Names of newly created pipes in this build */
|
|
48
|
+
new_pipe_names?: string[];
|
|
49
|
+
/** Names of pipes that were deleted in this build */
|
|
50
|
+
deleted_pipe_names?: string[];
|
|
51
|
+
/** Names of datasources that were changed in this build */
|
|
52
|
+
changed_datasource_names?: string[];
|
|
53
|
+
/** Names of newly created datasources in this build */
|
|
54
|
+
new_datasource_names?: string[];
|
|
55
|
+
/** Names of datasources that were deleted in this build */
|
|
56
|
+
deleted_datasource_names?: string[];
|
|
57
|
+
};
|
|
58
|
+
}
|
|
59
|
+
/**
|
|
60
|
+
* Resource changes in a build
|
|
61
|
+
*/
|
|
62
|
+
export interface ResourceChanges {
|
|
63
|
+
/** Names of resources that were changed */
|
|
64
|
+
changed: string[];
|
|
65
|
+
/** Names of newly created resources */
|
|
66
|
+
created: string[];
|
|
67
|
+
/** Names of resources that were deleted */
|
|
68
|
+
deleted: string[];
|
|
69
|
+
}
|
|
70
|
+
/**
|
|
71
|
+
* Build result with additional metadata
|
|
72
|
+
*/
|
|
73
|
+
export interface BuildApiResult {
|
|
74
|
+
/** Whether the build was successful */
|
|
75
|
+
success: boolean;
|
|
76
|
+
/** Result status from API */
|
|
77
|
+
result: "success" | "failed" | "no_changes";
|
|
78
|
+
/** Error message if failed */
|
|
79
|
+
error?: string;
|
|
80
|
+
/** Number of datasources deployed */
|
|
81
|
+
datasourceCount: number;
|
|
82
|
+
/** Number of pipes deployed */
|
|
83
|
+
pipeCount: number;
|
|
84
|
+
/** Build ID if successful */
|
|
85
|
+
buildId?: string;
|
|
86
|
+
/** Pipe changes in this build */
|
|
87
|
+
pipes?: ResourceChanges;
|
|
88
|
+
/** Datasource changes in this build */
|
|
89
|
+
datasources?: ResourceChanges;
|
|
90
|
+
/** @deprecated Use pipes.changed instead */
|
|
91
|
+
changedPipeNames?: string[];
|
|
92
|
+
/** @deprecated Use pipes.created instead */
|
|
93
|
+
newPipeNames?: string[];
|
|
94
|
+
}
|
|
95
|
+
/**
|
|
96
|
+
* Build and deploy generated resources to Tinybird API
|
|
97
|
+
*
|
|
98
|
+
* Uses the /v1/build endpoint which accepts all resources in a single
|
|
99
|
+
* multipart form request.
|
|
100
|
+
*
|
|
101
|
+
* @param config - Build configuration with API URL and token
|
|
102
|
+
* @param resources - Generated resources to deploy
|
|
103
|
+
* @returns Build result
|
|
104
|
+
*
|
|
105
|
+
* @example
|
|
106
|
+
* ```ts
|
|
107
|
+
* const result = await buildToTinybird(
|
|
108
|
+
* {
|
|
109
|
+
* baseUrl: 'https://api.tinybird.co',
|
|
110
|
+
* token: 'p.xxx',
|
|
111
|
+
* },
|
|
112
|
+
* {
|
|
113
|
+
* datasources: [{ name: 'events', content: '...' }],
|
|
114
|
+
* pipes: [{ name: 'top_events', content: '...' }],
|
|
115
|
+
* }
|
|
116
|
+
* );
|
|
117
|
+
*
|
|
118
|
+
* if (result.success) {
|
|
119
|
+
* console.log('Build deployed successfully!');
|
|
120
|
+
* }
|
|
121
|
+
* ```
|
|
122
|
+
*/
|
|
123
|
+
export declare function buildToTinybird(config: BuildConfig, resources: GeneratedResources, options?: {
|
|
124
|
+
debug?: boolean;
|
|
125
|
+
}): Promise<BuildApiResult>;
|
|
126
|
+
/**
|
|
127
|
+
* Validate that the configuration is complete
|
|
128
|
+
*/
|
|
129
|
+
export declare function validateBuildConfig(config: Partial<BuildConfig>): asserts config is BuildConfig;
|
|
130
|
+
//# sourceMappingURL=build.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"build.d.ts","sourceRoot":"","sources":["../../src/api/build.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,uBAAuB,CAAC;AAEhE;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B,4BAA4B;IAC5B,OAAO,EAAE,MAAM,CAAC;IAChB,mCAAmC;IACnC,KAAK,EAAE,MAAM,CAAC;CACf;AAED;;GAEG;AACH,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;CACd;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,KAAK,EAAE,MAAM,CAAC;CACf;AAED;;GAEG;AACH,MAAM,WAAW,aAAa;IAC5B,oBAAoB;IACpB,MAAM,EAAE,SAAS,GAAG,QAAQ,GAAG,YAAY,CAAC;IAC5C,6CAA6C;IAC7C,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,sDAAsD;IACtD,MAAM,CAAC,EAAE,UAAU,EAAE,CAAC;IACtB,oBAAoB;IACpB,KAAK,CAAC,EAAE;QACN,EAAE,EAAE,MAAM,CAAC;QACX,WAAW,CAAC,EAAE,YAAY,EAAE,CAAC;QAC7B,KAAK,CAAC,EAAE,YAAY,EAAE,CAAC;QACvB,qDAAqD;QACrD,kBAAkB,CAAC,EAAE,MAAM,EAAE,CAAC;QAC9B,iDAAiD;QACjD,cAAc,CAAC,EAAE,MAAM,EAAE,CAAC;QAC1B,qDAAqD;QACrD,kBAAkB,CAAC,EAAE,MAAM,EAAE,CAAC;QAC9B,2DAA2D;QAC3D,wBAAwB,CAAC,EAAE,MAAM,EAAE,CAAC;QACpC,uDAAuD;QACvD,oBAAoB,CAAC,EAAE,MAAM,EAAE,CAAC;QAChC,2DAA2D;QAC3D,wBAAwB,CAAC,EAAE,MAAM,EAAE,CAAC;KACrC,CAAC;CACH;AAED;;GAEG;AACH,MAAM,WAAW,eAAe;IAC9B,2CAA2C;IAC3C,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,uCAAuC;IACvC,OAAO,EAAE,MAAM,EAAE,CAAC;IAClB,2CAA2C;IAC3C,OAAO,EAAE,MAAM,EAAE,CAAC;CACnB;AAED;;GAEG;AACH,MAAM,WAAW,cAAc;IAC7B,uCAAuC;IACvC,OAAO,EAAE,OAAO,CAAC;IACjB,6BAA6B;IAC7B,MAAM,EAAE,SAAS,GAAG,QAAQ,GAAG,YAAY,CAAC;IAC5C,8BAA8B;IAC9B,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,qCAAqC;IACrC,eAAe,EAAE,MAAM,CAAC;IACxB,+BAA+B;IAC/B,SAAS,EAAE,MAAM,CAAC;IAClB,6BAA6B;IAC7B,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,iCAAiC;IACjC,KAAK,CAAC,EAAE,eAAe,CAAC;IACxB,uCAAuC;IACvC,WAAW,CAAC,EAAE,eAAe,CAAC;IAC9B,4CAA4C;IAC5C,gBAAgB,CAAC,EAAE,MAAM,EAAE,CAAC;IAC5B,4CAA4C;IAC5C,YAAY,CAAC,EAAE,MAAM,EAAE,CAAC;CACzB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,wBAAsB,eAAe,CACnC,MAAM,EAAE,WAAW,EACnB,SAAS,EAAE,kBAAkB,EAC7B,OAAO,CAAC,EAAE;IAAE,KAAK,CAAC,EAAE,OAAO,CAAA;CAAE,GAC5B,OAAO,CAAC,cAAc,CAAC,CAuHzB;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,OAAO,CAAC,WAAW,CAAC,GAAG,OAAO,CAAC,MAAM,IAAI,WAAW,CAO/F"}
|