@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/cli/index.js
CHANGED
|
@@ -910,17 +910,17 @@ var require_nacl_fast = __commonJS({
|
|
|
910
910
|
}
|
|
911
911
|
var sigma = new Uint8Array([101, 120, 112, 97, 110, 100, 32, 51, 50, 45, 98, 121, 116, 101, 32, 107]);
|
|
912
912
|
function crypto_stream_salsa20_xor(c6, cpos, m4, mpos, b6, n2, k6) {
|
|
913
|
-
var
|
|
913
|
+
var z98 = new Uint8Array(16), x = new Uint8Array(64);
|
|
914
914
|
var u, i6;
|
|
915
|
-
for (i6 = 0; i6 < 16; i6++)
|
|
916
|
-
for (i6 = 0; i6 < 8; i6++)
|
|
915
|
+
for (i6 = 0; i6 < 16; i6++) z98[i6] = 0;
|
|
916
|
+
for (i6 = 0; i6 < 8; i6++) z98[i6] = n2[i6];
|
|
917
917
|
while (b6 >= 64) {
|
|
918
|
-
crypto_core_salsa20(x,
|
|
918
|
+
crypto_core_salsa20(x, z98, k6, sigma);
|
|
919
919
|
for (i6 = 0; i6 < 64; i6++) c6[cpos + i6] = m4[mpos + i6] ^ x[i6];
|
|
920
920
|
u = 1;
|
|
921
921
|
for (i6 = 8; i6 < 16; i6++) {
|
|
922
|
-
u = u + (
|
|
923
|
-
|
|
922
|
+
u = u + (z98[i6] & 255) | 0;
|
|
923
|
+
z98[i6] = u & 255;
|
|
924
924
|
u >>>= 8;
|
|
925
925
|
}
|
|
926
926
|
b6 -= 64;
|
|
@@ -928,30 +928,30 @@ var require_nacl_fast = __commonJS({
|
|
|
928
928
|
mpos += 64;
|
|
929
929
|
}
|
|
930
930
|
if (b6 > 0) {
|
|
931
|
-
crypto_core_salsa20(x,
|
|
931
|
+
crypto_core_salsa20(x, z98, k6, sigma);
|
|
932
932
|
for (i6 = 0; i6 < b6; i6++) c6[cpos + i6] = m4[mpos + i6] ^ x[i6];
|
|
933
933
|
}
|
|
934
934
|
return 0;
|
|
935
935
|
}
|
|
936
936
|
function crypto_stream_salsa20(c6, cpos, b6, n2, k6) {
|
|
937
|
-
var
|
|
937
|
+
var z98 = new Uint8Array(16), x = new Uint8Array(64);
|
|
938
938
|
var u, i6;
|
|
939
|
-
for (i6 = 0; i6 < 16; i6++)
|
|
940
|
-
for (i6 = 0; i6 < 8; i6++)
|
|
939
|
+
for (i6 = 0; i6 < 16; i6++) z98[i6] = 0;
|
|
940
|
+
for (i6 = 0; i6 < 8; i6++) z98[i6] = n2[i6];
|
|
941
941
|
while (b6 >= 64) {
|
|
942
|
-
crypto_core_salsa20(x,
|
|
942
|
+
crypto_core_salsa20(x, z98, k6, sigma);
|
|
943
943
|
for (i6 = 0; i6 < 64; i6++) c6[cpos + i6] = x[i6];
|
|
944
944
|
u = 1;
|
|
945
945
|
for (i6 = 8; i6 < 16; i6++) {
|
|
946
|
-
u = u + (
|
|
947
|
-
|
|
946
|
+
u = u + (z98[i6] & 255) | 0;
|
|
947
|
+
z98[i6] = u & 255;
|
|
948
948
|
u >>>= 8;
|
|
949
949
|
}
|
|
950
950
|
b6 -= 64;
|
|
951
951
|
cpos += 64;
|
|
952
952
|
}
|
|
953
953
|
if (b6 > 0) {
|
|
954
|
-
crypto_core_salsa20(x,
|
|
954
|
+
crypto_core_salsa20(x, z98, k6, sigma);
|
|
955
955
|
for (i6 = 0; i6 < b6; i6++) c6[cpos + i6] = x[i6];
|
|
956
956
|
}
|
|
957
957
|
return 0;
|
|
@@ -1831,12 +1831,12 @@ var require_nacl_fast = __commonJS({
|
|
|
1831
1831
|
for (a6 = 0; a6 < 16; a6++) o2[a6] = c6[a6];
|
|
1832
1832
|
}
|
|
1833
1833
|
function crypto_scalarmult(q2, n2, p2) {
|
|
1834
|
-
var
|
|
1834
|
+
var z98 = new Uint8Array(32);
|
|
1835
1835
|
var x = new Float64Array(80), r6, i6;
|
|
1836
1836
|
var a6 = gf(), b6 = gf(), c6 = gf(), d6 = gf(), e6 = gf(), f6 = gf();
|
|
1837
|
-
for (i6 = 0; i6 < 31; i6++)
|
|
1838
|
-
|
|
1839
|
-
|
|
1837
|
+
for (i6 = 0; i6 < 31; i6++) z98[i6] = n2[i6];
|
|
1838
|
+
z98[31] = n2[31] & 127 | 64;
|
|
1839
|
+
z98[0] &= 248;
|
|
1840
1840
|
unpack25519(x, p2);
|
|
1841
1841
|
for (i6 = 0; i6 < 16; i6++) {
|
|
1842
1842
|
b6[i6] = x[i6];
|
|
@@ -1844,7 +1844,7 @@ var require_nacl_fast = __commonJS({
|
|
|
1844
1844
|
}
|
|
1845
1845
|
a6[0] = d6[0] = 1;
|
|
1846
1846
|
for (i6 = 254; i6 >= 0; --i6) {
|
|
1847
|
-
r6 =
|
|
1847
|
+
r6 = z98[i6 >>> 3] >>> (i6 & 7) & 1;
|
|
1848
1848
|
sel25519(a6, b6, r6);
|
|
1849
1849
|
sel25519(c6, d6, r6);
|
|
1850
1850
|
A(e6, a6, c6);
|
|
@@ -4861,8 +4861,8 @@ var require_poly1305 = __commonJS({
|
|
|
4861
4861
|
});
|
|
4862
4862
|
var u = {}, w;
|
|
4863
4863
|
for (w in b6) b6.hasOwnProperty(w) && (u[w] = b6[w]);
|
|
4864
|
-
var x = "object" === typeof window, y = "function" === typeof importScripts,
|
|
4865
|
-
if (
|
|
4864
|
+
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;
|
|
4865
|
+
if (z98) B = y ? __require("path").dirname(B) + "/" : __dirname + "/", C = function(a6, c6) {
|
|
4866
4866
|
var d6 = H(a6);
|
|
4867
4867
|
if (d6) return c6 ? d6 : d6.toString();
|
|
4868
4868
|
F || (F = __require("fs"));
|
|
@@ -5118,7 +5118,7 @@ var require_poly1305 = __commonJS({
|
|
|
5118
5118
|
function H(a6) {
|
|
5119
5119
|
if (a6.startsWith(V)) {
|
|
5120
5120
|
a6 = a6.slice(V.length);
|
|
5121
|
-
if ("boolean" === typeof
|
|
5121
|
+
if ("boolean" === typeof z98 && z98) {
|
|
5122
5122
|
var c6 = Buffer.from(a6, "base64");
|
|
5123
5123
|
c6 = new Uint8Array(c6.buffer, c6.byteOffset, c6.byteLength);
|
|
5124
5124
|
} else try {
|
|
@@ -39041,14 +39041,14 @@ var init_NormalizedSchema = __esm({
|
|
|
39041
39041
|
throw new Error("@smithy/core/schema - cannot iterate non-struct schema.");
|
|
39042
39042
|
}
|
|
39043
39043
|
const struct = this.getSchema();
|
|
39044
|
-
const
|
|
39044
|
+
const z98 = struct[4].length;
|
|
39045
39045
|
let it = struct[anno.it];
|
|
39046
|
-
if (it &&
|
|
39046
|
+
if (it && z98 === it.length) {
|
|
39047
39047
|
yield* it;
|
|
39048
39048
|
return;
|
|
39049
39049
|
}
|
|
39050
|
-
it = Array(
|
|
39051
|
-
for (let i6 = 0; i6 <
|
|
39050
|
+
it = Array(z98);
|
|
39051
|
+
for (let i6 = 0; i6 < z98; ++i6) {
|
|
39052
39052
|
const k6 = struct[4][i6];
|
|
39053
39053
|
const v = member([struct[5][i6], 0], k6);
|
|
39054
39054
|
yield it[i6] = [k6, v];
|
|
@@ -39729,12 +39729,12 @@ var init_split_header = __esm({
|
|
|
39729
39729
|
"../../node_modules/@smithy/core/dist-es/submodules/serde/split-header.js"() {
|
|
39730
39730
|
"use strict";
|
|
39731
39731
|
splitHeader = (value) => {
|
|
39732
|
-
const
|
|
39732
|
+
const z98 = value.length;
|
|
39733
39733
|
const values = [];
|
|
39734
39734
|
let withinQuotes = false;
|
|
39735
39735
|
let prevChar = void 0;
|
|
39736
39736
|
let anchor = 0;
|
|
39737
|
-
for (let i6 = 0; i6 <
|
|
39737
|
+
for (let i6 = 0; i6 < z98; ++i6) {
|
|
39738
39738
|
const char = value[i6];
|
|
39739
39739
|
switch (char) {
|
|
39740
39740
|
case `"`:
|
|
@@ -39755,12 +39755,12 @@ var init_split_header = __esm({
|
|
|
39755
39755
|
values.push(value.slice(anchor));
|
|
39756
39756
|
return values.map((v) => {
|
|
39757
39757
|
v = v.trim();
|
|
39758
|
-
const
|
|
39759
|
-
if (
|
|
39758
|
+
const z99 = v.length;
|
|
39759
|
+
if (z99 < 2) {
|
|
39760
39760
|
return v;
|
|
39761
39761
|
}
|
|
39762
|
-
if (v[0] === `"` && v[
|
|
39763
|
-
v = v.slice(1,
|
|
39762
|
+
if (v[0] === `"` && v[z99 - 1] === `"`) {
|
|
39763
|
+
v = v.slice(1, z99 - 1);
|
|
39764
39764
|
}
|
|
39765
39765
|
return v.replace(/\\"/g, '"');
|
|
39766
39766
|
});
|
|
@@ -41197,11 +41197,11 @@ var init_EndpointCache = __esm({
|
|
|
41197
41197
|
}
|
|
41198
41198
|
hash(endpointParams) {
|
|
41199
41199
|
let buffer = "";
|
|
41200
|
-
const { parameters:
|
|
41201
|
-
if (
|
|
41200
|
+
const { parameters: parameters80 } = this;
|
|
41201
|
+
if (parameters80.length === 0) {
|
|
41202
41202
|
return false;
|
|
41203
41203
|
}
|
|
41204
|
-
for (const param of
|
|
41204
|
+
for (const param of parameters80) {
|
|
41205
41205
|
const val = String(endpointParams[param] ?? "");
|
|
41206
41206
|
if (val.includes("|;")) {
|
|
41207
41207
|
return false;
|
|
@@ -47673,8 +47673,8 @@ var init_ProtocolLib = __esm({
|
|
|
47673
47673
|
constructor(queryCompat = false) {
|
|
47674
47674
|
this.queryCompat = queryCompat;
|
|
47675
47675
|
}
|
|
47676
|
-
resolveRestContentType(defaultContentType,
|
|
47677
|
-
const members =
|
|
47676
|
+
resolveRestContentType(defaultContentType, inputSchema97) {
|
|
47677
|
+
const members = inputSchema97.getMemberSchemas();
|
|
47678
47678
|
const httpPayloadMember = Object.values(members).find((m4) => {
|
|
47679
47679
|
return !!m4.getMergedTraits().httpPayload;
|
|
47680
47680
|
});
|
|
@@ -47689,7 +47689,7 @@ var init_ProtocolLib = __esm({
|
|
|
47689
47689
|
} else {
|
|
47690
47690
|
return defaultContentType;
|
|
47691
47691
|
}
|
|
47692
|
-
} else if (!
|
|
47692
|
+
} else if (!inputSchema97.isUnitSchema()) {
|
|
47693
47693
|
const hasBody = Object.values(members).find((m4) => {
|
|
47694
47694
|
const { httpQuery, httpQueryParams, httpHeader, httpLabel, httpPrefixHeaders } = m4.getMergedTraits();
|
|
47695
47695
|
const noPrefixHeaders = httpPrefixHeaders === void 0;
|
|
@@ -48542,9 +48542,9 @@ var init_AwsRestJsonProtocol = __esm({
|
|
|
48542
48542
|
}
|
|
48543
48543
|
async serializeRequest(operationSchema, input, context) {
|
|
48544
48544
|
const request2 = await super.serializeRequest(operationSchema, input, context);
|
|
48545
|
-
const
|
|
48545
|
+
const inputSchema97 = NormalizedSchema.of(operationSchema.input);
|
|
48546
48546
|
if (!request2.headers["content-type"]) {
|
|
48547
|
-
const contentType = this.mixin.resolveRestContentType(this.getDefaultContentType(),
|
|
48547
|
+
const contentType = this.mixin.resolveRestContentType(this.getDefaultContentType(), inputSchema97);
|
|
48548
48548
|
if (contentType) {
|
|
48549
48549
|
request2.headers["content-type"] = contentType;
|
|
48550
48550
|
}
|
|
@@ -48556,8 +48556,8 @@ var init_AwsRestJsonProtocol = __esm({
|
|
|
48556
48556
|
}
|
|
48557
48557
|
async deserializeResponse(operationSchema, context, response) {
|
|
48558
48558
|
const output = await super.deserializeResponse(operationSchema, context, response);
|
|
48559
|
-
const
|
|
48560
|
-
for (const [name, member2] of
|
|
48559
|
+
const outputSchema97 = NormalizedSchema.of(operationSchema.output);
|
|
48560
|
+
for (const [name, member2] of outputSchema97.structIterator()) {
|
|
48561
48561
|
if (member2.getMemberTraits().httpPayload && !(name in output)) {
|
|
48562
48562
|
output[name] = null;
|
|
48563
48563
|
}
|
|
@@ -54375,22 +54375,22 @@ var init_loadCognitoIdentity = __esm({
|
|
|
54375
54375
|
});
|
|
54376
54376
|
|
|
54377
54377
|
// ../../node_modules/@aws-sdk/credential-provider-cognito-identity/dist-es/fromCognitoIdentity.js
|
|
54378
|
-
function fromCognitoIdentity(
|
|
54378
|
+
function fromCognitoIdentity(parameters80) {
|
|
54379
54379
|
return async (awsIdentityProperties) => {
|
|
54380
|
-
|
|
54380
|
+
parameters80.logger?.debug("@aws-sdk/credential-provider-cognito-identity - fromCognitoIdentity");
|
|
54381
54381
|
const { GetCredentialsForIdentityCommand: GetCredentialsForIdentityCommand2, CognitoIdentityClient: CognitoIdentityClient2 } = await Promise.resolve().then(() => (init_loadCognitoIdentity(), loadCognitoIdentity_exports));
|
|
54382
|
-
const fromConfigs = (property) =>
|
|
54383
|
-
const { Credentials: { AccessKeyId = throwOnMissingAccessKeyId(
|
|
54382
|
+
const fromConfigs = (property) => parameters80.clientConfig?.[property] ?? parameters80.parentClientConfig?.[property] ?? awsIdentityProperties?.callerClientConfig?.[property];
|
|
54383
|
+
const { Credentials: { AccessKeyId = throwOnMissingAccessKeyId(parameters80.logger), Expiration, SecretKey = throwOnMissingSecretKey(parameters80.logger), SessionToken } = throwOnMissingCredentials(parameters80.logger) } = await (parameters80.client ?? new CognitoIdentityClient2(Object.assign({}, parameters80.clientConfig ?? {}, {
|
|
54384
54384
|
region: fromConfigs("region"),
|
|
54385
54385
|
profile: fromConfigs("profile"),
|
|
54386
54386
|
userAgentAppId: fromConfigs("userAgentAppId")
|
|
54387
54387
|
}))).send(new GetCredentialsForIdentityCommand2({
|
|
54388
|
-
CustomRoleArn:
|
|
54389
|
-
IdentityId:
|
|
54390
|
-
Logins:
|
|
54388
|
+
CustomRoleArn: parameters80.customRoleArn,
|
|
54389
|
+
IdentityId: parameters80.identityId,
|
|
54390
|
+
Logins: parameters80.logins ? await resolveLogins(parameters80.logins) : void 0
|
|
54391
54391
|
}));
|
|
54392
54392
|
return {
|
|
54393
|
-
identityId:
|
|
54393
|
+
identityId: parameters80.identityId,
|
|
54394
54394
|
accessKeyId: AccessKeyId,
|
|
54395
54395
|
secretAccessKey: SecretKey,
|
|
54396
54396
|
sessionToken: SessionToken,
|
|
@@ -67147,11 +67147,11 @@ var require_bignumber = __commonJS({
|
|
|
67147
67147
|
return n2 > 0 || n2 === i6 ? i6 : i6 - 1;
|
|
67148
67148
|
}
|
|
67149
67149
|
function coeffToString(a6) {
|
|
67150
|
-
var s,
|
|
67150
|
+
var s, z98, i6 = 1, j6 = a6.length, r6 = a6[0] + "";
|
|
67151
67151
|
for (; i6 < j6; ) {
|
|
67152
67152
|
s = a6[i6++] + "";
|
|
67153
|
-
|
|
67154
|
-
for (;
|
|
67153
|
+
z98 = LOG_BASE - s.length;
|
|
67154
|
+
for (; z98--; s = "0" + s) ;
|
|
67155
67155
|
r6 += s;
|
|
67156
67156
|
}
|
|
67157
67157
|
for (j6 = r6.length; r6.charCodeAt(--j6) === 48; ) ;
|
|
@@ -67184,15 +67184,15 @@ var require_bignumber = __commonJS({
|
|
|
67184
67184
|
function toExponential(str, e6) {
|
|
67185
67185
|
return (str.length > 1 ? str.charAt(0) + "." + str.slice(1) : str) + (e6 < 0 ? "e" : "e+") + e6;
|
|
67186
67186
|
}
|
|
67187
|
-
function toFixedPoint(str, e6,
|
|
67187
|
+
function toFixedPoint(str, e6, z98) {
|
|
67188
67188
|
var len, zs;
|
|
67189
67189
|
if (e6 < 0) {
|
|
67190
|
-
for (zs =
|
|
67190
|
+
for (zs = z98 + "."; ++e6; zs += z98) ;
|
|
67191
67191
|
str = zs + str;
|
|
67192
67192
|
} else {
|
|
67193
67193
|
len = str.length;
|
|
67194
67194
|
if (++e6 > len) {
|
|
67195
|
-
for (zs =
|
|
67195
|
+
for (zs = z98, e6 -= len; --e6; zs += z98) ;
|
|
67196
67196
|
str += zs;
|
|
67197
67197
|
} else if (e6 < len) {
|
|
67198
67198
|
str = str.slice(0, e6) + "." + str.slice(e6);
|
|
@@ -89708,6 +89708,12 @@ var NOOP_TUNNEL = (connectionUrl) => ({
|
|
|
89708
89708
|
close: async () => {
|
|
89709
89709
|
}
|
|
89710
89710
|
});
|
|
89711
|
+
var NOOP_TUNNEL_HOSTPORT = (host, port) => ({
|
|
89712
|
+
host,
|
|
89713
|
+
port,
|
|
89714
|
+
close: async () => {
|
|
89715
|
+
}
|
|
89716
|
+
});
|
|
89711
89717
|
function connectionParamsToRecord(connection) {
|
|
89712
89718
|
const out = {};
|
|
89713
89719
|
for (const p2 of connection.parameters) {
|
|
@@ -89715,9 +89721,9 @@ function connectionParamsToRecord(connection) {
|
|
|
89715
89721
|
}
|
|
89716
89722
|
return out;
|
|
89717
89723
|
}
|
|
89718
|
-
async function
|
|
89724
|
+
async function maybeOpenSshTunnelHostPort(params, dbHost, dbPort) {
|
|
89719
89725
|
const sshHost = params[sshTunnelParameters.sshHost.slug];
|
|
89720
|
-
if (!sshHost) return
|
|
89726
|
+
if (!sshHost) return NOOP_TUNNEL_HOSTPORT(dbHost, dbPort);
|
|
89721
89727
|
const sshUsername = params[sshTunnelParameters.sshUsername.slug];
|
|
89722
89728
|
const sshPrivateKeyBase64 = params[sshTunnelParameters.sshPrivateKeyBase64.slug];
|
|
89723
89729
|
if (!sshUsername || !sshPrivateKeyBase64) {
|
|
@@ -89727,9 +89733,6 @@ async function maybeOpenSshTunnel(params, connectionUrl, defaultDbPort) {
|
|
|
89727
89733
|
}
|
|
89728
89734
|
const sshPort = Number(params[sshTunnelParameters.sshPort.slug] || "22") || 22;
|
|
89729
89735
|
const sshPassphrase = params[sshTunnelParameters.sshPassphrase.slug];
|
|
89730
|
-
const url = new URL(connectionUrl);
|
|
89731
|
-
const dbHost = url.hostname;
|
|
89732
|
-
const dbPort = url.port ? Number(url.port) : defaultDbPort;
|
|
89733
89736
|
const [{ Client: Client2 }, net] = await Promise.all([
|
|
89734
89737
|
Promise.resolve().then(() => __toESM(require_lib3(), 1)),
|
|
89735
89738
|
import("net")
|
|
@@ -89772,16 +89775,29 @@ async function maybeOpenSshTunnel(params, connectionUrl, defaultDbPort) {
|
|
|
89772
89775
|
sshClient.end();
|
|
89773
89776
|
throw new Error("Failed to allocate local port for SSH tunnel.");
|
|
89774
89777
|
}
|
|
89775
|
-
url.hostname = "127.0.0.1";
|
|
89776
|
-
url.port = String(address.port);
|
|
89777
89778
|
return {
|
|
89778
|
-
|
|
89779
|
+
host: "127.0.0.1",
|
|
89780
|
+
port: address.port,
|
|
89779
89781
|
close: async () => {
|
|
89780
89782
|
await new Promise((resolve) => server.close(() => resolve()));
|
|
89781
89783
|
sshClient.end();
|
|
89782
89784
|
}
|
|
89783
89785
|
};
|
|
89784
89786
|
}
|
|
89787
|
+
async function maybeOpenSshTunnel(params, connectionUrl, defaultDbPort) {
|
|
89788
|
+
const sshHost = params[sshTunnelParameters.sshHost.slug];
|
|
89789
|
+
if (!sshHost) return NOOP_TUNNEL(connectionUrl);
|
|
89790
|
+
const url = new URL(connectionUrl);
|
|
89791
|
+
const dbHost = url.hostname;
|
|
89792
|
+
const dbPort = url.port ? Number(url.port) : defaultDbPort;
|
|
89793
|
+
const tunnel = await maybeOpenSshTunnelHostPort(params, dbHost, dbPort);
|
|
89794
|
+
url.hostname = tunnel.host;
|
|
89795
|
+
url.port = String(tunnel.port);
|
|
89796
|
+
return {
|
|
89797
|
+
connectionUrl: url.toString(),
|
|
89798
|
+
close: tunnel.close
|
|
89799
|
+
};
|
|
89800
|
+
}
|
|
89785
89801
|
|
|
89786
89802
|
// ../connectors/src/connectors/postgresql/setup.ts
|
|
89787
89803
|
var postgresqlOnboarding = new ConnectorOnboarding({
|
|
@@ -91923,9 +91939,16 @@ A Filter is an Expression. Leaves are \`Dimensions\`, \`Tags\`, or \`CostCategor
|
|
|
91923
91939
|
|
|
91924
91940
|
### Business Logic
|
|
91925
91941
|
|
|
91926
|
-
The business logic type for this connector is "typescript". The connector exposes resolved AWS credentials via \`connection(connectionId)
|
|
91942
|
+
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.
|
|
91927
91943
|
|
|
91928
|
-
####
|
|
91944
|
+
#### Server logic slug naming
|
|
91945
|
+
|
|
91946
|
+
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.
|
|
91947
|
+
|
|
91948
|
+
- OK: \`monthly-cost-trend\`, \`cost_by_service\`, \`top10-services\`
|
|
91949
|
+
- NG: \`monthlyCostTrend\`, \`MonthlyCostTrend\`, \`monthly cost trend\`
|
|
91950
|
+
|
|
91951
|
+
#### Example (slug: \`monthly-cost-trend\`)
|
|
91929
91952
|
|
|
91930
91953
|
\`\`\`ts
|
|
91931
91954
|
import type { Context } from "hono";
|
|
@@ -92001,9 +92024,16 @@ Filter \u306F Expression \u3067\u3059\u3002\u30EA\u30FC\u30D5\u306F \`Dimensions
|
|
|
92001
92024
|
|
|
92002
92025
|
### Business Logic
|
|
92003
92026
|
|
|
92004
|
-
\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
|
|
92027
|
+
\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
|
|
92005
92028
|
|
|
92006
|
-
####
|
|
92029
|
+
#### \u30B5\u30FC\u30D0\u30FC\u30ED\u30B8\u30C3\u30AF\u306E slug \u547D\u540D\u898F\u5247
|
|
92030
|
+
|
|
92031
|
+
\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
|
|
92032
|
+
|
|
92033
|
+
- OK: \`monthly-cost-trend\`\u3001\`cost_by_service\`\u3001\`top10-services\`
|
|
92034
|
+
- NG: \`monthlyCostTrend\`\u3001\`MonthlyCostTrend\`\u3001\`monthly cost trend\`
|
|
92035
|
+
|
|
92036
|
+
#### Example\uFF08slug: \`monthly-cost-trend\`\uFF09
|
|
92007
92037
|
|
|
92008
92038
|
\`\`\`ts
|
|
92009
92039
|
import type { Context } from "hono";
|
|
@@ -92912,30 +92942,6 @@ export default async function handler(c: Context) {
|
|
|
92912
92942
|
|
|
92913
92943
|
// ../connectors/src/connectors/google-ads/tools/list-customers.ts
|
|
92914
92944
|
import { z as z18 } from "zod";
|
|
92915
|
-
|
|
92916
|
-
// ../connectors/src/connectors/google-ads/parameters.ts
|
|
92917
|
-
var parameters12 = {
|
|
92918
|
-
customerId: new ParameterDefinition({
|
|
92919
|
-
slug: "customer-id",
|
|
92920
|
-
name: "Google Ads Customer ID",
|
|
92921
|
-
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.",
|
|
92922
|
-
envVarBaseKey: "GOOGLE_ADS_CUSTOMER_ID",
|
|
92923
|
-
type: "text",
|
|
92924
|
-
secret: false,
|
|
92925
|
-
required: false
|
|
92926
|
-
}),
|
|
92927
|
-
developerToken: new ParameterDefinition({
|
|
92928
|
-
slug: "developer-token",
|
|
92929
|
-
name: "Google Ads Developer Token",
|
|
92930
|
-
description: "The developer token for accessing the Google Ads API. Required for all API requests.",
|
|
92931
|
-
envVarBaseKey: "GOOGLE_ADS_DEVELOPER_TOKEN",
|
|
92932
|
-
type: "text",
|
|
92933
|
-
secret: true,
|
|
92934
|
-
required: true
|
|
92935
|
-
})
|
|
92936
|
-
};
|
|
92937
|
-
|
|
92938
|
-
// ../connectors/src/connectors/google-ads/tools/list-customers.ts
|
|
92939
92945
|
var BASE_URL2 = "https://googleads.googleapis.com/v18/";
|
|
92940
92946
|
var REQUEST_TIMEOUT_MS8 = 6e4;
|
|
92941
92947
|
var cachedToken4 = null;
|
|
@@ -93007,7 +93013,6 @@ var listCustomersTool = new ConnectorTool({
|
|
|
93007
93013
|
`[connector-request] google-ads/${connection.name}: listCustomers`
|
|
93008
93014
|
);
|
|
93009
93015
|
try {
|
|
93010
|
-
const developerToken = parameters12.developerToken.getValue(connection);
|
|
93011
93016
|
const token = await getProxyToken4(config.oauthProxy);
|
|
93012
93017
|
const proxyUrl = `https://${config.oauthProxy.sandboxId}.${config.oauthProxy.previewBaseDomain}/_sqcore/connections/${connectionId}/request`;
|
|
93013
93018
|
const controller = new AbortController();
|
|
@@ -93021,10 +93026,7 @@ var listCustomersTool = new ConnectorTool({
|
|
|
93021
93026
|
},
|
|
93022
93027
|
body: JSON.stringify({
|
|
93023
93028
|
url: `${BASE_URL2}customers:listAccessibleCustomers`,
|
|
93024
|
-
method: "GET"
|
|
93025
|
-
headers: {
|
|
93026
|
-
"developer-token": developerToken
|
|
93027
|
-
}
|
|
93029
|
+
method: "GET"
|
|
93028
93030
|
}),
|
|
93029
93031
|
signal: controller.signal
|
|
93030
93032
|
});
|
|
@@ -93050,7 +93052,6 @@ var listCustomersTool = new ConnectorTool({
|
|
|
93050
93052
|
method: "POST",
|
|
93051
93053
|
headers: {
|
|
93052
93054
|
"Content-Type": "application/json",
|
|
93053
|
-
"developer-token": developerToken,
|
|
93054
93055
|
"login-customer-id": cid
|
|
93055
93056
|
},
|
|
93056
93057
|
body: JSON.stringify({
|
|
@@ -93096,30 +93097,24 @@ var googleAdsOnboarding = new ConnectorOnboarding({
|
|
|
93096
93097
|
connectionSetupInstructions: {
|
|
93097
93098
|
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
|
|
93098
93099
|
|
|
93099
|
-
1. \
|
|
93100
|
+
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
|
|
93100
93101
|
2. \`updateConnectionParameters\` \u3092\u547C\u3073\u51FA\u3059:
|
|
93101
|
-
- \`parameterSlug\`: \`"developer-token"\`
|
|
93102
|
-
- \`value\`: \u30E6\u30FC\u30B6\u30FC\u304C\u63D0\u4F9B\u3057\u305F Developer Token
|
|
93103
|
-
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
|
|
93104
|
-
4. \`updateConnectionParameters\` \u3092\u547C\u3073\u51FA\u3059:
|
|
93105
93102
|
- \`parameterSlug\`: \`"customer-id"\`
|
|
93106
93103
|
- \`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
|
|
93107
|
-
|
|
93104
|
+
- \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
|
|
93105
|
+
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
|
|
93108
93106
|
|
|
93109
93107
|
#### \u5236\u7D04
|
|
93110
93108
|
- **\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
|
|
93111
93109
|
- \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`,
|
|
93112
93110
|
en: `Follow these steps to set up the Google Ads (OAuth) connection.
|
|
93113
93111
|
|
|
93114
|
-
1.
|
|
93112
|
+
1. Call \`${listCustomersToolName}\` to get the list of Google Ads customer accounts accessible with the OAuth credentials
|
|
93115
93113
|
2. Call \`updateConnectionParameters\`:
|
|
93116
|
-
- \`parameterSlug\`: \`"developer-token"\`
|
|
93117
|
-
- \`value\`: The Developer Token provided by the user
|
|
93118
|
-
3. Call \`${listCustomersToolName}\` to get the list of Google Ads customer accounts accessible with the OAuth credentials
|
|
93119
|
-
4. Call \`updateConnectionParameters\`:
|
|
93120
93114
|
- \`parameterSlug\`: \`"customer-id"\`
|
|
93121
93115
|
- \`options\`: The customer list. Each option's \`label\` should be \`Account Name (id: customerId)\`, \`value\` should be the customer ID
|
|
93122
|
-
|
|
93116
|
+
- If **0 customers** are returned, abort setup and inform the user that no accessible accounts are available
|
|
93117
|
+
3. The \`label\` of the user's selected customer will arrive as a message. Proceed to the next step
|
|
93123
93118
|
|
|
93124
93119
|
#### Constraints
|
|
93125
93120
|
- **Do NOT fetch report data during setup**. Only the metadata requests specified in the steps above are allowed
|
|
@@ -93133,6 +93128,19 @@ var googleAdsOnboarding = new ConnectorOnboarding({
|
|
|
93133
93128
|
}
|
|
93134
93129
|
});
|
|
93135
93130
|
|
|
93131
|
+
// ../connectors/src/connectors/google-ads/parameters.ts
|
|
93132
|
+
var parameters12 = {
|
|
93133
|
+
customerId: new ParameterDefinition({
|
|
93134
|
+
slug: "customer-id",
|
|
93135
|
+
name: "Google Ads Customer ID",
|
|
93136
|
+
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.",
|
|
93137
|
+
envVarBaseKey: "GOOGLE_ADS_CUSTOMER_ID",
|
|
93138
|
+
type: "text",
|
|
93139
|
+
secret: false,
|
|
93140
|
+
required: false
|
|
93141
|
+
})
|
|
93142
|
+
};
|
|
93143
|
+
|
|
93136
93144
|
// ../connectors/src/connectors/google-ads/tools/request.ts
|
|
93137
93145
|
import { z as z19 } from "zod";
|
|
93138
93146
|
var BASE_URL3 = "https://googleads.googleapis.com/v18/";
|
|
@@ -93218,7 +93226,6 @@ Authentication is handled automatically via OAuth proxy.
|
|
|
93218
93226
|
const controller = new AbortController();
|
|
93219
93227
|
const timeout = setTimeout(() => controller.abort(), REQUEST_TIMEOUT_MS9);
|
|
93220
93228
|
try {
|
|
93221
|
-
const developerToken = parameters12.developerToken.getValue(connection);
|
|
93222
93229
|
const response = await fetch(proxyUrl, {
|
|
93223
93230
|
method: "POST",
|
|
93224
93231
|
headers: {
|
|
@@ -93230,7 +93237,6 @@ Authentication is handled automatically via OAuth proxy.
|
|
|
93230
93237
|
method,
|
|
93231
93238
|
headers: {
|
|
93232
93239
|
"Content-Type": "application/json",
|
|
93233
|
-
"developer-token": developerToken,
|
|
93234
93240
|
...customerId ? { "login-customer-id": customerId } : {}
|
|
93235
93241
|
},
|
|
93236
93242
|
...method === "POST" && body ? { body: JSON.stringify(body) } : {}
|
|
@@ -93411,20 +93417,12 @@ const customerIds = await ads.listAccessibleCustomers();
|
|
|
93411
93417
|
if (!customerId) {
|
|
93412
93418
|
return { success: true };
|
|
93413
93419
|
}
|
|
93414
|
-
const developerToken = params[parameters12.developerToken.slug];
|
|
93415
|
-
if (!developerToken) {
|
|
93416
|
-
return {
|
|
93417
|
-
success: false,
|
|
93418
|
-
error: "Developer token is required"
|
|
93419
|
-
};
|
|
93420
|
-
}
|
|
93421
93420
|
const url = `https://googleads.googleapis.com/v18/customers/${customerId}/googleAds:searchStream`;
|
|
93422
93421
|
try {
|
|
93423
93422
|
const res = await proxyFetch(url, {
|
|
93424
93423
|
method: "POST",
|
|
93425
93424
|
headers: {
|
|
93426
93425
|
"Content-Type": "application/json",
|
|
93427
|
-
"developer-token": developerToken,
|
|
93428
93426
|
"login-customer-id": customerId
|
|
93429
93427
|
},
|
|
93430
93428
|
body: JSON.stringify({
|
|
@@ -111442,17 +111440,27 @@ async function importMssql() {
|
|
|
111442
111440
|
}
|
|
111443
111441
|
async function runMssqlQuery(parsed, sql, options = {}) {
|
|
111444
111442
|
const sqlMod = await importMssql();
|
|
111445
|
-
const
|
|
111446
|
-
|
|
111447
|
-
|
|
111448
|
-
|
|
111449
|
-
|
|
111443
|
+
const tunnel = options.tunnelParams ? await maybeOpenSshTunnelHostPort(
|
|
111444
|
+
options.tunnelParams,
|
|
111445
|
+
parsed.server,
|
|
111446
|
+
parsed.port
|
|
111447
|
+
) : null;
|
|
111450
111448
|
try {
|
|
111451
|
-
const
|
|
111452
|
-
const
|
|
111453
|
-
|
|
111449
|
+
const tunneled = tunnel ? { ...parsed, server: tunnel.host, port: tunnel.port } : parsed;
|
|
111450
|
+
const config = toMssqlConfig(tunneled, {
|
|
111451
|
+
encrypt: options.forceEncrypt
|
|
111452
|
+
});
|
|
111453
|
+
const pool = new sqlMod.ConnectionPool(config);
|
|
111454
|
+
await pool.connect();
|
|
111455
|
+
try {
|
|
111456
|
+
const result = await pool.request().query(sql);
|
|
111457
|
+
const recordset = result.recordset ?? [];
|
|
111458
|
+
return { rows: recordset };
|
|
111459
|
+
} finally {
|
|
111460
|
+
await pool.close();
|
|
111461
|
+
}
|
|
111454
111462
|
} finally {
|
|
111455
|
-
await
|
|
111463
|
+
await tunnel?.close();
|
|
111456
111464
|
}
|
|
111457
111465
|
}
|
|
111458
111466
|
async function checkMssqlConnection(url, credentials, options = {}) {
|
|
@@ -111540,35 +111548,69 @@ function parseOracleJdbcUrl(jdbcUrl, options = {}) {
|
|
|
111540
111548
|
function redactOracleUrl(jdbcUrl) {
|
|
111541
111549
|
return jdbcUrl.replace(/(:\/\/)([^@/]+)@/, "$1***@").replace(/(thin:)([^@]+)@/i, "$1***@");
|
|
111542
111550
|
}
|
|
111551
|
+
function parseOracleConnectStringHostPort(connectString) {
|
|
111552
|
+
const m4 = /^([^:/]+):(\d+)(.*)$/.exec(connectString);
|
|
111553
|
+
if (!m4) return null;
|
|
111554
|
+
return { host: m4[1], port: Number(m4[2]), trailing: m4[3] };
|
|
111555
|
+
}
|
|
111556
|
+
function rewriteOracleConnectStringHostPort(connectString, host, port) {
|
|
111557
|
+
const parts = parseOracleConnectStringHostPort(connectString);
|
|
111558
|
+
if (!parts) return connectString;
|
|
111559
|
+
return `${host}:${port}${parts.trailing}`;
|
|
111560
|
+
}
|
|
111543
111561
|
|
|
111544
111562
|
// ../connectors/src/lib/oracle-runner.ts
|
|
111545
111563
|
async function importOracleDb() {
|
|
111546
111564
|
const mod = await import("oracledb");
|
|
111547
111565
|
return mod.default ?? mod;
|
|
111548
111566
|
}
|
|
111549
|
-
async function runOracleQuery(parsed, sql) {
|
|
111567
|
+
async function runOracleQuery(parsed, sql, options = {}) {
|
|
111550
111568
|
const oracledb = await importOracleDb();
|
|
111551
|
-
|
|
111552
|
-
|
|
111553
|
-
|
|
111554
|
-
|
|
111555
|
-
|
|
111569
|
+
let tunnel = null;
|
|
111570
|
+
if (options.tunnelParams) {
|
|
111571
|
+
const hostPort = parseOracleConnectStringHostPort(parsed.connectString);
|
|
111572
|
+
if (hostPort) {
|
|
111573
|
+
tunnel = await maybeOpenSshTunnelHostPort(
|
|
111574
|
+
options.tunnelParams,
|
|
111575
|
+
hostPort.host,
|
|
111576
|
+
hostPort.port
|
|
111577
|
+
);
|
|
111578
|
+
}
|
|
111579
|
+
}
|
|
111556
111580
|
try {
|
|
111557
|
-
const
|
|
111558
|
-
|
|
111559
|
-
|
|
111560
|
-
|
|
111561
|
-
|
|
111581
|
+
const connectString = tunnel ? rewriteOracleConnectStringHostPort(
|
|
111582
|
+
parsed.connectString,
|
|
111583
|
+
tunnel.host,
|
|
111584
|
+
tunnel.port
|
|
111585
|
+
) : parsed.connectString;
|
|
111586
|
+
const connection = await oracledb.getConnection({
|
|
111587
|
+
user: parsed.user,
|
|
111588
|
+
password: parsed.password,
|
|
111589
|
+
connectString
|
|
111562
111590
|
});
|
|
111563
|
-
return { rows: result.rows ?? [] };
|
|
111564
|
-
} finally {
|
|
111565
111591
|
try {
|
|
111566
|
-
await connection.
|
|
111567
|
-
|
|
111592
|
+
const result = await connection.execute(
|
|
111593
|
+
sql,
|
|
111594
|
+
[],
|
|
111595
|
+
{
|
|
111596
|
+
outFormat: oracledb.OUT_FORMAT_OBJECT,
|
|
111597
|
+
// Bound by the connector's own row cap, but keep the driver from
|
|
111598
|
+
// streaming arbitrarily large result sets.
|
|
111599
|
+
maxRows: 5e3
|
|
111600
|
+
}
|
|
111601
|
+
);
|
|
111602
|
+
return { rows: result.rows ?? [] };
|
|
111603
|
+
} finally {
|
|
111604
|
+
try {
|
|
111605
|
+
await connection.close();
|
|
111606
|
+
} catch {
|
|
111607
|
+
}
|
|
111568
111608
|
}
|
|
111609
|
+
} finally {
|
|
111610
|
+
await tunnel?.close();
|
|
111569
111611
|
}
|
|
111570
111612
|
}
|
|
111571
|
-
async function checkOracleConnection(url, credentials) {
|
|
111613
|
+
async function checkOracleConnection(url, credentials, options = {}) {
|
|
111572
111614
|
let parsed;
|
|
111573
111615
|
try {
|
|
111574
111616
|
parsed = parseOracleJdbcUrl(url, credentials);
|
|
@@ -111579,7 +111621,7 @@ async function checkOracleConnection(url, credentials) {
|
|
|
111579
111621
|
};
|
|
111580
111622
|
}
|
|
111581
111623
|
try {
|
|
111582
|
-
await runOracleQuery(parsed, "SELECT 1 FROM DUAL");
|
|
111624
|
+
await runOracleQuery(parsed, "SELECT 1 FROM DUAL", options);
|
|
111583
111625
|
return { success: true };
|
|
111584
111626
|
} catch (err) {
|
|
111585
111627
|
let msg = err instanceof Error ? err.message : String(err);
|
|
@@ -111789,12 +111831,13 @@ Always bound results: LIMIT for PG/MySQL/Redshift, TOP for SQL Server, FETCH FIR
|
|
|
111789
111831
|
};
|
|
111790
111832
|
}
|
|
111791
111833
|
try {
|
|
111834
|
+
const tunnelParams = connectionParamsToRecord(connection);
|
|
111792
111835
|
if (parsed.driver === "sqlserver") {
|
|
111793
111836
|
const mssqlParsed = parseSqlServerJdbcUrl(parsed.originalUrl, {
|
|
111794
111837
|
username,
|
|
111795
111838
|
password
|
|
111796
111839
|
});
|
|
111797
|
-
const result = await runMssqlQuery(mssqlParsed, sql);
|
|
111840
|
+
const result = await runMssqlQuery(mssqlParsed, sql, { tunnelParams });
|
|
111798
111841
|
const rows = result.rows;
|
|
111799
111842
|
return {
|
|
111800
111843
|
success: true,
|
|
@@ -111809,7 +111852,9 @@ Always bound results: LIMIT for PG/MySQL/Redshift, TOP for SQL Server, FETCH FIR
|
|
|
111809
111852
|
password
|
|
111810
111853
|
});
|
|
111811
111854
|
const cleanSql = sql.replace(/;\s*$/, "");
|
|
111812
|
-
const result = await runOracleQuery(oracleParsed, cleanSql
|
|
111855
|
+
const result = await runOracleQuery(oracleParsed, cleanSql, {
|
|
111856
|
+
tunnelParams
|
|
111857
|
+
});
|
|
111813
111858
|
const rows = result.rows;
|
|
111814
111859
|
return {
|
|
111815
111860
|
success: true,
|
|
@@ -111821,7 +111866,7 @@ Always bound results: LIMIT for PG/MySQL/Redshift, TOP for SQL Server, FETCH FIR
|
|
|
111821
111866
|
let tunnel;
|
|
111822
111867
|
try {
|
|
111823
111868
|
tunnel = await maybeOpenSshTunnel(
|
|
111824
|
-
|
|
111869
|
+
tunnelParams,
|
|
111825
111870
|
parsed.nativeUrl,
|
|
111826
111871
|
parsed.defaultPort
|
|
111827
111872
|
);
|
|
@@ -111995,10 +112040,18 @@ JDBC URL \u306E\u30D7\u30EC\u30D5\u30A3\u30C3\u30AF\u30B9\u306B\u3088\u308A\u65B
|
|
|
111995
112040
|
};
|
|
111996
112041
|
}
|
|
111997
112042
|
if (parsed.driver === "sqlserver") {
|
|
111998
|
-
return checkMssqlConnection(
|
|
112043
|
+
return checkMssqlConnection(
|
|
112044
|
+
parsed.originalUrl,
|
|
112045
|
+
{ username, password },
|
|
112046
|
+
{ tunnelParams: params }
|
|
112047
|
+
);
|
|
111999
112048
|
}
|
|
112000
112049
|
if (parsed.driver === "oracle") {
|
|
112001
|
-
return checkOracleConnection(
|
|
112050
|
+
return checkOracleConnection(
|
|
112051
|
+
parsed.originalUrl,
|
|
112052
|
+
{ username, password },
|
|
112053
|
+
{ tunnelParams: params }
|
|
112054
|
+
);
|
|
112002
112055
|
}
|
|
112003
112056
|
const tunnel = await maybeOpenSshTunnel(
|
|
112004
112057
|
params,
|
|
@@ -112055,10 +112108,12 @@ JDBC URL \u306E\u30D7\u30EC\u30D5\u30A3\u30C3\u30AF\u30B9\u306B\u3088\u308A\u65B
|
|
|
112055
112108
|
});
|
|
112056
112109
|
const sample = unwrapSampleLimit(sql);
|
|
112057
112110
|
if (sample) {
|
|
112058
|
-
const result = await runMssqlQuery(mssqlParsed, sample.inner
|
|
112111
|
+
const result = await runMssqlQuery(mssqlParsed, sample.inner, {
|
|
112112
|
+
tunnelParams: params
|
|
112113
|
+
});
|
|
112059
112114
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
112060
112115
|
}
|
|
112061
|
-
return runMssqlQuery(mssqlParsed, sql);
|
|
112116
|
+
return runMssqlQuery(mssqlParsed, sql, { tunnelParams: params });
|
|
112062
112117
|
}
|
|
112063
112118
|
if (parsed.driver === "oracle") {
|
|
112064
112119
|
const oracleParsed = parseOracleJdbcUrl(parsed.originalUrl, {
|
|
@@ -112068,11 +112123,13 @@ JDBC URL \u306E\u30D7\u30EC\u30D5\u30A3\u30C3\u30AF\u30B9\u306B\u3088\u308A\u65B
|
|
|
112068
112123
|
const sample = unwrapSampleLimit(sql);
|
|
112069
112124
|
if (sample) {
|
|
112070
112125
|
const inner = sample.inner.replace(/;\s*$/, "");
|
|
112071
|
-
const result = await runOracleQuery(oracleParsed, inner
|
|
112126
|
+
const result = await runOracleQuery(oracleParsed, inner, {
|
|
112127
|
+
tunnelParams: params
|
|
112128
|
+
});
|
|
112072
112129
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
112073
112130
|
}
|
|
112074
112131
|
const cleanSql = sql.replace(/;\s*$/, "");
|
|
112075
|
-
return runOracleQuery(oracleParsed, cleanSql);
|
|
112132
|
+
return runOracleQuery(oracleParsed, cleanSql, { tunnelParams: params });
|
|
112076
112133
|
}
|
|
112077
112134
|
const tunnel = await maybeOpenSshTunnel(
|
|
112078
112135
|
params,
|
|
@@ -112304,16 +112361,18 @@ var semrushOnboarding = new ConnectorOnboarding({
|
|
|
112304
112361
|
- Write only 1 sentence between tool calls, then immediately call the next tool. Skip unnecessary explanations and proceed efficiently`
|
|
112305
112362
|
},
|
|
112306
112363
|
dataOverviewInstructions: {
|
|
112307
|
-
en: `1. Call ${requestToolName12} with path "/" and queryParams \`{ "type": "
|
|
112364
|
+
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)
|
|
112308
112365
|
2. Call ${requestToolName12} with path "/" and queryParams \`{ "type": "domain_organic", "domain": "<example.com>", "database": "us", "display_limit": "5" }\` to sample organic keywords
|
|
112309
112366
|
3. Call ${requestToolName12} with path "/" and queryParams \`{ "type": "phrase_this", "phrase": "<keyword>", "database": "us" }\` to inspect a keyword overview
|
|
112310
|
-
4.
|
|
112311
|
-
5.
|
|
112312
|
-
|
|
112367
|
+
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"\`)
|
|
112368
|
+
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
|
|
112369
|
+
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`,
|
|
112370
|
+
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
|
|
112313
112371
|
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
|
|
112314
112372
|
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
|
|
112315
|
-
4. \u5FC5\u8981\u306B\u5FDC\u3058\u3066\
|
|
112316
|
-
5. \
|
|
112373
|
+
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
|
|
112374
|
+
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
|
|
112375
|
+
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`
|
|
112317
112376
|
}
|
|
112318
112377
|
});
|
|
112319
112378
|
|
|
@@ -112340,10 +112399,19 @@ The business logic type for this connector is "typescript". Write handler code u
|
|
|
112340
112399
|
|
|
112341
112400
|
SDK methods (client created via \`connection(connectionId)\`):
|
|
112342
112401
|
- \`client.request(path, init?)\` \u2014 low-level authenticated fetch. Pass \`init.query\` to set query parameters; \`key\` is injected automatically
|
|
112343
|
-
- \`client.
|
|
112402
|
+
- \`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()\`
|
|
112403
|
+
- \`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
|
|
112344
112404
|
- \`client.trends(path, query?)\` \u2014 call a Trends API endpoint (\`/analytics/v1/...\`) and return parsed JSON
|
|
112345
112405
|
- \`client.projects(path, init?)\` \u2014 call a Projects API endpoint (\`/management/v1/...\`) and return parsed JSON
|
|
112346
112406
|
|
|
112407
|
+
\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.
|
|
112408
|
+
|
|
112409
|
+
\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.
|
|
112410
|
+
|
|
112411
|
+
\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.
|
|
112412
|
+
|
|
112413
|
+
\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"])\`.
|
|
112414
|
+
|
|
112347
112415
|
\`\`\`ts
|
|
112348
112416
|
import type { Context } from "hono";
|
|
112349
112417
|
import { connection } from "@squadbase/vite-server/connectors/semrush";
|
|
@@ -112356,9 +112424,25 @@ export default async function handler(c: Context) {
|
|
|
112356
112424
|
database?: string;
|
|
112357
112425
|
}>();
|
|
112358
112426
|
|
|
112359
|
-
const
|
|
112427
|
+
const result = await semrush.report("domain_organic", {
|
|
112428
|
+
domain,
|
|
112429
|
+
database,
|
|
112430
|
+
display_limit: "100",
|
|
112431
|
+
});
|
|
112432
|
+
|
|
112433
|
+
// \u2705 Correct: access by column name
|
|
112434
|
+
const rows = result.rows.map((row) => ({
|
|
112435
|
+
keyword: row["Keyword"],
|
|
112436
|
+
position: Number(row["Position"]) || 0,
|
|
112437
|
+
searchVolume: Number(row["Search Volume"]) || 0,
|
|
112438
|
+
url: row["Url"] ?? "",
|
|
112439
|
+
}));
|
|
112440
|
+
|
|
112441
|
+
// \u274C Wrong: do NOT do this \u2014 row[index] is undefined because rows are objects, not arrays
|
|
112442
|
+
// const urlIdx = result.columns.indexOf("Url");
|
|
112443
|
+
// const url = (row as unknown as string[])[urlIdx];
|
|
112360
112444
|
|
|
112361
|
-
return c.json({ columns:
|
|
112445
|
+
return c.json({ columns: result.columns, rows });
|
|
112362
112446
|
}
|
|
112363
112447
|
\`\`\`
|
|
112364
112448
|
|
|
@@ -112370,8 +112454,8 @@ export default async function handler(c: Context) {
|
|
|
112370
112454
|
|
|
112371
112455
|
Authentication: API key passed as the \`key\` query parameter on every request (handled automatically).
|
|
112372
112456
|
|
|
112373
|
-
#### Common Standard Analytics report types
|
|
112374
|
-
- \`
|
|
112457
|
+
#### Common Standard Analytics report types (path \`/\`, returns CSV)
|
|
112458
|
+
- \`domain_ranks\` \u2014 single-row domain summary (rank, organic/paid keywords, traffic, cost). **There is no \`domain_overview\` type \u2014 use \`domain_ranks\`.**
|
|
112375
112459
|
- \`domain_organic\` \u2014 organic keywords for a domain
|
|
112376
112460
|
- \`domain_adwords\` \u2014 paid keywords for a domain
|
|
112377
112461
|
- \`domain_organic_organic\` / \`domain_adwords_adwords\` \u2014 organic / paid competitors
|
|
@@ -112380,10 +112464,13 @@ Authentication: API key passed as the \`key\` query parameter on every request (
|
|
|
112380
112464
|
- \`phrase_fullsearch\` \u2014 full-text keyword research
|
|
112381
112465
|
- \`phrase_questions\` \u2014 question keywords
|
|
112382
112466
|
- \`phrase_kdi\` \u2014 keyword difficulty index
|
|
112467
|
+
- \`url_organic\` / \`url_adwords\` \u2014 keywords ranking for a specific URL
|
|
112468
|
+
|
|
112469
|
+
#### Backlinks API report types (path \`/analytics/v1/\`, also returns **CSV** \u2014 not JSON)
|
|
112470
|
+
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.
|
|
112383
112471
|
- \`backlinks_overview\` \u2014 backlinks summary
|
|
112384
112472
|
- \`backlinks\` \u2014 list of backlinks
|
|
112385
112473
|
- \`backlinks_refdomains\` \u2014 referring domains
|
|
112386
|
-
- \`url_organic\` / \`url_adwords\` \u2014 keywords ranking for a specific URL
|
|
112387
112474
|
|
|
112388
112475
|
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.
|
|
112389
112476
|
|
|
@@ -112391,7 +112478,7 @@ To check remaining API units (free, does NOT consume units), call the request to
|
|
|
112391
112478
|
- \`type\` \u2014 report type (required for the Standard API)
|
|
112392
112479
|
- \`domain\` / \`phrase\` / \`url\` \u2014 entity to query
|
|
112393
112480
|
- \`database\` \u2014 regional database (e.g. \`us\`, \`uk\`, \`de\`, \`fr\`, \`jp\`, \`br\`); required for most reports
|
|
112394
|
-
- \`display_limit\` \u2014 page size (default 10000, max 100000 depending on report)
|
|
112481
|
+
- \`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.
|
|
112395
112482
|
- \`display_offset\` \u2014 pagination offset
|
|
112396
112483
|
- \`display_date\` \u2014 historical date in \`YYYYMM15\` format (always day 15)
|
|
112397
112484
|
- \`export_columns\` \u2014 comma-separated columns to return (e.g. \`Ph,Po,Nq,Cp\`)
|
|
@@ -112402,6 +112489,7 @@ To check remaining API units (free, does NOT consume units), call the request to
|
|
|
112402
112489
|
- 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
|
|
112403
112490
|
- The CSV separator is \`;\` (semicolon), NOT \`,\`. Some cells may contain commas inside them.
|
|
112404
112491
|
- An HTTP 200 response with a body starting with \`ERROR\` indicates an API error (auth, parameters, or quota)
|
|
112492
|
+
- \`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.
|
|
112405
112493
|
- The Trends API requires a separate Trends subscription; calls without it will fail with an authorization error
|
|
112406
112494
|
- Date strings in historical endpoints must be the 15th of the month (\`YYYYMM15\`)`,
|
|
112407
112495
|
ja: `### \u30C4\u30FC\u30EB
|
|
@@ -112414,10 +112502,19 @@ To check remaining API units (free, does NOT consume units), call the request to
|
|
|
112414
112502
|
|
|
112415
112503
|
SDK\u30E1\u30BD\u30C3\u30C9 (\`connection(connectionId)\` \u3067\u4F5C\u6210\u3057\u305F\u30AF\u30E9\u30A4\u30A2\u30F3\u30C8):
|
|
112416
112504
|
- \`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
|
|
112417
|
-
- \`client.
|
|
112505
|
+
- \`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
|
|
112506
|
+
- \`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
|
|
112418
112507
|
- \`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
|
|
112419
112508
|
- \`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
|
|
112420
112509
|
|
|
112510
|
+
\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
|
|
112511
|
+
|
|
112512
|
+
\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
|
|
112513
|
+
|
|
112514
|
+
\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
|
|
112515
|
+
|
|
112516
|
+
\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
|
|
112517
|
+
|
|
112421
112518
|
\`\`\`ts
|
|
112422
112519
|
import type { Context } from "hono";
|
|
112423
112520
|
import { connection } from "@squadbase/vite-server/connectors/semrush";
|
|
@@ -112430,9 +112527,25 @@ export default async function handler(c: Context) {
|
|
|
112430
112527
|
database?: string;
|
|
112431
112528
|
}>();
|
|
112432
112529
|
|
|
112433
|
-
const
|
|
112530
|
+
const result = await semrush.report("domain_organic", {
|
|
112531
|
+
domain,
|
|
112532
|
+
database,
|
|
112533
|
+
display_limit: "100",
|
|
112534
|
+
});
|
|
112434
112535
|
|
|
112435
|
-
|
|
112536
|
+
// \u2705 \u6B63: \u30AB\u30E9\u30E0\u540D\u3067\u30A2\u30AF\u30BB\u30B9\u3059\u308B
|
|
112537
|
+
const rows = result.rows.map((row) => ({
|
|
112538
|
+
keyword: row["Keyword"],
|
|
112539
|
+
position: Number(row["Position"]) || 0,
|
|
112540
|
+
searchVolume: Number(row["Search Volume"]) || 0,
|
|
112541
|
+
url: row["Url"] ?? "",
|
|
112542
|
+
}));
|
|
112543
|
+
|
|
112544
|
+
// \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
|
|
112545
|
+
// const urlIdx = result.columns.indexOf("Url");
|
|
112546
|
+
// const url = (row as unknown as string[])[urlIdx];
|
|
112547
|
+
|
|
112548
|
+
return c.json({ columns: result.columns, rows });
|
|
112436
112549
|
}
|
|
112437
112550
|
\`\`\`
|
|
112438
112551
|
|
|
@@ -112444,8 +112557,8 @@ export default async function handler(c: Context) {
|
|
|
112444
112557
|
|
|
112445
112558
|
\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
|
|
112446
112559
|
|
|
112447
|
-
#### \u4E3B\u8981\u306A Standard Analytics \u30EC\u30DD\u30FC\u30C8\u30BF\u30A4\u30D7
|
|
112448
|
-
- \`
|
|
112560
|
+
#### \u4E3B\u8981\u306A Standard Analytics \u30EC\u30DD\u30FC\u30C8\u30BF\u30A4\u30D7\uFF08path \`/\`\u3001CSV\u3092\u8FD4\u3059\uFF09
|
|
112561
|
+
- \`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**
|
|
112449
112562
|
- \`domain_organic\` \u2014 \u30C9\u30E1\u30A4\u30F3\u306E\u30AA\u30FC\u30AC\u30CB\u30C3\u30AF\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112450
112563
|
- \`domain_adwords\` \u2014 \u30C9\u30E1\u30A4\u30F3\u306E\u6709\u6599\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112451
112564
|
- \`domain_organic_organic\` / \`domain_adwords_adwords\` \u2014 \u30AA\u30FC\u30AC\u30CB\u30C3\u30AF\uFF0F\u6709\u6599\u306E\u7AF6\u5408
|
|
@@ -112454,10 +112567,13 @@ export default async function handler(c: Context) {
|
|
|
112454
112567
|
- \`phrase_fullsearch\` \u2014 \u30D5\u30EB\u30C6\u30AD\u30B9\u30C8\u30AD\u30FC\u30EF\u30FC\u30C9\u30EA\u30B5\u30FC\u30C1
|
|
112455
112568
|
- \`phrase_questions\` \u2014 \u8CEA\u554F\u5F62\u5F0F\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112456
112569
|
- \`phrase_kdi\` \u2014 \u30AD\u30FC\u30EF\u30FC\u30C9\u96E3\u6613\u5EA6\uFF08KDI\uFF09
|
|
112570
|
+
- \`url_organic\` / \`url_adwords\` \u2014 \u7279\u5B9AURL\u3067\u30E9\u30F3\u30AF\u30A4\u30F3\u3057\u3066\u3044\u308B\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112571
|
+
|
|
112572
|
+
#### 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
|
|
112573
|
+
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
|
|
112457
112574
|
- \`backlinks_overview\` \u2014 \u30D0\u30C3\u30AF\u30EA\u30F3\u30AF\u6982\u8981
|
|
112458
112575
|
- \`backlinks\` \u2014 \u30D0\u30C3\u30AF\u30EA\u30F3\u30AF\u4E00\u89A7
|
|
112459
112576
|
- \`backlinks_refdomains\` \u2014 \u53C2\u7167\u30C9\u30E1\u30A4\u30F3
|
|
112460
|
-
- \`url_organic\` / \`url_adwords\` \u2014 \u7279\u5B9AURL\u3067\u30E9\u30F3\u30AF\u30A4\u30F3\u3057\u3066\u3044\u308B\u30AD\u30FC\u30EF\u30FC\u30C9
|
|
112461
112577
|
|
|
112462
112578
|
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
|
|
112463
112579
|
|
|
@@ -112465,7 +112581,7 @@ API \u30E6\u30CB\u30C3\u30C8\u6B8B\u91CF\u306E\u78BA\u8A8D\uFF08\u7121\u6599\u30
|
|
|
112465
112581
|
- \`type\` \u2014 \u30EC\u30DD\u30FC\u30C8\u7A2E\u5225\uFF08Standard API \u3067\u306F\u5FC5\u9808\uFF09
|
|
112466
112582
|
- \`domain\` / \`phrase\` / \`url\` \u2014 \u30AF\u30A8\u30EA\u5BFE\u8C61\u306E\u30A8\u30F3\u30C6\u30A3\u30C6\u30A3
|
|
112467
112583
|
- \`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
|
|
112468
|
-
- \`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
|
|
112584
|
+
- \`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
|
|
112469
112585
|
- \`display_offset\` \u2014 \u30DA\u30FC\u30B8\u30CD\u30FC\u30B7\u30E7\u30F3\u30AA\u30D5\u30BB\u30C3\u30C8
|
|
112470
112586
|
- \`display_date\` \u2014 \u5C65\u6B74\u306E\u65E5\u4ED8\u3002\`YYYYMM15\` \u5F62\u5F0F\uFF08\u5FC5\u305A\u6708\u306E15\u65E5\uFF09
|
|
112471
112587
|
- \`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
|
|
@@ -112476,6 +112592,7 @@ API \u30E6\u30CB\u30C3\u30C8\u6B8B\u91CF\u306E\u78BA\u8A8D\uFF08\u7121\u6599\u30
|
|
|
112476
112592
|
- 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
|
|
112477
112593
|
- 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
|
|
112478
112594
|
- 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
|
|
112595
|
+
- \`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
|
|
112479
112596
|
- 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
|
|
112480
112597
|
- \u5C65\u6B74\u30A8\u30F3\u30C9\u30DD\u30A4\u30F3\u30C8\u306E\u65E5\u4ED8\u306F\u5FC5\u305A\u6708\u306E15\u65E5\uFF08\`YYYYMM15\`\uFF09`
|
|
112481
112598
|
},
|
|
@@ -113595,7 +113712,8 @@ var parameters72 = {
|
|
|
113595
113712
|
type: "text",
|
|
113596
113713
|
secret: true,
|
|
113597
113714
|
required: false
|
|
113598
|
-
})
|
|
113715
|
+
}),
|
|
113716
|
+
...sshTunnelParameters
|
|
113599
113717
|
};
|
|
113600
113718
|
|
|
113601
113719
|
// ../connectors/src/connectors/sqlserver/tools/execute-query.ts
|
|
@@ -113654,7 +113772,9 @@ Avoid loading large amounts of data; always include \`TOP\` in queries.`,
|
|
|
113654
113772
|
};
|
|
113655
113773
|
}
|
|
113656
113774
|
try {
|
|
113657
|
-
const { rows } = await runMssqlQuery(parsed, sql
|
|
113775
|
+
const { rows } = await runMssqlQuery(parsed, sql, {
|
|
113776
|
+
tunnelParams: connectionParamsToRecord(connection)
|
|
113777
|
+
});
|
|
113658
113778
|
const truncated = rows.length > MAX_ROWS14;
|
|
113659
113779
|
return {
|
|
113660
113780
|
success: true,
|
|
@@ -113725,7 +113845,8 @@ The business logic type for this connector is "sql".
|
|
|
113725
113845
|
{
|
|
113726
113846
|
username: params[parameters72.username.slug],
|
|
113727
113847
|
password: params[parameters72.password.slug]
|
|
113728
|
-
}
|
|
113848
|
+
},
|
|
113849
|
+
{ tunnelParams: params }
|
|
113729
113850
|
);
|
|
113730
113851
|
},
|
|
113731
113852
|
async query(params, sql, _namedParams) {
|
|
@@ -113735,10 +113856,12 @@ The business logic type for this connector is "sql".
|
|
|
113735
113856
|
});
|
|
113736
113857
|
const sample = unwrapSampleLimit(sql);
|
|
113737
113858
|
if (sample) {
|
|
113738
|
-
const result = await runMssqlQuery(parsed, sample.inner
|
|
113859
|
+
const result = await runMssqlQuery(parsed, sample.inner, {
|
|
113860
|
+
tunnelParams: params
|
|
113861
|
+
});
|
|
113739
113862
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
113740
113863
|
}
|
|
113741
|
-
return runMssqlQuery(parsed, sql);
|
|
113864
|
+
return runMssqlQuery(parsed, sql, { tunnelParams: params });
|
|
113742
113865
|
}
|
|
113743
113866
|
});
|
|
113744
113867
|
|
|
@@ -113784,7 +113907,8 @@ var parameters73 = {
|
|
|
113784
113907
|
type: "text",
|
|
113785
113908
|
secret: true,
|
|
113786
113909
|
required: false
|
|
113787
|
-
})
|
|
113910
|
+
}),
|
|
113911
|
+
...sshTunnelParameters
|
|
113788
113912
|
};
|
|
113789
113913
|
|
|
113790
113914
|
// ../connectors/src/connectors/azure-sql/tools/execute-query.ts
|
|
@@ -113843,7 +113967,10 @@ Avoid loading large amounts of data; always include \`TOP\` in queries.`,
|
|
|
113843
113967
|
};
|
|
113844
113968
|
}
|
|
113845
113969
|
try {
|
|
113846
|
-
const { rows } = await runMssqlQuery(parsed, sql, {
|
|
113970
|
+
const { rows } = await runMssqlQuery(parsed, sql, {
|
|
113971
|
+
forceEncrypt: true,
|
|
113972
|
+
tunnelParams: connectionParamsToRecord(connection)
|
|
113973
|
+
});
|
|
113847
113974
|
const truncated = rows.length > MAX_ROWS15;
|
|
113848
113975
|
return {
|
|
113849
113976
|
success: true,
|
|
@@ -113868,7 +113995,7 @@ var azureSqlConnector = new ConnectorPlugin({
|
|
|
113868
113995
|
description: "Connect to Azure SQL Database (managed) using a JDBC-style URL. Encryption is enforced automatically.",
|
|
113869
113996
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/5TL0yBbxoLlk6jFZuiHl8w/55040f52d57bf0b77a2215c985c5a772/azure-sql-icon.png",
|
|
113870
113997
|
parameters: parameters73,
|
|
113871
|
-
releaseFlag: { dev1: true, dev2:
|
|
113998
|
+
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
113872
113999
|
categories: ["database"],
|
|
113873
114000
|
onboarding: azureSqlOnboarding,
|
|
113874
114001
|
systemPrompt: {
|
|
@@ -113915,7 +114042,7 @@ The business logic type for this connector is "sql".
|
|
|
113915
114042
|
username: params[parameters73.username.slug],
|
|
113916
114043
|
password: params[parameters73.password.slug]
|
|
113917
114044
|
},
|
|
113918
|
-
{ forceEncrypt: true }
|
|
114045
|
+
{ forceEncrypt: true, tunnelParams: params }
|
|
113919
114046
|
);
|
|
113920
114047
|
},
|
|
113921
114048
|
async query(params, sql, _namedParams) {
|
|
@@ -113926,11 +114053,353 @@ The business logic type for this connector is "sql".
|
|
|
113926
114053
|
const sample = unwrapSampleLimit(sql);
|
|
113927
114054
|
if (sample) {
|
|
113928
114055
|
const result = await runMssqlQuery(parsed, sample.inner, {
|
|
113929
|
-
forceEncrypt: true
|
|
114056
|
+
forceEncrypt: true,
|
|
114057
|
+
tunnelParams: params
|
|
113930
114058
|
});
|
|
113931
114059
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
113932
114060
|
}
|
|
113933
|
-
return runMssqlQuery(parsed, sql, {
|
|
114061
|
+
return runMssqlQuery(parsed, sql, {
|
|
114062
|
+
forceEncrypt: true,
|
|
114063
|
+
tunnelParams: params
|
|
114064
|
+
});
|
|
114065
|
+
}
|
|
114066
|
+
});
|
|
114067
|
+
|
|
114068
|
+
// ../connectors/src/connectors/cosmosdb/setup.ts
|
|
114069
|
+
var cosmosdbOnboarding = new ConnectorOnboarding({
|
|
114070
|
+
dataOverviewInstructions: {
|
|
114071
|
+
en: `1. Use cosmosdb_listContainers to list all containers in the configured database
|
|
114072
|
+
2. For key containers, sample documents with cosmosdb_query: container="users", sql="SELECT TOP 5 * FROM c"
|
|
114073
|
+
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)
|
|
114074
|
+
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\``,
|
|
114075
|
+
ja: `1. cosmosdb_listContainers \u3067\u5BFE\u8C61\u30C7\u30FC\u30BF\u30D9\u30FC\u30B9\u5185\u306E\u30B3\u30F3\u30C6\u30CA\u4E00\u89A7\u3092\u53D6\u5F97
|
|
114076
|
+
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"
|
|
114077
|
+
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
|
|
114078
|
+
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\``
|
|
114079
|
+
}
|
|
114080
|
+
});
|
|
114081
|
+
|
|
114082
|
+
// ../connectors/src/connectors/cosmosdb/parameters.ts
|
|
114083
|
+
var parameters74 = {
|
|
114084
|
+
endpoint: new ParameterDefinition({
|
|
114085
|
+
slug: "endpoint",
|
|
114086
|
+
name: "Cosmos DB Endpoint",
|
|
114087
|
+
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.",
|
|
114088
|
+
envVarBaseKey: "COSMOSDB_ENDPOINT",
|
|
114089
|
+
type: "text",
|
|
114090
|
+
secret: false,
|
|
114091
|
+
required: true
|
|
114092
|
+
}),
|
|
114093
|
+
key: new ParameterDefinition({
|
|
114094
|
+
slug: "key",
|
|
114095
|
+
name: "Account Key",
|
|
114096
|
+
description: "Cosmos DB account key (primary or secondary master key). Use a read-only key when only querying data.",
|
|
114097
|
+
envVarBaseKey: "COSMOSDB_KEY",
|
|
114098
|
+
type: "text",
|
|
114099
|
+
secret: true,
|
|
114100
|
+
required: true
|
|
114101
|
+
}),
|
|
114102
|
+
database: new ParameterDefinition({
|
|
114103
|
+
slug: "database",
|
|
114104
|
+
name: "Database",
|
|
114105
|
+
description: "The Cosmos DB database (a.k.a. database account namespace) to connect to.",
|
|
114106
|
+
envVarBaseKey: "COSMOSDB_DATABASE",
|
|
114107
|
+
type: "text",
|
|
114108
|
+
secret: false,
|
|
114109
|
+
required: true
|
|
114110
|
+
})
|
|
114111
|
+
};
|
|
114112
|
+
|
|
114113
|
+
// ../connectors/src/connectors/cosmosdb/tools/list-containers.ts
|
|
114114
|
+
import { z as z90 } from "zod";
|
|
114115
|
+
var inputSchema90 = z90.object({
|
|
114116
|
+
toolUseIntent: z90.string().optional().describe(
|
|
114117
|
+
"Brief description of what you intend to accomplish with this tool call"
|
|
114118
|
+
),
|
|
114119
|
+
connectionId: z90.string().describe("ID of the Cosmos DB connection to use")
|
|
114120
|
+
});
|
|
114121
|
+
var outputSchema90 = z90.discriminatedUnion("success", [
|
|
114122
|
+
z90.object({
|
|
114123
|
+
success: z90.literal(true),
|
|
114124
|
+
containers: z90.array(
|
|
114125
|
+
z90.object({
|
|
114126
|
+
id: z90.string(),
|
|
114127
|
+
partitionKey: z90.array(z90.string()).optional()
|
|
114128
|
+
})
|
|
114129
|
+
)
|
|
114130
|
+
}),
|
|
114131
|
+
z90.object({
|
|
114132
|
+
success: z90.literal(false),
|
|
114133
|
+
error: z90.string()
|
|
114134
|
+
})
|
|
114135
|
+
]);
|
|
114136
|
+
var listContainersTool = new ConnectorTool({
|
|
114137
|
+
name: "listContainers",
|
|
114138
|
+
description: `List all containers in the configured Cosmos DB database.
|
|
114139
|
+
Use this as the first step to explore the data structure. Returns container ids and their partition key paths.
|
|
114140
|
+
After listing containers, use the query tool to sample items and understand each container's schema.`,
|
|
114141
|
+
inputSchema: inputSchema90,
|
|
114142
|
+
outputSchema: outputSchema90,
|
|
114143
|
+
async execute({ connectionId }, connections) {
|
|
114144
|
+
const connection = connections.find((c6) => c6.id === connectionId);
|
|
114145
|
+
if (!connection) {
|
|
114146
|
+
return {
|
|
114147
|
+
success: false,
|
|
114148
|
+
error: `Connection ${connectionId} not found`
|
|
114149
|
+
};
|
|
114150
|
+
}
|
|
114151
|
+
console.log(
|
|
114152
|
+
`[connector-query] cosmosdb/${connection.name}: listContainers`
|
|
114153
|
+
);
|
|
114154
|
+
let key;
|
|
114155
|
+
try {
|
|
114156
|
+
const { CosmosClient } = await import("@azure/cosmos");
|
|
114157
|
+
const endpoint = parameters74.endpoint.getValue(connection);
|
|
114158
|
+
key = parameters74.key.getValue(connection);
|
|
114159
|
+
const database = parameters74.database.getValue(connection);
|
|
114160
|
+
const client = new CosmosClient({ endpoint, key });
|
|
114161
|
+
const db = client.database(database);
|
|
114162
|
+
const { resources } = await db.containers.readAll().fetchAll();
|
|
114163
|
+
return {
|
|
114164
|
+
success: true,
|
|
114165
|
+
containers: resources.map((c6) => ({
|
|
114166
|
+
id: c6.id,
|
|
114167
|
+
partitionKey: extractPartitionKeyPaths(c6.partitionKey)
|
|
114168
|
+
}))
|
|
114169
|
+
};
|
|
114170
|
+
} catch (err) {
|
|
114171
|
+
let msg = err instanceof Error ? err.message : String(err);
|
|
114172
|
+
if (key) msg = msg.replaceAll(key, "***");
|
|
114173
|
+
return { success: false, error: msg };
|
|
114174
|
+
}
|
|
114175
|
+
}
|
|
114176
|
+
});
|
|
114177
|
+
function extractPartitionKeyPaths(partitionKey) {
|
|
114178
|
+
if (!partitionKey || typeof partitionKey !== "object") return void 0;
|
|
114179
|
+
const paths = partitionKey.paths;
|
|
114180
|
+
if (!Array.isArray(paths)) return void 0;
|
|
114181
|
+
return paths.filter((p2) => typeof p2 === "string");
|
|
114182
|
+
}
|
|
114183
|
+
|
|
114184
|
+
// ../connectors/src/connectors/cosmosdb/tools/query.ts
|
|
114185
|
+
import { z as z91 } from "zod";
|
|
114186
|
+
var MAX_DOCUMENTS3 = 500;
|
|
114187
|
+
var inputSchema91 = z91.object({
|
|
114188
|
+
toolUseIntent: z91.string().optional().describe(
|
|
114189
|
+
"Brief description of what you intend to accomplish with this tool call"
|
|
114190
|
+
),
|
|
114191
|
+
connectionId: z91.string().describe("ID of the Cosmos DB connection to use"),
|
|
114192
|
+
container: z91.string().describe("Id of the container (a.k.a. collection) to query"),
|
|
114193
|
+
sql: z91.string().describe(
|
|
114194
|
+
"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`."
|
|
114195
|
+
),
|
|
114196
|
+
partitionKey: z91.string().optional().describe(
|
|
114197
|
+
`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.`
|
|
114198
|
+
)
|
|
114199
|
+
});
|
|
114200
|
+
var outputSchema91 = z91.discriminatedUnion("success", [
|
|
114201
|
+
z91.object({
|
|
114202
|
+
success: z91.literal(true),
|
|
114203
|
+
documentCount: z91.number(),
|
|
114204
|
+
truncated: z91.boolean(),
|
|
114205
|
+
requestCharge: z91.number().optional(),
|
|
114206
|
+
documents: z91.array(z91.unknown())
|
|
114207
|
+
}),
|
|
114208
|
+
z91.object({
|
|
114209
|
+
success: z91.literal(false),
|
|
114210
|
+
error: z91.string()
|
|
114211
|
+
})
|
|
114212
|
+
]);
|
|
114213
|
+
var queryTool = new ConnectorTool({
|
|
114214
|
+
name: "query",
|
|
114215
|
+
description: `Execute a Cosmos DB SQL (Core / NoSQL API) query against a container. Returns up to ${MAX_DOCUMENTS3} items.
|
|
114216
|
+
Use for: schema exploration, data sampling, aggregations, and analytical queries.
|
|
114217
|
+
Cosmos DB SQL targets a single container; reference items via the alias \`c\` (e.g. \`SELECT c.id FROM c WHERE c.userId = 'abc'\`).
|
|
114218
|
+
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.`,
|
|
114219
|
+
inputSchema: inputSchema91,
|
|
114220
|
+
outputSchema: outputSchema91,
|
|
114221
|
+
async execute({ connectionId, container, sql, partitionKey }, connections) {
|
|
114222
|
+
const connection = connections.find((c6) => c6.id === connectionId);
|
|
114223
|
+
if (!connection) {
|
|
114224
|
+
return {
|
|
114225
|
+
success: false,
|
|
114226
|
+
error: `Connection ${connectionId} not found`
|
|
114227
|
+
};
|
|
114228
|
+
}
|
|
114229
|
+
console.log(
|
|
114230
|
+
`[connector-query] cosmosdb/${connection.name} (${container}): ${sql}`
|
|
114231
|
+
);
|
|
114232
|
+
let key;
|
|
114233
|
+
try {
|
|
114234
|
+
const cosmos = await import("@azure/cosmos");
|
|
114235
|
+
const { CosmosClient } = cosmos;
|
|
114236
|
+
const endpoint = parameters74.endpoint.getValue(connection);
|
|
114237
|
+
key = parameters74.key.getValue(connection);
|
|
114238
|
+
const database = parameters74.database.getValue(connection);
|
|
114239
|
+
const client = new CosmosClient({ endpoint, key });
|
|
114240
|
+
const cont = client.database(database).container(container);
|
|
114241
|
+
const queryOptions = {
|
|
114242
|
+
// Bound by the connector's own row cap, but keep the SDK from
|
|
114243
|
+
// streaming arbitrarily large continuations.
|
|
114244
|
+
maxItemCount: MAX_DOCUMENTS3 + 1
|
|
114245
|
+
};
|
|
114246
|
+
if (partitionKey != null && partitionKey !== "") {
|
|
114247
|
+
try {
|
|
114248
|
+
queryOptions.partitionKey = JSON.parse(partitionKey);
|
|
114249
|
+
} catch {
|
|
114250
|
+
return {
|
|
114251
|
+
success: false,
|
|
114252
|
+
error: `Invalid partitionKey: must be a JSON-encoded scalar (e.g. '"abc"' or '123'). Got: ${partitionKey}`
|
|
114253
|
+
};
|
|
114254
|
+
}
|
|
114255
|
+
}
|
|
114256
|
+
const iterator = cont.items.query(sql, queryOptions);
|
|
114257
|
+
const { resources, requestCharge } = await iterator.fetchNext();
|
|
114258
|
+
const documents = resources ?? [];
|
|
114259
|
+
const truncated = documents.length > MAX_DOCUMENTS3;
|
|
114260
|
+
return {
|
|
114261
|
+
success: true,
|
|
114262
|
+
documentCount: Math.min(documents.length, MAX_DOCUMENTS3),
|
|
114263
|
+
truncated,
|
|
114264
|
+
requestCharge,
|
|
114265
|
+
documents: documents.slice(0, MAX_DOCUMENTS3)
|
|
114266
|
+
};
|
|
114267
|
+
} catch (err) {
|
|
114268
|
+
let msg = err instanceof Error ? err.message : String(err);
|
|
114269
|
+
if (key) msg = msg.replaceAll(key, "***");
|
|
114270
|
+
return { success: false, error: msg };
|
|
114271
|
+
}
|
|
114272
|
+
}
|
|
114273
|
+
});
|
|
114274
|
+
|
|
114275
|
+
// ../connectors/src/connectors/cosmosdb/index.ts
|
|
114276
|
+
var tools74 = {
|
|
114277
|
+
listContainers: listContainersTool,
|
|
114278
|
+
query: queryTool
|
|
114279
|
+
};
|
|
114280
|
+
var cosmosdbConnector = new ConnectorPlugin({
|
|
114281
|
+
slug: "cosmosdb",
|
|
114282
|
+
authType: AUTH_TYPES.USER_PASSWORD,
|
|
114283
|
+
name: "Azure Cosmos DB",
|
|
114284
|
+
description: "Connect to Azure Cosmos DB (Core / NoSQL API) for document-oriented data storage and SQL-style querying.",
|
|
114285
|
+
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/5p9B2Db0V2d8mK2jgBWtZu/dad72db8f41b16c50de2bcef03f9d415/cosmosdb-icon.png",
|
|
114286
|
+
parameters: parameters74,
|
|
114287
|
+
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
114288
|
+
categories: ["database"],
|
|
114289
|
+
onboarding: cosmosdbOnboarding,
|
|
114290
|
+
systemPrompt: {
|
|
114291
|
+
en: `### Tools
|
|
114292
|
+
|
|
114293
|
+
- \`cosmosdb_listContainers\`: Lists all containers in the configured database, with their partition key paths. Use this first to explore available data.
|
|
114294
|
+
- \`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).
|
|
114295
|
+
|
|
114296
|
+
### Business Logic
|
|
114297
|
+
|
|
114298
|
+
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.
|
|
114299
|
+
|
|
114300
|
+
\u26A0\uFE0F **The client returned by \`connection(connectionId)\` is NOT the raw \`@azure/cosmos\` \`CosmosClient\`.** It is a thin wrapper exposing only two methods:
|
|
114301
|
+
- \`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 }\`.
|
|
114302
|
+
- \`client.listContainers() => Promise<{ id: string; partitionKey?: string[] }[]>\` \u2014 lists containers in the configured database.
|
|
114303
|
+
|
|
114304
|
+
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\`.
|
|
114305
|
+
|
|
114306
|
+
\`\`\`ts
|
|
114307
|
+
import type { Context } from "hono";
|
|
114308
|
+
import { connection } from "@squadbase/vite-server/connectors/cosmosdb";
|
|
114309
|
+
|
|
114310
|
+
const cosmos = connection("<connectionId>");
|
|
114311
|
+
|
|
114312
|
+
export default async function handler(_c: Context) {
|
|
114313
|
+
// \`query\` returns the items array directly \u2014 no \`.resources\` to unwrap.
|
|
114314
|
+
const rows = await cosmos.query<{ prod: string; orderCount: number }>(
|
|
114315
|
+
"<containerName>",
|
|
114316
|
+
"SELECT c.prod, COUNT(1) AS orderCount FROM c GROUP BY c.prod",
|
|
114317
|
+
// Optional: scope to a single partition to save RUs.
|
|
114318
|
+
// { partitionKey: "<partitionKeyValue>" },
|
|
114319
|
+
);
|
|
114320
|
+
|
|
114321
|
+
rows.sort((a, b) => Number(b.orderCount) - Number(a.orderCount));
|
|
114322
|
+
|
|
114323
|
+
return new Response(JSON.stringify(rows), {
|
|
114324
|
+
headers: { "Content-Type": "application/json" },
|
|
114325
|
+
});
|
|
114326
|
+
}
|
|
114327
|
+
\`\`\`
|
|
114328
|
+
|
|
114329
|
+
### Cosmos DB SQL Reference
|
|
114330
|
+
- Cosmos DB stores schema-flexible JSON items in **containers** organised under a **database**. Items are partitioned by a per-container partition key path.
|
|
114331
|
+
- 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'\`).
|
|
114332
|
+
- 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.
|
|
114333
|
+
- System fields are prefixed with an underscore (\`c.id\`, \`c._ts\` for the modification timestamp, \`c._etag\`).
|
|
114334
|
+
- 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\`).
|
|
114335
|
+
- Joins: only **intra-document** joins via \`JOIN\` over arrays inside the same item; there is no cross-container/cross-document join.
|
|
114336
|
+
- Always bound results with \`TOP n\` and prefer scoped queries with a \`partitionKey\` value when possible \u2014 cross-partition queries cost more RUs.`,
|
|
114337
|
+
ja: `### \u30C4\u30FC\u30EB
|
|
114338
|
+
|
|
114339
|
+
- \`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
|
|
114340
|
+
- \`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
|
|
114341
|
+
|
|
114342
|
+
### Business Logic
|
|
114343
|
+
|
|
114344
|
+
\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
|
|
114345
|
+
|
|
114346
|
+
\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
|
|
114347
|
+
- \`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
|
|
114348
|
+
- \`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
|
|
114349
|
+
|
|
114350
|
+
\`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
|
|
114351
|
+
|
|
114352
|
+
\`\`\`ts
|
|
114353
|
+
import type { Context } from "hono";
|
|
114354
|
+
import { connection } from "@squadbase/vite-server/connectors/cosmosdb";
|
|
114355
|
+
|
|
114356
|
+
const cosmos = connection("<connectionId>");
|
|
114357
|
+
|
|
114358
|
+
export default async function handler(_c: Context) {
|
|
114359
|
+
// \`query\` \u306F items \u914D\u5217\u3092\u305D\u306E\u307E\u307E\u8FD4\u3059 \u2014 \`.resources\` \u306E\u5C55\u958B\u306F\u4E0D\u8981\u3002
|
|
114360
|
+
const rows = await cosmos.query<{ prod: string; orderCount: number }>(
|
|
114361
|
+
"<containerName>",
|
|
114362
|
+
"SELECT c.prod, COUNT(1) AS orderCount FROM c GROUP BY c.prod",
|
|
114363
|
+
// \u4EFB\u610F: \u5358\u4E00\u30D1\u30FC\u30C6\u30A3\u30B7\u30E7\u30F3\u306B\u30B9\u30B3\u30FC\u30D7\u3057\u3066 RU \u3092\u7BC0\u7D04\u3002
|
|
114364
|
+
// { partitionKey: "<partitionKeyValue>" },
|
|
114365
|
+
);
|
|
114366
|
+
|
|
114367
|
+
rows.sort((a, b) => Number(b.orderCount) - Number(a.orderCount));
|
|
114368
|
+
|
|
114369
|
+
return new Response(JSON.stringify(rows), {
|
|
114370
|
+
headers: { "Content-Type": "application/json" },
|
|
114371
|
+
});
|
|
114372
|
+
}
|
|
114373
|
+
\`\`\`
|
|
114374
|
+
|
|
114375
|
+
### Cosmos DB SQL \u30EA\u30D5\u30A1\u30EC\u30F3\u30B9
|
|
114376
|
+
- 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
|
|
114377
|
+
- \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
|
|
114378
|
+
- \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
|
|
114379
|
+
- \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
|
|
114380
|
+
- \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
|
|
114381
|
+
- \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
|
|
114382
|
+
- \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`
|
|
114383
|
+
},
|
|
114384
|
+
tools: tools74,
|
|
114385
|
+
async checkConnection(params, _config) {
|
|
114386
|
+
try {
|
|
114387
|
+
const { CosmosClient } = await import("@azure/cosmos");
|
|
114388
|
+
const client = new CosmosClient({
|
|
114389
|
+
endpoint: params[parameters74.endpoint.slug],
|
|
114390
|
+
key: params[parameters74.key.slug]
|
|
114391
|
+
});
|
|
114392
|
+
const database = params[parameters74.database.slug];
|
|
114393
|
+
await client.database(database).read();
|
|
114394
|
+
return { success: true };
|
|
114395
|
+
} catch (error2) {
|
|
114396
|
+
const msg = error2 instanceof Error ? error2.message : String(error2);
|
|
114397
|
+
const key = params[parameters74.key.slug];
|
|
114398
|
+
return {
|
|
114399
|
+
success: false,
|
|
114400
|
+
error: key ? msg.replaceAll(key, "***") : msg
|
|
114401
|
+
};
|
|
114402
|
+
}
|
|
113934
114403
|
}
|
|
113935
114404
|
});
|
|
113936
114405
|
|
|
@@ -113951,7 +114420,7 @@ var oracleOnboarding = new ConnectorOnboarding({
|
|
|
113951
114420
|
});
|
|
113952
114421
|
|
|
113953
114422
|
// ../connectors/src/connectors/oracle/parameters.ts
|
|
113954
|
-
var
|
|
114423
|
+
var parameters75 = {
|
|
113955
114424
|
jdbcUrl: new ParameterDefinition({
|
|
113956
114425
|
slug: "jdbc-url",
|
|
113957
114426
|
name: "Oracle JDBC URL",
|
|
@@ -113978,31 +114447,32 @@ var parameters74 = {
|
|
|
113978
114447
|
type: "text",
|
|
113979
114448
|
secret: true,
|
|
113980
114449
|
required: false
|
|
113981
|
-
})
|
|
114450
|
+
}),
|
|
114451
|
+
...sshTunnelParameters
|
|
113982
114452
|
};
|
|
113983
114453
|
|
|
113984
114454
|
// ../connectors/src/connectors/oracle/tools/execute-query.ts
|
|
113985
|
-
import { z as
|
|
114455
|
+
import { z as z92 } from "zod";
|
|
113986
114456
|
var MAX_ROWS16 = 500;
|
|
113987
|
-
var
|
|
113988
|
-
toolUseIntent:
|
|
114457
|
+
var inputSchema92 = z92.object({
|
|
114458
|
+
toolUseIntent: z92.string().optional().describe(
|
|
113989
114459
|
"Brief description of what you intend to accomplish with this tool call"
|
|
113990
114460
|
),
|
|
113991
|
-
connectionId:
|
|
113992
|
-
sql:
|
|
114461
|
+
connectionId: z92.string().describe("ID of the Oracle connection to use"),
|
|
114462
|
+
sql: z92.string().describe(
|
|
113993
114463
|
"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."
|
|
113994
114464
|
)
|
|
113995
114465
|
});
|
|
113996
|
-
var
|
|
113997
|
-
|
|
113998
|
-
success:
|
|
113999
|
-
rowCount:
|
|
114000
|
-
truncated:
|
|
114001
|
-
rows:
|
|
114466
|
+
var outputSchema92 = z92.discriminatedUnion("success", [
|
|
114467
|
+
z92.object({
|
|
114468
|
+
success: z92.literal(true),
|
|
114469
|
+
rowCount: z92.number(),
|
|
114470
|
+
truncated: z92.boolean(),
|
|
114471
|
+
rows: z92.array(z92.record(z92.string(), z92.unknown()))
|
|
114002
114472
|
}),
|
|
114003
|
-
|
|
114004
|
-
success:
|
|
114005
|
-
error:
|
|
114473
|
+
z92.object({
|
|
114474
|
+
success: z92.literal(false),
|
|
114475
|
+
error: z92.string()
|
|
114006
114476
|
})
|
|
114007
114477
|
]);
|
|
114008
114478
|
var executeQueryTool16 = new ConnectorTool({
|
|
@@ -114012,8 +114482,8 @@ Use for: schema exploration via \`USER_TABLES\` / \`USER_TAB_COLUMNS\` / \`ALL_T
|
|
|
114012
114482
|
Oracle uses \`FETCH FIRST n ROWS ONLY\` (12c+) or \`ROWNUM\` for row limiting \u2014 there is no \`LIMIT\` keyword.
|
|
114013
114483
|
Unquoted identifiers are stored upper-case (\`SELECT * FROM employees\` resolves to \`EMPLOYEES\`).
|
|
114014
114484
|
Do NOT terminate statements with a semicolon; the driver rejects trailing terminators.`,
|
|
114015
|
-
inputSchema:
|
|
114016
|
-
outputSchema:
|
|
114485
|
+
inputSchema: inputSchema92,
|
|
114486
|
+
outputSchema: outputSchema92,
|
|
114017
114487
|
async execute({ connectionId, sql }, connections) {
|
|
114018
114488
|
const connection = connections.find((c6) => c6.id === connectionId);
|
|
114019
114489
|
if (!connection) {
|
|
@@ -114022,9 +114492,9 @@ Do NOT terminate statements with a semicolon; the driver rejects trailing termin
|
|
|
114022
114492
|
error: `Connection ${connectionId} not found`
|
|
114023
114493
|
};
|
|
114024
114494
|
}
|
|
114025
|
-
const jdbcUrl =
|
|
114026
|
-
const username =
|
|
114027
|
-
const password =
|
|
114495
|
+
const jdbcUrl = parameters75.jdbcUrl.getValue(connection);
|
|
114496
|
+
const username = parameters75.username.tryGetValue(connection);
|
|
114497
|
+
const password = parameters75.password.tryGetValue(connection);
|
|
114028
114498
|
console.log(
|
|
114029
114499
|
`[connector-query] oracle/${connection.name} (${redactOracleUrl(jdbcUrl)}): ${sql}`
|
|
114030
114500
|
);
|
|
@@ -114039,7 +114509,9 @@ Do NOT terminate statements with a semicolon; the driver rejects trailing termin
|
|
|
114039
114509
|
}
|
|
114040
114510
|
try {
|
|
114041
114511
|
const cleanSql = sql.replace(/;\s*$/, "");
|
|
114042
|
-
const { rows } = await runOracleQuery(parsed, cleanSql
|
|
114512
|
+
const { rows } = await runOracleQuery(parsed, cleanSql, {
|
|
114513
|
+
tunnelParams: connectionParamsToRecord(connection)
|
|
114514
|
+
});
|
|
114043
114515
|
const truncated = rows.length > MAX_ROWS16;
|
|
114044
114516
|
return {
|
|
114045
114517
|
success: true,
|
|
@@ -114056,14 +114528,14 @@ Do NOT terminate statements with a semicolon; the driver rejects trailing termin
|
|
|
114056
114528
|
});
|
|
114057
114529
|
|
|
114058
114530
|
// ../connectors/src/connectors/oracle/index.ts
|
|
114059
|
-
var
|
|
114531
|
+
var tools75 = { executeQuery: executeQueryTool16 };
|
|
114060
114532
|
var oracleConnector = new ConnectorPlugin({
|
|
114061
114533
|
slug: "oracle",
|
|
114062
114534
|
authType: AUTH_TYPES.USER_PASSWORD,
|
|
114063
114535
|
name: "Oracle Database",
|
|
114064
114536
|
description: "Connect to Oracle Database using a JDBC-style URL via the pure-JS Thin driver (no Oracle Instant Client required).",
|
|
114065
114537
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/3iGEdzvGHncU5bYqFOROiV/9e7bdda7230d7ca6b34e7f6a862de876/oracle-icon.webp",
|
|
114066
|
-
parameters:
|
|
114538
|
+
parameters: parameters75,
|
|
114067
114539
|
releaseFlag: { dev1: true, dev2: false, prod: false },
|
|
114068
114540
|
categories: ["database"],
|
|
114069
114541
|
onboarding: oracleOnboarding,
|
|
@@ -114107,26 +114579,32 @@ The business logic type for this connector is "sql".
|
|
|
114107
114579
|
- \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
|
|
114108
114580
|
- \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`
|
|
114109
114581
|
},
|
|
114110
|
-
tools:
|
|
114582
|
+
tools: tools75,
|
|
114111
114583
|
async checkConnection(params, _config) {
|
|
114112
|
-
return checkOracleConnection(
|
|
114113
|
-
|
|
114114
|
-
|
|
114115
|
-
|
|
114584
|
+
return checkOracleConnection(
|
|
114585
|
+
params[parameters75.jdbcUrl.slug],
|
|
114586
|
+
{
|
|
114587
|
+
username: params[parameters75.username.slug],
|
|
114588
|
+
password: params[parameters75.password.slug]
|
|
114589
|
+
},
|
|
114590
|
+
{ tunnelParams: params }
|
|
114591
|
+
);
|
|
114116
114592
|
},
|
|
114117
114593
|
async query(params, sql, _namedParams) {
|
|
114118
|
-
const parsed = parseOracleJdbcUrl(params[
|
|
114119
|
-
username: params[
|
|
114120
|
-
password: params[
|
|
114594
|
+
const parsed = parseOracleJdbcUrl(params[parameters75.jdbcUrl.slug], {
|
|
114595
|
+
username: params[parameters75.username.slug],
|
|
114596
|
+
password: params[parameters75.password.slug]
|
|
114121
114597
|
});
|
|
114122
114598
|
const sample = unwrapSampleLimit(sql);
|
|
114123
114599
|
if (sample) {
|
|
114124
114600
|
const inner = sample.inner.replace(/;\s*$/, "");
|
|
114125
|
-
const result = await runOracleQuery(parsed, inner
|
|
114601
|
+
const result = await runOracleQuery(parsed, inner, {
|
|
114602
|
+
tunnelParams: params
|
|
114603
|
+
});
|
|
114126
114604
|
return { rows: result.rows.slice(0, sample.limit) };
|
|
114127
114605
|
}
|
|
114128
114606
|
const cleanSql = sql.replace(/;\s*$/, "");
|
|
114129
|
-
return runOracleQuery(parsed, cleanSql);
|
|
114607
|
+
return runOracleQuery(parsed, cleanSql, { tunnelParams: params });
|
|
114130
114608
|
}
|
|
114131
114609
|
});
|
|
114132
114610
|
|
|
@@ -114147,7 +114625,7 @@ var freshserviceOnboarding = new ConnectorOnboarding({
|
|
|
114147
114625
|
});
|
|
114148
114626
|
|
|
114149
114627
|
// ../connectors/src/connectors/freshservice/parameters.ts
|
|
114150
|
-
var
|
|
114628
|
+
var parameters76 = {
|
|
114151
114629
|
domain: new ParameterDefinition({
|
|
114152
114630
|
slug: "domain",
|
|
114153
114631
|
name: "Freshservice Domain",
|
|
@@ -114169,7 +114647,7 @@ var parameters75 = {
|
|
|
114169
114647
|
};
|
|
114170
114648
|
|
|
114171
114649
|
// ../connectors/src/connectors/freshservice/tools/request.ts
|
|
114172
|
-
import { z as
|
|
114650
|
+
import { z as z93 } from "zod";
|
|
114173
114651
|
var BASE_PATH_SEGMENT12 = "/api/v2";
|
|
114174
114652
|
var REQUEST_TIMEOUT_MS70 = 6e4;
|
|
114175
114653
|
function buildBaseUrl(domain) {
|
|
@@ -114180,33 +114658,33 @@ function buildBaseUrl(domain) {
|
|
|
114180
114658
|
function basicAuthHeader(apiKey) {
|
|
114181
114659
|
return `Basic ${Buffer.from(`${apiKey}:X`).toString("base64")}`;
|
|
114182
114660
|
}
|
|
114183
|
-
var
|
|
114184
|
-
toolUseIntent:
|
|
114661
|
+
var inputSchema93 = z93.object({
|
|
114662
|
+
toolUseIntent: z93.string().optional().describe(
|
|
114185
114663
|
"Brief description of what you intend to accomplish with this tool call"
|
|
114186
114664
|
),
|
|
114187
|
-
connectionId:
|
|
114188
|
-
method:
|
|
114665
|
+
connectionId: z93.string().describe("ID of the Freshservice connection to use"),
|
|
114666
|
+
method: z93.enum(["GET", "POST", "PUT", "DELETE"]).describe(
|
|
114189
114667
|
"HTTP method. GET for reading resources, POST for creating, PUT for updating, DELETE for removing."
|
|
114190
114668
|
),
|
|
114191
|
-
path:
|
|
114669
|
+
path: z93.string().describe(
|
|
114192
114670
|
"API path (e.g., '/tickets', '/tickets/123', '/agents'). Append query parameters such as '?per_page=100&page=1' for pagination."
|
|
114193
114671
|
),
|
|
114194
|
-
body:
|
|
114672
|
+
body: z93.record(z93.string(), z93.unknown()).optional().describe(
|
|
114195
114673
|
'Request body (JSON) for POST/PUT requests. Example: { "subject": "...", "description": "...", "email": "...", "priority": 2, "status": 2, "source": 2 }.'
|
|
114196
114674
|
)
|
|
114197
114675
|
});
|
|
114198
|
-
var
|
|
114199
|
-
|
|
114200
|
-
success:
|
|
114201
|
-
status:
|
|
114202
|
-
data:
|
|
114203
|
-
|
|
114204
|
-
|
|
114676
|
+
var outputSchema93 = z93.discriminatedUnion("success", [
|
|
114677
|
+
z93.object({
|
|
114678
|
+
success: z93.literal(true),
|
|
114679
|
+
status: z93.number(),
|
|
114680
|
+
data: z93.union([
|
|
114681
|
+
z93.record(z93.string(), z93.unknown()),
|
|
114682
|
+
z93.array(z93.unknown())
|
|
114205
114683
|
])
|
|
114206
114684
|
}),
|
|
114207
|
-
|
|
114208
|
-
success:
|
|
114209
|
-
error:
|
|
114685
|
+
z93.object({
|
|
114686
|
+
success: z93.literal(false),
|
|
114687
|
+
error: z93.string()
|
|
114210
114688
|
})
|
|
114211
114689
|
]);
|
|
114212
114690
|
var requestTool52 = new ConnectorTool({
|
|
@@ -114237,8 +114715,8 @@ Field codes:
|
|
|
114237
114715
|
- ticket priority: 1 Low, 2 Medium, 3 High, 4 Urgent
|
|
114238
114716
|
- ticket status: 2 Open, 3 Pending, 4 Resolved, 5 Closed
|
|
114239
114717
|
- ticket source: 1 Email, 2 Portal, 3 Phone, 4 Chat, 5 Feedback widget, 7 Yammer, 8 AwsCloudwatch, 9 Pagerduty, 10 Walkup, 11 Slack`,
|
|
114240
|
-
inputSchema:
|
|
114241
|
-
outputSchema:
|
|
114718
|
+
inputSchema: inputSchema93,
|
|
114719
|
+
outputSchema: outputSchema93,
|
|
114242
114720
|
async execute({ connectionId, method, path: path5, body }, connections) {
|
|
114243
114721
|
const connection = connections.find((c6) => c6.id === connectionId);
|
|
114244
114722
|
if (!connection) {
|
|
@@ -114251,8 +114729,8 @@ Field codes:
|
|
|
114251
114729
|
`[connector-request] freshservice/${connection.name}: ${method} ${path5}`
|
|
114252
114730
|
);
|
|
114253
114731
|
try {
|
|
114254
|
-
const apiKey =
|
|
114255
|
-
const domain =
|
|
114732
|
+
const apiKey = parameters76.apiKey.getValue(connection);
|
|
114733
|
+
const domain = parameters76.domain.getValue(connection);
|
|
114256
114734
|
const baseUrl = buildBaseUrl(domain);
|
|
114257
114735
|
const normalizedPath = normalizeRequestPath(path5, BASE_PATH_SEGMENT12);
|
|
114258
114736
|
const url = `${baseUrl}${normalizedPath}`;
|
|
@@ -114291,14 +114769,14 @@ Field codes:
|
|
|
114291
114769
|
});
|
|
114292
114770
|
|
|
114293
114771
|
// ../connectors/src/connectors/freshservice/index.ts
|
|
114294
|
-
var
|
|
114772
|
+
var tools76 = { request: requestTool52 };
|
|
114295
114773
|
var freshserviceConnector = new ConnectorPlugin({
|
|
114296
114774
|
slug: "freshservice",
|
|
114297
114775
|
authType: AUTH_TYPES.API_KEY,
|
|
114298
114776
|
name: "Freshservice",
|
|
114299
114777
|
description: "Connect to Freshservice (ITSM) for ticket, agent, asset, and ITIL workflow data via API key.",
|
|
114300
114778
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/6Tj64HZOoIrGgQYDayBosY/3f45b29d3479726b5d245ac38d5a7036/freshservice-icon.svg",
|
|
114301
|
-
parameters:
|
|
114779
|
+
parameters: parameters76,
|
|
114302
114780
|
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
114303
114781
|
categories: ["productivity"],
|
|
114304
114782
|
onboarding: freshserviceOnboarding,
|
|
@@ -114456,7 +114934,7 @@ export default async function handler(c: Context) {
|
|
|
114456
114934
|
- \`status\`: 2=Open, 3=Pending, 4=Resolved, 5=Closed
|
|
114457
114935
|
- \`source\`: 1=Email, 2=Portal, 3=Phone, 4=Chat, 5=Feedback widget, 7=Yammer, 8=AwsCloudwatch, 9=Pagerduty, 10=Walkup, 11=Slack`
|
|
114458
114936
|
},
|
|
114459
|
-
tools:
|
|
114937
|
+
tools: tools76
|
|
114460
114938
|
});
|
|
114461
114939
|
|
|
114462
114940
|
// ../connectors/src/connectors/freshdesk/setup.ts
|
|
@@ -114476,7 +114954,7 @@ var freshdeskOnboarding = new ConnectorOnboarding({
|
|
|
114476
114954
|
});
|
|
114477
114955
|
|
|
114478
114956
|
// ../connectors/src/connectors/freshdesk/parameters.ts
|
|
114479
|
-
var
|
|
114957
|
+
var parameters77 = {
|
|
114480
114958
|
domain: new ParameterDefinition({
|
|
114481
114959
|
slug: "domain",
|
|
114482
114960
|
name: "Freshdesk Domain",
|
|
@@ -114498,7 +114976,7 @@ var parameters76 = {
|
|
|
114498
114976
|
};
|
|
114499
114977
|
|
|
114500
114978
|
// ../connectors/src/connectors/freshdesk/tools/request.ts
|
|
114501
|
-
import { z as
|
|
114979
|
+
import { z as z94 } from "zod";
|
|
114502
114980
|
var BASE_PATH_SEGMENT13 = "/api/v2";
|
|
114503
114981
|
var REQUEST_TIMEOUT_MS71 = 6e4;
|
|
114504
114982
|
function buildBaseUrl2(domain) {
|
|
@@ -114509,33 +114987,33 @@ function buildBaseUrl2(domain) {
|
|
|
114509
114987
|
function basicAuthHeader2(apiKey) {
|
|
114510
114988
|
return `Basic ${Buffer.from(`${apiKey}:X`).toString("base64")}`;
|
|
114511
114989
|
}
|
|
114512
|
-
var
|
|
114513
|
-
toolUseIntent:
|
|
114990
|
+
var inputSchema94 = z94.object({
|
|
114991
|
+
toolUseIntent: z94.string().optional().describe(
|
|
114514
114992
|
"Brief description of what you intend to accomplish with this tool call"
|
|
114515
114993
|
),
|
|
114516
|
-
connectionId:
|
|
114517
|
-
method:
|
|
114994
|
+
connectionId: z94.string().describe("ID of the Freshdesk connection to use"),
|
|
114995
|
+
method: z94.enum(["GET", "POST", "PUT", "DELETE"]).describe(
|
|
114518
114996
|
"HTTP method. GET for reading resources, POST for creating, PUT for updating, DELETE for removing."
|
|
114519
114997
|
),
|
|
114520
|
-
path:
|
|
114998
|
+
path: z94.string().describe(
|
|
114521
114999
|
"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'."
|
|
114522
115000
|
),
|
|
114523
|
-
body:
|
|
115001
|
+
body: z94.record(z94.string(), z94.unknown()).optional().describe(
|
|
114524
115002
|
'Request body (JSON) for POST/PUT requests. Example creating a ticket: { "subject": "...", "description": "...", "email": "...", "priority": 2, "status": 2, "source": 1 }.'
|
|
114525
115003
|
)
|
|
114526
115004
|
});
|
|
114527
|
-
var
|
|
114528
|
-
|
|
114529
|
-
success:
|
|
114530
|
-
status:
|
|
114531
|
-
data:
|
|
114532
|
-
|
|
114533
|
-
|
|
115005
|
+
var outputSchema94 = z94.discriminatedUnion("success", [
|
|
115006
|
+
z94.object({
|
|
115007
|
+
success: z94.literal(true),
|
|
115008
|
+
status: z94.number(),
|
|
115009
|
+
data: z94.union([
|
|
115010
|
+
z94.record(z94.string(), z94.unknown()),
|
|
115011
|
+
z94.array(z94.unknown())
|
|
114534
115012
|
])
|
|
114535
115013
|
}),
|
|
114536
|
-
|
|
114537
|
-
success:
|
|
114538
|
-
error:
|
|
115014
|
+
z94.object({
|
|
115015
|
+
success: z94.literal(false),
|
|
115016
|
+
error: z94.string()
|
|
114539
115017
|
})
|
|
114540
115018
|
]);
|
|
114541
115019
|
var requestTool53 = new ConnectorTool({
|
|
@@ -114566,8 +115044,8 @@ Field codes (tickets):
|
|
|
114566
115044
|
- priority: 1 Low, 2 Medium, 3 High, 4 Urgent
|
|
114567
115045
|
- status: 2 Open, 3 Pending, 4 Resolved, 5 Closed
|
|
114568
115046
|
- source: 1 Email, 2 Portal, 3 Phone, 7 Chat, 9 Feedback widget, 10 Outbound email`,
|
|
114569
|
-
inputSchema:
|
|
114570
|
-
outputSchema:
|
|
115047
|
+
inputSchema: inputSchema94,
|
|
115048
|
+
outputSchema: outputSchema94,
|
|
114571
115049
|
async execute({ connectionId, method, path: path5, body }, connections) {
|
|
114572
115050
|
const connection = connections.find((c6) => c6.id === connectionId);
|
|
114573
115051
|
if (!connection) {
|
|
@@ -114580,8 +115058,8 @@ Field codes (tickets):
|
|
|
114580
115058
|
`[connector-request] freshdesk/${connection.name}: ${method} ${path5}`
|
|
114581
115059
|
);
|
|
114582
115060
|
try {
|
|
114583
|
-
const apiKey =
|
|
114584
|
-
const domain =
|
|
115061
|
+
const apiKey = parameters77.apiKey.getValue(connection);
|
|
115062
|
+
const domain = parameters77.domain.getValue(connection);
|
|
114585
115063
|
const baseUrl = buildBaseUrl2(domain);
|
|
114586
115064
|
const normalizedPath = normalizeRequestPath(path5, BASE_PATH_SEGMENT13);
|
|
114587
115065
|
const url = `${baseUrl}${normalizedPath}`;
|
|
@@ -114620,14 +115098,14 @@ Field codes (tickets):
|
|
|
114620
115098
|
});
|
|
114621
115099
|
|
|
114622
115100
|
// ../connectors/src/connectors/freshdesk/index.ts
|
|
114623
|
-
var
|
|
115101
|
+
var tools77 = { request: requestTool53 };
|
|
114624
115102
|
var freshdeskConnector = new ConnectorPlugin({
|
|
114625
115103
|
slug: "freshdesk",
|
|
114626
115104
|
authType: AUTH_TYPES.API_KEY,
|
|
114627
115105
|
name: "Freshdesk",
|
|
114628
115106
|
description: "Connect to Freshdesk for customer support ticket, contact, and company data via API key.",
|
|
114629
115107
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/1PSjIfQJgTYmiWriNTx4uE/26905f4120713bda0afd0b23d02a154e/freshdesk-icon.png",
|
|
114630
|
-
parameters:
|
|
115108
|
+
parameters: parameters77,
|
|
114631
115109
|
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
114632
115110
|
categories: ["crm"],
|
|
114633
115111
|
onboarding: freshdeskOnboarding,
|
|
@@ -114787,7 +115265,7 @@ export default async function handler(c: Context) {
|
|
|
114787
115265
|
- \`status\`: 2=Open, 3=Pending, 4=Resolved, 5=Closed
|
|
114788
115266
|
- \`source\`: 1=Email, 2=Portal, 3=Phone, 7=Chat, 9=Feedback widget, 10=Outbound email`
|
|
114789
115267
|
},
|
|
114790
|
-
tools:
|
|
115268
|
+
tools: tools77
|
|
114791
115269
|
});
|
|
114792
115270
|
|
|
114793
115271
|
// ../connectors/src/connectors/freshsales/setup.ts
|
|
@@ -114807,7 +115285,7 @@ var freshsalesOnboarding = new ConnectorOnboarding({
|
|
|
114807
115285
|
});
|
|
114808
115286
|
|
|
114809
115287
|
// ../connectors/src/connectors/freshsales/parameters.ts
|
|
114810
|
-
var
|
|
115288
|
+
var parameters78 = {
|
|
114811
115289
|
bundleAlias: new ParameterDefinition({
|
|
114812
115290
|
slug: "bundle-alias",
|
|
114813
115291
|
name: "Freshsales Bundle Alias",
|
|
@@ -114829,7 +115307,7 @@ var parameters77 = {
|
|
|
114829
115307
|
};
|
|
114830
115308
|
|
|
114831
115309
|
// ../connectors/src/connectors/freshsales/tools/request.ts
|
|
114832
|
-
import { z as
|
|
115310
|
+
import { z as z95 } from "zod";
|
|
114833
115311
|
var BASE_PATH_SEGMENT14 = "/crm/sales/api";
|
|
114834
115312
|
var REQUEST_TIMEOUT_MS72 = 6e4;
|
|
114835
115313
|
function buildBaseUrl3(bundleAlias) {
|
|
@@ -114837,33 +115315,33 @@ function buildBaseUrl3(bundleAlias) {
|
|
|
114837
115315
|
const subdomain = trimmed.split(".")[0];
|
|
114838
115316
|
return `https://${subdomain}.myfreshworks.com${BASE_PATH_SEGMENT14}`;
|
|
114839
115317
|
}
|
|
114840
|
-
var
|
|
114841
|
-
toolUseIntent:
|
|
115318
|
+
var inputSchema95 = z95.object({
|
|
115319
|
+
toolUseIntent: z95.string().optional().describe(
|
|
114842
115320
|
"Brief description of what you intend to accomplish with this tool call"
|
|
114843
115321
|
),
|
|
114844
|
-
connectionId:
|
|
114845
|
-
method:
|
|
115322
|
+
connectionId: z95.string().describe("ID of the Freshsales connection to use"),
|
|
115323
|
+
method: z95.enum(["GET", "POST", "PUT", "DELETE"]).describe(
|
|
114846
115324
|
"HTTP method. GET for reading resources (including /lookup), POST for creating, PUT for updating, DELETE for removing."
|
|
114847
115325
|
),
|
|
114848
|
-
path:
|
|
115326
|
+
path: z95.string().describe(
|
|
114849
115327
|
"API path (e.g., '/contacts', '/contacts/filters', '/contacts/view/{view_id}', '/deals/{id}', '/lookup'). Append query parameters such as '?page=1&per_page=100'."
|
|
114850
115328
|
),
|
|
114851
|
-
body:
|
|
115329
|
+
body: z95.record(z95.string(), z95.unknown()).optional().describe(
|
|
114852
115330
|
'Request body (JSON). For creating a contact: { "contact": { "first_name": "...", "last_name": "...", "email": "..." } }. For lookup: { "q": "john@example.com", "f": "email", "entities": "contact" }.'
|
|
114853
115331
|
)
|
|
114854
115332
|
});
|
|
114855
|
-
var
|
|
114856
|
-
|
|
114857
|
-
success:
|
|
114858
|
-
status:
|
|
114859
|
-
data:
|
|
114860
|
-
|
|
114861
|
-
|
|
115333
|
+
var outputSchema95 = z95.discriminatedUnion("success", [
|
|
115334
|
+
z95.object({
|
|
115335
|
+
success: z95.literal(true),
|
|
115336
|
+
status: z95.number(),
|
|
115337
|
+
data: z95.union([
|
|
115338
|
+
z95.record(z95.string(), z95.unknown()),
|
|
115339
|
+
z95.array(z95.unknown())
|
|
114862
115340
|
])
|
|
114863
115341
|
}),
|
|
114864
|
-
|
|
114865
|
-
success:
|
|
114866
|
-
error:
|
|
115342
|
+
z95.object({
|
|
115343
|
+
success: z95.literal(false),
|
|
115344
|
+
error: z95.string()
|
|
114867
115345
|
})
|
|
114868
115346
|
]);
|
|
114869
115347
|
var requestTool54 = new ConnectorTool({
|
|
@@ -114896,8 +115374,8 @@ Common endpoints:
|
|
|
114896
115374
|
Pagination: 1-indexed \`page\` + \`per_page\` (default 25, max 100). View endpoints return \`{ contacts/sales_accounts/deals: [...], meta: { total_pages, total } }\`.
|
|
114897
115375
|
|
|
114898
115376
|
Includes: most GET endpoints accept \`?include=\` with a comma-separated list (\`owner\`, \`creator\`, \`deals\`, \`contacts\`, etc.) to inline related records.`,
|
|
114899
|
-
inputSchema:
|
|
114900
|
-
outputSchema:
|
|
115377
|
+
inputSchema: inputSchema95,
|
|
115378
|
+
outputSchema: outputSchema95,
|
|
114901
115379
|
async execute({ connectionId, method, path: path5, body }, connections) {
|
|
114902
115380
|
const connection = connections.find((c6) => c6.id === connectionId);
|
|
114903
115381
|
if (!connection) {
|
|
@@ -114910,8 +115388,8 @@ Includes: most GET endpoints accept \`?include=\` with a comma-separated list (\
|
|
|
114910
115388
|
`[connector-request] freshsales/${connection.name}: ${method} ${path5}`
|
|
114911
115389
|
);
|
|
114912
115390
|
try {
|
|
114913
|
-
const apiKey =
|
|
114914
|
-
const bundle =
|
|
115391
|
+
const apiKey = parameters78.apiKey.getValue(connection);
|
|
115392
|
+
const bundle = parameters78.bundleAlias.getValue(connection);
|
|
114915
115393
|
const baseUrl = buildBaseUrl3(bundle);
|
|
114916
115394
|
const normalizedPath = normalizeRequestPath(path5, BASE_PATH_SEGMENT14);
|
|
114917
115395
|
const url = `${baseUrl}${normalizedPath}`;
|
|
@@ -114949,14 +115427,14 @@ Includes: most GET endpoints accept \`?include=\` with a comma-separated list (\
|
|
|
114949
115427
|
});
|
|
114950
115428
|
|
|
114951
115429
|
// ../connectors/src/connectors/freshsales/index.ts
|
|
114952
|
-
var
|
|
115430
|
+
var tools78 = { request: requestTool54 };
|
|
114953
115431
|
var freshsalesConnector = new ConnectorPlugin({
|
|
114954
115432
|
slug: "freshsales",
|
|
114955
115433
|
authType: AUTH_TYPES.API_KEY,
|
|
114956
115434
|
name: "Freshsales",
|
|
114957
115435
|
description: "Connect to Freshsales / Freshworks CRM for contact, account, and deal data via API key.",
|
|
114958
115436
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/4UDOrFPM6wOFekbMVljjgl/4acc6060c3a1ff703980e6f4e76a3cd4/629b6c6f7c5cd817694c321f.png",
|
|
114959
|
-
parameters:
|
|
115437
|
+
parameters: parameters78,
|
|
114960
115438
|
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
114961
115439
|
categories: ["crm"],
|
|
114962
115440
|
onboarding: freshsalesOnboarding,
|
|
@@ -115128,7 +115606,7 @@ export default async function handler(c: Context) {
|
|
|
115128
115606
|
- GET \`/selector/lifecycle_stages\` \u2014 \u30E9\u30A4\u30D5\u30B5\u30A4\u30AF\u30EB\u30B9\u30C6\u30FC\u30B8
|
|
115129
115607
|
- GET \`/selector/territories\` / \`/selector/business_types\` / \`/selector/industry_types\` / \`/selector/contact_statuses\` / \`/selector/sales_activity_types\``
|
|
115130
115608
|
},
|
|
115131
|
-
tools:
|
|
115609
|
+
tools: tools78
|
|
115132
115610
|
});
|
|
115133
115611
|
|
|
115134
115612
|
// ../connectors/src/connectors/github/setup.ts
|
|
@@ -115154,7 +115632,7 @@ var githubOnboarding = new ConnectorOnboarding({
|
|
|
115154
115632
|
});
|
|
115155
115633
|
|
|
115156
115634
|
// ../connectors/src/connectors/github/parameters.ts
|
|
115157
|
-
var
|
|
115635
|
+
var parameters79 = {
|
|
115158
115636
|
personalAccessToken: new ParameterDefinition({
|
|
115159
115637
|
slug: "personal-access-token",
|
|
115160
115638
|
name: "GitHub Personal Access Token",
|
|
@@ -115177,42 +115655,42 @@ var parameters78 = {
|
|
|
115177
115655
|
var DEFAULT_BASE_URL = "https://api.github.com";
|
|
115178
115656
|
|
|
115179
115657
|
// ../connectors/src/connectors/github/tools/request.ts
|
|
115180
|
-
import { z as
|
|
115658
|
+
import { z as z96 } from "zod";
|
|
115181
115659
|
var REQUEST_TIMEOUT_MS73 = 6e4;
|
|
115182
115660
|
function resolveBaseUrl(connectionBaseUrl) {
|
|
115183
115661
|
const trimmed = connectionBaseUrl?.trim();
|
|
115184
115662
|
return trimmed && trimmed.replace(/\/+$/, "") || DEFAULT_BASE_URL;
|
|
115185
115663
|
}
|
|
115186
|
-
var
|
|
115187
|
-
toolUseIntent:
|
|
115664
|
+
var inputSchema96 = z96.object({
|
|
115665
|
+
toolUseIntent: z96.string().optional().describe(
|
|
115188
115666
|
"Brief description of what you intend to accomplish with this tool call"
|
|
115189
115667
|
),
|
|
115190
|
-
connectionId:
|
|
115191
|
-
method:
|
|
115668
|
+
connectionId: z96.string().describe("ID of the GitHub connection to use"),
|
|
115669
|
+
method: z96.enum(["GET", "POST", "PUT", "PATCH", "DELETE"]).describe(
|
|
115192
115670
|
"HTTP method. GET for reading, POST for creating, PATCH for partial updates, PUT for replacement (e.g. starring), DELETE for removal."
|
|
115193
115671
|
),
|
|
115194
|
-
path:
|
|
115672
|
+
path: z96.string().describe(
|
|
115195
115673
|
"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'."
|
|
115196
115674
|
),
|
|
115197
|
-
body:
|
|
115198
|
-
|
|
115199
|
-
|
|
115675
|
+
body: z96.union([
|
|
115676
|
+
z96.record(z96.string(), z96.unknown()),
|
|
115677
|
+
z96.array(z96.unknown())
|
|
115200
115678
|
]).optional().describe(
|
|
115201
115679
|
'Request body (JSON). Example creating an issue: { "title": "...", "body": "...", "labels": ["bug"] }.'
|
|
115202
115680
|
)
|
|
115203
115681
|
});
|
|
115204
|
-
var
|
|
115205
|
-
|
|
115206
|
-
success:
|
|
115207
|
-
status:
|
|
115208
|
-
data:
|
|
115209
|
-
|
|
115210
|
-
|
|
115682
|
+
var outputSchema96 = z96.discriminatedUnion("success", [
|
|
115683
|
+
z96.object({
|
|
115684
|
+
success: z96.literal(true),
|
|
115685
|
+
status: z96.number(),
|
|
115686
|
+
data: z96.union([
|
|
115687
|
+
z96.record(z96.string(), z96.unknown()),
|
|
115688
|
+
z96.array(z96.unknown())
|
|
115211
115689
|
])
|
|
115212
115690
|
}),
|
|
115213
|
-
|
|
115214
|
-
success:
|
|
115215
|
-
error:
|
|
115691
|
+
z96.object({
|
|
115692
|
+
success: z96.literal(false),
|
|
115693
|
+
error: z96.string()
|
|
115216
115694
|
})
|
|
115217
115695
|
]);
|
|
115218
115696
|
var requestTool55 = new ConnectorTool({
|
|
@@ -115250,8 +115728,8 @@ Common endpoints:
|
|
|
115250
115728
|
Pagination: 1-indexed \`page\` + \`per_page\` (max 100). The \`Link\` response header exposes \`rel="next"\`/\`rel="last"\` URLs.
|
|
115251
115729
|
|
|
115252
115730
|
Rate limits: 5,000 req/hr on REST endpoints, 30 req/min on /search/*. Inspect \`X-RateLimit-Remaining\` to throttle.`,
|
|
115253
|
-
inputSchema:
|
|
115254
|
-
outputSchema:
|
|
115731
|
+
inputSchema: inputSchema96,
|
|
115732
|
+
outputSchema: outputSchema96,
|
|
115255
115733
|
async execute({ connectionId, method, path: path5, body }, connections) {
|
|
115256
115734
|
const connection = connections.find((c6) => c6.id === connectionId);
|
|
115257
115735
|
if (!connection) {
|
|
@@ -115264,8 +115742,8 @@ Rate limits: 5,000 req/hr on REST endpoints, 30 req/min on /search/*. Inspect \`
|
|
|
115264
115742
|
`[connector-request] github/${connection.name}: ${method} ${path5}`
|
|
115265
115743
|
);
|
|
115266
115744
|
try {
|
|
115267
|
-
const token =
|
|
115268
|
-
const baseUrl = resolveBaseUrl(
|
|
115745
|
+
const token = parameters79.personalAccessToken.getValue(connection);
|
|
115746
|
+
const baseUrl = resolveBaseUrl(parameters79.baseUrl.tryGetValue(connection));
|
|
115269
115747
|
const trimmedPath = path5.trim().replace(/^\/+/, "/");
|
|
115270
115748
|
const url = `${baseUrl}${trimmedPath.startsWith("/") ? "" : "/"}${trimmedPath}`;
|
|
115271
115749
|
const controller = new AbortController();
|
|
@@ -115305,14 +115783,14 @@ Rate limits: 5,000 req/hr on REST endpoints, 30 req/min on /search/*. Inspect \`
|
|
|
115305
115783
|
});
|
|
115306
115784
|
|
|
115307
115785
|
// ../connectors/src/connectors/github/index.ts
|
|
115308
|
-
var
|
|
115786
|
+
var tools79 = { request: requestTool55 };
|
|
115309
115787
|
var githubConnector = new ConnectorPlugin({
|
|
115310
115788
|
slug: "github",
|
|
115311
115789
|
authType: AUTH_TYPES.PAT,
|
|
115312
115790
|
name: "GitHub",
|
|
115313
115791
|
description: "Connect to GitHub for repository, issue, pull request, commit, and search data via Personal Access Token (Classic or fine-grained).",
|
|
115314
115792
|
iconUrl: "https://images.ctfassets.net/9ncizv60xc5y/2flOAufkhDrLKuOQqEVS3/1f9dcf145680ef77aef149709263e2d4/github-icon.svg",
|
|
115315
|
-
parameters:
|
|
115793
|
+
parameters: parameters79,
|
|
115316
115794
|
releaseFlag: { dev1: true, dev2: true, prod: true },
|
|
115317
115795
|
categories: ["productivity"],
|
|
115318
115796
|
onboarding: githubOnboarding,
|
|
@@ -115532,7 +116010,7 @@ export default async function handler(c: Context) {
|
|
|
115532
116010
|
**\u30AF\u30A9\u30FC\u30BF**
|
|
115533
116011
|
- GET \`/rate_limit\` \u2014 REST / GraphQL / search \u306E\u6B8B\u30EC\u30FC\u30C8\u78BA\u8A8D`
|
|
115534
116012
|
},
|
|
115535
|
-
tools:
|
|
116013
|
+
tools: tools79
|
|
115536
116014
|
});
|
|
115537
116015
|
|
|
115538
116016
|
// ../connectors/src/connectors/registry.ts
|
|
@@ -115610,6 +116088,7 @@ var plugins = {
|
|
|
115610
116088
|
clickup: clickupConnector,
|
|
115611
116089
|
sqlserver: sqlserverConnector,
|
|
115612
116090
|
azureSql: azureSqlConnector,
|
|
116091
|
+
cosmosdb: cosmosdbConnector,
|
|
115613
116092
|
oracle: oracleConnector,
|
|
115614
116093
|
freshservice: freshserviceConnector,
|
|
115615
116094
|
freshdesk: freshdeskConnector,
|
|
@@ -115841,62 +116320,62 @@ import { watch as fsWatch2 } from "fs";
|
|
|
115841
116320
|
import path2 from "path";
|
|
115842
116321
|
|
|
115843
116322
|
// src/types/server-logic.ts
|
|
115844
|
-
import { z as
|
|
115845
|
-
var parameterMetaSchema =
|
|
115846
|
-
name:
|
|
115847
|
-
type:
|
|
115848
|
-
description:
|
|
115849
|
-
required:
|
|
115850
|
-
default:
|
|
115851
|
-
});
|
|
115852
|
-
var serverLogicCacheConfigSchema =
|
|
115853
|
-
ttl:
|
|
115854
|
-
staleWhileRevalidate:
|
|
115855
|
-
});
|
|
115856
|
-
var serverLogicSchemaObjectSchema =
|
|
115857
|
-
() =>
|
|
115858
|
-
type:
|
|
115859
|
-
format:
|
|
115860
|
-
description:
|
|
115861
|
-
nullable:
|
|
115862
|
-
enum:
|
|
116323
|
+
import { z as z97 } from "zod";
|
|
116324
|
+
var parameterMetaSchema = z97.object({
|
|
116325
|
+
name: z97.string(),
|
|
116326
|
+
type: z97.enum(["string", "number", "boolean"]),
|
|
116327
|
+
description: z97.string(),
|
|
116328
|
+
required: z97.boolean().optional(),
|
|
116329
|
+
default: z97.union([z97.string(), z97.number(), z97.boolean()]).optional()
|
|
116330
|
+
});
|
|
116331
|
+
var serverLogicCacheConfigSchema = z97.object({
|
|
116332
|
+
ttl: z97.number(),
|
|
116333
|
+
staleWhileRevalidate: z97.boolean().optional()
|
|
116334
|
+
});
|
|
116335
|
+
var serverLogicSchemaObjectSchema = z97.lazy(
|
|
116336
|
+
() => z97.object({
|
|
116337
|
+
type: z97.enum(["string", "number", "integer", "boolean", "object", "array", "null"]).optional(),
|
|
116338
|
+
format: z97.string().optional(),
|
|
116339
|
+
description: z97.string().optional(),
|
|
116340
|
+
nullable: z97.boolean().optional(),
|
|
116341
|
+
enum: z97.array(z97.union([z97.string(), z97.number(), z97.boolean(), z97.null()])).optional(),
|
|
115863
116342
|
items: serverLogicSchemaObjectSchema.optional(),
|
|
115864
|
-
properties:
|
|
115865
|
-
required:
|
|
115866
|
-
additionalProperties:
|
|
115867
|
-
minimum:
|
|
115868
|
-
maximum:
|
|
115869
|
-
minLength:
|
|
115870
|
-
maxLength:
|
|
115871
|
-
pattern:
|
|
116343
|
+
properties: z97.record(z97.string(), serverLogicSchemaObjectSchema).optional(),
|
|
116344
|
+
required: z97.array(z97.string()).optional(),
|
|
116345
|
+
additionalProperties: z97.union([z97.boolean(), serverLogicSchemaObjectSchema]).optional(),
|
|
116346
|
+
minimum: z97.number().optional(),
|
|
116347
|
+
maximum: z97.number().optional(),
|
|
116348
|
+
minLength: z97.number().optional(),
|
|
116349
|
+
maxLength: z97.number().optional(),
|
|
116350
|
+
pattern: z97.string().optional()
|
|
115872
116351
|
})
|
|
115873
116352
|
);
|
|
115874
|
-
var serverLogicMediaTypeSchema =
|
|
116353
|
+
var serverLogicMediaTypeSchema = z97.object({
|
|
115875
116354
|
schema: serverLogicSchemaObjectSchema.optional(),
|
|
115876
|
-
example:
|
|
116355
|
+
example: z97.unknown().optional()
|
|
115877
116356
|
});
|
|
115878
|
-
var serverLogicResponseSchema =
|
|
115879
|
-
description:
|
|
115880
|
-
content:
|
|
116357
|
+
var serverLogicResponseSchema = z97.object({
|
|
116358
|
+
description: z97.string().optional(),
|
|
116359
|
+
content: z97.record(z97.string(), serverLogicMediaTypeSchema).optional()
|
|
115881
116360
|
});
|
|
115882
116361
|
var jsonBaseFields = {
|
|
115883
|
-
description:
|
|
115884
|
-
parameters:
|
|
116362
|
+
description: z97.string(),
|
|
116363
|
+
parameters: z97.array(parameterMetaSchema).optional(),
|
|
115885
116364
|
response: serverLogicResponseSchema.optional(),
|
|
115886
116365
|
cache: serverLogicCacheConfigSchema.optional()
|
|
115887
116366
|
};
|
|
115888
|
-
var jsonSqlServerLogicSchema =
|
|
116367
|
+
var jsonSqlServerLogicSchema = z97.object({
|
|
115889
116368
|
...jsonBaseFields,
|
|
115890
|
-
type:
|
|
115891
|
-
query:
|
|
115892
|
-
connectionId:
|
|
116369
|
+
type: z97.literal("sql").optional(),
|
|
116370
|
+
query: z97.string(),
|
|
116371
|
+
connectionId: z97.string()
|
|
115893
116372
|
});
|
|
115894
|
-
var jsonTypeScriptServerLogicSchema =
|
|
116373
|
+
var jsonTypeScriptServerLogicSchema = z97.object({
|
|
115895
116374
|
...jsonBaseFields,
|
|
115896
|
-
type:
|
|
115897
|
-
handlerPath:
|
|
116375
|
+
type: z97.literal("typescript"),
|
|
116376
|
+
handlerPath: z97.string()
|
|
115898
116377
|
});
|
|
115899
|
-
var anyJsonServerLogicSchema =
|
|
116378
|
+
var anyJsonServerLogicSchema = z97.union([
|
|
115900
116379
|
jsonTypeScriptServerLogicSchema,
|
|
115901
116380
|
jsonSqlServerLogicSchema
|
|
115902
116381
|
]);
|