@squadbase/vite-server 0.1.9-dev.f236b23 → 0.1.10-dev.cec85c2
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 +843 -364
- package/dist/connectors/aws-billing.js +18 -4
- package/dist/connectors/azure-sql.js +20374 -16
- package/dist/connectors/cosmosdb.d.ts +5 -0
- package/dist/connectors/cosmosdb.js +743 -0
- package/dist/connectors/google-ads.js +8 -48
- package/dist/connectors/jdbc.js +244 -165
- package/dist/connectors/oracle.js +20408 -26
- package/dist/connectors/semrush.js +109 -21
- package/dist/connectors/sqlserver.js +20370 -15
- package/dist/index.js +843 -364
- package/dist/main.js +843 -364
- package/dist/vite-plugin.js +843 -364
- package/package.json +7 -2
package/dist/main.js
CHANGED
|
@@ -909,17 +909,17 @@ var require_nacl_fast = __commonJS({
|
|
|
909
909
|
}
|
|
910
910
|
var sigma = new Uint8Array([101, 120, 112, 97, 110, 100, 32, 51, 50, 45, 98, 121, 116, 101, 32, 107]);
|
|
911
911
|
function crypto_stream_salsa20_xor(c6, cpos, m4, mpos, b6, n2, k6) {
|
|
912
|
-
var
|
|
912
|
+
var z98 = new Uint8Array(16), x = new Uint8Array(64);
|
|
913
913
|
var u, i6;
|
|
914
|
-
for (i6 = 0; i6 < 16; i6++)
|
|
915
|
-
for (i6 = 0; i6 < 8; i6++)
|
|
914
|
+
for (i6 = 0; i6 < 16; i6++) z98[i6] = 0;
|
|
915
|
+
for (i6 = 0; i6 < 8; i6++) z98[i6] = n2[i6];
|
|
916
916
|
while (b6 >= 64) {
|
|
917
|
-
crypto_core_salsa20(x,
|
|
917
|
+
crypto_core_salsa20(x, z98, k6, sigma);
|
|
918
918
|
for (i6 = 0; i6 < 64; i6++) c6[cpos + i6] = m4[mpos + i6] ^ x[i6];
|
|
919
919
|
u = 1;
|
|
920
920
|
for (i6 = 8; i6 < 16; i6++) {
|
|
921
|
-
u = u + (
|
|
922
|
-
|
|
921
|
+
u = u + (z98[i6] & 255) | 0;
|
|
922
|
+
z98[i6] = u & 255;
|
|
923
923
|
u >>>= 8;
|
|
924
924
|
}
|
|
925
925
|
b6 -= 64;
|
|
@@ -927,30 +927,30 @@ var require_nacl_fast = __commonJS({
|
|
|
927
927
|
mpos += 64;
|
|
928
928
|
}
|
|
929
929
|
if (b6 > 0) {
|
|
930
|
-
crypto_core_salsa20(x,
|
|
930
|
+
crypto_core_salsa20(x, z98, k6, sigma);
|
|
931
931
|
for (i6 = 0; i6 < b6; i6++) c6[cpos + i6] = m4[mpos + i6] ^ x[i6];
|
|
932
932
|
}
|
|
933
933
|
return 0;
|
|
934
934
|
}
|
|
935
935
|
function crypto_stream_salsa20(c6, cpos, b6, n2, k6) {
|
|
936
|
-
var
|
|
936
|
+
var z98 = new Uint8Array(16), x = new Uint8Array(64);
|
|
937
937
|
var u, i6;
|
|
938
|
-
for (i6 = 0; i6 < 16; i6++)
|
|
939
|
-
for (i6 = 0; i6 < 8; i6++)
|
|
938
|
+
for (i6 = 0; i6 < 16; i6++) z98[i6] = 0;
|
|
939
|
+
for (i6 = 0; i6 < 8; i6++) z98[i6] = n2[i6];
|
|
940
940
|
while (b6 >= 64) {
|
|
941
|
-
crypto_core_salsa20(x,
|
|
941
|
+
crypto_core_salsa20(x, z98, k6, sigma);
|
|
942
942
|
for (i6 = 0; i6 < 64; i6++) c6[cpos + i6] = x[i6];
|
|
943
943
|
u = 1;
|
|
944
944
|
for (i6 = 8; i6 < 16; i6++) {
|
|
945
|
-
u = u + (
|
|
946
|
-
|
|
945
|
+
u = u + (z98[i6] & 255) | 0;
|
|
946
|
+
z98[i6] = u & 255;
|
|
947
947
|
u >>>= 8;
|
|
948
948
|
}
|
|
949
949
|
b6 -= 64;
|
|
950
950
|
cpos += 64;
|
|
951
951
|
}
|
|
952
952
|
if (b6 > 0) {
|
|
953
|
-
crypto_core_salsa20(x,
|
|
953
|
+
crypto_core_salsa20(x, z98, k6, sigma);
|
|
954
954
|
for (i6 = 0; i6 < b6; i6++) c6[cpos + i6] = x[i6];
|
|
955
955
|
}
|
|
956
956
|
return 0;
|
|
@@ -1830,12 +1830,12 @@ var require_nacl_fast = __commonJS({
|
|
|
1830
1830
|
for (a6 = 0; a6 < 16; a6++) o2[a6] = c6[a6];
|
|
1831
1831
|
}
|
|
1832
1832
|
function crypto_scalarmult(q2, n2, p2) {
|
|
1833
|
-
var
|
|
1833
|
+
var z98 = new Uint8Array(32);
|
|
1834
1834
|
var x = new Float64Array(80), r6, i6;
|
|
1835
1835
|
var a6 = gf(), b6 = gf(), c6 = gf(), d6 = gf(), e6 = gf(), f6 = gf();
|
|
1836
|
-
for (i6 = 0; i6 < 31; i6++)
|
|
1837
|
-
|
|
1838
|
-
|
|
1836
|
+
for (i6 = 0; i6 < 31; i6++) z98[i6] = n2[i6];
|
|
1837
|
+
z98[31] = n2[31] & 127 | 64;
|
|
1838
|
+
z98[0] &= 248;
|
|
1839
1839
|
unpack25519(x, p2);
|
|
1840
1840
|
for (i6 = 0; i6 < 16; i6++) {
|
|
1841
1841
|
b6[i6] = x[i6];
|
|
@@ -1843,7 +1843,7 @@ var require_nacl_fast = __commonJS({
|
|
|
1843
1843
|
}
|
|
1844
1844
|
a6[0] = d6[0] = 1;
|
|
1845
1845
|
for (i6 = 254; i6 >= 0; --i6) {
|
|
1846
|
-
r6 =
|
|
1846
|
+
r6 = z98[i6 >>> 3] >>> (i6 & 7) & 1;
|
|
1847
1847
|
sel25519(a6, b6, r6);
|
|
1848
1848
|
sel25519(c6, d6, r6);
|
|
1849
1849
|
A(e6, a6, c6);
|
|
@@ -4860,8 +4860,8 @@ var require_poly1305 = __commonJS({
|
|
|
4860
4860
|
});
|
|
4861
4861
|
var u = {}, w;
|
|
4862
4862
|
for (w in b6) b6.hasOwnProperty(w) && (u[w] = b6[w]);
|
|
4863
|
-
var x = "object" === typeof window, y = "function" === typeof importScripts,
|
|
4864
|
-
if (
|
|
4863
|
+
var x = "object" === typeof window, y = "function" === typeof importScripts, z98 = "object" === typeof process && "object" === typeof process.versions && "string" === typeof process.versions.node, B = "", C, D, E, F, G;
|
|
4864
|
+
if (z98) B = y ? __require("path").dirname(B) + "/" : __dirname + "/", C = function(a6, c6) {
|
|
4865
4865
|
var d6 = H(a6);
|
|
4866
4866
|
if (d6) return c6 ? d6 : d6.toString();
|
|
4867
4867
|
F || (F = __require("fs"));
|
|
@@ -5117,7 +5117,7 @@ var require_poly1305 = __commonJS({
|
|
|
5117
5117
|
function H(a6) {
|
|
5118
5118
|
if (a6.startsWith(V)) {
|
|
5119
5119
|
a6 = a6.slice(V.length);
|
|
5120
|
-
if ("boolean" === typeof
|
|
5120
|
+
if ("boolean" === typeof z98 && z98) {
|
|
5121
5121
|
var c6 = Buffer.from(a6, "base64");
|
|
5122
5122
|
c6 = new Uint8Array(c6.buffer, c6.byteOffset, c6.byteLength);
|
|
5123
5123
|
} else try {
|
|
@@ -39040,14 +39040,14 @@ var init_NormalizedSchema = __esm({
|
|
|
39040
39040
|
throw new Error("@smithy/core/schema - cannot iterate non-struct schema.");
|
|
39041
39041
|
}
|
|
39042
39042
|
const struct = this.getSchema();
|
|
39043
|
-
const
|
|
39043
|
+
const z98 = struct[4].length;
|
|
39044
39044
|
let it = struct[anno.it];
|
|
39045
|
-
if (it &&
|
|
39045
|
+
if (it && z98 === it.length) {
|
|
39046
39046
|
yield* it;
|
|
39047
39047
|
return;
|
|
39048
39048
|
}
|
|
39049
|
-
it = Array(
|
|
39050
|
-
for (let i6 = 0; i6 <
|
|
39049
|
+
it = Array(z98);
|
|
39050
|
+
for (let i6 = 0; i6 < z98; ++i6) {
|
|
39051
39051
|
const k6 = struct[4][i6];
|
|
39052
39052
|
const v = member([struct[5][i6], 0], k6);
|
|
39053
39053
|
yield it[i6] = [k6, v];
|
|
@@ -39728,12 +39728,12 @@ var init_split_header = __esm({
|
|
|
39728
39728
|
"../../node_modules/@smithy/core/dist-es/submodules/serde/split-header.js"() {
|
|
39729
39729
|
"use strict";
|
|
39730
39730
|
splitHeader = (value) => {
|
|
39731
|
-
const
|
|
39731
|
+
const z98 = value.length;
|
|
39732
39732
|
const values = [];
|
|
39733
39733
|
let withinQuotes = false;
|
|
39734
39734
|
let prevChar = void 0;
|
|
39735
39735
|
let anchor = 0;
|
|
39736
|
-
for (let i6 = 0; i6 <
|
|
39736
|
+
for (let i6 = 0; i6 < z98; ++i6) {
|
|
39737
39737
|
const char = value[i6];
|
|
39738
39738
|
switch (char) {
|
|
39739
39739
|
case `"`:
|
|
@@ -39754,12 +39754,12 @@ var init_split_header = __esm({
|
|
|
39754
39754
|
values.push(value.slice(anchor));
|
|
39755
39755
|
return values.map((v) => {
|
|
39756
39756
|
v = v.trim();
|
|
39757
|
-
const
|
|
39758
|
-
if (
|
|
39757
|
+
const z99 = v.length;
|
|
39758
|
+
if (z99 < 2) {
|
|
39759
39759
|
return v;
|
|
39760
39760
|
}
|
|
39761
|
-
if (v[0] === `"` && v[
|
|
39762
|
-
v = v.slice(1,
|
|
39761
|
+
if (v[0] === `"` && v[z99 - 1] === `"`) {
|
|
39762
|
+
v = v.slice(1, z99 - 1);
|
|
39763
39763
|
}
|
|
39764
39764
|
return v.replace(/\\"/g, '"');
|
|
39765
39765
|
});
|
|
@@ -41196,11 +41196,11 @@ var init_EndpointCache = __esm({
|
|
|
41196
41196
|
}
|
|
41197
41197
|
hash(endpointParams) {
|
|
41198
41198
|
let buffer = "";
|
|
41199
|
-
const { parameters:
|
|
41200
|
-
if (
|
|
41199
|
+
const { parameters: parameters80 } = this;
|
|
41200
|
+
if (parameters80.length === 0) {
|
|
41201
41201
|
return false;
|
|
41202
41202
|
}
|
|
41203
|
-
for (const param of
|
|
41203
|
+
for (const param of parameters80) {
|
|
41204
41204
|
const val = String(endpointParams[param] ?? "");
|
|
41205
41205
|
if (val.includes("|;")) {
|
|
41206
41206
|
return false;
|
|
@@ -47672,8 +47672,8 @@ var init_ProtocolLib = __esm({
|
|
|
47672
47672
|
constructor(queryCompat = false) {
|
|
47673
47673
|
this.queryCompat = queryCompat;
|
|
47674
47674
|
}
|
|
47675
|
-
resolveRestContentType(defaultContentType,
|
|
47676
|
-
const members =
|
|
47675
|
+
resolveRestContentType(defaultContentType, inputSchema97) {
|
|
47676
|
+
const members = inputSchema97.getMemberSchemas();
|
|
47677
47677
|
const httpPayloadMember = Object.values(members).find((m4) => {
|
|
47678
47678
|
return !!m4.getMergedTraits().httpPayload;
|
|
47679
47679
|
});
|
|
@@ -47688,7 +47688,7 @@ var init_ProtocolLib = __esm({
|
|
|
47688
47688
|
} else {
|
|
47689
47689
|
return defaultContentType;
|
|
47690
47690
|
}
|
|
47691
|
-
} else if (!
|
|
47691
|
+
} else if (!inputSchema97.isUnitSchema()) {
|
|
47692
47692
|
const hasBody = Object.values(members).find((m4) => {
|
|
47693
47693
|
const { httpQuery, httpQueryParams, httpHeader, httpLabel, httpPrefixHeaders } = m4.getMergedTraits();
|
|
47694
47694
|
const noPrefixHeaders = httpPrefixHeaders === void 0;
|
|
@@ -48541,9 +48541,9 @@ var init_AwsRestJsonProtocol = __esm({
|
|
|
48541
48541
|
}
|
|
48542
48542
|
async serializeRequest(operationSchema, input, context) {
|
|
48543
48543
|
const request2 = await super.serializeRequest(operationSchema, input, context);
|
|
48544
|
-
const
|
|
48544
|
+
const inputSchema97 = NormalizedSchema.of(operationSchema.input);
|
|
48545
48545
|
if (!request2.headers["content-type"]) {
|
|
48546
|
-
const contentType = this.mixin.resolveRestContentType(this.getDefaultContentType(),
|
|
48546
|
+
const contentType = this.mixin.resolveRestContentType(this.getDefaultContentType(), inputSchema97);
|
|
48547
48547
|
if (contentType) {
|
|
48548
48548
|
request2.headers["content-type"] = contentType;
|
|
48549
48549
|
}
|
|
@@ -48555,8 +48555,8 @@ var init_AwsRestJsonProtocol = __esm({
|
|
|
48555
48555
|
}
|
|
48556
48556
|
async deserializeResponse(operationSchema, context, response) {
|
|
48557
48557
|
const output = await super.deserializeResponse(operationSchema, context, response);
|
|
48558
|
-
const
|
|
48559
|
-
for (const [name, member2] of
|
|
48558
|
+
const outputSchema97 = NormalizedSchema.of(operationSchema.output);
|
|
48559
|
+
for (const [name, member2] of outputSchema97.structIterator()) {
|
|
48560
48560
|
if (member2.getMemberTraits().httpPayload && !(name in output)) {
|
|
48561
48561
|
output[name] = null;
|
|
48562
48562
|
}
|
|
@@ -54374,22 +54374,22 @@ var init_loadCognitoIdentity = __esm({
|
|
|
54374
54374
|
});
|
|
54375
54375
|
|
|
54376
54376
|
// ../../node_modules/@aws-sdk/credential-provider-cognito-identity/dist-es/fromCognitoIdentity.js
|
|
54377
|
-
function fromCognitoIdentity(
|
|
54377
|
+
function fromCognitoIdentity(parameters80) {
|
|
54378
54378
|
return async (awsIdentityProperties) => {
|
|
54379
|
-
|
|
54379
|
+
parameters80.logger?.debug("@aws-sdk/credential-provider-cognito-identity - fromCognitoIdentity");
|
|
54380
54380
|
const { GetCredentialsForIdentityCommand: GetCredentialsForIdentityCommand2, CognitoIdentityClient: CognitoIdentityClient2 } = await Promise.resolve().then(() => (init_loadCognitoIdentity(), loadCognitoIdentity_exports));
|
|
54381
|
-
const fromConfigs = (property) =>
|
|
54382
|
-
const { Credentials: { AccessKeyId = throwOnMissingAccessKeyId(
|
|
54381
|
+
const fromConfigs = (property) => parameters80.clientConfig?.[property] ?? parameters80.parentClientConfig?.[property] ?? awsIdentityProperties?.callerClientConfig?.[property];
|
|
54382
|
+
const { Credentials: { AccessKeyId = throwOnMissingAccessKeyId(parameters80.logger), Expiration, SecretKey = throwOnMissingSecretKey(parameters80.logger), SessionToken } = throwOnMissingCredentials(parameters80.logger) } = await (parameters80.client ?? new CognitoIdentityClient2(Object.assign({}, parameters80.clientConfig ?? {}, {
|
|
54383
54383
|
region: fromConfigs("region"),
|
|
54384
54384
|
profile: fromConfigs("profile"),
|
|
54385
54385
|
userAgentAppId: fromConfigs("userAgentAppId")
|
|
54386
54386
|
}))).send(new GetCredentialsForIdentityCommand2({
|
|
54387
|
-
CustomRoleArn:
|
|
54388
|
-
IdentityId:
|
|
54389
|
-
Logins:
|
|
54387
|
+
CustomRoleArn: parameters80.customRoleArn,
|
|
54388
|
+
IdentityId: parameters80.identityId,
|
|
54389
|
+
Logins: parameters80.logins ? await resolveLogins(parameters80.logins) : void 0
|
|
54390
54390
|
}));
|
|
54391
54391
|
return {
|
|
54392
|
-
identityId:
|
|
54392
|
+
identityId: parameters80.identityId,
|
|
54393
54393
|
accessKeyId: AccessKeyId,
|
|
54394
54394
|
secretAccessKey: SecretKey,
|
|
54395
54395
|
sessionToken: SessionToken,
|
|
@@ -67146,11 +67146,11 @@ var require_bignumber = __commonJS({
|
|
|
67146
67146
|
return n2 > 0 || n2 === i6 ? i6 : i6 - 1;
|
|
67147
67147
|
}
|
|
67148
67148
|
function coeffToString(a6) {
|
|
67149
|
-
var s,
|
|
67149
|
+
var s, z98, i6 = 1, j6 = a6.length, r6 = a6[0] + "";
|
|
67150
67150
|
for (; i6 < j6; ) {
|
|
67151
67151
|
s = a6[i6++] + "";
|
|
67152
|
-
|
|
67153
|
-
for (;
|
|
67152
|
+
z98 = LOG_BASE - s.length;
|
|
67153
|
+
for (; z98--; s = "0" + s) ;
|
|
67154
67154
|
r6 += s;
|
|
67155
67155
|
}
|
|
67156
67156
|
for (j6 = r6.length; r6.charCodeAt(--j6) === 48; ) ;
|
|
@@ -67183,15 +67183,15 @@ var require_bignumber = __commonJS({
|
|
|
67183
67183
|
function toExponential(str, e6) {
|
|
67184
67184
|
return (str.length > 1 ? str.charAt(0) + "." + str.slice(1) : str) + (e6 < 0 ? "e" : "e+") + e6;
|
|
67185
67185
|
}
|
|
67186
|
-
function toFixedPoint(str, e6,
|
|
67186
|
+
function toFixedPoint(str, e6, z98) {
|
|
67187
67187
|
var len, zs;
|
|
67188
67188
|
if (e6 < 0) {
|
|
67189
|
-
for (zs =
|
|
67189
|
+
for (zs = z98 + "."; ++e6; zs += z98) ;
|
|
67190
67190
|
str = zs + str;
|
|
67191
67191
|
} else {
|
|
67192
67192
|
len = str.length;
|
|
67193
67193
|
if (++e6 > len) {
|
|
67194
|
-
for (zs =
|
|
67194
|
+
for (zs = z98, e6 -= len; --e6; zs += z98) ;
|
|
67195
67195
|
str += zs;
|
|
67196
67196
|
} else if (e6 < len) {
|
|
67197
67197
|
str = str.slice(0, e6) + "." + str.slice(e6);
|
|
@@ -89643,6 +89643,12 @@ var NOOP_TUNNEL = (connectionUrl) => ({
|
|
|
89643
89643
|
close: async () => {
|
|
89644
89644
|
}
|
|
89645
89645
|
});
|
|
89646
|
+
var NOOP_TUNNEL_HOSTPORT = (host, port) => ({
|
|
89647
|
+
host,
|
|
89648
|
+
port,
|
|
89649
|
+
close: async () => {
|
|
89650
|
+
}
|
|
89651
|
+
});
|
|
89646
89652
|
function connectionParamsToRecord(connection2) {
|
|
89647
89653
|
const out = {};
|
|
89648
89654
|
for (const p2 of connection2.parameters) {
|
|
@@ -89650,9 +89656,9 @@ function connectionParamsToRecord(connection2) {
|
|
|
89650
89656
|
}
|
|
89651
89657
|
return out;
|
|
89652
89658
|
}
|
|
89653
|
-
async function
|
|
89659
|
+
async function maybeOpenSshTunnelHostPort(params, dbHost, dbPort) {
|
|
89654
89660
|
const sshHost = params[sshTunnelParameters.sshHost.slug];
|
|
89655
|
-
if (!sshHost) return
|
|
89661
|
+
if (!sshHost) return NOOP_TUNNEL_HOSTPORT(dbHost, dbPort);
|
|
89656
89662
|
const sshUsername = params[sshTunnelParameters.sshUsername.slug];
|
|
89657
89663
|
const sshPrivateKeyBase64 = params[sshTunnelParameters.sshPrivateKeyBase64.slug];
|
|
89658
89664
|
if (!sshUsername || !sshPrivateKeyBase64) {
|
|
@@ -89662,9 +89668,6 @@ async function maybeOpenSshTunnel(params, connectionUrl, defaultDbPort) {
|
|
|
89662
89668
|
}
|
|
89663
89669
|
const sshPort = Number(params[sshTunnelParameters.sshPort.slug] || "22") || 22;
|
|
89664
89670
|
const sshPassphrase = params[sshTunnelParameters.sshPassphrase.slug];
|
|
89665
|
-
const url = new URL(connectionUrl);
|
|
89666
|
-
const dbHost = url.hostname;
|
|
89667
|
-
const dbPort = url.port ? Number(url.port) : defaultDbPort;
|
|
89668
89671
|
const [{ Client: Client2 }, net] = await Promise.all([
|
|
89669
89672
|
Promise.resolve().then(() => __toESM(require_lib3(), 1)),
|
|
89670
89673
|
import("net")
|
|
@@ -89707,16 +89710,29 @@ async function maybeOpenSshTunnel(params, connectionUrl, defaultDbPort) {
|
|
|
89707
89710
|
sshClient.end();
|
|
89708
89711
|
throw new Error("Failed to allocate local port for SSH tunnel.");
|
|
89709
89712
|
}
|
|
89710
|
-
url.hostname = "127.0.0.1";
|
|
89711
|
-
url.port = String(address.port);
|
|
89712
89713
|
return {
|
|
89713
|
-
|
|
89714
|
+
host: "127.0.0.1",
|
|
89715
|
+
port: address.port,
|
|
89714
89716
|
close: async () => {
|
|
89715
89717
|
await new Promise((resolve) => server.close(() => resolve()));
|
|
89716
89718
|
sshClient.end();
|
|
89717
89719
|
}
|
|
89718
89720
|
};
|
|
89719
89721
|
}
|
|
89722
|
+
async function maybeOpenSshTunnel(params, connectionUrl, defaultDbPort) {
|
|
89723
|
+
const sshHost = params[sshTunnelParameters.sshHost.slug];
|
|
89724
|
+
if (!sshHost) return NOOP_TUNNEL(connectionUrl);
|
|
89725
|
+
const url = new URL(connectionUrl);
|
|
89726
|
+
const dbHost = url.hostname;
|
|
89727
|
+
const dbPort = url.port ? Number(url.port) : defaultDbPort;
|
|
89728
|
+
const tunnel = await maybeOpenSshTunnelHostPort(params, dbHost, dbPort);
|
|
89729
|
+
url.hostname = tunnel.host;
|
|
89730
|
+
url.port = String(tunnel.port);
|
|
89731
|
+
return {
|
|
89732
|
+
connectionUrl: url.toString(),
|
|
89733
|
+
close: tunnel.close
|
|
89734
|
+
};
|
|
89735
|
+
}
|
|
89720
89736
|
|
|
89721
89737
|
// ../connectors/src/connectors/postgresql/setup.ts
|
|
89722
89738
|
var postgresqlOnboarding = new ConnectorOnboarding({
|
|
@@ -91858,9 +91874,16 @@ A Filter is an Expression. Leaves are \`Dimensions\`, \`Tags\`, or \`CostCategor
|
|
|
91858
91874
|
|
|
91859
91875
|
### Business Logic
|
|
91860
91876
|
|
|
91861
|
-
The business logic type for this connector is "typescript". The connector exposes resolved AWS credentials via \`connection(connectionId)
|
|
91877
|
+
The business logic type for this connector is "typescript". The connector exposes resolved AWS credentials via \`connection(connectionId)\` (already typed as \`{ accessKeyId, secretAccessKey, region }\` \u2014 do NOT add an \`as\` cast). Pass them to \`@aws-sdk/client-cost-explorer\` directly inside the handler. Do NOT read AWS credentials from environment variables.
|
|
91862
91878
|
|
|
91863
|
-
####
|
|
91879
|
+
#### Server logic slug naming
|
|
91880
|
+
|
|
91881
|
+
When creating a server logic for this connector, the \`slug\` (file name) MUST be lowercase kebab-case or snake_case \u2014 only \`[a-z0-9-_]\` is allowed. camelCase and uppercase will fail validation.
|
|
91882
|
+
|
|
91883
|
+
- OK: \`monthly-cost-trend\`, \`cost_by_service\`, \`top10-services\`
|
|
91884
|
+
- NG: \`monthlyCostTrend\`, \`MonthlyCostTrend\`, \`monthly cost trend\`
|
|
91885
|
+
|
|
91886
|
+
#### Example (slug: \`monthly-cost-trend\`)
|
|
91864
91887
|
|
|
91865
91888
|
\`\`\`ts
|
|
91866
91889
|
import type { Context } from "hono";
|
|
@@ -91936,9 +91959,16 @@ Filter \u306F Expression \u3067\u3059\u3002\u30EA\u30FC\u30D5\u306F \`Dimensions
|
|
|
91936
91959
|
|
|
91937
91960
|
### Business Logic
|
|
91938
91961
|
|
|
91939
|
-
\u3053\u306E\u30B3\u30CD\u30AF\u30BF\u306E\u30D3\u30B8\u30CD\u30B9\u30ED\u30B8\u30C3\u30AF\u30BF\u30A4\u30D7\u306F "typescript" \u3067\u3059\u3002\`connection(connectionId)\` \u3067\u89E3\u6C7A\u6E08\u307F\u306E AWS \u8A8D\u8A3C\u60C5\u5831\u3092\u53D6\u5F97\u3057\u3001\`@aws-sdk/client-cost-explorer\` \u306B\u76F4\u63A5\u6E21\u3057\u3066\u30CF\u30F3\u30C9\u30E9\u5185\u3067\u5229\u7528\u3057\u3066\u304F\u3060\u3055\u3044\u3002\u74B0\u5883\u5909\u6570\u304B\u3089 AWS \u8A8D\u8A3C\u60C5\u5831\u3092\u8AAD\u307F\u53D6\u3089\u306A\u3044\u3067\u304F\u3060\u3055\u3044\u3002
|
|
91962
|
+
\u3053\u306E\u30B3\u30CD\u30AF\u30BF\u306E\u30D3\u30B8\u30CD\u30B9\u30ED\u30B8\u30C3\u30AF\u30BF\u30A4\u30D7\u306F "typescript" \u3067\u3059\u3002\`connection(connectionId)\` \u3067\u89E3\u6C7A\u6E08\u307F\u306E AWS \u8A8D\u8A3C\u60C5\u5831\uFF08\`{ accessKeyId, secretAccessKey, region }\` \u3068\u3057\u3066\u578B\u4ED8\u3051\u6E08\u307F \u2014 \`as\` \u30AD\u30E3\u30B9\u30C8\u306F\u4E0D\u8981\uFF09\u3092\u53D6\u5F97\u3057\u3001\`@aws-sdk/client-cost-explorer\` \u306B\u76F4\u63A5\u6E21\u3057\u3066\u30CF\u30F3\u30C9\u30E9\u5185\u3067\u5229\u7528\u3057\u3066\u304F\u3060\u3055\u3044\u3002\u74B0\u5883\u5909\u6570\u304B\u3089 AWS \u8A8D\u8A3C\u60C5\u5831\u3092\u8AAD\u307F\u53D6\u3089\u306A\u3044\u3067\u304F\u3060\u3055\u3044\u3002
|
|
91940
91963
|
|
|
91941
|
-
####
|
|
91964
|
+
#### \u30B5\u30FC\u30D0\u30FC\u30ED\u30B8\u30C3\u30AF\u306E slug \u547D\u540D\u898F\u5247
|
|
91965
|
+
|
|
91966
|
+
\u3053\u306E\u30B3\u30CD\u30AF\u30BF\u7528\u306E\u30B5\u30FC\u30D0\u30FC\u30ED\u30B8\u30C3\u30AF\u3092\u4F5C\u6210\u3059\u308B\u969B\u3001\`slug\`\uFF08\u30D5\u30A1\u30A4\u30EB\u540D\uFF09\u306F **\u5C0F\u6587\u5B57\u306E kebab-case \u307E\u305F\u306F snake_case** \u306B\u3057\u3066\u304F\u3060\u3055\u3044\uFF08\u8A31\u5BB9\u6587\u5B57\u306F \`[a-z0-9-_]\` \u306E\u307F\uFF09\u3002camelCase \u3084\u5927\u6587\u5B57\u3092\u542B\u3080\u3068\u30D0\u30EA\u30C7\u30FC\u30B7\u30E7\u30F3\u30A8\u30E9\u30FC\u306B\u306A\u308A\u307E\u3059\u3002
|
|
91967
|
+
|
|
91968
|
+
- OK: \`monthly-cost-trend\`\u3001\`cost_by_service\`\u3001\`top10-services\`
|
|
91969
|
+
- NG: \`monthlyCostTrend\`\u3001\`MonthlyCostTrend\`\u3001\`monthly cost trend\`
|
|
91970
|
+
|
|
91971
|
+
#### Example\uFF08slug: \`monthly-cost-trend\`\uFF09
|
|
91942
91972
|
|
|
91943
91973
|
\`\`\`ts
|
|
91944
91974
|
import type { Context } from "hono";
|
|
@@ -92847,30 +92877,6 @@ export default async function handler(c: Context) {
|
|
|
92847
92877
|
|
|
92848
92878
|
// ../connectors/src/connectors/google-ads/tools/list-customers.ts
|
|
92849
92879
|
import { z as z18 } from "zod";
|
|
92850
|
-
|
|
92851
|
-
// ../connectors/src/connectors/google-ads/parameters.ts
|
|
92852
|
-
var parameters12 = {
|
|
92853
|
-
customerId: new ParameterDefinition({
|
|
92854
|
-
slug: "customer-id",
|
|
92855
|
-
name: "Google Ads Customer ID",
|
|
92856
|
-
description: "The Google Ads customer ID (e.g., 123-456-7890 or 1234567890). Can be found in the top-right corner of your Google Ads account.",
|
|
92857
|
-
envVarBaseKey: "GOOGLE_ADS_CUSTOMER_ID",
|
|
92858
|
-
type: "text",
|
|
92859
|
-
secret: false,
|
|
92860
|
-
required: false
|
|
92861
|
-
}),
|
|
92862
|
-
developerToken: new ParameterDefinition({
|
|
92863
|
-
slug: "developer-token",
|
|
92864
|
-
name: "Google Ads Developer Token",
|
|
92865
|
-
description: "The developer token for accessing the Google Ads API. Required for all API requests.",
|
|
92866
|
-
envVarBaseKey: "GOOGLE_ADS_DEVELOPER_TOKEN",
|
|
92867
|
-
type: "text",
|
|
92868
|
-
secret: true,
|
|
92869
|
-
required: true
|
|
92870
|
-
})
|
|
92871
|
-
};
|
|
92872
|
-
|
|
92873
|
-
// ../connectors/src/connectors/google-ads/tools/list-customers.ts
|
|
92874
92880
|
var BASE_URL2 = "https://googleads.googleapis.com/v18/";
|
|
92875
92881
|
var REQUEST_TIMEOUT_MS8 = 6e4;
|
|
92876
92882
|
var cachedToken4 = null;
|
|
@@ -92942,7 +92948,6 @@ var listCustomersTool = new ConnectorTool({
|
|
|
92942
92948
|
`[connector-request] google-ads/${connection2.name}: listCustomers`
|
|
92943
92949
|
);
|
|
92944
92950
|
try {
|
|
92945
|
-
const developerToken = parameters12.developerToken.getValue(connection2);
|
|
92946
92951
|
const token = await getProxyToken4(config.oauthProxy);
|
|
92947
92952
|
const proxyUrl = `https://${config.oauthProxy.sandboxId}.${config.oauthProxy.previewBaseDomain}/_sqcore/connections/${connectionId}/request`;
|
|
92948
92953
|
const controller = new AbortController();
|
|
@@ -92956,10 +92961,7 @@ var listCustomersTool = new ConnectorTool({
|
|
|
92956
92961
|
},
|
|
92957
92962
|
body: JSON.stringify({
|
|
92958
92963
|
url: `${BASE_URL2}customers:listAccessibleCustomers`,
|
|
92959
|
-
method: "GET"
|
|
92960
|
-
headers: {
|
|
92961
|
-
"developer-token": developerToken
|
|
92962
|
-
}
|
|
92964
|
+
method: "GET"
|
|
92963
92965
|
}),
|
|
92964
92966
|
signal: controller.signal
|
|
92965
92967
|
});
|
|
@@ -92985,7 +92987,6 @@ var listCustomersTool = new ConnectorTool({
|
|
|
92985
92987
|
method: "POST",
|
|
92986
92988
|
headers: {
|
|
92987
92989
|
"Content-Type": "application/json",
|
|
92988
|
-
"developer-token": developerToken,
|
|
92989
92990
|
"login-customer-id": cid
|
|
92990
92991
|
},
|
|
92991
92992
|
body: JSON.stringify({
|
|
@@ -93031,30 +93032,24 @@ var googleAdsOnboarding = new ConnectorOnboarding({
|
|
|
93031
93032
|
connectionSetupInstructions: {
|
|
93032
93033
|
ja: `\u4EE5\u4E0B\u306E\u624B\u9806\u3067Google Ads (OAuth) \u30B3\u30CD\u30AF\u30B7\u30E7\u30F3\u306E\u30BB\u30C3\u30C8\u30A2\u30C3\u30D7\u3092\u884C\u3063\u3066\u304F\u3060\u3055\u3044\u3002
|
|
93033
93034
|
|
|
93034
|
-
1. \
|
|
93035
|
+
1. \`${listCustomersToolName}\` \u3092\u547C\u3073\u51FA\u3057\u3066\u3001OAuth\u3067\u30A2\u30AF\u30BB\u30B9\u53EF\u80FD\u306AGoogle Ads\u30AB\u30B9\u30BF\u30DE\u30FC\u30A2\u30AB\u30A6\u30F3\u30C8\u4E00\u89A7\u3092\u53D6\u5F97\u3059\u308B
|
|
93035
93036
|
2. \`updateConnectionParameters\` \u3092\u547C\u3073\u51FA\u3059:
|
|
93036
|
-
- \`parameterSlug\`: \`"developer-token"\`
|
|
93037
|
-
- \`value\`: \u30E6\u30FC\u30B6\u30FC\u304C\u63D0\u4F9B\u3057\u305F Developer Token
|
|
93038
|
-
3. \`${listCustomersToolName}\` \u3092\u547C\u3073\u51FA\u3057\u3066\u3001OAuth\u3067\u30A2\u30AF\u30BB\u30B9\u53EF\u80FD\u306AGoogle Ads\u30AB\u30B9\u30BF\u30DE\u30FC\u30A2\u30AB\u30A6\u30F3\u30C8\u4E00\u89A7\u3092\u53D6\u5F97\u3059\u308B
|
|
93039
|
-
4. \`updateConnectionParameters\` \u3092\u547C\u3073\u51FA\u3059:
|
|
93040
93037
|
- \`parameterSlug\`: \`"customer-id"\`
|
|
93041
93038
|
- \`options\`: \u30AB\u30B9\u30BF\u30DE\u30FC\u4E00\u89A7\u3002\u5404 option \u306E \`label\` \u306F \`\u30A2\u30AB\u30A6\u30F3\u30C8\u540D (id: \u30AB\u30B9\u30BF\u30DE\u30FCID)\` \u306E\u5F62\u5F0F\u3001\`value\` \u306F\u30AB\u30B9\u30BF\u30DE\u30FCID
|
|
93042
|
-
|
|
93039
|
+
- \u30AB\u30B9\u30BF\u30DE\u30FC\u304C **0\u4EF6** \u306E\u5834\u5408\u306F\u30BB\u30C3\u30C8\u30A2\u30C3\u30D7\u3092\u4E2D\u65AD\u3057\u3001\u30E6\u30FC\u30B6\u30FC\u306B\u30A2\u30AF\u30BB\u30B9\u53EF\u80FD\u306A\u30A2\u30AB\u30A6\u30F3\u30C8\u304C\u306A\u3044\u65E8\u3092\u4F1D\u3048\u308B
|
|
93040
|
+
3. \u30E6\u30FC\u30B6\u30FC\u304C\u9078\u629E\u3057\u305F\u30AB\u30B9\u30BF\u30DE\u30FC\u306E \`label\` \u304C\u30E1\u30C3\u30BB\u30FC\u30B8\u3068\u3057\u3066\u5C4A\u304F\u306E\u3067\u3001\u6B21\u306E\u30B9\u30C6\u30C3\u30D7\u306B\u9032\u3080
|
|
93043
93041
|
|
|
93044
93042
|
#### \u5236\u7D04
|
|
93045
93043
|
- **\u30BB\u30C3\u30C8\u30A2\u30C3\u30D7\u4E2D\u306B\u30EC\u30DD\u30FC\u30C8\u30C7\u30FC\u30BF\u3092\u53D6\u5F97\u3057\u306A\u3044\u3053\u3068**\u3002\u5B9F\u884C\u3057\u3066\u3088\u3044\u306E\u306F\u4E0A\u8A18\u624B\u9806\u3067\u6307\u5B9A\u3055\u308C\u305F\u30E1\u30BF\u30C7\u30FC\u30BF\u53D6\u5F97\u306E\u307F
|
|
93046
93044
|
- \u30C4\u30FC\u30EB\u9593\u306F1\u6587\u3060\u3051\u66F8\u3044\u3066\u5373\u6B21\u306E\u30C4\u30FC\u30EB\u547C\u3073\u51FA\u3057\u3002\u4E0D\u8981\u306A\u8AAC\u660E\u306F\u7701\u7565\u3057\u3001\u52B9\u7387\u7684\u306B\u9032\u3081\u308B`,
|
|
93047
93045
|
en: `Follow these steps to set up the Google Ads (OAuth) connection.
|
|
93048
93046
|
|
|
93049
|
-
1.
|
|
93047
|
+
1. Call \`${listCustomersToolName}\` to get the list of Google Ads customer accounts accessible with the OAuth credentials
|
|
93050
93048
|
2. Call \`updateConnectionParameters\`:
|
|
93051
|
-
- \`parameterSlug\`: \`"developer-token"\`
|
|
93052
|
-
- \`value\`: The Developer Token provided by the user
|
|
93053
|
-
3. Call \`${listCustomersToolName}\` to get the list of Google Ads customer accounts accessible with the OAuth credentials
|
|
93054
|
-
4. Call \`updateConnectionParameters\`:
|
|
93055
93049
|
- \`parameterSlug\`: \`"customer-id"\`
|
|
93056
93050
|
- \`options\`: The customer list. Each option's \`label\` should be \`Account Name (id: customerId)\`, \`value\` should be the customer ID
|
|
93057
|
-
|
|
93051
|
+
- If **0 customers** are returned, abort setup and inform the user that no accessible accounts are available
|
|
93052
|
+
3. The \`label\` of the user's selected customer will arrive as a message. Proceed to the next step
|
|
93058
93053
|
|
|
93059
93054
|
#### Constraints
|
|
93060
93055
|
- **Do NOT fetch report data during setup**. Only the metadata requests specified in the steps above are allowed
|
|
@@ -93068,6 +93063,19 @@ var googleAdsOnboarding = new ConnectorOnboarding({
|
|
|
93068
93063
|
}
|
|
93069
93064
|
});
|
|
93070
93065
|
|
|
93066
|
+
// ../connectors/src/connectors/google-ads/parameters.ts
|
|
93067
|
+
var parameters12 = {
|
|
93068
|
+
customerId: new ParameterDefinition({
|
|
93069
|
+
slug: "customer-id",
|
|
93070
|
+
name: "Google Ads Customer ID",
|
|
93071
|
+
description: "The Google Ads customer ID (e.g., 123-456-7890 or 1234567890). Can be found in the top-right corner of your Google Ads account.",
|
|
93072
|
+
envVarBaseKey: "GOOGLE_ADS_CUSTOMER_ID",
|
|
93073
|
+
type: "text",
|
|
93074
|
+
secret: false,
|
|
93075
|
+
required: false
|
|
93076
|
+
})
|
|
93077
|
+
};
|
|
93078
|
+
|
|
93071
93079
|
// ../connectors/src/connectors/google-ads/tools/request.ts
|
|
93072
93080
|
import { z as z19 } from "zod";
|
|
93073
93081
|
var BASE_URL3 = "https://googleads.googleapis.com/v18/";
|
|
@@ -93153,7 +93161,6 @@ Authentication is handled automatically via OAuth proxy.
|
|
|
93153
93161
|
const controller = new AbortController();
|
|
93154
93162
|
const timeout = setTimeout(() => controller.abort(), REQUEST_TIMEOUT_MS9);
|
|
93155
93163
|
try {
|
|
93156
|
-
const developerToken = parameters12.developerToken.getValue(connection2);
|
|
93157
93164
|
const response = await fetch(proxyUrl, {
|
|
93158
93165
|
method: "POST",
|
|
93159
93166
|
headers: {
|
|
@@ -93165,7 +93172,6 @@ Authentication is handled automatically via OAuth proxy.
|
|
|
93165
93172
|
method,
|
|
93166
93173
|
headers: {
|
|
93167
93174
|
"Content-Type": "application/json",
|
|
93168
|
-
"developer-token": developerToken,
|
|
93169
93175
|
...customerId ? { "login-customer-id": customerId } : {}
|
|
93170
93176
|
},
|
|
93171
93177
|
...method === "POST" && body ? { body: JSON.stringify(body) } : {}
|
|
@@ -93346,20 +93352,12 @@ const customerIds = await ads.listAccessibleCustomers();
|
|
|
93346
93352
|
if (!customerId) {
|
|
93347
93353
|
return { success: true };
|
|
93348
93354
|
}
|
|
93349
|
-
const developerToken = params[parameters12.developerToken.slug];
|
|
93350
|
-
if (!developerToken) {
|
|
93351
|
-
return {
|
|
93352
|
-
success: false,
|
|
93353
|
-
error: "Developer token is required"
|
|
93354
|
-
};
|
|
93355
|
-
}
|
|
93356
93355
|
const url = `https://googleads.googleapis.com/v18/customers/${customerId}/googleAds:searchStream`;
|
|
93357
93356
|
try {
|
|
93358
93357
|
const res = await proxyFetch(url, {
|
|
93359
93358
|
method: "POST",
|
|
93360
93359
|
headers: {
|
|
93361
93360
|
"Content-Type": "application/json",
|
|
93362
|
-
"developer-token": developerToken,
|
|
93363
93361
|
"login-customer-id": customerId
|
|
93364
93362
|
},
|
|
93365
93363
|
body: JSON.stringify({
|
|
@@ -111377,17 +111375,27 @@ async function importMssql() {
|
|
|
111377
111375
|
}
|
|
111378
111376
|
async function runMssqlQuery(parsed, sql, options = {}) {
|
|
111379
111377
|
const sqlMod = await importMssql();
|
|
111380
|
-
const
|
|
111381
|
-
|
|
111382
|
-
|
|
111383
|
-
|
|
111384
|
-
|
|
111378
|
+
const tunnel = options.tunnelParams ? await maybeOpenSshTunnelHostPort(
|
|
111379
|
+
options.tunnelParams,
|
|
111380
|
+
parsed.server,
|
|
111381
|
+
parsed.port
|
|
111382
|
+
) : null;
|
|
111385
111383
|
try {
|
|
111386
|
-
const
|
|
111387
|
-
const
|
|
111388
|
-
|
|
111384
|
+
const tunneled = tunnel ? { ...parsed, server: tunnel.host, port: tunnel.port } : parsed;
|
|
111385
|
+
const config = toMssqlConfig(tunneled, {
|
|
111386
|
+
encrypt: options.forceEncrypt
|
|
111387
|
+
});
|
|
111388
|
+
const pool = new sqlMod.ConnectionPool(config);
|
|
111389
|
+
await pool.connect();
|
|
111390
|
+
try {
|
|
111391
|
+
const result = await pool.request().query(sql);
|
|
111392
|
+
const recordset = result.recordset ?? [];
|
|
111393
|
+
return { rows: recordset };
|
|
111394
|
+
} finally {
|
|
111395
|
+
await pool.close();
|
|
111396
|
+
}
|
|
111389
111397
|
} finally {
|
|
111390
|
-
await
|
|
111398
|
+
await tunnel?.close();
|
|
111391
111399
|
}
|
|
111392
111400
|
}
|
|
111393
111401
|
async function checkMssqlConnection(url, credentials, options = {}) {
|
|
@@ -111475,35 +111483,69 @@ function parseOracleJdbcUrl(jdbcUrl, options = {}) {
|
|
|
111475
111483
|
function redactOracleUrl(jdbcUrl) {
|
|
111476
111484
|
return jdbcUrl.replace(/(:\/\/)([^@/]+)@/, "$1***@").replace(/(thin:)([^@]+)@/i, "$1***@");
|
|
111477
111485
|
}
|
|
111486
|
+
function parseOracleConnectStringHostPort(connectString) {
|
|
111487
|
+
const m4 = /^([^:/]+):(\d+)(.*)$/.exec(connectString);
|
|
111488
|
+
if (!m4) return null;
|
|
111489
|
+
return { host: m4[1], port: Number(m4[2]), trailing: m4[3] };
|
|
111490
|
+
}
|
|
111491
|
+
function rewriteOracleConnectStringHostPort(connectString, host, port) {
|
|
111492
|
+
const parts = parseOracleConnectStringHostPort(connectString);
|
|
111493
|
+
if (!parts) return connectString;
|
|
111494
|
+
return `${host}:${port}${parts.trailing}`;
|
|
111495
|
+
}
|
|
111478
111496
|
|
|
111479
111497
|
// ../connectors/src/lib/oracle-runner.ts
|
|
111480
111498
|
async function importOracleDb() {
|
|
111481
111499
|
const mod = await import("oracledb");
|
|
111482
111500
|
return mod.default ?? mod;
|
|
111483
111501
|
}
|
|
111484
|
-
async function runOracleQuery(parsed, sql) {
|
|
111502
|
+
async function runOracleQuery(parsed, sql, options = {}) {
|
|
111485
111503
|
const oracledb = await importOracleDb();
|
|
111486
|
-
|
|
111487
|
-
|
|
111488
|
-
|
|
111489
|
-
|
|
111490
|
-
|
|
111504
|
+
let tunnel = null;
|
|
111505
|
+
if (options.tunnelParams) {
|
|
111506
|
+
const hostPort = parseOracleConnectStringHostPort(parsed.connectString);
|
|
111507
|
+
if (hostPort) {
|
|
111508
|
+
tunnel = await maybeOpenSshTunnelHostPort(
|
|
111509
|
+
options.tunnelParams,
|
|
111510
|
+
hostPort.host,
|
|
111511
|
+
hostPort.port
|
|
111512
|
+
);
|
|
111513
|
+
}
|
|
111514
|
+
}
|
|
111491
111515
|
try {
|
|
111492
|
-
const
|
|
111493
|
-
|
|
111494
|
-
|
|
111495
|
-
|
|
111496
|
-
|
|
111516
|
+
const connectString = tunnel ? rewriteOracleConnectStringHostPort(
|
|
111517
|
+
parsed.connectString,
|
|
111518
|
+
tunnel.host,
|
|
111519
|
+
tunnel.port
|
|
111520
|
+
) : parsed.connectString;
|
|
111521
|
+
const connection2 = await oracledb.getConnection({
|
|
111522
|
+
user: parsed.user,
|
|
111523
|
+
password: parsed.password,
|
|
111524
|
+
connectString
|
|
111497
111525
|
});
|
|
111498
|
-
return { rows: result.rows ?? [] };
|
|
111499
|
-
} finally {
|
|
111500
111526
|
try {
|
|
111501
|
-
await connection2.
|
|
111502
|
-
|
|
111527
|
+
const result = await connection2.execute(
|
|
111528
|
+
sql,
|
|
111529
|
+
[],
|
|
111530
|
+
{
|
|
111531
|
+
outFormat: oracledb.OUT_FORMAT_OBJECT,
|
|
111532
|
+
// Bound by the connector's own row cap, but keep the driver from
|
|
111533
|
+
// streaming arbitrarily large result sets.
|
|
111534
|
+
maxRows: 5e3
|
|
111535
|
+
}
|
|
111536
|
+
);
|
|
111537
|
+
return { rows: result.rows ?? [] };
|
|
111538
|
+
} finally {
|
|
111539
|
+
try {
|
|
111540
|
+
await connection2.close();
|
|
111541
|
+
} catch {
|
|
111542
|
+
}
|
|
111503
111543
|
}
|
|
111544
|
+
} finally {
|
|
111545
|
+
await tunnel?.close();
|
|
111504
111546
|
}
|
|
111505
111547
|
}
|
|
111506
|
-
async function checkOracleConnection(url, credentials) {
|
|
111548
|
+
async function checkOracleConnection(url, credentials, options = {}) {
|
|
111507
111549
|
let parsed;
|
|
111508
111550
|
try {
|
|
111509
111551
|
parsed = parseOracleJdbcUrl(url, credentials);
|
|
@@ -111514,7 +111556,7 @@ async function checkOracleConnection(url, credentials) {
|
|
|
111514
111556
|
};
|
|
111515
111557
|
}
|
|
111516
111558
|
try {
|
|
111517
|
-
await runOracleQuery(parsed, "SELECT 1 FROM DUAL");
|
|
111559
|
+
await runOracleQuery(parsed, "SELECT 1 FROM DUAL", options);
|
|
111518
111560
|
return { success: true };
|
|
111519
111561
|
} catch (err) {
|
|
111520
111562
|
let msg = err instanceof Error ? err.message : String(err);
|
|
@@ -111724,12 +111766,13 @@ Always bound results: LIMIT for PG/MySQL/Redshift, TOP for SQL Server, FETCH FIR
|
|
|
111724
111766
|
};
|
|
111725
111767
|
}
|
|
111726
111768
|
try {
|
|
111769
|
+
const tunnelParams = connectionParamsToRecord(connection2);
|
|
111727
111770
|
if (parsed.driver === "sqlserver") {
|
|
111728
111771
|
const mssqlParsed = parseSqlServerJdbcUrl(parsed.originalUrl, {
|
|
111729
111772
|
username,
|
|
111730
111773
|
password
|
|
111731
111774
|
});
|
|
111732
|
-
const result = await runMssqlQuery(mssqlParsed, sql);
|
|
111775
|
+
const result = await runMssqlQuery(mssqlParsed, sql, { tunnelParams });
|
|
111733
111776
|
const rows = result.rows;
|
|
111734
111777
|
return {
|
|
111735
111778
|
success: true,
|
|
@@ -111744,7 +111787,9 @@ Always bound results: LIMIT for PG/MySQL/Redshift, TOP for SQL Server, FETCH FIR
|
|
|
111744
111787
|
password
|
|
111745
111788
|
});
|
|
111746
111789
|
const cleanSql = sql.replace(/;\s*$/, "");
|
|
111747
|
-
const result = await runOracleQuery(oracleParsed, cleanSql
|
|
111790
|
+
const result = await runOracleQuery(oracleParsed, cleanSql, {
|
|
111791
|
+
tunnelParams
|
|
111792
|
+
});
|
|
111748
111793
|
const rows = result.rows;
|
|
111749
111794
|
return {
|
|
111750
111795
|
success: true,
|
|
@@ -111756,7 +111801,7 @@ Always bound results: LIMIT for PG/MySQL/Redshift, TOP for SQL Server, FETCH FIR
|
|
|
111756
111801
|
let tunnel;
|
|
111757
111802
|
try {
|
|
111758
111803
|
tunnel = await maybeOpenSshTunnel(
|
|
111759
|
-
|
|
111804
|
+
tunnelParams,
|
|
111760
111805
|
parsed.nativeUrl,
|
|
111761
111806
|
parsed.defaultPort
|
|
111762
111807
|
);
|
|
@@ -111930,10 +111975,18 @@ JDBC URL \u306E\u30D7\u30EC\u30D5\u30A3\u30C3\u30AF\u30B9\u306B\u3088\u308A\u65B
|
|
|
111930
111975
|
};
|
|
111931
111976
|
}
|
|
111932
111977
|
if (parsed.driver === "sqlserver") {
|
|
111933
|
-
return checkMssqlConnection(
|
|
111978
|
+
return checkMssqlConnection(
|
|
111979
|
+
parsed.originalUrl,
|
|
111980
|
+
{ username, password },
|
|
111981
|
+
{ tunnelParams: params }
|
|
111982
|
+
);
|
|
111934
111983
|
}
|
|
111935
111984
|
if (parsed.driver === "oracle") {
|
|
111936
|
-
return checkOracleConnection(
|
|
111985
|
+
return checkOracleConnection(
|
|
111986
|
+
parsed.originalUrl,
|
|
111987
|
+
{ username, password },
|
|
111988
|
+
{ tunnelParams: params }
|
|
111989
|
+
);
|
|
111937
111990
|
}
|
|
111938
111991
|
const tunnel = await maybeOpenSshTunnel(
|
|
111939
111992
|
params,
|
|
@@ -111990,10 +112043,12 @@ JDBC URL \u306E\u30D7\u30EC\u30D5\u30A3\u30C3\u30AF\u30B9\u306B\u3088\u308A\u65B
|
|
|
111990
112043
|
});
|
|
111991
112044
|
const sample = unwrapSampleLimit(sql);
|
|
111992
112045
|
if (sample) {
|
|
111993
|
-
const result = await runMssqlQuery(mssqlParsed, sample.inner
|
|
112046
|
+
const result = await runMssqlQuery(mssqlParsed, sample.inner, {
|
|
112047
|
+
tunnelParams: params
|
|
112048
|
+
});
|
|
111994
112049
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
111995
112050
|
}
|
|
111996
|
-
return runMssqlQuery(mssqlParsed, sql);
|
|
112051
|
+
return runMssqlQuery(mssqlParsed, sql, { tunnelParams: params });
|
|
111997
112052
|
}
|
|
111998
112053
|
if (parsed.driver === "oracle") {
|
|
111999
112054
|
const oracleParsed = parseOracleJdbcUrl(parsed.originalUrl, {
|
|
@@ -112003,11 +112058,13 @@ JDBC URL \u306E\u30D7\u30EC\u30D5\u30A3\u30C3\u30AF\u30B9\u306B\u3088\u308A\u65B
|
|
|
112003
112058
|
const sample = unwrapSampleLimit(sql);
|
|
112004
112059
|
if (sample) {
|
|
112005
112060
|
const inner = sample.inner.replace(/;\s*$/, "");
|
|
112006
|
-
const result = await runOracleQuery(oracleParsed, inner
|
|
112061
|
+
const result = await runOracleQuery(oracleParsed, inner, {
|
|
112062
|
+
tunnelParams: params
|
|
112063
|
+
});
|
|
112007
112064
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
112008
112065
|
}
|
|
112009
112066
|
const cleanSql = sql.replace(/;\s*$/, "");
|
|
112010
|
-
return runOracleQuery(oracleParsed, cleanSql);
|
|
112067
|
+
return runOracleQuery(oracleParsed, cleanSql, { tunnelParams: params });
|
|
112011
112068
|
}
|
|
112012
112069
|
const tunnel = await maybeOpenSshTunnel(
|
|
112013
112070
|
params,
|
|
@@ -112239,16 +112296,18 @@ var semrushOnboarding = new ConnectorOnboarding({
|
|
|
112239
112296
|
- Write only 1 sentence between tool calls, then immediately call the next tool. Skip unnecessary explanations and proceed efficiently`
|
|
112240
112297
|
},
|
|
112241
112298
|
dataOverviewInstructions: {
|
|
112242
|
-
en: `1. Call ${requestToolName12} with path "/" and queryParams \`{ "type": "
|
|
112299
|
+
en: `1. Call ${requestToolName12} with path "/" and queryParams \`{ "type": "domain_ranks", "domain": "<example.com>", "database": "us" }\` to inspect the domain summary report (single-row CSV: rank, organic/paid keywords, traffic, cost)
|
|
112243
112300
|
2. Call ${requestToolName12} with path "/" and queryParams \`{ "type": "domain_organic", "domain": "<example.com>", "database": "us", "display_limit": "5" }\` to sample organic keywords
|
|
112244
112301
|
3. Call ${requestToolName12} with path "/" and queryParams \`{ "type": "phrase_this", "phrase": "<keyword>", "database": "us" }\` to inspect a keyword overview
|
|
112245
|
-
4.
|
|
112246
|
-
5.
|
|
112247
|
-
|
|
112302
|
+
4. Optionally call ${requestToolName12} with path "/analytics/v1/" and queryParams \`{ "type": "backlinks_overview", "target": "<example.com>", "target_type": "root_domain" }\` to inspect a backlinks summary (returns semicolon-separated CSV \u2014 keep \`responseFormat="text"\`)
|
|
112303
|
+
5. Always pass an explicit small \`display_limit\` (e.g. \`"5"\`) \u2014 never rely on the default 10000, which can trip \`ERROR 132\` even when units remain
|
|
112304
|
+
6. Remember: the Standard Analytics API and the \`/analytics/v1/?type=backlinks_*\` Backlinks endpoints both return semicolon-separated CSV with the first row as the header`,
|
|
112305
|
+
ja: `1. ${requestToolName12} \u3067 path "/" \u3068 queryParams \`{ "type": "domain_ranks", "domain": "<example.com>", "database": "us" }\` \u3092\u547C\u3073\u51FA\u3057\u3001\u30C9\u30E1\u30A4\u30F3\u30B5\u30DE\u30EA\u30FC\u30EC\u30DD\u30FC\u30C8\uFF08rank\u30FB\u30AA\u30FC\u30AC\u30CB\u30C3\u30AF/\u6709\u6599\u30AD\u30FC\u30EF\u30FC\u30C9\u30FB\u30C8\u30E9\u30D5\u30A3\u30C3\u30AF\u30FB\u30B3\u30B9\u30C8\u7B49\u306E1\u884CCSV\uFF09\u3092\u78BA\u8A8D
|
|
112248
112306
|
2. ${requestToolName12} \u3067 path "/" \u3068 queryParams \`{ "type": "domain_organic", "domain": "<example.com>", "database": "us", "display_limit": "5" }\` \u3092\u547C\u3073\u51FA\u3057\u3001\u30AA\u30FC\u30AC\u30CB\u30C3\u30AF\u30AD\u30FC\u30EF\u30FC\u30C9\u3092\u30B5\u30F3\u30D7\u30EA\u30F3\u30B0
|
|
112249
112307
|
3. ${requestToolName12} \u3067 path "/" \u3068 queryParams \`{ "type": "phrase_this", "phrase": "<keyword>", "database": "us" }\` \u3092\u547C\u3073\u51FA\u3057\u3001\u30AD\u30FC\u30EF\u30FC\u30C9\u6982\u8981\u3092\u78BA\u8A8D
|
|
112250
|
-
4. \u5FC5\u8981\u306B\u5FDC\u3058\u3066\
|
|
112251
|
-
5. \
|
|
112308
|
+
4. \u5FC5\u8981\u306B\u5FDC\u3058\u3066 ${requestToolName12} \u3067 path "/analytics/v1/" \u3068 queryParams \`{ "type": "backlinks_overview", "target": "<example.com>", "target_type": "root_domain" }\` \u3092\u547C\u3073\u51FA\u3057\u3066\u30D0\u30C3\u30AF\u30EA\u30F3\u30AF\u30B5\u30DE\u30EA\u30FC\u3092\u78BA\u8A8D\uFF08\u30BB\u30DF\u30B3\u30ED\u30F3\u533A\u5207\u308ACSV\u3092\u8FD4\u3059\u305F\u3081 \`responseFormat="text"\` \u306E\u307E\u307E\uFF09
|
|
112309
|
+
5. \`display_limit\` \u306F\u5FC5\u305A\u660E\u793A\u7684\u306B\u5C0F\u3055\u3044\u5024\uFF08\u4F8B: \`"5"\`\uFF09\u3092\u6307\u5B9A\u3059\u308B\u3053\u3068\u3002\u30C7\u30D5\u30A9\u30EB\u30C810000\u306E\u307E\u307E\u3060\u3068\u30E6\u30CB\u30C3\u30C8\u6B8B\u91CF\u304C\u3042\u3063\u3066\u3082 \`ERROR 132\` \u3067\u62D2\u5426\u3055\u308C\u308B\u3053\u3068\u304C\u3042\u308B
|
|
112310
|
+
6. \u6CE8\u610F: Standard Analytics API \u304A\u3088\u3073 \`/analytics/v1/?type=backlinks_*\` \u306E\u30D0\u30C3\u30AF\u30EA\u30F3\u30AF\u7CFB\u30A8\u30F3\u30C9\u30DD\u30A4\u30F3\u30C8\u306F\u3069\u3061\u3089\u3082\u30BB\u30DF\u30B3\u30ED\u30F3\u533A\u5207\u308ACSV\uFF081\u884C\u76EE\u304C\u30D8\u30C3\u30C0\u30FC\uFF09\u3092\u8FD4\u3059`
|
|
112252
112311
|
}
|
|
112253
112312
|
});
|
|
112254
112313
|
|
|
@@ -112275,10 +112334,19 @@ The business logic type for this connector is "typescript". Write handler code u
|
|
|
112275
112334
|
|
|
112276
112335
|
SDK methods (client created via \`connection(connectionId)\`):
|
|
112277
112336
|
- \`client.request(path, init?)\` \u2014 low-level authenticated fetch. Pass \`init.query\` to set query parameters; \`key\` is injected automatically
|
|
112278
|
-
- \`client.
|
|
112337
|
+
- \`client.checkUnits()\` \u2014 return the current API unit balance as a number. **FREE \u2014 does not consume units.** Use as a pre-flight before \`report()\`
|
|
112338
|
+
- \`client.report(type, query?)\` \u2014 call a Standard Analytics report and parse the CSV into \`{ columns: string[], rows: Record<string, string>[], raw: string }\`. Throws \`API UNITS BALANCE IS ZERO\` when the account is out of units
|
|
112279
112339
|
- \`client.trends(path, query?)\` \u2014 call a Trends API endpoint (\`/analytics/v1/...\`) and return parsed JSON
|
|
112280
112340
|
- \`client.projects(path, init?)\` \u2014 call a Projects API endpoint (\`/management/v1/...\`) and return parsed JSON
|
|
112281
112341
|
|
|
112342
|
+
\u{1F6A8} **MANDATORY pre-flight before creating any server logic that calls \`report()\`.** Before authoring a TypeScript handler that invokes \`client.report(...)\` (Standard Analytics \u2014 \`domain_ranks\`, \`domain_organic\`, \`phrase_this\`, etc.), you MUST first call the \`semrush-api-key_request\` tool with \`path: "https://www.semrush.com/users/countapiunits.html"\`, no \`queryParams\`, \`responseFormat: "text"\` to confirm the unit balance is greater than 0. If the balance is 0, **stop, do not create the server logic**, and report the issue to the user (the account owner needs to top up API units in the Semrush console). \`testFetchServerLogic\` will execute the handler and consume units; creating handlers when the balance is 0 produces \`ERROR 132 :: API UNITS BALANCE IS ZERO\` failures across every server logic.
|
|
112343
|
+
|
|
112344
|
+
\u{1F6A8} **Always set a small \`display_limit\` explicitly \u2014 never rely on the default.** Semrush computes "required units = display_limit \xD7 per-row cost" up front, and rejects the request with \`ERROR 132 :: API UNITS BALANCE IS ZERO\` when the *estimated* cost exceeds the remaining balance, **even when the actual balance is non-zero** (e.g. balance \u2248 40,950 still fails for \`display_limit=10000\` on costly reports). Default to \`display_limit: "1000"\` (or smaller \u2014 \`"100"\` is plenty for most dashboards), and only increase it when the user explicitly asks for a larger sample AND \`checkUnits()\` confirms enough headroom. If you truly need all rows, paginate with \`display_offset\` in chunks of 1000 instead of bumping \`display_limit\`. Treat \`ERROR 132\` as "request too large for the current balance" first, and only as "balance is literally zero" after re-checking units.
|
|
112345
|
+
|
|
112346
|
+
\u{1F6AB} **Do NOT use the Trends API (\`client.trends\`) or Projects API (\`client.projects\`) unless the user explicitly requests them.** These APIs require separate paid subscriptions (Trends and Projects/Management) that not every Semrush account has. Calls without the corresponding subscription fail with an authorization error. Default to the Standard Analytics API (\`client.report\`) for all SEO/keyword/backlink/competitor analysis. Only reach for \`trends()\` / \`projects()\` when the user explicitly mentions Trends data (traffic analytics, market explorer, etc.) or Projects (site audit, position tracking, etc.) \u2014 and confirm the user has the subscription before building the server logic.
|
|
112347
|
+
|
|
112348
|
+
\u26A0\uFE0F **Important: \`report()\` row shape.** \`rows\` is \`Record<string, string>[]\` \u2014 each row is an object keyed by the CSV column NAME (matching \`columns\`), NOT a positional array. Access fields with \`row["Url"]\`, \`row["Keyword"]\`, \`row["Search Volume"]\` (column names may contain spaces). Do NOT use \`columns.indexOf("Url")\` and then \`row[index]\` \u2014 that returns \`undefined\` and silently produces empty results when combined with \`?? ""\` or \`Number(...) || 0\`. All values are strings; convert numeric columns with \`Number(row["Position"])\`.
|
|
112349
|
+
|
|
112282
112350
|
\`\`\`ts
|
|
112283
112351
|
import type { Context } from "hono";
|
|
112284
112352
|
import { connection } from "@squadbase/vite-server/connectors/semrush";
|
|
@@ -112291,9 +112359,25 @@ export default async function handler(c: Context) {
|
|
|
112291
112359
|
database?: string;
|
|
112292
112360
|
}>();
|
|
112293
112361
|
|
|
112294
|
-
const
|
|
112362
|
+
const result = await semrush.report("domain_organic", {
|
|
112363
|
+
domain,
|
|
112364
|
+
database,
|
|
112365
|
+
display_limit: "100",
|
|
112366
|
+
});
|
|
112367
|
+
|
|
112368
|
+
// \u2705 Correct: access by column name
|
|
112369
|
+
const rows = result.rows.map((row) => ({
|
|
112370
|
+
keyword: row["Keyword"],
|
|
112371
|
+
position: Number(row["Position"]) || 0,
|
|
112372
|
+
searchVolume: Number(row["Search Volume"]) || 0,
|
|
112373
|
+
url: row["Url"] ?? "",
|
|
112374
|
+
}));
|
|
112375
|
+
|
|
112376
|
+
// \u274C Wrong: do NOT do this \u2014 row[index] is undefined because rows are objects, not arrays
|
|
112377
|
+
// const urlIdx = result.columns.indexOf("Url");
|
|
112378
|
+
// const url = (row as unknown as string[])[urlIdx];
|
|
112295
112379
|
|
|
112296
|
-
return c.json({ columns:
|
|
112380
|
+
return c.json({ columns: result.columns, rows });
|
|
112297
112381
|
}
|
|
112298
112382
|
\`\`\`
|
|
112299
112383
|
|
|
@@ -112305,8 +112389,8 @@ export default async function handler(c: Context) {
|
|
|
112305
112389
|
|
|
112306
112390
|
Authentication: API key passed as the \`key\` query parameter on every request (handled automatically).
|
|
112307
112391
|
|
|
112308
|
-
#### Common Standard Analytics report types
|
|
112309
|
-
- \`
|
|
112392
|
+
#### Common Standard Analytics report types (path \`/\`, returns CSV)
|
|
112393
|
+
- \`domain_ranks\` \u2014 single-row domain summary (rank, organic/paid keywords, traffic, cost). **There is no \`domain_overview\` type \u2014 use \`domain_ranks\`.**
|
|
112310
112394
|
- \`domain_organic\` \u2014 organic keywords for a domain
|
|
112311
112395
|
- \`domain_adwords\` \u2014 paid keywords for a domain
|
|
112312
112396
|
- \`domain_organic_organic\` / \`domain_adwords_adwords\` \u2014 organic / paid competitors
|
|
@@ -112315,10 +112399,13 @@ Authentication: API key passed as the \`key\` query parameter on every request (
|
|
|
112315
112399
|
- \`phrase_fullsearch\` \u2014 full-text keyword research
|
|
112316
112400
|
- \`phrase_questions\` \u2014 question keywords
|
|
112317
112401
|
- \`phrase_kdi\` \u2014 keyword difficulty index
|
|
112402
|
+
- \`url_organic\` / \`url_adwords\` \u2014 keywords ranking for a specific URL
|
|
112403
|
+
|
|
112404
|
+
#### Backlinks API report types (path \`/analytics/v1/\`, also returns **CSV** \u2014 not JSON)
|
|
112405
|
+
Backlinks endpoints live under \`/analytics/v1/?type=backlinks_*\` and require \`target\` + \`target_type\` (\`root_domain\` | \`domain\` | \`url\`) instead of \`domain\`/\`database\`. They return semicolon-separated CSV, so use \`responseFormat="text"\` from the request tool, and from the SDK use \`client.request("/analytics/v1/", { query: { type: "backlinks_overview", target, target_type: "root_domain" } })\` and parse the CSV yourself \u2014 \`client.trends()\` will throw because it JSON-parses the body.
|
|
112318
112406
|
- \`backlinks_overview\` \u2014 backlinks summary
|
|
112319
112407
|
- \`backlinks\` \u2014 list of backlinks
|
|
112320
112408
|
- \`backlinks_refdomains\` \u2014 referring domains
|
|
112321
|
-
- \`url_organic\` / \`url_adwords\` \u2014 keywords ranking for a specific URL
|
|
112322
112409
|
|
|
112323
112410
|
To check remaining API units (free, does NOT consume units), call the request tool with an absolute URL: \`path: "https://www.semrush.com/users/countapiunits.html"\`, no query params, \`responseFormat: "text"\`. The response body is just a number.
|
|
112324
112411
|
|
|
@@ -112326,7 +112413,7 @@ To check remaining API units (free, does NOT consume units), call the request to
|
|
|
112326
112413
|
- \`type\` \u2014 report type (required for the Standard API)
|
|
112327
112414
|
- \`domain\` / \`phrase\` / \`url\` \u2014 entity to query
|
|
112328
112415
|
- \`database\` \u2014 regional database (e.g. \`us\`, \`uk\`, \`de\`, \`fr\`, \`jp\`, \`br\`); required for most reports
|
|
112329
|
-
- \`display_limit\` \u2014 page size (default 10000, max 100000 depending on report)
|
|
112416
|
+
- \`display_limit\` \u2014 page size (default 10000, max 100000 depending on report). **Do NOT use the default \u2014 always pass an explicit small value like \`"1000"\`.** Large limits make Semrush pre-charge required units and reject with \`ERROR 132\` even when the balance is non-zero.
|
|
112330
112417
|
- \`display_offset\` \u2014 pagination offset
|
|
112331
112418
|
- \`display_date\` \u2014 historical date in \`YYYYMM15\` format (always day 15)
|
|
112332
112419
|
- \`export_columns\` \u2014 comma-separated columns to return (e.g. \`Ph,Po,Nq,Cp\`)
|
|
@@ -112337,6 +112424,7 @@ To check remaining API units (free, does NOT consume units), call the request to
|
|
|
112337
112424
|
- Each Standard Analytics report consumes API units; check the unit balance via \`https://www.semrush.com/users/countapiunits.html?key=...\` (free) first if you suspect a quota issue
|
|
112338
112425
|
- The CSV separator is \`;\` (semicolon), NOT \`,\`. Some cells may contain commas inside them.
|
|
112339
112426
|
- An HTTP 200 response with a body starting with \`ERROR\` indicates an API error (auth, parameters, or quota)
|
|
112427
|
+
- \`ERROR 132 :: API UNITS BALANCE IS ZERO\` does NOT only mean the balance is literally 0. Semrush also returns it when \`display_limit \xD7 per-row cost\` exceeds the remaining balance. Re-check the balance with \`countapiunits.html\` and lower \`display_limit\` (e.g. to \`1000\` or \`100\`) before assuming the account is empty.
|
|
112340
112428
|
- The Trends API requires a separate Trends subscription; calls without it will fail with an authorization error
|
|
112341
112429
|
- Date strings in historical endpoints must be the 15th of the month (\`YYYYMM15\`)`,
|
|
112342
112430
|
ja: `### \u30C4\u30FC\u30EB
|
|
@@ -112349,10 +112437,19 @@ To check remaining API units (free, does NOT consume units), call the request to
|
|
|
112349
112437
|
|
|
112350
112438
|
SDK\u30E1\u30BD\u30C3\u30C9 (\`connection(connectionId)\` \u3067\u4F5C\u6210\u3057\u305F\u30AF\u30E9\u30A4\u30A2\u30F3\u30C8):
|
|
112351
112439
|
- \`client.request(path, init?)\` \u2014 \u8A8D\u8A3C\u4ED8\u304D\u306E\u4F4E\u30EC\u30D9\u30EBfetch\u3002\`init.query\` \u3067\u30AF\u30A8\u30EA\u30D1\u30E9\u30E1\u30FC\u30BF\u3092\u6307\u5B9A\u3002\`key\` \u306F\u81EA\u52D5\u4ED8\u4E0E
|
|
112352
|
-
- \`client.
|
|
112440
|
+
- \`client.checkUnits()\` \u2014 \u73FE\u5728\u306E API \u30E6\u30CB\u30C3\u30C8\u6B8B\u91CF\u3092\u6570\u5024\u3067\u8FD4\u3059\u3002**\u7121\u6599\u3067\u3001\u30E6\u30CB\u30C3\u30C8\u3092\u6D88\u8CBB\u3057\u306A\u3044\u3002** \`report()\` \u5B9F\u884C\u524D\u306E\u30D7\u30EA\u30D5\u30E9\u30A4\u30C8\u306B\u4F7F\u3046
|
|
112441
|
+
- \`client.report(type, query?)\` \u2014 Standard Analytics \u306E\u30EC\u30DD\u30FC\u30C8\u3092\u547C\u3073\u51FA\u3057\u3001CSV\u3092 \`{ columns: string[], rows: Record<string, string>[], raw: string }\` \u306B\u30D1\u30FC\u30B9\u3002\u6B8B\u91CF\u30BC\u30ED\u306E\u5834\u5408\u306F \`API UNITS BALANCE IS ZERO\` \u3092\u542B\u3080\u30A8\u30E9\u30FC\u3092 throw
|
|
112353
112442
|
- \`client.trends(path, query?)\` \u2014 Trends API \u30A8\u30F3\u30C9\u30DD\u30A4\u30F3\u30C8\uFF08\`/analytics/v1/...\`\uFF09\u3092\u547C\u3073\u51FA\u3057 JSON \u3092\u8FD4\u3059
|
|
112354
112443
|
- \`client.projects(path, init?)\` \u2014 Projects API \u30A8\u30F3\u30C9\u30DD\u30A4\u30F3\u30C8\uFF08\`/management/v1/...\`\uFF09\u3092\u547C\u3073\u51FA\u3057 JSON \u3092\u8FD4\u3059
|
|
112355
112444
|
|
|
112445
|
+
\u{1F6A8} **\`report()\` \u3092\u547C\u3076\u30B5\u30FC\u30D0\u30FC\u30ED\u30B8\u30C3\u30AF\u3092\u4F5C\u6210\u3059\u308B\u524D\u306E\u5FC5\u9808\u30D7\u30EA\u30D5\u30E9\u30A4\u30C8\u3002** Standard Analytics\uFF08\`domain_ranks\`\u3001\`domain_organic\`\u3001\`phrase_this\` \u306A\u3069\uFF09\u306E \`client.report(...)\` \u3092\u542B\u3080 TypeScript \u30CF\u30F3\u30C9\u30E9\u3092\u4F5C\u6210\u3059\u308B\u524D\u306B\u3001\u5FC5\u305A \`semrush-api-key_request\` \u30C4\u30FC\u30EB\u3092 \`path: "https://www.semrush.com/users/countapiunits.html"\`\u3001\`queryParams\` \u7121\u3057\u3001\`responseFormat: "text"\` \u3067\u547C\u3073\u51FA\u3057\u3066\u30E6\u30CB\u30C3\u30C8\u6B8B\u91CF\u304C 0 \u3088\u308A\u5927\u304D\u3044\u3053\u3068\u3092\u78BA\u8A8D\u3059\u308B\u3053\u3068\u3002\u6B8B\u91CF\u304C 0 \u306E\u5834\u5408\u306F **\u30B5\u30FC\u30D0\u30FC\u30ED\u30B8\u30C3\u30AF\u3092\u4F5C\u6210\u305B\u305A\u306B\u505C\u6B62\u3057\u3001\u30E6\u30FC\u30B6\u30FC\u306B\u5831\u544A**\u3059\u308B\uFF08Semrush \u306E\u7BA1\u7406\u30B3\u30F3\u30BD\u30FC\u30EB\u304B\u3089 API \u30E6\u30CB\u30C3\u30C8\u3092\u88DC\u5145\u3059\u308B\u5FC5\u8981\u304C\u3042\u308B\uFF09\u3002\`testFetchServerLogic\` \u306F\u30CF\u30F3\u30C9\u30E9\u3092\u5B9F\u884C\u3057\u3066\u30E6\u30CB\u30C3\u30C8\u3092\u6D88\u8CBB\u3059\u308B\u305F\u3081\u3001\u6B8B\u91CF 0 \u306E\u307E\u307E\u4F5C\u6210\u3059\u308B\u3068\u5168\u30B5\u30FC\u30D0\u30FC\u30ED\u30B8\u30C3\u30AF\u304C \`ERROR 132 :: API UNITS BALANCE IS ZERO\` \u3067\u5931\u6557\u3059\u308B\u3002
|
|
112446
|
+
|
|
112447
|
+
\u{1F6A8} **\`display_limit\` \u306F\u5FC5\u305A\u660E\u793A\u7684\u306B\u5C0F\u3055\u3044\u5024\u3092\u6307\u5B9A\u3057\u3001\u30C7\u30D5\u30A9\u30EB\u30C8\u306B\u983C\u3089\u306A\u3044\u3053\u3068\u3002** Semrush \u306F\u4E8B\u524D\u306B\u300C\u5FC5\u8981\u30E6\u30CB\u30C3\u30C8 = display_limit \xD7 \u884C\u3042\u305F\u308A\u5358\u4FA1\u300D\u3092\u8A08\u7B97\u3057\u3001\u305D\u306E**\u898B\u7A4D\u984D**\u304C\u6B8B\u91CF\u3092\u8D85\u3048\u308B\u3068\u30EA\u30AF\u30A8\u30B9\u30C8\u3092 \`ERROR 132 :: API UNITS BALANCE IS ZERO\` \u3067\u62D2\u5426\u3059\u308B\u3002**\u5B9F\u6B8B\u91CF\u304C\u30BC\u30ED\u3067\u306A\u304F\u3066\u3082**\u8D77\u3053\u308B\uFF08\u4F8B\uFF1A\u6B8B\u91CF\u7D04 40,950 \u3067\u3082\u3001\u30B3\u30B9\u30C8\u306E\u9AD8\u3044\u30EC\u30DD\u30FC\u30C8\u3067 \`display_limit=10000\` \u3060\u3068\u5931\u6557\u3059\u308B\uFF09\u3002\u539F\u5247\u3068\u3057\u3066 \`display_limit: "1000"\`\uFF08\u30C0\u30C3\u30B7\u30E5\u30DC\u30FC\u30C9\u7528\u9014\u306A\u3089 \`"100"\` \u3067\u3082\u5341\u5206\uFF09\u3092\u6307\u5B9A\u3057\u3001\u30E6\u30FC\u30B6\u30FC\u304C\u660E\u793A\u7684\u306B\u5927\u304D\u306A\u30B5\u30F3\u30D7\u30EB\u3092\u8981\u6C42\u3057\u3001\u304B\u3064 \`checkUnits()\` \u3067\u6B8B\u91CF\u306B\u5341\u5206\u306A\u4F59\u88D5\u304C\u3042\u308B\u3053\u3068\u3092\u78BA\u8A8D\u3067\u304D\u305F\u5834\u5408\u306E\u307F\u5897\u3084\u3059\u3002\u5168\u884C\u304C\u5FC5\u8981\u306A\u5834\u5408\u306F \`display_limit\` \u3092\u4E0A\u3052\u308B\u306E\u3067\u306F\u306A\u304F\u3001\`display_offset\` \u3067 1000 \u4EF6\u523B\u307F\u306E\u30DA\u30FC\u30B8\u30CD\u30FC\u30B7\u30E7\u30F3\u3092\u5B9F\u88C5\u3059\u308B\u3053\u3068\u3002\`ERROR 132\` \u306F\u300C\u6B8B\u91CF\u304C\u6587\u5B57\u901A\u308A\u30BC\u30ED\u300D\u3088\u308A\u5148\u306B\u300C\u73FE\u5728\u306E\u6B8B\u91CF\u306B\u5BFE\u3057\u3066\u30EA\u30AF\u30A8\u30B9\u30C8\u304C\u5927\u304D\u3059\u304E\u308B\u300D\u3092\u7591\u3044\u3001\u30E6\u30CB\u30C3\u30C8\u3092\u518D\u78BA\u8A8D\u3057\u3066\u304B\u3089\u5224\u65AD\u3059\u308B\u3053\u3068\u3002
|
|
112448
|
+
|
|
112449
|
+
\u{1F6AB} **Trends API\uFF08\`client.trends\`\uFF09\u3068 Projects API\uFF08\`client.projects\`\uFF09\u306F\u3001\u30E6\u30FC\u30B6\u30FC\u304B\u3089\u660E\u793A\u7684\u306B\u6307\u793A\u3055\u308C\u306A\u3044\u9650\u308A\u4F7F\u7528\u3057\u306A\u3044\u3053\u3068\u3002** \u3053\u308C\u3089\u306E API \u306F\u5225\u9014\u6709\u6599\u30B5\u30D6\u30B9\u30AF\u30EA\u30D7\u30B7\u30E7\u30F3\uFF08Trends / Projects\uFF08Management\uFF09\uFF09\u304C\u5FC5\u8981\u3067\u3001\u3059\u3079\u3066\u306E Semrush \u30A2\u30AB\u30A6\u30F3\u30C8\u304C\u5951\u7D04\u3057\u3066\u3044\u308B\u308F\u3051\u3067\u306F\u306A\u3044\u3002\u30B5\u30D6\u30B9\u30AF\u30EA\u30D7\u30B7\u30E7\u30F3\u304C\u306A\u3044\u72B6\u614B\u3067\u547C\u3073\u51FA\u3059\u3068\u8A8D\u53EF\u30A8\u30E9\u30FC\u3067\u5931\u6557\u3059\u308B\u3002SEO\u30FB\u30AD\u30FC\u30EF\u30FC\u30C9\u30FB\u88AB\u30EA\u30F3\u30AF\u30FB\u7AF6\u5408\u5206\u6790\u306F\u539F\u5247 Standard Analytics API\uFF08\`client.report\`\uFF09\u3067\u884C\u3046\u3002\`trends()\` / \`projects()\` \u3092\u4F7F\u3046\u306E\u306F\u3001\u30E6\u30FC\u30B6\u30FC\u304C Trends \u30C7\u30FC\u30BF\uFF08\u30C8\u30E9\u30D5\u30A3\u30C3\u30AF\u30A2\u30CA\u30EA\u30C6\u30A3\u30AF\u30B9\u3001\u30DE\u30FC\u30B1\u30C3\u30C8\u30A8\u30AF\u30B9\u30D7\u30ED\u30FC\u30E9\u30FC\u7B49\uFF09\u307E\u305F\u306F Projects \u6A5F\u80FD\uFF08\u30B5\u30A4\u30C8\u76E3\u67FB\u3001\u30DD\u30B8\u30B7\u30E7\u30F3\u30C8\u30E9\u30C3\u30AD\u30F3\u30B0\u7B49\uFF09\u3092**\u660E\u793A\u7684\u306B\u6C42\u3081\u305F\u5834\u5408\u306E\u307F**\u3067\u3001\u305D\u306E\u969B\u3082\u30B5\u30D6\u30B9\u30AF\u30EA\u30D7\u30B7\u30E7\u30F3\u306E\u6709\u7121\u3092\u30E6\u30FC\u30B6\u30FC\u306B\u78BA\u8A8D\u3057\u3066\u304B\u3089\u30B5\u30FC\u30D0\u30FC\u30ED\u30B8\u30C3\u30AF\u3092\u4F5C\u6210\u3059\u308B\u3053\u3068\u3002
|
|
112450
|
+
|
|
112451
|
+
\u26A0\uFE0F **\u91CD\u8981: \`report()\` \u306E\u884C\uFF08row\uFF09\u306E\u5F62\u72B6\u306B\u3064\u3044\u3066\u3002** \`rows\` \u306F \`Record<string, string>[]\` \u3067\u3059 \u2014 \u5404\u884C\u306F CSV \u306E\u30AB\u30E9\u30E0\u300C\u540D\u300D\uFF08\`columns\` \u3068\u4E00\u81F4\uFF09\u3092\u30AD\u30FC\u3068\u3057\u305F\u30AA\u30D6\u30B8\u30A7\u30AF\u30C8\u3067\u3042\u308A\u3001\u4F4D\u7F6E\u30A4\u30F3\u30C7\u30C3\u30AF\u30B9\u306E\u914D\u5217\u3067\u306F\u3042\u308A\u307E\u305B\u3093\u3002\u30D5\u30A3\u30FC\u30EB\u30C9\u3078\u306E\u30A2\u30AF\u30BB\u30B9\u306F\u5FC5\u305A \`row["Url"]\`\u3001\`row["Keyword"]\`\u3001\`row["Search Volume"]\`\uFF08\u30AB\u30E9\u30E0\u540D\u306B\u30B9\u30DA\u30FC\u30B9\u3092\u542B\u3080\u3053\u3068\u3042\u308A\uFF09\u306E\u3088\u3046\u306B\u30AB\u30E9\u30E0\u540D\u3067\u884C\u3063\u3066\u304F\u3060\u3055\u3044\u3002\`columns.indexOf("Url")\` \u3067\u30A4\u30F3\u30C7\u30C3\u30AF\u30B9\u3092\u53D6\u5F97\u3057\u3066\u304B\u3089 \`row[index]\` \u3067\u30A2\u30AF\u30BB\u30B9\u3057\u3066\u306F\u3044\u3051\u307E\u305B\u3093 \u2014 \u305D\u308C\u306F \`undefined\` \u3092\u8FD4\u3057\u3001\`?? ""\` \u3084 \`Number(...) || 0\` \u3068\u7D44\u307F\u5408\u308F\u3055\u308B\u3053\u3068\u3067\u7D50\u679C\u304C\u7A7A\u306B\u306A\u308B\u7121\u97F3\u306E\u5931\u6557\u3092\u751F\u307F\u307E\u3059\u3002\u5168\u3066\u306E\u5024\u306F\u6587\u5B57\u5217\u306A\u306E\u3067\u3001\u6570\u5024\u30AB\u30E9\u30E0\u306F \`Number(row["Position"])\` \u3067\u660E\u793A\u5909\u63DB\u3057\u3066\u304F\u3060\u3055\u3044\u3002
|
|
112452
|
+
|
|
112356
112453
|
\`\`\`ts
|
|
112357
112454
|
import type { Context } from "hono";
|
|
112358
112455
|
import { connection } from "@squadbase/vite-server/connectors/semrush";
|
|
@@ -112365,9 +112462,25 @@ export default async function handler(c: Context) {
|
|
|
112365
112462
|
database?: string;
|
|
112366
112463
|
}>();
|
|
112367
112464
|
|
|
112368
|
-
const
|
|
112465
|
+
const result = await semrush.report("domain_organic", {
|
|
112466
|
+
domain,
|
|
112467
|
+
database,
|
|
112468
|
+
display_limit: "100",
|
|
112469
|
+
});
|
|
112369
112470
|
|
|
112370
|
-
|
|
112471
|
+
// \u2705 \u6B63: \u30AB\u30E9\u30E0\u540D\u3067\u30A2\u30AF\u30BB\u30B9\u3059\u308B
|
|
112472
|
+
const rows = result.rows.map((row) => ({
|
|
112473
|
+
keyword: row["Keyword"],
|
|
112474
|
+
position: Number(row["Position"]) || 0,
|
|
112475
|
+
searchVolume: Number(row["Search Volume"]) || 0,
|
|
112476
|
+
url: row["Url"] ?? "",
|
|
112477
|
+
}));
|
|
112478
|
+
|
|
112479
|
+
// \u274C \u8AA4: \u884C\u306F\u30AA\u30D6\u30B8\u30A7\u30AF\u30C8\u3067\u3042\u308A\u914D\u5217\u3067\u306F\u306A\u3044\u305F\u3081 row[index] \u306F undefined \u306B\u306A\u308B
|
|
112480
|
+
// const urlIdx = result.columns.indexOf("Url");
|
|
112481
|
+
// const url = (row as unknown as string[])[urlIdx];
|
|
112482
|
+
|
|
112483
|
+
return c.json({ columns: result.columns, rows });
|
|
112371
112484
|
}
|
|
112372
112485
|
\`\`\`
|
|
112373
112486
|
|
|
@@ -112379,8 +112492,8 @@ export default async function handler(c: Context) {
|
|
|
112379
112492
|
|
|
112380
112493
|
\u8A8D\u8A3C: API\u30AD\u30FC\u3092\u3059\u3079\u3066\u306E\u30EA\u30AF\u30A8\u30B9\u30C8\u306B \`key\` \u30AF\u30A8\u30EA\u30D1\u30E9\u30E1\u30FC\u30BF\u3068\u3057\u3066\u4ED8\u4E0E\uFF08\u81EA\u52D5\uFF09\u3002
|
|
112381
112494
|
|
|
112382
|
-
#### \u4E3B\u8981\u306A Standard Analytics \u30EC\u30DD\u30FC\u30C8\u30BF\u30A4\u30D7
|
|
112383
|
-
- \`
|
|
112495
|
+
#### \u4E3B\u8981\u306A Standard Analytics \u30EC\u30DD\u30FC\u30C8\u30BF\u30A4\u30D7\uFF08path \`/\`\u3001CSV\u3092\u8FD4\u3059\uFF09
|
|
112496
|
+
- \`domain_ranks\` \u2014 \u30C9\u30E1\u30A4\u30F3\u306E\u30B5\u30DE\u30EA\u30FC\uFF08rank\u3001\u30AA\u30FC\u30AC\u30CB\u30C3\u30AF/\u6709\u6599\u30AD\u30FC\u30EF\u30FC\u30C9\u6570\u3001\u30C8\u30E9\u30D5\u30A3\u30C3\u30AF\u3001\u30B3\u30B9\u30C8\u306E1\u884CCSV\uFF09\u3002**\`domain_overview\` \u3068\u3044\u3046\u30BF\u30A4\u30D7\u306F\u5B58\u5728\u3057\u306A\u3044\u3002\`domain_ranks\` \u3092\u4F7F\u3046\u3053\u3068\u3002**
|
|
112384
112497
|
- \`domain_organic\` \u2014 \u30C9\u30E1\u30A4\u30F3\u306E\u30AA\u30FC\u30AC\u30CB\u30C3\u30AF\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112385
112498
|
- \`domain_adwords\` \u2014 \u30C9\u30E1\u30A4\u30F3\u306E\u6709\u6599\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112386
112499
|
- \`domain_organic_organic\` / \`domain_adwords_adwords\` \u2014 \u30AA\u30FC\u30AC\u30CB\u30C3\u30AF\uFF0F\u6709\u6599\u306E\u7AF6\u5408
|
|
@@ -112389,10 +112502,13 @@ export default async function handler(c: Context) {
|
|
|
112389
112502
|
- \`phrase_fullsearch\` \u2014 \u30D5\u30EB\u30C6\u30AD\u30B9\u30C8\u30AD\u30FC\u30EF\u30FC\u30C9\u30EA\u30B5\u30FC\u30C1
|
|
112390
112503
|
- \`phrase_questions\` \u2014 \u8CEA\u554F\u5F62\u5F0F\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112391
112504
|
- \`phrase_kdi\` \u2014 \u30AD\u30FC\u30EF\u30FC\u30C9\u96E3\u6613\u5EA6\uFF08KDI\uFF09
|
|
112505
|
+
- \`url_organic\` / \`url_adwords\` \u2014 \u7279\u5B9AURL\u3067\u30E9\u30F3\u30AF\u30A4\u30F3\u3057\u3066\u3044\u308B\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112506
|
+
|
|
112507
|
+
#### Backlinks API \u30EC\u30DD\u30FC\u30C8\u30BF\u30A4\u30D7\uFF08path \`/analytics/v1/\`\u3001\u3053\u3061\u3089\u3082 **CSV** \u3092\u8FD4\u3059\u3002JSON \u3067\u306F\u306A\u3044\uFF09
|
|
112508
|
+
Backlinks \u7CFB\u30A8\u30F3\u30C9\u30DD\u30A4\u30F3\u30C8\u306F \`/analytics/v1/?type=backlinks_*\` \u914D\u4E0B\u306B\u3042\u308A\u3001\`domain\`/\`database\` \u3067\u306F\u306A\u304F \`target\` + \`target_type\`\uFF08\`root_domain\` | \`domain\` | \`url\`\uFF09\u3092\u8981\u6C42\u3059\u308B\u3002\u30EC\u30B9\u30DD\u30F3\u30B9\u306F\u30BB\u30DF\u30B3\u30ED\u30F3\u533A\u5207\u308ACSV\u306A\u306E\u3067\u3001request \u30C4\u30FC\u30EB\u3067\u306F \`responseFormat="text"\` \u3092\u4F7F\u3044\u3001SDK \u3067\u306F \`client.request("/analytics/v1/", { query: { type: "backlinks_overview", target, target_type: "root_domain" } })\` \u3092\u547C\u3093\u3067 CSV \u3092\u81EA\u524D\u3067\u30D1\u30FC\u30B9\u3059\u308B\u3053\u3068\u3002\`client.trends()\` \u306F JSON.parse \u3059\u308B\u305F\u3081 backlinks \u7CFB\u3067\u4F7F\u3046\u3068 throw \u3059\u308B\u3002
|
|
112392
112509
|
- \`backlinks_overview\` \u2014 \u30D0\u30C3\u30AF\u30EA\u30F3\u30AF\u6982\u8981
|
|
112393
112510
|
- \`backlinks\` \u2014 \u30D0\u30C3\u30AF\u30EA\u30F3\u30AF\u4E00\u89A7
|
|
112394
112511
|
- \`backlinks_refdomains\` \u2014 \u53C2\u7167\u30C9\u30E1\u30A4\u30F3
|
|
112395
|
-
- \`url_organic\` / \`url_adwords\` \u2014 \u7279\u5B9AURL\u3067\u30E9\u30F3\u30AF\u30A4\u30F3\u3057\u3066\u3044\u308B\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112396
112512
|
|
|
112397
112513
|
API \u30E6\u30CB\u30C3\u30C8\u6B8B\u91CF\u306E\u78BA\u8A8D\uFF08\u7121\u6599\u3001\u30E6\u30CB\u30C3\u30C8\u3092\u6D88\u8CBB\u3057\u306A\u3044\uFF09\u306F request \u30C4\u30FC\u30EB\u306B\u7D76\u5BFEURL\u3092\u6E21\u3059: \`path: "https://www.semrush.com/users/countapiunits.html"\`\u3001queryParams \u306A\u3057\u3001\`responseFormat: "text"\`\u3002\u30EC\u30B9\u30DD\u30F3\u30B9\u672C\u6587\u306F\u6570\u5024\u306E\u307F\u3002
|
|
112398
112514
|
|
|
@@ -112400,7 +112516,7 @@ API \u30E6\u30CB\u30C3\u30C8\u6B8B\u91CF\u306E\u78BA\u8A8D\uFF08\u7121\u6599\u30
|
|
|
112400
112516
|
- \`type\` \u2014 \u30EC\u30DD\u30FC\u30C8\u7A2E\u5225\uFF08Standard API \u3067\u306F\u5FC5\u9808\uFF09
|
|
112401
112517
|
- \`domain\` / \`phrase\` / \`url\` \u2014 \u30AF\u30A8\u30EA\u5BFE\u8C61\u306E\u30A8\u30F3\u30C6\u30A3\u30C6\u30A3
|
|
112402
112518
|
- \`database\` \u2014 \u5730\u57DF\u5225\u30C7\u30FC\u30BF\u30D9\u30FC\u30B9\uFF08\`us\`, \`uk\`, \`de\`, \`fr\`, \`jp\`, \`br\` \u306A\u3069\uFF09\u3002\u591A\u304F\u306E\u30EC\u30DD\u30FC\u30C8\u3067\u5FC5\u9808
|
|
112403
|
-
- \`display_limit\` \u2014 \u30DA\u30FC\u30B8\u30B5\u30A4\u30BA\uFF08\u30C7\u30D5\u30A9\u30EB\u30C810000\u3001\u30EC\u30DD\u30FC\u30C8\u306B\u3088\u3063\u3066\u306F\u6700\u5927100000\uFF09
|
|
112519
|
+
- \`display_limit\` \u2014 \u30DA\u30FC\u30B8\u30B5\u30A4\u30BA\uFF08\u30C7\u30D5\u30A9\u30EB\u30C810000\u3001\u30EC\u30DD\u30FC\u30C8\u306B\u3088\u3063\u3066\u306F\u6700\u5927100000\uFF09\u3002**\u30C7\u30D5\u30A9\u30EB\u30C8\u3092\u4F7F\u308F\u305A\u3001\u5FC5\u305A \`"1000"\` \u7A0B\u5EA6\u306E\u5C0F\u3055\u3044\u5024\u3092\u660E\u793A\u7684\u306B\u6307\u5B9A\u3059\u308B\u3053\u3068\u3002** \u5927\u304D\u3044\u5024\u3060\u3068 Semrush \u304C\u5FC5\u8981\u30E6\u30CB\u30C3\u30C8\u3092\u4E8B\u524D\u8A08\u7B97\u3057\u3001\u6B8B\u91CF\u304C\u3042\u3063\u3066\u3082 \`ERROR 132\` \u3067\u62D2\u5426\u3059\u308B\u3002
|
|
112404
112520
|
- \`display_offset\` \u2014 \u30DA\u30FC\u30B8\u30CD\u30FC\u30B7\u30E7\u30F3\u30AA\u30D5\u30BB\u30C3\u30C8
|
|
112405
112521
|
- \`display_date\` \u2014 \u5C65\u6B74\u306E\u65E5\u4ED8\u3002\`YYYYMM15\` \u5F62\u5F0F\uFF08\u5FC5\u305A\u6708\u306E15\u65E5\uFF09
|
|
112406
112522
|
- \`export_columns\` \u2014 \u8FD4\u5374\u30AB\u30E9\u30E0\u3092\u30AB\u30F3\u30DE\u533A\u5207\u308A\u3067\u6307\u5B9A\uFF08\u4F8B: \`Ph,Po,Nq,Cp\`\uFF09
|
|
@@ -112411,6 +112527,7 @@ API \u30E6\u30CB\u30C3\u30C8\u6B8B\u91CF\u306E\u78BA\u8A8D\uFF08\u7121\u6599\u30
|
|
|
112411
112527
|
- Standard Analytics \u306E\u5404\u30EC\u30DD\u30FC\u30C8\u306F API \u30E6\u30CB\u30C3\u30C8\u3092\u6D88\u8CBB\u3059\u308B\u3002\u30AF\u30A9\u30FC\u30BF\u304C\u7591\u308F\u3057\u3044\u5834\u5408\u306F \`https://www.semrush.com/users/countapiunits.html?key=...\` \u3067\u6B8B\u91CF\u3092\u5148\u306B\u78BA\u8A8D\u3059\u308B\uFF08\u7121\u6599\uFF09
|
|
112412
112528
|
- CSV \u306E\u30BB\u30D1\u30EC\u30FC\u30BF\u306F \`;\`\uFF08\u30BB\u30DF\u30B3\u30ED\u30F3\uFF09\u3067\u3042\u308A \`,\` \u3067\u306F\u306A\u3044\u3002\u30BB\u30EB\u5185\u306B\u30AB\u30F3\u30DE\u304C\u542B\u307E\u308C\u308B\u3053\u3068\u304C\u3042\u308B
|
|
112413
112529
|
- HTTP 200 \u3067\u3082\u672C\u6587\u304C \`ERROR\` \u3067\u59CB\u307E\u308B\u5834\u5408\u306F API\u30A8\u30E9\u30FC\uFF08\u8A8D\u8A3C\u3001\u30D1\u30E9\u30E1\u30FC\u30BF\u3001\u30AF\u30A9\u30FC\u30BF\uFF09
|
|
112530
|
+
- \`ERROR 132 :: API UNITS BALANCE IS ZERO\` \u306F\u300C\u6B8B\u91CF\u304C\u6587\u5B57\u901A\u308A 0\u300D\u3060\u3051\u3092\u610F\u5473\u3059\u308B\u308F\u3051\u3067\u306F\u306A\u3044\u3002Semrush \u306F \`display_limit \xD7 \u884C\u3042\u305F\u308A\u5358\u4FA1\` \u304C\u6B8B\u91CF\u3092\u8D85\u3048\u308B\u5834\u5408\u3082\u540C\u3058\u30A8\u30E9\u30FC\u3092\u8FD4\u3059\u3002\`countapiunits.html\` \u3067\u6B8B\u91CF\u3092\u518D\u78BA\u8A8D\u3057\u3001\`display_limit\` \u3092 \`1000\` \u3084 \`100\` \u307E\u3067\u4E0B\u3052\u3066\u304B\u3089\u300C\u6B8B\u91CF\u5207\u308C\u300D\u3068\u5224\u65AD\u3059\u308B\u3053\u3068\u3002
|
|
112414
112531
|
- Trends API \u306F\u5225\u9014 Trends \u30B5\u30D6\u30B9\u30AF\u30EA\u30D7\u30B7\u30E7\u30F3\u304C\u5FC5\u8981\u3002\u672A\u5951\u7D04\u3060\u3068\u8A8D\u53EF\u30A8\u30E9\u30FC\u306B\u306A\u308B
|
|
112415
112532
|
- \u5C65\u6B74\u30A8\u30F3\u30C9\u30DD\u30A4\u30F3\u30C8\u306E\u65E5\u4ED8\u306F\u5FC5\u305A\u6708\u306E15\u65E5\uFF08\`YYYYMM15\`\uFF09`
|
|
112416
112533
|
},
|
|
@@ -113530,7 +113647,8 @@ var parameters72 = {
|
|
|
113530
113647
|
type: "text",
|
|
113531
113648
|
secret: true,
|
|
113532
113649
|
required: false
|
|
113533
|
-
})
|
|
113650
|
+
}),
|
|
113651
|
+
...sshTunnelParameters
|
|
113534
113652
|
};
|
|
113535
113653
|
|
|
113536
113654
|
// ../connectors/src/connectors/sqlserver/tools/execute-query.ts
|
|
@@ -113589,7 +113707,9 @@ Avoid loading large amounts of data; always include \`TOP\` in queries.`,
|
|
|
113589
113707
|
};
|
|
113590
113708
|
}
|
|
113591
113709
|
try {
|
|
113592
|
-
const { rows } = await runMssqlQuery(parsed, sql
|
|
113710
|
+
const { rows } = await runMssqlQuery(parsed, sql, {
|
|
113711
|
+
tunnelParams: connectionParamsToRecord(connection2)
|
|
113712
|
+
});
|
|
113593
113713
|
const truncated = rows.length > MAX_ROWS14;
|
|
113594
113714
|
return {
|
|
113595
113715
|
success: true,
|
|
@@ -113660,7 +113780,8 @@ The business logic type for this connector is "sql".
|
|
|
113660
113780
|
{
|
|
113661
113781
|
username: params[parameters72.username.slug],
|
|
113662
113782
|
password: params[parameters72.password.slug]
|
|
113663
|
-
}
|
|
113783
|
+
},
|
|
113784
|
+
{ tunnelParams: params }
|
|
113664
113785
|
);
|
|
113665
113786
|
},
|
|
113666
113787
|
async query(params, sql, _namedParams) {
|
|
@@ -113670,10 +113791,12 @@ The business logic type for this connector is "sql".
|
|
|
113670
113791
|
});
|
|
113671
113792
|
const sample = unwrapSampleLimit(sql);
|
|
113672
113793
|
if (sample) {
|
|
113673
|
-
const result = await runMssqlQuery(parsed, sample.inner
|
|
113794
|
+
const result = await runMssqlQuery(parsed, sample.inner, {
|
|
113795
|
+
tunnelParams: params
|
|
113796
|
+
});
|
|
113674
113797
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
113675
113798
|
}
|
|
113676
|
-
return runMssqlQuery(parsed, sql);
|
|
113799
|
+
return runMssqlQuery(parsed, sql, { tunnelParams: params });
|
|
113677
113800
|
}
|
|
113678
113801
|
});
|
|
113679
113802
|
|
|
@@ -113719,7 +113842,8 @@ var parameters73 = {
|
|
|
113719
113842
|
type: "text",
|
|
113720
113843
|
secret: true,
|
|
113721
113844
|
required: false
|
|
113722
|
-
})
|
|
113845
|
+
}),
|
|
113846
|
+
...sshTunnelParameters
|
|
113723
113847
|
};
|
|
113724
113848
|
|
|
113725
113849
|
// ../connectors/src/connectors/azure-sql/tools/execute-query.ts
|
|
@@ -113778,7 +113902,10 @@ Avoid loading large amounts of data; always include \`TOP\` in queries.`,
|
|
|
113778
113902
|
};
|
|
113779
113903
|
}
|
|
113780
113904
|
try {
|
|
113781
|
-
const { rows } = await runMssqlQuery(parsed, sql, {
|
|
113905
|
+
const { rows } = await runMssqlQuery(parsed, sql, {
|
|
113906
|
+
forceEncrypt: true,
|
|
113907
|
+
tunnelParams: connectionParamsToRecord(connection2)
|
|
113908
|
+
});
|
|
113782
113909
|
const truncated = rows.length > MAX_ROWS15;
|
|
113783
113910
|
return {
|
|
113784
113911
|
success: true,
|
|
@@ -113803,7 +113930,7 @@ var azureSqlConnector = new ConnectorPlugin({
|
|
|
113803
113930
|
description: "Connect to Azure SQL Database (managed) using a JDBC-style URL. Encryption is enforced automatically.",
|
|
113804
113931
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/5TL0yBbxoLlk6jFZuiHl8w/55040f52d57bf0b77a2215c985c5a772/azure-sql-icon.png",
|
|
113805
113932
|
parameters: parameters73,
|
|
113806
|
-
releaseFlag: { dev1: true, dev2:
|
|
113933
|
+
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
113807
113934
|
categories: ["database"],
|
|
113808
113935
|
onboarding: azureSqlOnboarding,
|
|
113809
113936
|
systemPrompt: {
|
|
@@ -113850,7 +113977,7 @@ The business logic type for this connector is "sql".
|
|
|
113850
113977
|
username: params[parameters73.username.slug],
|
|
113851
113978
|
password: params[parameters73.password.slug]
|
|
113852
113979
|
},
|
|
113853
|
-
{ forceEncrypt: true }
|
|
113980
|
+
{ forceEncrypt: true, tunnelParams: params }
|
|
113854
113981
|
);
|
|
113855
113982
|
},
|
|
113856
113983
|
async query(params, sql, _namedParams) {
|
|
@@ -113861,11 +113988,353 @@ The business logic type for this connector is "sql".
|
|
|
113861
113988
|
const sample = unwrapSampleLimit(sql);
|
|
113862
113989
|
if (sample) {
|
|
113863
113990
|
const result = await runMssqlQuery(parsed, sample.inner, {
|
|
113864
|
-
forceEncrypt: true
|
|
113991
|
+
forceEncrypt: true,
|
|
113992
|
+
tunnelParams: params
|
|
113865
113993
|
});
|
|
113866
113994
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
113867
113995
|
}
|
|
113868
|
-
return runMssqlQuery(parsed, sql, {
|
|
113996
|
+
return runMssqlQuery(parsed, sql, {
|
|
113997
|
+
forceEncrypt: true,
|
|
113998
|
+
tunnelParams: params
|
|
113999
|
+
});
|
|
114000
|
+
}
|
|
114001
|
+
});
|
|
114002
|
+
|
|
114003
|
+
// ../connectors/src/connectors/cosmosdb/setup.ts
|
|
114004
|
+
var cosmosdbOnboarding = new ConnectorOnboarding({
|
|
114005
|
+
dataOverviewInstructions: {
|
|
114006
|
+
en: `1. Use cosmosdb_listContainers to list all containers in the configured database
|
|
114007
|
+
2. For key containers, sample documents with cosmosdb_query: container="users", sql="SELECT TOP 5 * FROM c"
|
|
114008
|
+
3. Examine the document structure to understand the schema (Cosmos DB containers are schema-flexible \u2014 items in the same container may have different fields)
|
|
114009
|
+
4. Use cosmosdb_query with GROUP BY to analyse data distribution if needed: \`SELECT c.status, COUNT(1) AS n FROM c GROUP BY c.status\``,
|
|
114010
|
+
ja: `1. cosmosdb_listContainers \u3067\u5BFE\u8C61\u30C7\u30FC\u30BF\u30D9\u30FC\u30B9\u5185\u306E\u30B3\u30F3\u30C6\u30CA\u4E00\u89A7\u3092\u53D6\u5F97
|
|
114011
|
+
2. \u4E3B\u8981\u30B3\u30F3\u30C6\u30CA\u306B\u3064\u3044\u3066 cosmosdb_query \u3067\u30C9\u30AD\u30E5\u30E1\u30F3\u30C8\u3092\u30B5\u30F3\u30D7\u30EA\u30F3\u30B0: container="users", sql="SELECT TOP 5 * FROM c"
|
|
114012
|
+
3. \u30C9\u30AD\u30E5\u30E1\u30F3\u30C8\u69CB\u9020\u3092\u78BA\u8A8D\u3057\u3066\u30B9\u30AD\u30FC\u30DE\u3092\u628A\u63E1\uFF08Cosmos DB \u306E\u30B3\u30F3\u30C6\u30CA\u306F\u30B9\u30AD\u30FC\u30DE\u304C\u67D4\u8EDF\u306A\u305F\u3081\u3001\u540C\u3058\u30B3\u30F3\u30C6\u30CA\u5185\u3067\u3082\u30C9\u30AD\u30E5\u30E1\u30F3\u30C8\u306E\u30D5\u30A3\u30FC\u30EB\u30C9\u304C\u7570\u306A\u308B\u5834\u5408\u304C\u3042\u308A\u307E\u3059\uFF09
|
|
114013
|
+
4. \u5FC5\u8981\u306B\u5FDC\u3058\u3066 cosmosdb_query \u306E GROUP BY \u3067\u30C7\u30FC\u30BF\u5206\u5E03\u3092\u78BA\u8A8D: \`SELECT c.status, COUNT(1) AS n FROM c GROUP BY c.status\``
|
|
114014
|
+
}
|
|
114015
|
+
});
|
|
114016
|
+
|
|
114017
|
+
// ../connectors/src/connectors/cosmosdb/parameters.ts
|
|
114018
|
+
var parameters74 = {
|
|
114019
|
+
endpoint: new ParameterDefinition({
|
|
114020
|
+
slug: "endpoint",
|
|
114021
|
+
name: "Cosmos DB Endpoint",
|
|
114022
|
+
description: "Cosmos DB account endpoint URL (e.g. `https://<account>.documents.azure.com:443/`). Found in the Azure Portal under the account's *Keys* blade.",
|
|
114023
|
+
envVarBaseKey: "COSMOSDB_ENDPOINT",
|
|
114024
|
+
type: "text",
|
|
114025
|
+
secret: false,
|
|
114026
|
+
required: true
|
|
114027
|
+
}),
|
|
114028
|
+
key: new ParameterDefinition({
|
|
114029
|
+
slug: "key",
|
|
114030
|
+
name: "Account Key",
|
|
114031
|
+
description: "Cosmos DB account key (primary or secondary master key). Use a read-only key when only querying data.",
|
|
114032
|
+
envVarBaseKey: "COSMOSDB_KEY",
|
|
114033
|
+
type: "text",
|
|
114034
|
+
secret: true,
|
|
114035
|
+
required: true
|
|
114036
|
+
}),
|
|
114037
|
+
database: new ParameterDefinition({
|
|
114038
|
+
slug: "database",
|
|
114039
|
+
name: "Database",
|
|
114040
|
+
description: "The Cosmos DB database (a.k.a. database account namespace) to connect to.",
|
|
114041
|
+
envVarBaseKey: "COSMOSDB_DATABASE",
|
|
114042
|
+
type: "text",
|
|
114043
|
+
secret: false,
|
|
114044
|
+
required: true
|
|
114045
|
+
})
|
|
114046
|
+
};
|
|
114047
|
+
|
|
114048
|
+
// ../connectors/src/connectors/cosmosdb/tools/list-containers.ts
|
|
114049
|
+
import { z as z90 } from "zod";
|
|
114050
|
+
var inputSchema90 = z90.object({
|
|
114051
|
+
toolUseIntent: z90.string().optional().describe(
|
|
114052
|
+
"Brief description of what you intend to accomplish with this tool call"
|
|
114053
|
+
),
|
|
114054
|
+
connectionId: z90.string().describe("ID of the Cosmos DB connection to use")
|
|
114055
|
+
});
|
|
114056
|
+
var outputSchema90 = z90.discriminatedUnion("success", [
|
|
114057
|
+
z90.object({
|
|
114058
|
+
success: z90.literal(true),
|
|
114059
|
+
containers: z90.array(
|
|
114060
|
+
z90.object({
|
|
114061
|
+
id: z90.string(),
|
|
114062
|
+
partitionKey: z90.array(z90.string()).optional()
|
|
114063
|
+
})
|
|
114064
|
+
)
|
|
114065
|
+
}),
|
|
114066
|
+
z90.object({
|
|
114067
|
+
success: z90.literal(false),
|
|
114068
|
+
error: z90.string()
|
|
114069
|
+
})
|
|
114070
|
+
]);
|
|
114071
|
+
var listContainersTool = new ConnectorTool({
|
|
114072
|
+
name: "listContainers",
|
|
114073
|
+
description: `List all containers in the configured Cosmos DB database.
|
|
114074
|
+
Use this as the first step to explore the data structure. Returns container ids and their partition key paths.
|
|
114075
|
+
After listing containers, use the query tool to sample items and understand each container's schema.`,
|
|
114076
|
+
inputSchema: inputSchema90,
|
|
114077
|
+
outputSchema: outputSchema90,
|
|
114078
|
+
async execute({ connectionId }, connections) {
|
|
114079
|
+
const connection2 = connections.find((c6) => c6.id === connectionId);
|
|
114080
|
+
if (!connection2) {
|
|
114081
|
+
return {
|
|
114082
|
+
success: false,
|
|
114083
|
+
error: `Connection ${connectionId} not found`
|
|
114084
|
+
};
|
|
114085
|
+
}
|
|
114086
|
+
console.log(
|
|
114087
|
+
`[connector-query] cosmosdb/${connection2.name}: listContainers`
|
|
114088
|
+
);
|
|
114089
|
+
let key;
|
|
114090
|
+
try {
|
|
114091
|
+
const { CosmosClient } = await import("@azure/cosmos");
|
|
114092
|
+
const endpoint = parameters74.endpoint.getValue(connection2);
|
|
114093
|
+
key = parameters74.key.getValue(connection2);
|
|
114094
|
+
const database = parameters74.database.getValue(connection2);
|
|
114095
|
+
const client = new CosmosClient({ endpoint, key });
|
|
114096
|
+
const db = client.database(database);
|
|
114097
|
+
const { resources } = await db.containers.readAll().fetchAll();
|
|
114098
|
+
return {
|
|
114099
|
+
success: true,
|
|
114100
|
+
containers: resources.map((c6) => ({
|
|
114101
|
+
id: c6.id,
|
|
114102
|
+
partitionKey: extractPartitionKeyPaths(c6.partitionKey)
|
|
114103
|
+
}))
|
|
114104
|
+
};
|
|
114105
|
+
} catch (err) {
|
|
114106
|
+
let msg = err instanceof Error ? err.message : String(err);
|
|
114107
|
+
if (key) msg = msg.replaceAll(key, "***");
|
|
114108
|
+
return { success: false, error: msg };
|
|
114109
|
+
}
|
|
114110
|
+
}
|
|
114111
|
+
});
|
|
114112
|
+
function extractPartitionKeyPaths(partitionKey) {
|
|
114113
|
+
if (!partitionKey || typeof partitionKey !== "object") return void 0;
|
|
114114
|
+
const paths = partitionKey.paths;
|
|
114115
|
+
if (!Array.isArray(paths)) return void 0;
|
|
114116
|
+
return paths.filter((p2) => typeof p2 === "string");
|
|
114117
|
+
}
|
|
114118
|
+
|
|
114119
|
+
// ../connectors/src/connectors/cosmosdb/tools/query.ts
|
|
114120
|
+
import { z as z91 } from "zod";
|
|
114121
|
+
var MAX_DOCUMENTS3 = 500;
|
|
114122
|
+
var inputSchema91 = z91.object({
|
|
114123
|
+
toolUseIntent: z91.string().optional().describe(
|
|
114124
|
+
"Brief description of what you intend to accomplish with this tool call"
|
|
114125
|
+
),
|
|
114126
|
+
connectionId: z91.string().describe("ID of the Cosmos DB connection to use"),
|
|
114127
|
+
container: z91.string().describe("Id of the container (a.k.a. collection) to query"),
|
|
114128
|
+
sql: z91.string().describe(
|
|
114129
|
+
"Cosmos DB SQL query (Core / NoSQL API). Reference items via the alias `c` (e.g. `SELECT TOP 100 c.id, c.name FROM c WHERE c.status = 'active'`). Use `TOP n` rather than `LIMIT n` \u2014 Cosmos DB does not understand `LIMIT`."
|
|
114130
|
+
),
|
|
114131
|
+
partitionKey: z91.string().optional().describe(
|
|
114132
|
+
`Optional partition key value to scope the query to a single partition. Pass as a JSON-encoded scalar (e.g. '"abc"' or '123'). Omit for cross-partition queries.`
|
|
114133
|
+
)
|
|
114134
|
+
});
|
|
114135
|
+
var outputSchema91 = z91.discriminatedUnion("success", [
|
|
114136
|
+
z91.object({
|
|
114137
|
+
success: z91.literal(true),
|
|
114138
|
+
documentCount: z91.number(),
|
|
114139
|
+
truncated: z91.boolean(),
|
|
114140
|
+
requestCharge: z91.number().optional(),
|
|
114141
|
+
documents: z91.array(z91.unknown())
|
|
114142
|
+
}),
|
|
114143
|
+
z91.object({
|
|
114144
|
+
success: z91.literal(false),
|
|
114145
|
+
error: z91.string()
|
|
114146
|
+
})
|
|
114147
|
+
]);
|
|
114148
|
+
var queryTool = new ConnectorTool({
|
|
114149
|
+
name: "query",
|
|
114150
|
+
description: `Execute a Cosmos DB SQL (Core / NoSQL API) query against a container. Returns up to ${MAX_DOCUMENTS3} items.
|
|
114151
|
+
Use for: schema exploration, data sampling, aggregations, and analytical queries.
|
|
114152
|
+
Cosmos DB SQL targets a single container; reference items via the alias \`c\` (e.g. \`SELECT c.id FROM c WHERE c.userId = 'abc'\`).
|
|
114153
|
+
Use \`TOP n\` (not \`LIMIT n\`) to bound the result. Cross-partition queries are enabled by default \u2014 pass \`partitionKey\` to restrict to a single partition.`,
|
|
114154
|
+
inputSchema: inputSchema91,
|
|
114155
|
+
outputSchema: outputSchema91,
|
|
114156
|
+
async execute({ connectionId, container, sql, partitionKey }, connections) {
|
|
114157
|
+
const connection2 = connections.find((c6) => c6.id === connectionId);
|
|
114158
|
+
if (!connection2) {
|
|
114159
|
+
return {
|
|
114160
|
+
success: false,
|
|
114161
|
+
error: `Connection ${connectionId} not found`
|
|
114162
|
+
};
|
|
114163
|
+
}
|
|
114164
|
+
console.log(
|
|
114165
|
+
`[connector-query] cosmosdb/${connection2.name} (${container}): ${sql}`
|
|
114166
|
+
);
|
|
114167
|
+
let key;
|
|
114168
|
+
try {
|
|
114169
|
+
const cosmos = await import("@azure/cosmos");
|
|
114170
|
+
const { CosmosClient } = cosmos;
|
|
114171
|
+
const endpoint = parameters74.endpoint.getValue(connection2);
|
|
114172
|
+
key = parameters74.key.getValue(connection2);
|
|
114173
|
+
const database = parameters74.database.getValue(connection2);
|
|
114174
|
+
const client = new CosmosClient({ endpoint, key });
|
|
114175
|
+
const cont = client.database(database).container(container);
|
|
114176
|
+
const queryOptions = {
|
|
114177
|
+
// Bound by the connector's own row cap, but keep the SDK from
|
|
114178
|
+
// streaming arbitrarily large continuations.
|
|
114179
|
+
maxItemCount: MAX_DOCUMENTS3 + 1
|
|
114180
|
+
};
|
|
114181
|
+
if (partitionKey != null && partitionKey !== "") {
|
|
114182
|
+
try {
|
|
114183
|
+
queryOptions.partitionKey = JSON.parse(partitionKey);
|
|
114184
|
+
} catch {
|
|
114185
|
+
return {
|
|
114186
|
+
success: false,
|
|
114187
|
+
error: `Invalid partitionKey: must be a JSON-encoded scalar (e.g. '"abc"' or '123'). Got: ${partitionKey}`
|
|
114188
|
+
};
|
|
114189
|
+
}
|
|
114190
|
+
}
|
|
114191
|
+
const iterator = cont.items.query(sql, queryOptions);
|
|
114192
|
+
const { resources, requestCharge } = await iterator.fetchNext();
|
|
114193
|
+
const documents = resources ?? [];
|
|
114194
|
+
const truncated = documents.length > MAX_DOCUMENTS3;
|
|
114195
|
+
return {
|
|
114196
|
+
success: true,
|
|
114197
|
+
documentCount: Math.min(documents.length, MAX_DOCUMENTS3),
|
|
114198
|
+
truncated,
|
|
114199
|
+
requestCharge,
|
|
114200
|
+
documents: documents.slice(0, MAX_DOCUMENTS3)
|
|
114201
|
+
};
|
|
114202
|
+
} catch (err) {
|
|
114203
|
+
let msg = err instanceof Error ? err.message : String(err);
|
|
114204
|
+
if (key) msg = msg.replaceAll(key, "***");
|
|
114205
|
+
return { success: false, error: msg };
|
|
114206
|
+
}
|
|
114207
|
+
}
|
|
114208
|
+
});
|
|
114209
|
+
|
|
114210
|
+
// ../connectors/src/connectors/cosmosdb/index.ts
|
|
114211
|
+
var tools74 = {
|
|
114212
|
+
listContainers: listContainersTool,
|
|
114213
|
+
query: queryTool
|
|
114214
|
+
};
|
|
114215
|
+
var cosmosdbConnector = new ConnectorPlugin({
|
|
114216
|
+
slug: "cosmosdb",
|
|
114217
|
+
authType: AUTH_TYPES.USER_PASSWORD,
|
|
114218
|
+
name: "Azure Cosmos DB",
|
|
114219
|
+
description: "Connect to Azure Cosmos DB (Core / NoSQL API) for document-oriented data storage and SQL-style querying.",
|
|
114220
|
+
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/5p9B2Db0V2d8mK2jgBWtZu/dad72db8f41b16c50de2bcef03f9d415/cosmosdb-icon.png",
|
|
114221
|
+
parameters: parameters74,
|
|
114222
|
+
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
114223
|
+
categories: ["database"],
|
|
114224
|
+
onboarding: cosmosdbOnboarding,
|
|
114225
|
+
systemPrompt: {
|
|
114226
|
+
en: `### Tools
|
|
114227
|
+
|
|
114228
|
+
- \`cosmosdb_listContainers\`: Lists all containers in the configured database, with their partition key paths. Use this first to explore available data.
|
|
114229
|
+
- \`cosmosdb_query\`: Executes a Cosmos DB SQL (Core / NoSQL API) query against a single container and returns items. Use for schema exploration, data sampling, and analytical queries. Pass \`partitionKey\` to scope the query to a single partition (cross-partition queries are enabled by default).
|
|
114230
|
+
|
|
114231
|
+
### Business Logic
|
|
114232
|
+
|
|
114233
|
+
The business logic type for this connector is "typescript". Write handler code using the connector SDK shown below. Do NOT access credentials directly from environment variables.
|
|
114234
|
+
|
|
114235
|
+
\u26A0\uFE0F **The client returned by \`connection(connectionId)\` is NOT the raw \`@azure/cosmos\` \`CosmosClient\`.** It is a thin wrapper exposing only two methods:
|
|
114236
|
+
- \`client.query<T>(container, sql, options?) => Promise<T[]>\` \u2014 runs a Cosmos SQL query against the named container and returns the **already-unwrapped** items array (no \`{ resources }\` wrapper). \`options\` accepts \`{ maxItemCount?: number; partitionKey?: unknown }\`.
|
|
114237
|
+
- \`client.listContainers() => Promise<{ id: string; partitionKey?: string[] }[]>\` \u2014 lists containers in the configured database.
|
|
114238
|
+
|
|
114239
|
+
There is **no** \`client.databases\`, \`client.database(...)\`, \`client.container(...)\`, or \`client.items\`. Do NOT attempt to use the \`@azure/cosmos\` \`CosmosClient\` API directly through this client \u2014 those calls will fail with \`Cannot read properties of undefined\`.
|
|
114240
|
+
|
|
114241
|
+
\`\`\`ts
|
|
114242
|
+
import type { Context } from "hono";
|
|
114243
|
+
import { connection } from "@squadbase/vite-server/connectors/cosmosdb";
|
|
114244
|
+
|
|
114245
|
+
const cosmos = connection("<connectionId>");
|
|
114246
|
+
|
|
114247
|
+
export default async function handler(_c: Context) {
|
|
114248
|
+
// \`query\` returns the items array directly \u2014 no \`.resources\` to unwrap.
|
|
114249
|
+
const rows = await cosmos.query<{ prod: string; orderCount: number }>(
|
|
114250
|
+
"<containerName>",
|
|
114251
|
+
"SELECT c.prod, COUNT(1) AS orderCount FROM c GROUP BY c.prod",
|
|
114252
|
+
// Optional: scope to a single partition to save RUs.
|
|
114253
|
+
// { partitionKey: "<partitionKeyValue>" },
|
|
114254
|
+
);
|
|
114255
|
+
|
|
114256
|
+
rows.sort((a, b) => Number(b.orderCount) - Number(a.orderCount));
|
|
114257
|
+
|
|
114258
|
+
return new Response(JSON.stringify(rows), {
|
|
114259
|
+
headers: { "Content-Type": "application/json" },
|
|
114260
|
+
});
|
|
114261
|
+
}
|
|
114262
|
+
\`\`\`
|
|
114263
|
+
|
|
114264
|
+
### Cosmos DB SQL Reference
|
|
114265
|
+
- Cosmos DB stores schema-flexible JSON items in **containers** organised under a **database**. Items are partitioned by a per-container partition key path.
|
|
114266
|
+
- Queries always target a single container and reference items via the alias \`c\` (e.g. \`SELECT c.id, c.name FROM c WHERE c.status = 'active'\`).
|
|
114267
|
+
- Row limiting: use \`TOP n\` (e.g. \`SELECT TOP 100 * FROM c\`). \`LIMIT\` is **not** supported. \`OFFSET m LIMIT n\` is supported on newer accounts but \`TOP\` is the safe default.
|
|
114268
|
+
- System fields are prefixed with an underscore (\`c.id\`, \`c._ts\` for the modification timestamp, \`c._etag\`).
|
|
114269
|
+
- Aggregates: \`COUNT(1)\`, \`SUM\`, \`AVG\`, \`MIN\`, \`MAX\`, with \`GROUP BY\` (e.g. \`SELECT c.country, COUNT(1) AS n FROM c GROUP BY c.country\`).
|
|
114270
|
+
- Joins: only **intra-document** joins via \`JOIN\` over arrays inside the same item; there is no cross-container/cross-document join.
|
|
114271
|
+
- Always bound results with \`TOP n\` and prefer scoped queries with a \`partitionKey\` value when possible \u2014 cross-partition queries cost more RUs.`,
|
|
114272
|
+
ja: `### \u30C4\u30FC\u30EB
|
|
114273
|
+
|
|
114274
|
+
- \`cosmosdb_listContainers\`: \u8A2D\u5B9A\u3055\u308C\u305F\u30C7\u30FC\u30BF\u30D9\u30FC\u30B9\u5185\u306E\u30B3\u30F3\u30C6\u30CA\u4E00\u89A7\uFF08\u30D1\u30FC\u30C6\u30A3\u30B7\u30E7\u30F3\u30AD\u30FC\u306E\u30D1\u30B9\u4ED8\u304D\uFF09\u3092\u53D6\u5F97\u3057\u307E\u3059\u3002\u30C7\u30FC\u30BF\u63A2\u7D22\u306E\u6700\u521D\u306E\u30B9\u30C6\u30C3\u30D7\u3068\u3057\u3066\u4F7F\u7528\u3057\u3066\u304F\u3060\u3055\u3044\u3002
|
|
114275
|
+
- \`cosmosdb_query\`: \u5358\u4E00\u306E\u30B3\u30F3\u30C6\u30CA\u306B\u5BFE\u3057\u3066 Cosmos DB SQL\uFF08Core / NoSQL API\uFF09\u30AF\u30A8\u30EA\u3092\u5B9F\u884C\u3057\u3001\u30A2\u30A4\u30C6\u30E0\u3092\u8FD4\u3057\u307E\u3059\u3002\u30B9\u30AD\u30FC\u30DE\u63A2\u7D22\u3001\u30C7\u30FC\u30BF\u306E\u30B5\u30F3\u30D7\u30EA\u30F3\u30B0\u3001\u5206\u6790\u30AF\u30A8\u30EA\u306B\u4F7F\u7528\u3057\u307E\u3059\u3002\`partitionKey\` \u3092\u6E21\u3059\u3068\u5358\u4E00\u30D1\u30FC\u30C6\u30A3\u30B7\u30E7\u30F3\u306B\u30B9\u30B3\u30FC\u30D7\u3067\u304D\u3001\u672A\u6307\u5B9A\u3060\u3068\u30AF\u30ED\u30B9\u30D1\u30FC\u30C6\u30A3\u30B7\u30E7\u30F3\u30AF\u30A8\u30EA\u306B\u306A\u308A\u307E\u3059\u3002
|
|
114276
|
+
|
|
114277
|
+
### Business Logic
|
|
114278
|
+
|
|
114279
|
+
\u3053\u306E\u30B3\u30CD\u30AF\u30BF\u306E\u30D3\u30B8\u30CD\u30B9\u30ED\u30B8\u30C3\u30AF\u30BF\u30A4\u30D7\u306F "typescript" \u3067\u3059\u3002\u4EE5\u4E0B\u306B\u793A\u3059\u30B3\u30CD\u30AF\u30BFSDK\u3092\u4F7F\u7528\u3057\u3066\u30CF\u30F3\u30C9\u30E9\u30B3\u30FC\u30C9\u3092\u8A18\u8FF0\u3057\u3066\u304F\u3060\u3055\u3044\u3002\u74B0\u5883\u5909\u6570\u304B\u3089\u76F4\u63A5\u8A8D\u8A3C\u60C5\u5831\u306B\u30A2\u30AF\u30BB\u30B9\u3057\u306A\u3044\u3067\u304F\u3060\u3055\u3044\u3002
|
|
114280
|
+
|
|
114281
|
+
\u26A0\uFE0F **\`connection(connectionId)\` \u304C\u8FD4\u3059\u30AF\u30E9\u30A4\u30A2\u30F3\u30C8\u306F \`@azure/cosmos\` \u306E \`CosmosClient\` \u305D\u306E\u3082\u306E\u3067\u306F\u3042\u308A\u307E\u305B\u3093\u3002** \u4EE5\u4E0B\u306E2\u30E1\u30BD\u30C3\u30C9\u306E\u307F\u3092\u516C\u958B\u3059\u308B\u8584\u3044\u30E9\u30C3\u30D1\u30FC\u3067\u3059\uFF1A
|
|
114282
|
+
- \`client.query<T>(container, sql, options?) => Promise<T[]>\` \u2014 \u6307\u5B9A\u30B3\u30F3\u30C6\u30CA\u306B\u5BFE\u3057\u3066 Cosmos SQL \u3092\u5B9F\u884C\u3057\u3001**\u3059\u3067\u306B\u5C55\u958B\u6E08\u307F\u306E\u30A2\u30A4\u30C6\u30E0\u914D\u5217**\u3092\u8FD4\u3059\uFF08\`{ resources }\` \u3067\u30E9\u30C3\u30D7\u3055\u308C\u3066\u3044\u306A\u3044\uFF09\u3002\`options\` \u306F \`{ maxItemCount?: number; partitionKey?: unknown }\`\u3002
|
|
114283
|
+
- \`client.listContainers() => Promise<{ id: string; partitionKey?: string[] }[]>\` \u2014 \u8A2D\u5B9A\u3055\u308C\u305F\u30C7\u30FC\u30BF\u30D9\u30FC\u30B9\u5185\u306E\u30B3\u30F3\u30C6\u30CA\u4E00\u89A7\u3092\u8FD4\u3059\u3002
|
|
114284
|
+
|
|
114285
|
+
\`client.databases\`\u3001\`client.database(...)\`\u3001\`client.container(...)\`\u3001\`client.items\` \u306F **\u5B58\u5728\u3057\u306A\u3044**\u3002\`@azure/cosmos\` \u306E \`CosmosClient\` API \u3092\u3053\u306E\u30AF\u30E9\u30A4\u30A2\u30F3\u30C8\u8D8A\u3057\u306B\u76F4\u63A5\u4F7F\u304A\u3046\u3068\u3057\u306A\u3044\u3053\u3068 \u2014 \`Cannot read properties of undefined\` \u3067\u5931\u6557\u3059\u308B\u3002
|
|
114286
|
+
|
|
114287
|
+
\`\`\`ts
|
|
114288
|
+
import type { Context } from "hono";
|
|
114289
|
+
import { connection } from "@squadbase/vite-server/connectors/cosmosdb";
|
|
114290
|
+
|
|
114291
|
+
const cosmos = connection("<connectionId>");
|
|
114292
|
+
|
|
114293
|
+
export default async function handler(_c: Context) {
|
|
114294
|
+
// \`query\` \u306F items \u914D\u5217\u3092\u305D\u306E\u307E\u307E\u8FD4\u3059 \u2014 \`.resources\` \u306E\u5C55\u958B\u306F\u4E0D\u8981\u3002
|
|
114295
|
+
const rows = await cosmos.query<{ prod: string; orderCount: number }>(
|
|
114296
|
+
"<containerName>",
|
|
114297
|
+
"SELECT c.prod, COUNT(1) AS orderCount FROM c GROUP BY c.prod",
|
|
114298
|
+
// \u4EFB\u610F: \u5358\u4E00\u30D1\u30FC\u30C6\u30A3\u30B7\u30E7\u30F3\u306B\u30B9\u30B3\u30FC\u30D7\u3057\u3066 RU \u3092\u7BC0\u7D04\u3002
|
|
114299
|
+
// { partitionKey: "<partitionKeyValue>" },
|
|
114300
|
+
);
|
|
114301
|
+
|
|
114302
|
+
rows.sort((a, b) => Number(b.orderCount) - Number(a.orderCount));
|
|
114303
|
+
|
|
114304
|
+
return new Response(JSON.stringify(rows), {
|
|
114305
|
+
headers: { "Content-Type": "application/json" },
|
|
114306
|
+
});
|
|
114307
|
+
}
|
|
114308
|
+
\`\`\`
|
|
114309
|
+
|
|
114310
|
+
### Cosmos DB SQL \u30EA\u30D5\u30A1\u30EC\u30F3\u30B9
|
|
114311
|
+
- Cosmos DB \u306F\u30B9\u30AD\u30FC\u30DE\u67D4\u8EDF\u306A JSON \u30A2\u30A4\u30C6\u30E0\u3092 **\u30B3\u30F3\u30C6\u30CA** \u306B\u683C\u7D0D\u3057\u3001\u30B3\u30F3\u30C6\u30CA\u306F\u30B3\u30F3\u30C6\u30CA\u3054\u3068\u306E\u30D1\u30FC\u30C6\u30A3\u30B7\u30E7\u30F3\u30AD\u30FC\u30D1\u30B9\u3067\u30D1\u30FC\u30C6\u30A3\u30B7\u30E7\u30F3\u5206\u5272\u3055\u308C\u307E\u3059\u3002\u30B3\u30F3\u30C6\u30CA\u306F **\u30C7\u30FC\u30BF\u30D9\u30FC\u30B9** \u306B\u307E\u3068\u3081\u3089\u308C\u307E\u3059\u3002
|
|
114312
|
+
- \u30AF\u30A8\u30EA\u306F\u5E38\u306B\u5358\u4E00\u30B3\u30F3\u30C6\u30CA\u3092\u5BFE\u8C61\u3068\u3057\u3001\u30A2\u30A4\u30C6\u30E0\u306F\u5225\u540D \`c\` \u3067\u53C2\u7167\u3057\u307E\u3059\uFF08\u4F8B: \`SELECT c.id, c.name FROM c WHERE c.status = 'active'\`\uFF09\u3002
|
|
114313
|
+
- \u884C\u6570\u5236\u9650: \`TOP n\` \u3092\u4F7F\u7528\u3057\u307E\u3059\uFF08\u4F8B: \`SELECT TOP 100 * FROM c\`\uFF09\u3002\`LIMIT\` \u306F **\u4F7F\u7528\u3067\u304D\u307E\u305B\u3093**\u3002\u65B0\u3057\u3044\u30A2\u30AB\u30A6\u30F3\u30C8\u3067\u306F \`OFFSET m LIMIT n\` \u304C\u4F7F\u3048\u307E\u3059\u304C\u3001\u5B89\u5168\u5074\u306E\u65E2\u5B9A\u306F \`TOP\` \u3067\u3059\u3002
|
|
114314
|
+
- \u30B7\u30B9\u30C6\u30E0\u30D5\u30A3\u30FC\u30EB\u30C9\u306F\u30A2\u30F3\u30C0\u30FC\u30B9\u30B3\u30A2\u59CB\u307E\u308A\uFF08\`c.id\`\u3001\u5909\u66F4\u6642\u523B\u306E \`c._ts\`\u3001\`c._etag\`\uFF09\u3002
|
|
114315
|
+
- \u96C6\u7D04: \`COUNT(1)\`\u3001\`SUM\`\u3001\`AVG\`\u3001\`MIN\`\u3001\`MAX\` \u3092 \`GROUP BY\` \u3068\u7D44\u307F\u5408\u308F\u305B\u307E\u3059\uFF08\u4F8B: \`SELECT c.country, COUNT(1) AS n FROM c GROUP BY c.country\`\uFF09\u3002
|
|
114316
|
+
- \u7D50\u5408: \u540C\u4E00\u30A2\u30A4\u30C6\u30E0\u5185\u306E\u914D\u5217\u306B\u5BFE\u3059\u308B **\u30A4\u30F3\u30C8\u30E9\u30C9\u30AD\u30E5\u30E1\u30F3\u30C8** \`JOIN\` \u306E\u307F\u3067\u3001\u30B3\u30F3\u30C6\u30CA\u9593\uFF0F\u30C9\u30AD\u30E5\u30E1\u30F3\u30C8\u9593\u306E\u7D50\u5408\u306F\u30B5\u30DD\u30FC\u30C8\u3055\u308C\u307E\u305B\u3093\u3002
|
|
114317
|
+
- \u7D50\u679C\u4EF6\u6570\u306F\u5FC5\u305A \`TOP n\` \u3067\u5236\u9650\u3057\u3001\u53EF\u80FD\u3067\u3042\u308C\u3070 \`partitionKey\` \u3067\u5358\u4E00\u30D1\u30FC\u30C6\u30A3\u30B7\u30E7\u30F3\u306B\u30B9\u30B3\u30FC\u30D7\u3057\u3066\u304F\u3060\u3055\u3044\uFF08\u30AF\u30ED\u30B9\u30D1\u30FC\u30C6\u30A3\u30B7\u30E7\u30F3\u30AF\u30A8\u30EA\u306F RU \u3092\u591A\u304F\u6D88\u8CBB\u3057\u307E\u3059\uFF09\u3002`
|
|
114318
|
+
},
|
|
114319
|
+
tools: tools74,
|
|
114320
|
+
async checkConnection(params, _config) {
|
|
114321
|
+
try {
|
|
114322
|
+
const { CosmosClient } = await import("@azure/cosmos");
|
|
114323
|
+
const client = new CosmosClient({
|
|
114324
|
+
endpoint: params[parameters74.endpoint.slug],
|
|
114325
|
+
key: params[parameters74.key.slug]
|
|
114326
|
+
});
|
|
114327
|
+
const database = params[parameters74.database.slug];
|
|
114328
|
+
await client.database(database).read();
|
|
114329
|
+
return { success: true };
|
|
114330
|
+
} catch (error2) {
|
|
114331
|
+
const msg = error2 instanceof Error ? error2.message : String(error2);
|
|
114332
|
+
const key = params[parameters74.key.slug];
|
|
114333
|
+
return {
|
|
114334
|
+
success: false,
|
|
114335
|
+
error: key ? msg.replaceAll(key, "***") : msg
|
|
114336
|
+
};
|
|
114337
|
+
}
|
|
113869
114338
|
}
|
|
113870
114339
|
});
|
|
113871
114340
|
|
|
@@ -113886,7 +114355,7 @@ var oracleOnboarding = new ConnectorOnboarding({
|
|
|
113886
114355
|
});
|
|
113887
114356
|
|
|
113888
114357
|
// ../connectors/src/connectors/oracle/parameters.ts
|
|
113889
|
-
var
|
|
114358
|
+
var parameters75 = {
|
|
113890
114359
|
jdbcUrl: new ParameterDefinition({
|
|
113891
114360
|
slug: "jdbc-url",
|
|
113892
114361
|
name: "Oracle JDBC URL",
|
|
@@ -113913,31 +114382,32 @@ var parameters74 = {
|
|
|
113913
114382
|
type: "text",
|
|
113914
114383
|
secret: true,
|
|
113915
114384
|
required: false
|
|
113916
|
-
})
|
|
114385
|
+
}),
|
|
114386
|
+
...sshTunnelParameters
|
|
113917
114387
|
};
|
|
113918
114388
|
|
|
113919
114389
|
// ../connectors/src/connectors/oracle/tools/execute-query.ts
|
|
113920
|
-
import { z as
|
|
114390
|
+
import { z as z92 } from "zod";
|
|
113921
114391
|
var MAX_ROWS16 = 500;
|
|
113922
|
-
var
|
|
113923
|
-
toolUseIntent:
|
|
114392
|
+
var inputSchema92 = z92.object({
|
|
114393
|
+
toolUseIntent: z92.string().optional().describe(
|
|
113924
114394
|
"Brief description of what you intend to accomplish with this tool call"
|
|
113925
114395
|
),
|
|
113926
|
-
connectionId:
|
|
113927
|
-
sql:
|
|
114396
|
+
connectionId: z92.string().describe("ID of the Oracle connection to use"),
|
|
114397
|
+
sql: z92.string().describe(
|
|
113928
114398
|
"PL/SQL-compatible query. Oracle has no `LIMIT`; use `FETCH FIRST n ROWS ONLY` or filter on `ROWNUM`. Don't end the statement with a semicolon \u2014 the driver rejects trailing terminators."
|
|
113929
114399
|
)
|
|
113930
114400
|
});
|
|
113931
|
-
var
|
|
113932
|
-
|
|
113933
|
-
success:
|
|
113934
|
-
rowCount:
|
|
113935
|
-
truncated:
|
|
113936
|
-
rows:
|
|
114401
|
+
var outputSchema92 = z92.discriminatedUnion("success", [
|
|
114402
|
+
z92.object({
|
|
114403
|
+
success: z92.literal(true),
|
|
114404
|
+
rowCount: z92.number(),
|
|
114405
|
+
truncated: z92.boolean(),
|
|
114406
|
+
rows: z92.array(z92.record(z92.string(), z92.unknown()))
|
|
113937
114407
|
}),
|
|
113938
|
-
|
|
113939
|
-
success:
|
|
113940
|
-
error:
|
|
114408
|
+
z92.object({
|
|
114409
|
+
success: z92.literal(false),
|
|
114410
|
+
error: z92.string()
|
|
113941
114411
|
})
|
|
113942
114412
|
]);
|
|
113943
114413
|
var executeQueryTool16 = new ConnectorTool({
|
|
@@ -113947,8 +114417,8 @@ Use for: schema exploration via \`USER_TABLES\` / \`USER_TAB_COLUMNS\` / \`ALL_T
|
|
|
113947
114417
|
Oracle uses \`FETCH FIRST n ROWS ONLY\` (12c+) or \`ROWNUM\` for row limiting \u2014 there is no \`LIMIT\` keyword.
|
|
113948
114418
|
Unquoted identifiers are stored upper-case (\`SELECT * FROM employees\` resolves to \`EMPLOYEES\`).
|
|
113949
114419
|
Do NOT terminate statements with a semicolon; the driver rejects trailing terminators.`,
|
|
113950
|
-
inputSchema:
|
|
113951
|
-
outputSchema:
|
|
114420
|
+
inputSchema: inputSchema92,
|
|
114421
|
+
outputSchema: outputSchema92,
|
|
113952
114422
|
async execute({ connectionId, sql }, connections) {
|
|
113953
114423
|
const connection2 = connections.find((c6) => c6.id === connectionId);
|
|
113954
114424
|
if (!connection2) {
|
|
@@ -113957,9 +114427,9 @@ Do NOT terminate statements with a semicolon; the driver rejects trailing termin
|
|
|
113957
114427
|
error: `Connection ${connectionId} not found`
|
|
113958
114428
|
};
|
|
113959
114429
|
}
|
|
113960
|
-
const jdbcUrl =
|
|
113961
|
-
const username =
|
|
113962
|
-
const password =
|
|
114430
|
+
const jdbcUrl = parameters75.jdbcUrl.getValue(connection2);
|
|
114431
|
+
const username = parameters75.username.tryGetValue(connection2);
|
|
114432
|
+
const password = parameters75.password.tryGetValue(connection2);
|
|
113963
114433
|
console.log(
|
|
113964
114434
|
`[connector-query] oracle/${connection2.name} (${redactOracleUrl(jdbcUrl)}): ${sql}`
|
|
113965
114435
|
);
|
|
@@ -113974,7 +114444,9 @@ Do NOT terminate statements with a semicolon; the driver rejects trailing termin
|
|
|
113974
114444
|
}
|
|
113975
114445
|
try {
|
|
113976
114446
|
const cleanSql = sql.replace(/;\s*$/, "");
|
|
113977
|
-
const { rows } = await runOracleQuery(parsed, cleanSql
|
|
114447
|
+
const { rows } = await runOracleQuery(parsed, cleanSql, {
|
|
114448
|
+
tunnelParams: connectionParamsToRecord(connection2)
|
|
114449
|
+
});
|
|
113978
114450
|
const truncated = rows.length > MAX_ROWS16;
|
|
113979
114451
|
return {
|
|
113980
114452
|
success: true,
|
|
@@ -113991,14 +114463,14 @@ Do NOT terminate statements with a semicolon; the driver rejects trailing termin
|
|
|
113991
114463
|
});
|
|
113992
114464
|
|
|
113993
114465
|
// ../connectors/src/connectors/oracle/index.ts
|
|
113994
|
-
var
|
|
114466
|
+
var tools75 = { executeQuery: executeQueryTool16 };
|
|
113995
114467
|
var oracleConnector = new ConnectorPlugin({
|
|
113996
114468
|
slug: "oracle",
|
|
113997
114469
|
authType: AUTH_TYPES.USER_PASSWORD,
|
|
113998
114470
|
name: "Oracle Database",
|
|
113999
114471
|
description: "Connect to Oracle Database using a JDBC-style URL via the pure-JS Thin driver (no Oracle Instant Client required).",
|
|
114000
114472
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/3iGEdzvGHncU5bYqFOROiV/9e7bdda7230d7ca6b34e7f6a862de876/oracle-icon.webp",
|
|
114001
|
-
parameters:
|
|
114473
|
+
parameters: parameters75,
|
|
114002
114474
|
releaseFlag: { dev1: true, dev2: false, prod: false },
|
|
114003
114475
|
categories: ["database"],
|
|
114004
114476
|
onboarding: oracleOnboarding,
|
|
@@ -114042,26 +114514,32 @@ The business logic type for this connector is "sql".
|
|
|
114042
114514
|
- \u30B9\u30C6\u30FC\u30C8\u30E1\u30F3\u30C8\u672B\u5C3E\u306B\u30BB\u30DF\u30B3\u30ED\u30F3\u3092\u4ED8\u3051\u306A\u3044\u3067\u304F\u3060\u3055\u3044\uFF08thin \u30C9\u30E9\u30A4\u30D0\u304C\u62D2\u5426\u3057\u307E\u3059\uFF09\u3002
|
|
114043
114515
|
- \u884C\u6570\u5236\u9650\u306E\u4E92\u63DB\u6027: \u30D7\u30E9\u30C3\u30C8\u30D5\u30A9\u30FC\u30E0\u306E server-logic \u30B9\u30AD\u30FC\u30DE\u63A8\u8AD6\u306F\u3001\u30AF\u30A8\u30EA\u3092 \`SELECT * FROM (<inner>) AS _sq LIMIT N\` \u306E\u5F62\u3067\u30E9\u30C3\u30D7\u3057\u3066\u304F\u308B\u3053\u3068\u304C\u3042\u308A\u307E\u3059\u3002Oracle \u306B\u306F \`LIMIT\` \u30AD\u30FC\u30EF\u30FC\u30C9\u304C\u5B58\u5728\u3057\u306A\u3044\u305F\u3081\u3001\u30B3\u30CD\u30AF\u30BF\u306F \`query()\` \u5185\u3067\u3053\u306E\u30E9\u30C3\u30D1\u3092\u691C\u51FA\u3057\u3001\`<inner>\` \u3092\u305D\u306E\u307E\u307E\u5B9F\u884C\u3057\u3066 JS \u5074\u3067\u5148\u982D N \u884C\u306B\u5207\u308A\u8A70\u3081\u307E\u3059\u3002\u5229\u7528\u8005\u5074\u3067\u5BFE\u51E6\u3059\u308B\u5FC5\u8981\u306F\u3042\u308A\u307E\u305B\u3093\u304C\u3001\u81EA\u5206\u3067\u66F8\u304F SQL \u3067\u306F \`LIMIT\` \u3092\u4F7F\u308F\u305A \`FETCH FIRST N ROWS ONLY\` / \`OFFSET m ROWS FETCH NEXT N ROWS ONLY\` / \`ROWNUM\` \u3092\u4F7F\u3063\u3066\u304F\u3060\u3055\u3044\u3002`
|
|
114044
114516
|
},
|
|
114045
|
-
tools:
|
|
114517
|
+
tools: tools75,
|
|
114046
114518
|
async checkConnection(params, _config) {
|
|
114047
|
-
return checkOracleConnection(
|
|
114048
|
-
|
|
114049
|
-
|
|
114050
|
-
|
|
114519
|
+
return checkOracleConnection(
|
|
114520
|
+
params[parameters75.jdbcUrl.slug],
|
|
114521
|
+
{
|
|
114522
|
+
username: params[parameters75.username.slug],
|
|
114523
|
+
password: params[parameters75.password.slug]
|
|
114524
|
+
},
|
|
114525
|
+
{ tunnelParams: params }
|
|
114526
|
+
);
|
|
114051
114527
|
},
|
|
114052
114528
|
async query(params, sql, _namedParams) {
|
|
114053
|
-
const parsed = parseOracleJdbcUrl(params[
|
|
114054
|
-
username: params[
|
|
114055
|
-
password: params[
|
|
114529
|
+
const parsed = parseOracleJdbcUrl(params[parameters75.jdbcUrl.slug], {
|
|
114530
|
+
username: params[parameters75.username.slug],
|
|
114531
|
+
password: params[parameters75.password.slug]
|
|
114056
114532
|
});
|
|
114057
114533
|
const sample = unwrapSampleLimit(sql);
|
|
114058
114534
|
if (sample) {
|
|
114059
114535
|
const inner = sample.inner.replace(/;\s*$/, "");
|
|
114060
|
-
const result = await runOracleQuery(parsed, inner
|
|
114536
|
+
const result = await runOracleQuery(parsed, inner, {
|
|
114537
|
+
tunnelParams: params
|
|
114538
|
+
});
|
|
114061
114539
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
114062
114540
|
}
|
|
114063
114541
|
const cleanSql = sql.replace(/;\s*$/, "");
|
|
114064
|
-
return runOracleQuery(parsed, cleanSql);
|
|
114542
|
+
return runOracleQuery(parsed, cleanSql, { tunnelParams: params });
|
|
114065
114543
|
}
|
|
114066
114544
|
});
|
|
114067
114545
|
|
|
@@ -114082,7 +114560,7 @@ var freshserviceOnboarding = new ConnectorOnboarding({
|
|
|
114082
114560
|
});
|
|
114083
114561
|
|
|
114084
114562
|
// ../connectors/src/connectors/freshservice/parameters.ts
|
|
114085
|
-
var
|
|
114563
|
+
var parameters76 = {
|
|
114086
114564
|
domain: new ParameterDefinition({
|
|
114087
114565
|
slug: "domain",
|
|
114088
114566
|
name: "Freshservice Domain",
|
|
@@ -114104,7 +114582,7 @@ var parameters75 = {
|
|
|
114104
114582
|
};
|
|
114105
114583
|
|
|
114106
114584
|
// ../connectors/src/connectors/freshservice/tools/request.ts
|
|
114107
|
-
import { z as
|
|
114585
|
+
import { z as z93 } from "zod";
|
|
114108
114586
|
var BASE_PATH_SEGMENT12 = "/api/v2";
|
|
114109
114587
|
var REQUEST_TIMEOUT_MS70 = 6e4;
|
|
114110
114588
|
function buildBaseUrl(domain) {
|
|
@@ -114115,33 +114593,33 @@ function buildBaseUrl(domain) {
|
|
|
114115
114593
|
function basicAuthHeader(apiKey) {
|
|
114116
114594
|
return `Basic ${Buffer.from(`${apiKey}:X`).toString("base64")}`;
|
|
114117
114595
|
}
|
|
114118
|
-
var
|
|
114119
|
-
toolUseIntent:
|
|
114596
|
+
var inputSchema93 = z93.object({
|
|
114597
|
+
toolUseIntent: z93.string().optional().describe(
|
|
114120
114598
|
"Brief description of what you intend to accomplish with this tool call"
|
|
114121
114599
|
),
|
|
114122
|
-
connectionId:
|
|
114123
|
-
method:
|
|
114600
|
+
connectionId: z93.string().describe("ID of the Freshservice connection to use"),
|
|
114601
|
+
method: z93.enum(["GET", "POST", "PUT", "DELETE"]).describe(
|
|
114124
114602
|
"HTTP method. GET for reading resources, POST for creating, PUT for updating, DELETE for removing."
|
|
114125
114603
|
),
|
|
114126
|
-
path:
|
|
114604
|
+
path: z93.string().describe(
|
|
114127
114605
|
"API path (e.g., '/tickets', '/tickets/123', '/agents'). Append query parameters such as '?per_page=100&page=1' for pagination."
|
|
114128
114606
|
),
|
|
114129
|
-
body:
|
|
114607
|
+
body: z93.record(z93.string(), z93.unknown()).optional().describe(
|
|
114130
114608
|
'Request body (JSON) for POST/PUT requests. Example: { "subject": "...", "description": "...", "email": "...", "priority": 2, "status": 2, "source": 2 }.'
|
|
114131
114609
|
)
|
|
114132
114610
|
});
|
|
114133
|
-
var
|
|
114134
|
-
|
|
114135
|
-
success:
|
|
114136
|
-
status:
|
|
114137
|
-
data:
|
|
114138
|
-
|
|
114139
|
-
|
|
114611
|
+
var outputSchema93 = z93.discriminatedUnion("success", [
|
|
114612
|
+
z93.object({
|
|
114613
|
+
success: z93.literal(true),
|
|
114614
|
+
status: z93.number(),
|
|
114615
|
+
data: z93.union([
|
|
114616
|
+
z93.record(z93.string(), z93.unknown()),
|
|
114617
|
+
z93.array(z93.unknown())
|
|
114140
114618
|
])
|
|
114141
114619
|
}),
|
|
114142
|
-
|
|
114143
|
-
success:
|
|
114144
|
-
error:
|
|
114620
|
+
z93.object({
|
|
114621
|
+
success: z93.literal(false),
|
|
114622
|
+
error: z93.string()
|
|
114145
114623
|
})
|
|
114146
114624
|
]);
|
|
114147
114625
|
var requestTool52 = new ConnectorTool({
|
|
@@ -114172,8 +114650,8 @@ Field codes:
|
|
|
114172
114650
|
- ticket priority: 1 Low, 2 Medium, 3 High, 4 Urgent
|
|
114173
114651
|
- ticket status: 2 Open, 3 Pending, 4 Resolved, 5 Closed
|
|
114174
114652
|
- ticket source: 1 Email, 2 Portal, 3 Phone, 4 Chat, 5 Feedback widget, 7 Yammer, 8 AwsCloudwatch, 9 Pagerduty, 10 Walkup, 11 Slack`,
|
|
114175
|
-
inputSchema:
|
|
114176
|
-
outputSchema:
|
|
114653
|
+
inputSchema: inputSchema93,
|
|
114654
|
+
outputSchema: outputSchema93,
|
|
114177
114655
|
async execute({ connectionId, method, path: path6, body }, connections) {
|
|
114178
114656
|
const connection2 = connections.find((c6) => c6.id === connectionId);
|
|
114179
114657
|
if (!connection2) {
|
|
@@ -114186,8 +114664,8 @@ Field codes:
|
|
|
114186
114664
|
`[connector-request] freshservice/${connection2.name}: ${method} ${path6}`
|
|
114187
114665
|
);
|
|
114188
114666
|
try {
|
|
114189
|
-
const apiKey =
|
|
114190
|
-
const domain =
|
|
114667
|
+
const apiKey = parameters76.apiKey.getValue(connection2);
|
|
114668
|
+
const domain = parameters76.domain.getValue(connection2);
|
|
114191
114669
|
const baseUrl = buildBaseUrl(domain);
|
|
114192
114670
|
const normalizedPath = normalizeRequestPath(path6, BASE_PATH_SEGMENT12);
|
|
114193
114671
|
const url = `${baseUrl}${normalizedPath}`;
|
|
@@ -114226,14 +114704,14 @@ Field codes:
|
|
|
114226
114704
|
});
|
|
114227
114705
|
|
|
114228
114706
|
// ../connectors/src/connectors/freshservice/index.ts
|
|
114229
|
-
var
|
|
114707
|
+
var tools76 = { request: requestTool52 };
|
|
114230
114708
|
var freshserviceConnector = new ConnectorPlugin({
|
|
114231
114709
|
slug: "freshservice",
|
|
114232
114710
|
authType: AUTH_TYPES.API_KEY,
|
|
114233
114711
|
name: "Freshservice",
|
|
114234
114712
|
description: "Connect to Freshservice (ITSM) for ticket, agent, asset, and ITIL workflow data via API key.",
|
|
114235
114713
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/6Tj64HZOoIrGgQYDayBosY/3f45b29d3479726b5d245ac38d5a7036/freshservice-icon.svg",
|
|
114236
|
-
parameters:
|
|
114714
|
+
parameters: parameters76,
|
|
114237
114715
|
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
114238
114716
|
categories: ["productivity"],
|
|
114239
114717
|
onboarding: freshserviceOnboarding,
|
|
@@ -114391,7 +114869,7 @@ export default async function handler(c: Context) {
|
|
|
114391
114869
|
- \`status\`: 2=Open, 3=Pending, 4=Resolved, 5=Closed
|
|
114392
114870
|
- \`source\`: 1=Email, 2=Portal, 3=Phone, 4=Chat, 5=Feedback widget, 7=Yammer, 8=AwsCloudwatch, 9=Pagerduty, 10=Walkup, 11=Slack`
|
|
114393
114871
|
},
|
|
114394
|
-
tools:
|
|
114872
|
+
tools: tools76
|
|
114395
114873
|
});
|
|
114396
114874
|
|
|
114397
114875
|
// ../connectors/src/connectors/freshdesk/setup.ts
|
|
@@ -114411,7 +114889,7 @@ var freshdeskOnboarding = new ConnectorOnboarding({
|
|
|
114411
114889
|
});
|
|
114412
114890
|
|
|
114413
114891
|
// ../connectors/src/connectors/freshdesk/parameters.ts
|
|
114414
|
-
var
|
|
114892
|
+
var parameters77 = {
|
|
114415
114893
|
domain: new ParameterDefinition({
|
|
114416
114894
|
slug: "domain",
|
|
114417
114895
|
name: "Freshdesk Domain",
|
|
@@ -114433,7 +114911,7 @@ var parameters76 = {
|
|
|
114433
114911
|
};
|
|
114434
114912
|
|
|
114435
114913
|
// ../connectors/src/connectors/freshdesk/tools/request.ts
|
|
114436
|
-
import { z as
|
|
114914
|
+
import { z as z94 } from "zod";
|
|
114437
114915
|
var BASE_PATH_SEGMENT13 = "/api/v2";
|
|
114438
114916
|
var REQUEST_TIMEOUT_MS71 = 6e4;
|
|
114439
114917
|
function buildBaseUrl2(domain) {
|
|
@@ -114444,33 +114922,33 @@ function buildBaseUrl2(domain) {
|
|
|
114444
114922
|
function basicAuthHeader2(apiKey) {
|
|
114445
114923
|
return `Basic ${Buffer.from(`${apiKey}:X`).toString("base64")}`;
|
|
114446
114924
|
}
|
|
114447
|
-
var
|
|
114448
|
-
toolUseIntent:
|
|
114925
|
+
var inputSchema94 = z94.object({
|
|
114926
|
+
toolUseIntent: z94.string().optional().describe(
|
|
114449
114927
|
"Brief description of what you intend to accomplish with this tool call"
|
|
114450
114928
|
),
|
|
114451
|
-
connectionId:
|
|
114452
|
-
method:
|
|
114929
|
+
connectionId: z94.string().describe("ID of the Freshdesk connection to use"),
|
|
114930
|
+
method: z94.enum(["GET", "POST", "PUT", "DELETE"]).describe(
|
|
114453
114931
|
"HTTP method. GET for reading resources, POST for creating, PUT for updating, DELETE for removing."
|
|
114454
114932
|
),
|
|
114455
|
-
path:
|
|
114933
|
+
path: z94.string().describe(
|
|
114456
114934
|
"API path (e.g., '/tickets', '/tickets/123', '/contacts'). Append query parameters such as '?per_page=100&page=1&order_by=created_at&order_type=desc'."
|
|
114457
114935
|
),
|
|
114458
|
-
body:
|
|
114936
|
+
body: z94.record(z94.string(), z94.unknown()).optional().describe(
|
|
114459
114937
|
'Request body (JSON) for POST/PUT requests. Example creating a ticket: { "subject": "...", "description": "...", "email": "...", "priority": 2, "status": 2, "source": 1 }.'
|
|
114460
114938
|
)
|
|
114461
114939
|
});
|
|
114462
|
-
var
|
|
114463
|
-
|
|
114464
|
-
success:
|
|
114465
|
-
status:
|
|
114466
|
-
data:
|
|
114467
|
-
|
|
114468
|
-
|
|
114940
|
+
var outputSchema94 = z94.discriminatedUnion("success", [
|
|
114941
|
+
z94.object({
|
|
114942
|
+
success: z94.literal(true),
|
|
114943
|
+
status: z94.number(),
|
|
114944
|
+
data: z94.union([
|
|
114945
|
+
z94.record(z94.string(), z94.unknown()),
|
|
114946
|
+
z94.array(z94.unknown())
|
|
114469
114947
|
])
|
|
114470
114948
|
}),
|
|
114471
|
-
|
|
114472
|
-
success:
|
|
114473
|
-
error:
|
|
114949
|
+
z94.object({
|
|
114950
|
+
success: z94.literal(false),
|
|
114951
|
+
error: z94.string()
|
|
114474
114952
|
})
|
|
114475
114953
|
]);
|
|
114476
114954
|
var requestTool53 = new ConnectorTool({
|
|
@@ -114501,8 +114979,8 @@ Field codes (tickets):
|
|
|
114501
114979
|
- priority: 1 Low, 2 Medium, 3 High, 4 Urgent
|
|
114502
114980
|
- status: 2 Open, 3 Pending, 4 Resolved, 5 Closed
|
|
114503
114981
|
- source: 1 Email, 2 Portal, 3 Phone, 7 Chat, 9 Feedback widget, 10 Outbound email`,
|
|
114504
|
-
inputSchema:
|
|
114505
|
-
outputSchema:
|
|
114982
|
+
inputSchema: inputSchema94,
|
|
114983
|
+
outputSchema: outputSchema94,
|
|
114506
114984
|
async execute({ connectionId, method, path: path6, body }, connections) {
|
|
114507
114985
|
const connection2 = connections.find((c6) => c6.id === connectionId);
|
|
114508
114986
|
if (!connection2) {
|
|
@@ -114515,8 +114993,8 @@ Field codes (tickets):
|
|
|
114515
114993
|
`[connector-request] freshdesk/${connection2.name}: ${method} ${path6}`
|
|
114516
114994
|
);
|
|
114517
114995
|
try {
|
|
114518
|
-
const apiKey =
|
|
114519
|
-
const domain =
|
|
114996
|
+
const apiKey = parameters77.apiKey.getValue(connection2);
|
|
114997
|
+
const domain = parameters77.domain.getValue(connection2);
|
|
114520
114998
|
const baseUrl = buildBaseUrl2(domain);
|
|
114521
114999
|
const normalizedPath = normalizeRequestPath(path6, BASE_PATH_SEGMENT13);
|
|
114522
115000
|
const url = `${baseUrl}${normalizedPath}`;
|
|
@@ -114555,14 +115033,14 @@ Field codes (tickets):
|
|
|
114555
115033
|
});
|
|
114556
115034
|
|
|
114557
115035
|
// ../connectors/src/connectors/freshdesk/index.ts
|
|
114558
|
-
var
|
|
115036
|
+
var tools77 = { request: requestTool53 };
|
|
114559
115037
|
var freshdeskConnector = new ConnectorPlugin({
|
|
114560
115038
|
slug: "freshdesk",
|
|
114561
115039
|
authType: AUTH_TYPES.API_KEY,
|
|
114562
115040
|
name: "Freshdesk",
|
|
114563
115041
|
description: "Connect to Freshdesk for customer support ticket, contact, and company data via API key.",
|
|
114564
115042
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/1PSjIfQJgTYmiWriNTx4uE/26905f4120713bda0afd0b23d02a154e/freshdesk-icon.png",
|
|
114565
|
-
parameters:
|
|
115043
|
+
parameters: parameters77,
|
|
114566
115044
|
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
114567
115045
|
categories: ["crm"],
|
|
114568
115046
|
onboarding: freshdeskOnboarding,
|
|
@@ -114722,7 +115200,7 @@ export default async function handler(c: Context) {
|
|
|
114722
115200
|
- \`status\`: 2=Open, 3=Pending, 4=Resolved, 5=Closed
|
|
114723
115201
|
- \`source\`: 1=Email, 2=Portal, 3=Phone, 7=Chat, 9=Feedback widget, 10=Outbound email`
|
|
114724
115202
|
},
|
|
114725
|
-
tools:
|
|
115203
|
+
tools: tools77
|
|
114726
115204
|
});
|
|
114727
115205
|
|
|
114728
115206
|
// ../connectors/src/connectors/freshsales/setup.ts
|
|
@@ -114742,7 +115220,7 @@ var freshsalesOnboarding = new ConnectorOnboarding({
|
|
|
114742
115220
|
});
|
|
114743
115221
|
|
|
114744
115222
|
// ../connectors/src/connectors/freshsales/parameters.ts
|
|
114745
|
-
var
|
|
115223
|
+
var parameters78 = {
|
|
114746
115224
|
bundleAlias: new ParameterDefinition({
|
|
114747
115225
|
slug: "bundle-alias",
|
|
114748
115226
|
name: "Freshsales Bundle Alias",
|
|
@@ -114764,7 +115242,7 @@ var parameters77 = {
|
|
|
114764
115242
|
};
|
|
114765
115243
|
|
|
114766
115244
|
// ../connectors/src/connectors/freshsales/tools/request.ts
|
|
114767
|
-
import { z as
|
|
115245
|
+
import { z as z95 } from "zod";
|
|
114768
115246
|
var BASE_PATH_SEGMENT14 = "/crm/sales/api";
|
|
114769
115247
|
var REQUEST_TIMEOUT_MS72 = 6e4;
|
|
114770
115248
|
function buildBaseUrl3(bundleAlias) {
|
|
@@ -114772,33 +115250,33 @@ function buildBaseUrl3(bundleAlias) {
|
|
|
114772
115250
|
const subdomain = trimmed.split(".")[0];
|
|
114773
115251
|
return `https://${subdomain}.myfreshworks.com${BASE_PATH_SEGMENT14}`;
|
|
114774
115252
|
}
|
|
114775
|
-
var
|
|
114776
|
-
toolUseIntent:
|
|
115253
|
+
var inputSchema95 = z95.object({
|
|
115254
|
+
toolUseIntent: z95.string().optional().describe(
|
|
114777
115255
|
"Brief description of what you intend to accomplish with this tool call"
|
|
114778
115256
|
),
|
|
114779
|
-
connectionId:
|
|
114780
|
-
method:
|
|
115257
|
+
connectionId: z95.string().describe("ID of the Freshsales connection to use"),
|
|
115258
|
+
method: z95.enum(["GET", "POST", "PUT", "DELETE"]).describe(
|
|
114781
115259
|
"HTTP method. GET for reading resources (including /lookup), POST for creating, PUT for updating, DELETE for removing."
|
|
114782
115260
|
),
|
|
114783
|
-
path:
|
|
115261
|
+
path: z95.string().describe(
|
|
114784
115262
|
"API path (e.g., '/contacts', '/contacts/filters', '/contacts/view/{view_id}', '/deals/{id}', '/lookup'). Append query parameters such as '?page=1&per_page=100'."
|
|
114785
115263
|
),
|
|
114786
|
-
body:
|
|
115264
|
+
body: z95.record(z95.string(), z95.unknown()).optional().describe(
|
|
114787
115265
|
'Request body (JSON). For creating a contact: { "contact": { "first_name": "...", "last_name": "...", "email": "..." } }. For lookup: { "q": "john@example.com", "f": "email", "entities": "contact" }.'
|
|
114788
115266
|
)
|
|
114789
115267
|
});
|
|
114790
|
-
var
|
|
114791
|
-
|
|
114792
|
-
success:
|
|
114793
|
-
status:
|
|
114794
|
-
data:
|
|
114795
|
-
|
|
114796
|
-
|
|
115268
|
+
var outputSchema95 = z95.discriminatedUnion("success", [
|
|
115269
|
+
z95.object({
|
|
115270
|
+
success: z95.literal(true),
|
|
115271
|
+
status: z95.number(),
|
|
115272
|
+
data: z95.union([
|
|
115273
|
+
z95.record(z95.string(), z95.unknown()),
|
|
115274
|
+
z95.array(z95.unknown())
|
|
114797
115275
|
])
|
|
114798
115276
|
}),
|
|
114799
|
-
|
|
114800
|
-
success:
|
|
114801
|
-
error:
|
|
115277
|
+
z95.object({
|
|
115278
|
+
success: z95.literal(false),
|
|
115279
|
+
error: z95.string()
|
|
114802
115280
|
})
|
|
114803
115281
|
]);
|
|
114804
115282
|
var requestTool54 = new ConnectorTool({
|
|
@@ -114831,8 +115309,8 @@ Common endpoints:
|
|
|
114831
115309
|
Pagination: 1-indexed \`page\` + \`per_page\` (default 25, max 100). View endpoints return \`{ contacts/sales_accounts/deals: [...], meta: { total_pages, total } }\`.
|
|
114832
115310
|
|
|
114833
115311
|
Includes: most GET endpoints accept \`?include=\` with a comma-separated list (\`owner\`, \`creator\`, \`deals\`, \`contacts\`, etc.) to inline related records.`,
|
|
114834
|
-
inputSchema:
|
|
114835
|
-
outputSchema:
|
|
115312
|
+
inputSchema: inputSchema95,
|
|
115313
|
+
outputSchema: outputSchema95,
|
|
114836
115314
|
async execute({ connectionId, method, path: path6, body }, connections) {
|
|
114837
115315
|
const connection2 = connections.find((c6) => c6.id === connectionId);
|
|
114838
115316
|
if (!connection2) {
|
|
@@ -114845,8 +115323,8 @@ Includes: most GET endpoints accept \`?include=\` with a comma-separated list (\
|
|
|
114845
115323
|
`[connector-request] freshsales/${connection2.name}: ${method} ${path6}`
|
|
114846
115324
|
);
|
|
114847
115325
|
try {
|
|
114848
|
-
const apiKey =
|
|
114849
|
-
const bundle =
|
|
115326
|
+
const apiKey = parameters78.apiKey.getValue(connection2);
|
|
115327
|
+
const bundle = parameters78.bundleAlias.getValue(connection2);
|
|
114850
115328
|
const baseUrl = buildBaseUrl3(bundle);
|
|
114851
115329
|
const normalizedPath = normalizeRequestPath(path6, BASE_PATH_SEGMENT14);
|
|
114852
115330
|
const url = `${baseUrl}${normalizedPath}`;
|
|
@@ -114884,14 +115362,14 @@ Includes: most GET endpoints accept \`?include=\` with a comma-separated list (\
|
|
|
114884
115362
|
});
|
|
114885
115363
|
|
|
114886
115364
|
// ../connectors/src/connectors/freshsales/index.ts
|
|
114887
|
-
var
|
|
115365
|
+
var tools78 = { request: requestTool54 };
|
|
114888
115366
|
var freshsalesConnector = new ConnectorPlugin({
|
|
114889
115367
|
slug: "freshsales",
|
|
114890
115368
|
authType: AUTH_TYPES.API_KEY,
|
|
114891
115369
|
name: "Freshsales",
|
|
114892
115370
|
description: "Connect to Freshsales / Freshworks CRM for contact, account, and deal data via API key.",
|
|
114893
115371
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/4UDOrFPM6wOFekbMVljjgl/4acc6060c3a1ff703980e6f4e76a3cd4/629b6c6f7c5cd817694c321f.png",
|
|
114894
|
-
parameters:
|
|
115372
|
+
parameters: parameters78,
|
|
114895
115373
|
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
114896
115374
|
categories: ["crm"],
|
|
114897
115375
|
onboarding: freshsalesOnboarding,
|
|
@@ -115063,7 +115541,7 @@ export default async function handler(c: Context) {
|
|
|
115063
115541
|
- GET \`/selector/lifecycle_stages\` \u2014 \u30E9\u30A4\u30D5\u30B5\u30A4\u30AF\u30EB\u30B9\u30C6\u30FC\u30B8
|
|
115064
115542
|
- GET \`/selector/territories\` / \`/selector/business_types\` / \`/selector/industry_types\` / \`/selector/contact_statuses\` / \`/selector/sales_activity_types\``
|
|
115065
115543
|
},
|
|
115066
|
-
tools:
|
|
115544
|
+
tools: tools78
|
|
115067
115545
|
});
|
|
115068
115546
|
|
|
115069
115547
|
// ../connectors/src/connectors/github/setup.ts
|
|
@@ -115089,7 +115567,7 @@ var githubOnboarding = new ConnectorOnboarding({
|
|
|
115089
115567
|
});
|
|
115090
115568
|
|
|
115091
115569
|
// ../connectors/src/connectors/github/parameters.ts
|
|
115092
|
-
var
|
|
115570
|
+
var parameters79 = {
|
|
115093
115571
|
personalAccessToken: new ParameterDefinition({
|
|
115094
115572
|
slug: "personal-access-token",
|
|
115095
115573
|
name: "GitHub Personal Access Token",
|
|
@@ -115112,42 +115590,42 @@ var parameters78 = {
|
|
|
115112
115590
|
var DEFAULT_BASE_URL = "https://api.github.com";
|
|
115113
115591
|
|
|
115114
115592
|
// ../connectors/src/connectors/github/tools/request.ts
|
|
115115
|
-
import { z as
|
|
115593
|
+
import { z as z96 } from "zod";
|
|
115116
115594
|
var REQUEST_TIMEOUT_MS73 = 6e4;
|
|
115117
115595
|
function resolveBaseUrl(connectionBaseUrl) {
|
|
115118
115596
|
const trimmed = connectionBaseUrl?.trim();
|
|
115119
115597
|
return trimmed && trimmed.replace(/\/+$/, "") || DEFAULT_BASE_URL;
|
|
115120
115598
|
}
|
|
115121
|
-
var
|
|
115122
|
-
toolUseIntent:
|
|
115599
|
+
var inputSchema96 = z96.object({
|
|
115600
|
+
toolUseIntent: z96.string().optional().describe(
|
|
115123
115601
|
"Brief description of what you intend to accomplish with this tool call"
|
|
115124
115602
|
),
|
|
115125
|
-
connectionId:
|
|
115126
|
-
method:
|
|
115603
|
+
connectionId: z96.string().describe("ID of the GitHub connection to use"),
|
|
115604
|
+
method: z96.enum(["GET", "POST", "PUT", "PATCH", "DELETE"]).describe(
|
|
115127
115605
|
"HTTP method. GET for reading, POST for creating, PATCH for partial updates, PUT for replacement (e.g. starring), DELETE for removal."
|
|
115128
115606
|
),
|
|
115129
|
-
path:
|
|
115607
|
+
path: z96.string().describe(
|
|
115130
115608
|
"API path (e.g., '/user', '/repos/{owner}/{repo}/issues', '/search/repositories?q=topic:react'). Append query parameters such as '?state=open&per_page=100&page=1'."
|
|
115131
115609
|
),
|
|
115132
|
-
body:
|
|
115133
|
-
|
|
115134
|
-
|
|
115610
|
+
body: z96.union([
|
|
115611
|
+
z96.record(z96.string(), z96.unknown()),
|
|
115612
|
+
z96.array(z96.unknown())
|
|
115135
115613
|
]).optional().describe(
|
|
115136
115614
|
'Request body (JSON). Example creating an issue: { "title": "...", "body": "...", "labels": ["bug"] }.'
|
|
115137
115615
|
)
|
|
115138
115616
|
});
|
|
115139
|
-
var
|
|
115140
|
-
|
|
115141
|
-
success:
|
|
115142
|
-
status:
|
|
115143
|
-
data:
|
|
115144
|
-
|
|
115145
|
-
|
|
115617
|
+
var outputSchema96 = z96.discriminatedUnion("success", [
|
|
115618
|
+
z96.object({
|
|
115619
|
+
success: z96.literal(true),
|
|
115620
|
+
status: z96.number(),
|
|
115621
|
+
data: z96.union([
|
|
115622
|
+
z96.record(z96.string(), z96.unknown()),
|
|
115623
|
+
z96.array(z96.unknown())
|
|
115146
115624
|
])
|
|
115147
115625
|
}),
|
|
115148
|
-
|
|
115149
|
-
success:
|
|
115150
|
-
error:
|
|
115626
|
+
z96.object({
|
|
115627
|
+
success: z96.literal(false),
|
|
115628
|
+
error: z96.string()
|
|
115151
115629
|
})
|
|
115152
115630
|
]);
|
|
115153
115631
|
var requestTool55 = new ConnectorTool({
|
|
@@ -115185,8 +115663,8 @@ Common endpoints:
|
|
|
115185
115663
|
Pagination: 1-indexed \`page\` + \`per_page\` (max 100). The \`Link\` response header exposes \`rel="next"\`/\`rel="last"\` URLs.
|
|
115186
115664
|
|
|
115187
115665
|
Rate limits: 5,000 req/hr on REST endpoints, 30 req/min on /search/*. Inspect \`X-RateLimit-Remaining\` to throttle.`,
|
|
115188
|
-
inputSchema:
|
|
115189
|
-
outputSchema:
|
|
115666
|
+
inputSchema: inputSchema96,
|
|
115667
|
+
outputSchema: outputSchema96,
|
|
115190
115668
|
async execute({ connectionId, method, path: path6, body }, connections) {
|
|
115191
115669
|
const connection2 = connections.find((c6) => c6.id === connectionId);
|
|
115192
115670
|
if (!connection2) {
|
|
@@ -115199,8 +115677,8 @@ Rate limits: 5,000 req/hr on REST endpoints, 30 req/min on /search/*. Inspect \`
|
|
|
115199
115677
|
`[connector-request] github/${connection2.name}: ${method} ${path6}`
|
|
115200
115678
|
);
|
|
115201
115679
|
try {
|
|
115202
|
-
const token =
|
|
115203
|
-
const baseUrl = resolveBaseUrl(
|
|
115680
|
+
const token = parameters79.personalAccessToken.getValue(connection2);
|
|
115681
|
+
const baseUrl = resolveBaseUrl(parameters79.baseUrl.tryGetValue(connection2));
|
|
115204
115682
|
const trimmedPath = path6.trim().replace(/^\/+/, "/");
|
|
115205
115683
|
const url = `${baseUrl}${trimmedPath.startsWith("/") ? "" : "/"}${trimmedPath}`;
|
|
115206
115684
|
const controller = new AbortController();
|
|
@@ -115240,14 +115718,14 @@ Rate limits: 5,000 req/hr on REST endpoints, 30 req/min on /search/*. Inspect \`
|
|
|
115240
115718
|
});
|
|
115241
115719
|
|
|
115242
115720
|
// ../connectors/src/connectors/github/index.ts
|
|
115243
|
-
var
|
|
115721
|
+
var tools79 = { request: requestTool55 };
|
|
115244
115722
|
var githubConnector = new ConnectorPlugin({
|
|
115245
115723
|
slug: "github",
|
|
115246
115724
|
authType: AUTH_TYPES.PAT,
|
|
115247
115725
|
name: "GitHub",
|
|
115248
115726
|
description: "Connect to GitHub for repository, issue, pull request, commit, and search data via Personal Access Token (Classic or fine-grained).",
|
|
115249
115727
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/2flOAufkhDrLKuOQqEVS3/1f9dcf145680ef77aef149709263e2d4/github-icon.svg",
|
|
115250
|
-
parameters:
|
|
115728
|
+
parameters: parameters79,
|
|
115251
115729
|
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
115252
115730
|
categories: ["productivity"],
|
|
115253
115731
|
onboarding: githubOnboarding,
|
|
@@ -115467,7 +115945,7 @@ export default async function handler(c: Context) {
|
|
|
115467
115945
|
**\u30AF\u30A9\u30FC\u30BF**
|
|
115468
115946
|
- GET \`/rate_limit\` \u2014 REST / GraphQL / search \u306E\u6B8B\u30EC\u30FC\u30C8\u78BA\u8A8D`
|
|
115469
115947
|
},
|
|
115470
|
-
tools:
|
|
115948
|
+
tools: tools79
|
|
115471
115949
|
});
|
|
115472
115950
|
|
|
115473
115951
|
// ../connectors/src/connectors/registry.ts
|
|
@@ -115545,6 +116023,7 @@ var plugins = {
|
|
|
115545
116023
|
clickup: clickupConnector,
|
|
115546
116024
|
sqlserver: sqlserverConnector,
|
|
115547
116025
|
azureSql: azureSqlConnector,
|
|
116026
|
+
cosmosdb: cosmosdbConnector,
|
|
115548
116027
|
oracle: oracleConnector,
|
|
115549
116028
|
freshservice: freshserviceConnector,
|
|
115550
116029
|
freshdesk: freshdeskConnector,
|
|
@@ -115760,62 +116239,62 @@ function resolveParams2(entry, connectionId, plugin) {
|
|
|
115760
116239
|
var { getQuery, loadConnections, reloadEnvFile, watchConnectionsFile } = createConnectorRegistry();
|
|
115761
116240
|
|
|
115762
116241
|
// src/types/server-logic.ts
|
|
115763
|
-
import { z as
|
|
115764
|
-
var parameterMetaSchema =
|
|
115765
|
-
name:
|
|
115766
|
-
type:
|
|
115767
|
-
description:
|
|
115768
|
-
required:
|
|
115769
|
-
default:
|
|
115770
|
-
});
|
|
115771
|
-
var serverLogicCacheConfigSchema =
|
|
115772
|
-
ttl:
|
|
115773
|
-
staleWhileRevalidate:
|
|
115774
|
-
});
|
|
115775
|
-
var serverLogicSchemaObjectSchema =
|
|
115776
|
-
() =>
|
|
115777
|
-
type:
|
|
115778
|
-
format:
|
|
115779
|
-
description:
|
|
115780
|
-
nullable:
|
|
115781
|
-
enum:
|
|
116242
|
+
import { z as z97 } from "zod";
|
|
116243
|
+
var parameterMetaSchema = z97.object({
|
|
116244
|
+
name: z97.string(),
|
|
116245
|
+
type: z97.enum(["string", "number", "boolean"]),
|
|
116246
|
+
description: z97.string(),
|
|
116247
|
+
required: z97.boolean().optional(),
|
|
116248
|
+
default: z97.union([z97.string(), z97.number(), z97.boolean()]).optional()
|
|
116249
|
+
});
|
|
116250
|
+
var serverLogicCacheConfigSchema = z97.object({
|
|
116251
|
+
ttl: z97.number(),
|
|
116252
|
+
staleWhileRevalidate: z97.boolean().optional()
|
|
116253
|
+
});
|
|
116254
|
+
var serverLogicSchemaObjectSchema = z97.lazy(
|
|
116255
|
+
() => z97.object({
|
|
116256
|
+
type: z97.enum(["string", "number", "integer", "boolean", "object", "array", "null"]).optional(),
|
|
116257
|
+
format: z97.string().optional(),
|
|
116258
|
+
description: z97.string().optional(),
|
|
116259
|
+
nullable: z97.boolean().optional(),
|
|
116260
|
+
enum: z97.array(z97.union([z97.string(), z97.number(), z97.boolean(), z97.null()])).optional(),
|
|
115782
116261
|
items: serverLogicSchemaObjectSchema.optional(),
|
|
115783
|
-
properties:
|
|
115784
|
-
required:
|
|
115785
|
-
additionalProperties:
|
|
115786
|
-
minimum:
|
|
115787
|
-
maximum:
|
|
115788
|
-
minLength:
|
|
115789
|
-
maxLength:
|
|
115790
|
-
pattern:
|
|
116262
|
+
properties: z97.record(z97.string(), serverLogicSchemaObjectSchema).optional(),
|
|
116263
|
+
required: z97.array(z97.string()).optional(),
|
|
116264
|
+
additionalProperties: z97.union([z97.boolean(), serverLogicSchemaObjectSchema]).optional(),
|
|
116265
|
+
minimum: z97.number().optional(),
|
|
116266
|
+
maximum: z97.number().optional(),
|
|
116267
|
+
minLength: z97.number().optional(),
|
|
116268
|
+
maxLength: z97.number().optional(),
|
|
116269
|
+
pattern: z97.string().optional()
|
|
115791
116270
|
})
|
|
115792
116271
|
);
|
|
115793
|
-
var serverLogicMediaTypeSchema =
|
|
116272
|
+
var serverLogicMediaTypeSchema = z97.object({
|
|
115794
116273
|
schema: serverLogicSchemaObjectSchema.optional(),
|
|
115795
|
-
example:
|
|
116274
|
+
example: z97.unknown().optional()
|
|
115796
116275
|
});
|
|
115797
|
-
var serverLogicResponseSchema =
|
|
115798
|
-
description:
|
|
115799
|
-
content:
|
|
116276
|
+
var serverLogicResponseSchema = z97.object({
|
|
116277
|
+
description: z97.string().optional(),
|
|
116278
|
+
content: z97.record(z97.string(), serverLogicMediaTypeSchema).optional()
|
|
115800
116279
|
});
|
|
115801
116280
|
var jsonBaseFields = {
|
|
115802
|
-
description:
|
|
115803
|
-
parameters:
|
|
116281
|
+
description: z97.string(),
|
|
116282
|
+
parameters: z97.array(parameterMetaSchema).optional(),
|
|
115804
116283
|
response: serverLogicResponseSchema.optional(),
|
|
115805
116284
|
cache: serverLogicCacheConfigSchema.optional()
|
|
115806
116285
|
};
|
|
115807
|
-
var jsonSqlServerLogicSchema =
|
|
116286
|
+
var jsonSqlServerLogicSchema = z97.object({
|
|
115808
116287
|
...jsonBaseFields,
|
|
115809
|
-
type:
|
|
115810
|
-
query:
|
|
115811
|
-
connectionId:
|
|
116288
|
+
type: z97.literal("sql").optional(),
|
|
116289
|
+
query: z97.string(),
|
|
116290
|
+
connectionId: z97.string()
|
|
115812
116291
|
});
|
|
115813
|
-
var jsonTypeScriptServerLogicSchema =
|
|
116292
|
+
var jsonTypeScriptServerLogicSchema = z97.object({
|
|
115814
116293
|
...jsonBaseFields,
|
|
115815
|
-
type:
|
|
115816
|
-
handlerPath:
|
|
116294
|
+
type: z97.literal("typescript"),
|
|
116295
|
+
handlerPath: z97.string()
|
|
115817
116296
|
});
|
|
115818
|
-
var anyJsonServerLogicSchema =
|
|
116297
|
+
var anyJsonServerLogicSchema = z97.union([
|
|
115819
116298
|
jsonTypeScriptServerLogicSchema,
|
|
115820
116299
|
jsonSqlServerLogicSchema
|
|
115821
116300
|
]);
|