@squadbase/vite-server 0.1.12-dev.a9ac647 → 0.1.17-dev.3b633bb
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/dist/cli/index.js +14375 -1652
- package/dist/connectors/airtable-oauth.js +282 -46
- package/dist/connectors/airtable.js +319 -51
- package/dist/connectors/amplitude.js +322 -47
- package/dist/connectors/anthropic.js +135 -47
- package/dist/connectors/asana.js +327 -49
- package/dist/connectors/attio.js +302 -49
- package/dist/connectors/aws-billing.js +287 -46
- package/dist/connectors/azure-sql.js +421 -102
- package/dist/connectors/backlog-api-key.js +317 -47
- package/dist/connectors/clickup.js +338 -49
- package/dist/connectors/cosmosdb.js +305 -50
- package/dist/connectors/customerio.js +319 -47
- package/dist/connectors/dbt.js +340 -47
- package/dist/connectors/freshdesk.js +342 -53
- package/dist/connectors/freshsales.js +333 -52
- package/dist/connectors/freshservice.js +361 -53
- package/dist/connectors/gamma.js +327 -52
- package/dist/connectors/gemini.js +134 -47
- package/dist/connectors/github.js +386 -49
- package/dist/connectors/gmail-oauth.js +204 -7
- package/dist/connectors/gmail.js +350 -47
- package/dist/connectors/google-ads.js +288 -46
- package/dist/connectors/google-analytics-oauth.js +310 -46
- package/dist/connectors/google-analytics.js +547 -87
- package/dist/connectors/google-audit-log.js +438 -47
- package/dist/connectors/google-calendar-oauth.js +259 -46
- package/dist/connectors/google-calendar.js +359 -47
- package/dist/connectors/google-docs.js +220 -6
- package/dist/connectors/google-drive.js +262 -5
- package/dist/connectors/google-search-console-oauth.js +256 -46
- package/dist/connectors/google-sheets.js +272 -47
- package/dist/connectors/google-slides.js +205 -6
- package/dist/connectors/grafana.js +332 -49
- package/dist/connectors/hubspot-oauth.js +208 -5
- package/dist/connectors/hubspot.js +306 -49
- package/dist/connectors/influxdb.js +416 -51
- package/dist/connectors/intercom-oauth.js +210 -5
- package/dist/connectors/intercom.js +302 -49
- package/dist/connectors/jdbc.js +762 -110
- package/dist/connectors/jira-api-key.js +326 -47
- package/dist/connectors/kintone-api-token.js +281 -47
- package/dist/connectors/kintone.js +328 -47
- package/dist/connectors/linear.js +330 -49
- package/dist/connectors/linkedin-ads.js +268 -50
- package/dist/connectors/mailchimp-oauth.js +268 -46
- package/dist/connectors/mailchimp.js +320 -49
- package/dist/connectors/meta-ads-oauth.js +273 -48
- package/dist/connectors/meta-ads.js +285 -50
- package/dist/connectors/mixpanel.js +338 -47
- package/dist/connectors/monday.js +360 -49
- package/dist/connectors/mongodb.js +319 -57
- package/dist/connectors/notion-oauth.js +231 -5
- package/dist/connectors/notion.js +323 -51
- package/dist/connectors/openai.js +134 -47
- package/dist/connectors/oracle.js +454 -103
- package/dist/connectors/outlook-oauth.js +204 -5
- package/dist/connectors/powerbi-oauth.js +498 -5
- package/dist/connectors/salesforce.js +384 -49
- package/dist/connectors/semrush.js +609 -49
- package/dist/connectors/sentry.js +289 -50
- package/dist/connectors/shopify-oauth.js +187 -5
- package/dist/connectors/shopify.js +357 -47
- package/dist/connectors/sqlserver.js +415 -102
- package/dist/connectors/stripe-api-key.js +269 -46
- package/dist/connectors/stripe-oauth.js +202 -5
- package/dist/connectors/supabase.js +303 -48
- package/dist/connectors/tableau.js +536 -163
- package/dist/connectors/tiktok-ads.js +279 -48
- package/dist/connectors/wix-store.js +320 -49
- package/dist/connectors/zendesk-oauth.js +239 -5
- package/dist/connectors/zendesk.js +358 -47
- package/dist/index.d.ts +149 -1
- package/dist/index.js +15057 -2117
- package/dist/main.js +15005 -2073
- package/dist/vite-plugin.js +14752 -2019
- package/package.json +1 -1
|
@@ -1,48 +1,60 @@
|
|
|
1
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
2
|
+
var __esm = (fn, res) => function __init() {
|
|
3
|
+
return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
|
|
4
|
+
};
|
|
5
|
+
|
|
1
6
|
// ../connectors/src/parameter-definition.ts
|
|
2
|
-
var ParameterDefinition
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
7
|
+
var ParameterDefinition;
|
|
8
|
+
var init_parameter_definition = __esm({
|
|
9
|
+
"../connectors/src/parameter-definition.ts"() {
|
|
10
|
+
"use strict";
|
|
11
|
+
ParameterDefinition = class {
|
|
12
|
+
slug;
|
|
13
|
+
name;
|
|
14
|
+
description;
|
|
15
|
+
envVarBaseKey;
|
|
16
|
+
type;
|
|
17
|
+
secret;
|
|
18
|
+
required;
|
|
19
|
+
constructor(config) {
|
|
20
|
+
this.slug = config.slug;
|
|
21
|
+
this.name = config.name;
|
|
22
|
+
this.description = config.description;
|
|
23
|
+
this.envVarBaseKey = config.envVarBaseKey;
|
|
24
|
+
this.type = config.type;
|
|
25
|
+
this.secret = config.secret;
|
|
26
|
+
this.required = config.required;
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Get the parameter value from a ConnectorConnectionObject.
|
|
30
|
+
*/
|
|
31
|
+
getValue(connection2) {
|
|
32
|
+
const param = connection2.parameters.find(
|
|
33
|
+
(p) => p.parameterSlug === this.slug
|
|
34
|
+
);
|
|
35
|
+
if (!param || param.value == null) {
|
|
36
|
+
throw new Error(
|
|
37
|
+
`Parameter "${this.slug}" not found or has no value in connection "${connection2.id}"`
|
|
38
|
+
);
|
|
39
|
+
}
|
|
40
|
+
return param.value;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Try to get the parameter value. Returns undefined if not found (for optional params).
|
|
44
|
+
*/
|
|
45
|
+
tryGetValue(connection2) {
|
|
46
|
+
const param = connection2.parameters.find(
|
|
47
|
+
(p) => p.parameterSlug === this.slug
|
|
48
|
+
);
|
|
49
|
+
if (!param || param.value == null) return void 0;
|
|
50
|
+
return param.value;
|
|
51
|
+
}
|
|
52
|
+
};
|
|
42
53
|
}
|
|
43
|
-
};
|
|
54
|
+
});
|
|
44
55
|
|
|
45
56
|
// ../connectors/src/connectors/backlog/parameters.ts
|
|
57
|
+
init_parameter_definition();
|
|
46
58
|
var parameters = {
|
|
47
59
|
spaceUrl: new ParameterDefinition({
|
|
48
60
|
slug: "space-url",
|
|
@@ -151,6 +163,28 @@ var ConnectorPlugin = class _ConnectorPlugin {
|
|
|
151
163
|
tools;
|
|
152
164
|
query;
|
|
153
165
|
checkConnection;
|
|
166
|
+
/**
|
|
167
|
+
* SQPD-1212: Logic-based, rule-driven connection setup. Connectors that
|
|
168
|
+
* implement this expose a step-by-step exploration flow (database/schema/
|
|
169
|
+
* table/etc. discovery) that the dashboard backend drives via the
|
|
170
|
+
* `/connections/:connectionId/setup` endpoint. Implement by delegating to
|
|
171
|
+
* `runSetupFlow` from `setup-flow.ts`.
|
|
172
|
+
*/
|
|
173
|
+
setup;
|
|
174
|
+
/**
|
|
175
|
+
* Opt-out of the default "verify before save" behavior on connection
|
|
176
|
+
* creation. The backend invokes `checkConnection` synchronously while
|
|
177
|
+
* creating the connection and aborts (no row inserted) if it fails — this
|
|
178
|
+
* flag disables that for connectors where the check cannot succeed pre-save:
|
|
179
|
+
*
|
|
180
|
+
* - `squadbase-db` populates `connection-url` only after Neon provisioning
|
|
181
|
+
* - OAuth connectors require an OAuth-aware proxyFetch keyed by the
|
|
182
|
+
* connectionId, which doesn't exist until the row is saved
|
|
183
|
+
*
|
|
184
|
+
* Exceptions are the explicit position; new credential-input connectors get
|
|
185
|
+
* the default verify-on-create behavior without opt-in.
|
|
186
|
+
*/
|
|
187
|
+
skipConnectionCheckOnCreate;
|
|
154
188
|
constructor(config) {
|
|
155
189
|
this.slug = config.slug;
|
|
156
190
|
this.authType = config.authType;
|
|
@@ -167,6 +201,8 @@ var ConnectorPlugin = class _ConnectorPlugin {
|
|
|
167
201
|
this.tools = config.tools;
|
|
168
202
|
this.query = config.query;
|
|
169
203
|
this.checkConnection = config.checkConnection;
|
|
204
|
+
this.setup = config.setup;
|
|
205
|
+
this.skipConnectionCheckOnCreate = config.skipConnectionCheckOnCreate;
|
|
170
206
|
}
|
|
171
207
|
get connectorKey() {
|
|
172
208
|
return _ConnectorPlugin.deriveKey(this.slug, this.authType);
|
|
@@ -231,6 +267,76 @@ var ConnectorPlugin = class _ConnectorPlugin {
|
|
|
231
267
|
}
|
|
232
268
|
};
|
|
233
269
|
|
|
270
|
+
// ../connectors/src/setup-flow.ts
|
|
271
|
+
async function runSetupFlow(flow, params, ctx, config) {
|
|
272
|
+
const runtime = {
|
|
273
|
+
params,
|
|
274
|
+
language: ctx.language,
|
|
275
|
+
config
|
|
276
|
+
};
|
|
277
|
+
let state = flow.initialState();
|
|
278
|
+
let answerIdx = 0;
|
|
279
|
+
const pendingParameterUpdates = [];
|
|
280
|
+
for (const step of flow.steps) {
|
|
281
|
+
const ans = ctx.answers[answerIdx];
|
|
282
|
+
if (ans && ans.questionSlug === step.slug) {
|
|
283
|
+
state = step.applyAnswer(state, ans.answer);
|
|
284
|
+
if (step.toParameterUpdates) {
|
|
285
|
+
pendingParameterUpdates.push(...step.toParameterUpdates(state));
|
|
286
|
+
}
|
|
287
|
+
answerIdx += 1;
|
|
288
|
+
continue;
|
|
289
|
+
}
|
|
290
|
+
const resolvedAllowFreeText = step.allowFreeText !== void 0 ? step.allowFreeText : true;
|
|
291
|
+
if (step.type === "text") {
|
|
292
|
+
if (step.fetchOptions) {
|
|
293
|
+
const options2 = await step.fetchOptions(state, runtime);
|
|
294
|
+
if (options2.length === 0) {
|
|
295
|
+
continue;
|
|
296
|
+
}
|
|
297
|
+
}
|
|
298
|
+
return {
|
|
299
|
+
type: "nextQuestion",
|
|
300
|
+
questionSlug: step.slug,
|
|
301
|
+
question: step.question[ctx.language],
|
|
302
|
+
questionType: "text",
|
|
303
|
+
allowFreeText: resolvedAllowFreeText,
|
|
304
|
+
...pendingParameterUpdates.length > 0 && {
|
|
305
|
+
parameterUpdates: pendingParameterUpdates
|
|
306
|
+
}
|
|
307
|
+
};
|
|
308
|
+
}
|
|
309
|
+
const options = step.fetchOptions ? await step.fetchOptions(state, runtime) : [];
|
|
310
|
+
if (options.length === 0) {
|
|
311
|
+
continue;
|
|
312
|
+
}
|
|
313
|
+
return {
|
|
314
|
+
type: "nextQuestion",
|
|
315
|
+
questionSlug: step.slug,
|
|
316
|
+
question: step.question[ctx.language],
|
|
317
|
+
questionType: step.type,
|
|
318
|
+
options,
|
|
319
|
+
allowFreeText: resolvedAllowFreeText,
|
|
320
|
+
...pendingParameterUpdates.length > 0 && {
|
|
321
|
+
parameterUpdates: pendingParameterUpdates
|
|
322
|
+
}
|
|
323
|
+
};
|
|
324
|
+
}
|
|
325
|
+
const dataInvestigationResult = await flow.finalize(state, runtime);
|
|
326
|
+
return {
|
|
327
|
+
type: "fulfilled",
|
|
328
|
+
dataInvestigationResult,
|
|
329
|
+
...pendingParameterUpdates.length > 0 && {
|
|
330
|
+
parameterUpdates: pendingParameterUpdates
|
|
331
|
+
}
|
|
332
|
+
};
|
|
333
|
+
}
|
|
334
|
+
async function resolveSetupSelection(params) {
|
|
335
|
+
const { selected, allSentinel, fetchAll, limit } = params;
|
|
336
|
+
const resolved = selected.includes(allSentinel) ? await fetchAll() : selected.filter((v) => v !== allSentinel);
|
|
337
|
+
return resolved.slice(0, limit);
|
|
338
|
+
}
|
|
339
|
+
|
|
234
340
|
// ../connectors/src/auth-types.ts
|
|
235
341
|
var AUTH_TYPES = {
|
|
236
342
|
OAUTH: "oauth",
|
|
@@ -255,6 +361,114 @@ var backlogOnboarding = new ConnectorOnboarding({
|
|
|
255
361
|
}
|
|
256
362
|
});
|
|
257
363
|
|
|
364
|
+
// ../connectors/src/connectors/backlog/utils.ts
|
|
365
|
+
async function apiFetch(params, path2, init) {
|
|
366
|
+
const spaceUrl = params[parameters.spaceUrl.slug];
|
|
367
|
+
const apiKey = params[parameters.apiKey.slug];
|
|
368
|
+
if (!spaceUrl) {
|
|
369
|
+
throw new Error("backlog: missing required parameter: space-url");
|
|
370
|
+
}
|
|
371
|
+
if (!apiKey) {
|
|
372
|
+
throw new Error("backlog: missing required parameter: api-key");
|
|
373
|
+
}
|
|
374
|
+
const trimmedPath = path2.replace(/^\/+/, "");
|
|
375
|
+
const separator = trimmedPath.includes("?") ? "&" : "?";
|
|
376
|
+
const url = `${spaceUrl.replace(/\/+$/, "")}/api/v2/${trimmedPath}${separator}apiKey=${encodeURIComponent(apiKey)}`;
|
|
377
|
+
const headers = new Headers(init?.headers);
|
|
378
|
+
if (!headers.has("Accept")) headers.set("Accept", "application/json");
|
|
379
|
+
return fetch(url, { ...init, headers });
|
|
380
|
+
}
|
|
381
|
+
|
|
382
|
+
// ../connectors/src/connectors/backlog/setup-flow.ts
|
|
383
|
+
var ALL_PROJECTS = "__ALL_PROJECTS__";
|
|
384
|
+
var BACKLOG_SETUP_MAX_PROJECTS = 20;
|
|
385
|
+
async function listProjects(params) {
|
|
386
|
+
const res = await apiFetch(params, "projects?archived=false");
|
|
387
|
+
if (!res.ok) {
|
|
388
|
+
const body = await res.text().catch(() => res.statusText);
|
|
389
|
+
throw new Error(`backlog: listProjects failed (${res.status}): ${body}`);
|
|
390
|
+
}
|
|
391
|
+
return await res.json();
|
|
392
|
+
}
|
|
393
|
+
async function listIssueTypes(params, projectIdOrKey) {
|
|
394
|
+
const res = await apiFetch(
|
|
395
|
+
params,
|
|
396
|
+
`projects/${encodeURIComponent(projectIdOrKey)}/issueTypes`
|
|
397
|
+
);
|
|
398
|
+
if (!res.ok) return [];
|
|
399
|
+
return await res.json();
|
|
400
|
+
}
|
|
401
|
+
async function listStatuses(params, projectIdOrKey) {
|
|
402
|
+
const res = await apiFetch(
|
|
403
|
+
params,
|
|
404
|
+
`projects/${encodeURIComponent(projectIdOrKey)}/statuses`
|
|
405
|
+
);
|
|
406
|
+
if (!res.ok) return [];
|
|
407
|
+
return await res.json();
|
|
408
|
+
}
|
|
409
|
+
var backlogSetupFlow = {
|
|
410
|
+
initialState: () => ({}),
|
|
411
|
+
steps: [
|
|
412
|
+
{
|
|
413
|
+
slug: "projects",
|
|
414
|
+
type: "multiSelect",
|
|
415
|
+
question: {
|
|
416
|
+
ja: "\u5BFE\u8C61\u306E\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8\u3092\u9078\u3093\u3067\u304F\u3060\u3055\u3044\uFF08\u8907\u6570\u9078\u629E\u53EF\uFF09",
|
|
417
|
+
en: "Select target projects (multi-select allowed)"
|
|
418
|
+
},
|
|
419
|
+
async fetchOptions(_state, rt) {
|
|
420
|
+
const projects = await listProjects(rt.params);
|
|
421
|
+
const projectOptions = projects.filter((p) => p.id != null && p.name).map((p) => ({
|
|
422
|
+
value: String(p.id),
|
|
423
|
+
label: `${p.name} (${p.projectKey})`
|
|
424
|
+
}));
|
|
425
|
+
return [
|
|
426
|
+
{
|
|
427
|
+
value: ALL_PROJECTS,
|
|
428
|
+
label: rt.language === "ja" ? "\u3059\u3079\u3066\u306E\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8" : "All projects"
|
|
429
|
+
},
|
|
430
|
+
...projectOptions
|
|
431
|
+
];
|
|
432
|
+
},
|
|
433
|
+
applyAnswer: (state, answer) => ({ ...state, projects: answer })
|
|
434
|
+
}
|
|
435
|
+
],
|
|
436
|
+
async finalize(state, rt) {
|
|
437
|
+
if (!state.projects) {
|
|
438
|
+
throw new Error("Backlog setup: incomplete state on finalize");
|
|
439
|
+
}
|
|
440
|
+
const allProjects = await listProjects(rt.params);
|
|
441
|
+
const projectById = new Map(
|
|
442
|
+
allProjects.map((p) => [String(p.id), p])
|
|
443
|
+
);
|
|
444
|
+
const targetIds = await resolveSetupSelection({
|
|
445
|
+
selected: state.projects,
|
|
446
|
+
allSentinel: ALL_PROJECTS,
|
|
447
|
+
fetchAll: async () => allProjects.map((p) => String(p.id)).filter((id) => id),
|
|
448
|
+
limit: BACKLOG_SETUP_MAX_PROJECTS
|
|
449
|
+
});
|
|
450
|
+
const sections = ["## Backlog", ""];
|
|
451
|
+
for (const id of targetIds) {
|
|
452
|
+
const project = projectById.get(id);
|
|
453
|
+
if (!project) {
|
|
454
|
+
sections.push(`### Project: ${id}`, "", "_Not found._", "");
|
|
455
|
+
continue;
|
|
456
|
+
}
|
|
457
|
+
sections.push(`### Project: ${project.name} (${project.projectKey})`, "");
|
|
458
|
+
const [issueTypes, statuses] = await Promise.all([
|
|
459
|
+
listIssueTypes(rt.params, id),
|
|
460
|
+
listStatuses(rt.params, id)
|
|
461
|
+
]);
|
|
462
|
+
sections.push(`- Issue types (${issueTypes.length}):`);
|
|
463
|
+
for (const t of issueTypes) sections.push(` - ${t.name}`);
|
|
464
|
+
sections.push(`- Statuses (${statuses.length}):`);
|
|
465
|
+
for (const s of statuses) sections.push(` - ${s.name}`);
|
|
466
|
+
sections.push("");
|
|
467
|
+
}
|
|
468
|
+
return sections.join("\n");
|
|
469
|
+
}
|
|
470
|
+
};
|
|
471
|
+
|
|
258
472
|
// ../connectors/src/connectors/backlog/tools/request.ts
|
|
259
473
|
import { z } from "zod";
|
|
260
474
|
var REQUEST_TIMEOUT_MS = 6e4;
|
|
@@ -490,7 +704,43 @@ await backlog.request("/api/v2/issues", {
|
|
|
490
704
|
- sort: "created", "updated", "issueType", "category", "priority" \u7B49
|
|
491
705
|
- order: "asc" \u307E\u305F\u306F "desc"`
|
|
492
706
|
},
|
|
493
|
-
tools
|
|
707
|
+
tools,
|
|
708
|
+
setup: (params, ctx, config) => runSetupFlow(backlogSetupFlow, params, ctx, config),
|
|
709
|
+
async checkConnection(params, _config) {
|
|
710
|
+
try {
|
|
711
|
+
const spaceUrl = params[parameters.spaceUrl.slug];
|
|
712
|
+
const apiKey = params[parameters.apiKey.slug];
|
|
713
|
+
if (!spaceUrl || !apiKey) {
|
|
714
|
+
return {
|
|
715
|
+
success: false,
|
|
716
|
+
error: "Missing required parameters: space-url and api-key"
|
|
717
|
+
};
|
|
718
|
+
}
|
|
719
|
+
const host = spaceUrl.replace(/\/+$/, "");
|
|
720
|
+
const res = await fetch(
|
|
721
|
+
`${host}/api/v2/users/myself?apiKey=${encodeURIComponent(apiKey)}`,
|
|
722
|
+
{
|
|
723
|
+
method: "GET",
|
|
724
|
+
headers: {
|
|
725
|
+
Accept: "application/json"
|
|
726
|
+
}
|
|
727
|
+
}
|
|
728
|
+
);
|
|
729
|
+
if (!res.ok) {
|
|
730
|
+
const errorText = await res.text().catch(() => res.statusText);
|
|
731
|
+
return {
|
|
732
|
+
success: false,
|
|
733
|
+
error: `Backlog API failed: HTTP ${res.status} ${errorText}`
|
|
734
|
+
};
|
|
735
|
+
}
|
|
736
|
+
return { success: true };
|
|
737
|
+
} catch (error) {
|
|
738
|
+
return {
|
|
739
|
+
success: false,
|
|
740
|
+
error: error instanceof Error ? error.message : String(error)
|
|
741
|
+
};
|
|
742
|
+
}
|
|
743
|
+
}
|
|
494
744
|
});
|
|
495
745
|
|
|
496
746
|
// src/connectors/create-connector-sdk.ts
|
|
@@ -519,6 +769,7 @@ function resolveEnvVarOptional(entry, key) {
|
|
|
519
769
|
import { getContext } from "hono/context-storage";
|
|
520
770
|
import { getCookie } from "hono/cookie";
|
|
521
771
|
var APP_SESSION_COOKIE_NAME = "__Host-squadbase-session";
|
|
772
|
+
var TABLEAU_SESSION_SENTINEL_URL = "squadbase://tableau-session/";
|
|
522
773
|
function normalizeHeaders(input) {
|
|
523
774
|
const out = {};
|
|
524
775
|
if (!input) return out;
|
|
@@ -527,6 +778,11 @@ function normalizeHeaders(input) {
|
|
|
527
778
|
});
|
|
528
779
|
return out;
|
|
529
780
|
}
|
|
781
|
+
function extractInputUrl(input) {
|
|
782
|
+
if (typeof input === "string") return input;
|
|
783
|
+
if (input instanceof URL) return input.href;
|
|
784
|
+
return input.url;
|
|
785
|
+
}
|
|
530
786
|
function createSandboxProxyFetch(connectionId) {
|
|
531
787
|
return async (input, init) => {
|
|
532
788
|
const token = process.env.INTERNAL_SQUADBASE_OAUTH_MACHINE_CREDENTIAL;
|
|
@@ -536,10 +792,17 @@ function createSandboxProxyFetch(connectionId) {
|
|
|
536
792
|
"Connection proxy is not configured. Please check your deployment settings."
|
|
537
793
|
);
|
|
538
794
|
}
|
|
539
|
-
const originalUrl =
|
|
795
|
+
const originalUrl = extractInputUrl(input);
|
|
796
|
+
const baseDomain = process.env["SQUADBASE_PREVIEW_BASE_DOMAIN"] ?? "preview.app.squadbase.dev";
|
|
797
|
+
if (originalUrl === TABLEAU_SESSION_SENTINEL_URL) {
|
|
798
|
+
const sessionUrl = `https://${sandboxId}.${baseDomain}/_sqcore/connections/${connectionId}/tableau-session`;
|
|
799
|
+
return fetch(sessionUrl, {
|
|
800
|
+
method: "POST",
|
|
801
|
+
headers: { Authorization: `Bearer ${token}` }
|
|
802
|
+
});
|
|
803
|
+
}
|
|
540
804
|
const originalMethod = init?.method ?? "GET";
|
|
541
805
|
const originalBody = init?.body ? JSON.parse(init.body) : void 0;
|
|
542
|
-
const baseDomain = process.env["SQUADBASE_PREVIEW_BASE_DOMAIN"] ?? "preview.app.squadbase.dev";
|
|
543
806
|
const proxyUrl = `https://${sandboxId}.${baseDomain}/_sqcore/connections/${connectionId}/request`;
|
|
544
807
|
return fetch(proxyUrl, {
|
|
545
808
|
method: "POST",
|
|
@@ -565,10 +828,9 @@ function createDeployedAppProxyFetch(connectionId) {
|
|
|
565
828
|
}
|
|
566
829
|
const baseDomain = process.env["SQUADBASE_APP_BASE_DOMAIN"] ?? "squadbase.app";
|
|
567
830
|
const proxyUrl = `https://${projectId}.${baseDomain}/_sqcore/connections/${connectionId}/request`;
|
|
831
|
+
const sessionUrl = `https://${projectId}.${baseDomain}/_sqcore/connections/${connectionId}/tableau-session`;
|
|
568
832
|
return async (input, init) => {
|
|
569
|
-
const originalUrl =
|
|
570
|
-
const originalMethod = init?.method ?? "GET";
|
|
571
|
-
const originalBody = init?.body ? JSON.parse(init.body) : void 0;
|
|
833
|
+
const originalUrl = extractInputUrl(input);
|
|
572
834
|
const c = getContext();
|
|
573
835
|
const appSession = getCookie(c, APP_SESSION_COOKIE_NAME);
|
|
574
836
|
if (!appSession) {
|
|
@@ -576,6 +838,14 @@ function createDeployedAppProxyFetch(connectionId) {
|
|
|
576
838
|
"No authentication method available for connection proxy."
|
|
577
839
|
);
|
|
578
840
|
}
|
|
841
|
+
if (originalUrl === TABLEAU_SESSION_SENTINEL_URL) {
|
|
842
|
+
return fetch(sessionUrl, {
|
|
843
|
+
method: "POST",
|
|
844
|
+
headers: { Authorization: `Bearer ${appSession}` }
|
|
845
|
+
});
|
|
846
|
+
}
|
|
847
|
+
const originalMethod = init?.method ?? "GET";
|
|
848
|
+
const originalBody = init?.body ? JSON.parse(init.body) : void 0;
|
|
579
849
|
return fetch(proxyUrl, {
|
|
580
850
|
method: "POST",
|
|
581
851
|
headers: {
|