@tangle-network/agent-integrations 0.6.0 → 0.7.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1986,6 +1986,204 @@ function readMetaString3(meta, key) {
1986
1986
  return v;
1987
1987
  }
1988
1988
 
1989
+ // src/connectors/adapters/declarative-rest.ts
1990
+ function declarativeRestConnector(spec) {
1991
+ const capabilities = spec.capabilities.map(operationToCapability);
1992
+ const adapter = {
1993
+ manifest: {
1994
+ kind: spec.kind,
1995
+ displayName: spec.displayName,
1996
+ description: spec.description,
1997
+ auth: spec.auth,
1998
+ category: spec.category,
1999
+ defaultConsistencyModel: spec.defaultConsistencyModel,
2000
+ capabilities
2001
+ },
2002
+ async executeRead(inv) {
2003
+ const op = readOperation(spec, inv.capabilityName, "read");
2004
+ const response = await executeRestRequest(spec, op.request, inv);
2005
+ return {
2006
+ data: response.data,
2007
+ etag: response.etag,
2008
+ fetchedAt: Date.now()
2009
+ };
2010
+ },
2011
+ async executeMutation(inv) {
2012
+ const op = readOperation(spec, inv.capabilityName, "mutation");
2013
+ const response = await executeRestRequest(spec, op.request, inv);
2014
+ return {
2015
+ status: "committed",
2016
+ data: response.data,
2017
+ etagAfter: response.etag,
2018
+ committedAt: Date.now(),
2019
+ idempotentReplay: false
2020
+ };
2021
+ },
2022
+ async test(source) {
2023
+ if (!spec.test) return { ok: true };
2024
+ try {
2025
+ await executeRestRequest(spec, spec.test, {
2026
+ source,
2027
+ capabilityName: "__test__",
2028
+ args: {},
2029
+ idempotencyKey: "test"
2030
+ });
2031
+ return { ok: true };
2032
+ } catch (error) {
2033
+ return { ok: false, reason: error instanceof Error ? error.message : "unknown error" };
2034
+ }
2035
+ }
2036
+ };
2037
+ return adapter;
2038
+ }
2039
+ function operationToCapability(op) {
2040
+ const base = {
2041
+ name: op.name,
2042
+ description: op.description,
2043
+ parameters: op.parameters,
2044
+ requiredScopes: op.requiredScopes
2045
+ };
2046
+ if (op.class === "read") {
2047
+ return { ...base, class: "read" };
2048
+ }
2049
+ return {
2050
+ ...base,
2051
+ class: "mutation",
2052
+ cas: op.cas ?? "native-idempotency",
2053
+ externalEffect: op.externalEffect ?? true
2054
+ };
2055
+ }
2056
+ function readOperation(spec, name, expected) {
2057
+ const op = spec.capabilities.find((candidate) => candidate.name === name);
2058
+ if (!op || op.class !== expected) {
2059
+ throw new Error(`${spec.kind}: unknown ${expected} capability ${name}`);
2060
+ }
2061
+ return op;
2062
+ }
2063
+ async function executeRestRequest(spec, request, inv) {
2064
+ const baseUrl = resolveBaseUrl(spec.baseUrl, inv.source.metadata);
2065
+ const url = new URL(interpolate(request.path, inv.args), baseUrl.endsWith("/") ? baseUrl : `${baseUrl}/`);
2066
+ for (const [key, value] of Object.entries(request.query ?? {})) {
2067
+ const rendered = renderQueryValue(value, inv.args);
2068
+ if (rendered !== void 0 && rendered !== "") url.searchParams.set(key, String(rendered));
2069
+ }
2070
+ const headers = {
2071
+ accept: "application/json",
2072
+ ...spec.defaultHeaders,
2073
+ ...renderHeaders(request.headers ?? {}, inv.args)
2074
+ };
2075
+ applyCredentials(headers, url, spec.credentialPlacement ?? { kind: "bearer" }, inv.source.credentials);
2076
+ if (inv.expectedEtag) headers["if-match"] = inv.expectedEtag;
2077
+ if (request.method !== "GET" && request.method !== "DELETE") {
2078
+ headers["content-type"] = headers["content-type"] ?? "application/json";
2079
+ }
2080
+ const res = await fetch(url, {
2081
+ method: request.method,
2082
+ headers,
2083
+ body: request.method === "GET" || request.method === "DELETE" ? void 0 : JSON.stringify(resolveBody(request.body, inv.args)),
2084
+ signal: AbortSignal.timeout(2e4)
2085
+ });
2086
+ if (res.status === 401 || res.status === 403) {
2087
+ throw new CredentialsExpired(`${spec.displayName} rejected credentials (${res.status})`, inv.source.id);
2088
+ }
2089
+ if (res.status === 409 || res.status === 412) {
2090
+ return {
2091
+ data: {
2092
+ status: "conflict",
2093
+ message: await safeErrorText(res)
2094
+ },
2095
+ etag: res.headers.get("etag") ?? void 0
2096
+ };
2097
+ }
2098
+ if (res.status === 429) {
2099
+ return {
2100
+ data: {
2101
+ status: "rate-limited",
2102
+ retryAfter: res.headers.get("retry-after") ?? void 0,
2103
+ message: await safeErrorText(res)
2104
+ }
2105
+ };
2106
+ }
2107
+ if (!res.ok) {
2108
+ throw new Error(`${spec.kind} ${request.method} ${url.pathname} HTTP ${res.status}: ${(await safeErrorText(res)).slice(0, 300)}`);
2109
+ }
2110
+ const text = await res.text();
2111
+ const data = text ? JSON.parse(text) : null;
2112
+ return { data, etag: res.headers.get("etag") ?? void 0 };
2113
+ }
2114
+ function resolveBaseUrl(baseUrl, metadata) {
2115
+ if (typeof baseUrl === "string") return baseUrl;
2116
+ const value = metadata[baseUrl.metadataKey];
2117
+ if (typeof value === "string" && value.trim()) return value;
2118
+ if (baseUrl.fallback) return baseUrl.fallback;
2119
+ throw new Error(`missing metadata.${baseUrl.metadataKey} base URL`);
2120
+ }
2121
+ function applyCredentials(headers, url, placement, credentials) {
2122
+ const token = credentialToken(credentials);
2123
+ if (placement.kind === "bearer") headers.authorization = `Bearer ${token}`;
2124
+ if (placement.kind === "header") headers[placement.header] = `${placement.prefix ?? ""}${token}`;
2125
+ if (placement.kind === "query") url.searchParams.set(placement.parameter, token);
2126
+ }
2127
+ function credentialToken(credentials) {
2128
+ if (credentials.kind === "oauth2") return credentials.accessToken;
2129
+ if (credentials.kind === "api-key") return credentials.apiKey;
2130
+ throw new Error(`declarative REST connectors require oauth2 or api-key credentials, got ${credentials.kind}`);
2131
+ }
2132
+ function resolveBody(body, args) {
2133
+ if (!body || body === "args") return args;
2134
+ if (typeof body === "string") return renderValue(body, args);
2135
+ return renderObject(body, args);
2136
+ }
2137
+ function renderHeaders(headers, args) {
2138
+ return Object.fromEntries(Object.entries(headers).map(([key, value]) => [key, interpolate(value, args)]));
2139
+ }
2140
+ function renderObject(input, args) {
2141
+ return Object.fromEntries(Object.entries(input).map(([key, value]) => [key, renderValue(value, args)]));
2142
+ }
2143
+ function renderValue(value, args) {
2144
+ if (typeof value === "string") {
2145
+ const exact = value.match(/^\{([a-zA-Z0-9_.-]+)\}$/);
2146
+ if (exact) return readRequiredPath(args, exact[1]);
2147
+ return interpolate(value, args);
2148
+ }
2149
+ return value;
2150
+ }
2151
+ function renderQueryValue(value, args) {
2152
+ if (typeof value !== "string") return value;
2153
+ const exact = value.match(/^\{([a-zA-Z0-9_.-]+)\}$/);
2154
+ if (exact) return readPath(args, exact[1]);
2155
+ try {
2156
+ return interpolate(value, args);
2157
+ } catch {
2158
+ return void 0;
2159
+ }
2160
+ }
2161
+ function interpolate(template, args) {
2162
+ return template.replace(/\{([a-zA-Z0-9_.-]+)\}/g, (_match, key) => {
2163
+ const value = readPath(args, key);
2164
+ if (value === void 0 || value === null) {
2165
+ throw new Error(`missing required argument: ${key}`);
2166
+ }
2167
+ return encodeURIComponent(String(value));
2168
+ });
2169
+ }
2170
+ function readRequiredPath(input, path) {
2171
+ const value = readPath(input, path);
2172
+ if (value === void 0 || value === null) throw new Error(`missing required argument: ${path}`);
2173
+ return value;
2174
+ }
2175
+ function readPath(input, path) {
2176
+ return path.split(".").reduce((value, part) => {
2177
+ if (value && typeof value === "object" && part in value) {
2178
+ return value[part];
2179
+ }
2180
+ return void 0;
2181
+ }, input);
2182
+ }
2183
+ async function safeErrorText(res) {
2184
+ return await res.text().catch(() => res.statusText) || res.statusText;
2185
+ }
2186
+
1989
2187
  // src/connectors/adapters/twilio-sms.ts
1990
2188
  var API4 = "https://api.twilio.com/2010-04-01";
1991
2189
  var LOOKUP_API = "https://lookups.twilio.com/v1";
@@ -2654,6 +2852,349 @@ var slackEventsConnector = {
2654
2852
  }
2655
2853
  };
2656
2854
 
2855
+ // src/connectors/adapters/github.ts
2856
+ var repoParams = {
2857
+ type: "object",
2858
+ properties: {
2859
+ owner: { type: "string" },
2860
+ repo: { type: "string" }
2861
+ },
2862
+ required: ["owner", "repo"]
2863
+ };
2864
+ var githubConnector = declarativeRestConnector({
2865
+ kind: "github",
2866
+ displayName: "GitHub",
2867
+ description: "Search repositories/issues and create or update GitHub issues through a user-scoped token.",
2868
+ auth: { kind: "api-key", hint: "GitHub fine-grained personal access token or installation token." },
2869
+ category: "other",
2870
+ defaultConsistencyModel: "authoritative",
2871
+ baseUrl: "https://api.github.com",
2872
+ defaultHeaders: {
2873
+ "x-github-api-version": "2022-11-28"
2874
+ },
2875
+ test: { method: "GET", path: "/user" },
2876
+ capabilities: [
2877
+ {
2878
+ name: "repositories.get",
2879
+ class: "read",
2880
+ description: "Read repository metadata.",
2881
+ parameters: repoParams,
2882
+ request: { method: "GET", path: "/repos/{owner}/{repo}" }
2883
+ },
2884
+ {
2885
+ name: "issues.search",
2886
+ class: "read",
2887
+ description: "Search GitHub issues and pull requests.",
2888
+ parameters: {
2889
+ type: "object",
2890
+ properties: { q: { type: "string" }, per_page: { type: "integer", minimum: 1, maximum: 100 } },
2891
+ required: ["q"]
2892
+ },
2893
+ request: { method: "GET", path: "/search/issues", query: { q: "{q}", per_page: "{per_page}" } }
2894
+ },
2895
+ {
2896
+ name: "issues.create",
2897
+ class: "mutation",
2898
+ description: "Create an issue in a repository.",
2899
+ parameters: {
2900
+ type: "object",
2901
+ properties: {
2902
+ owner: { type: "string" },
2903
+ repo: { type: "string" },
2904
+ title: { type: "string" },
2905
+ body: { type: "string" },
2906
+ labels: { type: "array", items: { type: "string" } }
2907
+ },
2908
+ required: ["owner", "repo", "title"]
2909
+ },
2910
+ request: { method: "POST", path: "/repos/{owner}/{repo}/issues", body: "args" },
2911
+ cas: "native-idempotency"
2912
+ },
2913
+ {
2914
+ name: "issues.update",
2915
+ class: "mutation",
2916
+ description: "Update an issue by number.",
2917
+ parameters: {
2918
+ type: "object",
2919
+ properties: {
2920
+ owner: { type: "string" },
2921
+ repo: { type: "string" },
2922
+ issue_number: { type: "integer" },
2923
+ title: { type: "string" },
2924
+ body: { type: "string" },
2925
+ state: { type: "string", enum: ["open", "closed"] }
2926
+ },
2927
+ required: ["owner", "repo", "issue_number"]
2928
+ },
2929
+ request: { method: "PATCH", path: "/repos/{owner}/{repo}/issues/{issue_number}", body: "args" },
2930
+ cas: "etag-if-match"
2931
+ }
2932
+ ]
2933
+ });
2934
+
2935
+ // src/connectors/adapters/gitlab.ts
2936
+ var gitlabConnector = declarativeRestConnector({
2937
+ kind: "gitlab",
2938
+ displayName: "GitLab",
2939
+ description: "Search GitLab projects/issues and create or update issues through a personal, project, or group token.",
2940
+ auth: { kind: "api-key", hint: "GitLab access token with api/read_api scope." },
2941
+ category: "other",
2942
+ defaultConsistencyModel: "authoritative",
2943
+ baseUrl: { metadataKey: "baseUrl", fallback: "https://gitlab.com/api/v4" },
2944
+ credentialPlacement: { kind: "header", header: "PRIVATE-TOKEN" },
2945
+ test: { method: "GET", path: "/user" },
2946
+ capabilities: [
2947
+ {
2948
+ name: "projects.search",
2949
+ class: "read",
2950
+ description: "Search projects visible to the token.",
2951
+ parameters: {
2952
+ type: "object",
2953
+ properties: { search: { type: "string" }, per_page: { type: "integer", minimum: 1, maximum: 100 } },
2954
+ required: ["search"]
2955
+ },
2956
+ request: { method: "GET", path: "/projects", query: { search: "{search}", per_page: "{per_page}" } }
2957
+ },
2958
+ {
2959
+ name: "issues.search",
2960
+ class: "read",
2961
+ description: "Search issues in a project.",
2962
+ parameters: {
2963
+ type: "object",
2964
+ properties: { projectId: { type: "string" }, search: { type: "string" }, per_page: { type: "integer" } },
2965
+ required: ["projectId", "search"]
2966
+ },
2967
+ request: { method: "GET", path: "/projects/{projectId}/issues", query: { search: "{search}", per_page: "{per_page}" } }
2968
+ },
2969
+ {
2970
+ name: "issues.create",
2971
+ class: "mutation",
2972
+ description: "Create a GitLab project issue.",
2973
+ parameters: {
2974
+ type: "object",
2975
+ properties: { projectId: { type: "string" }, title: { type: "string" }, description: { type: "string" } },
2976
+ required: ["projectId", "title"]
2977
+ },
2978
+ request: { method: "POST", path: "/projects/{projectId}/issues", body: "args" },
2979
+ cas: "native-idempotency"
2980
+ },
2981
+ {
2982
+ name: "issues.update",
2983
+ class: "mutation",
2984
+ description: "Update a GitLab issue.",
2985
+ parameters: {
2986
+ type: "object",
2987
+ properties: { projectId: { type: "string" }, issueIid: { type: "integer" }, title: { type: "string" }, description: { type: "string" }, state_event: { type: "string" } },
2988
+ required: ["projectId", "issueIid"]
2989
+ },
2990
+ request: { method: "PUT", path: "/projects/{projectId}/issues/{issueIid}", body: "args" },
2991
+ cas: "etag-if-match"
2992
+ }
2993
+ ]
2994
+ });
2995
+
2996
+ // src/connectors/adapters/airtable.ts
2997
+ var baseTableParams = {
2998
+ type: "object",
2999
+ properties: {
3000
+ baseId: { type: "string" },
3001
+ tableName: { type: "string" }
3002
+ },
3003
+ required: ["baseId", "tableName"]
3004
+ };
3005
+ var airtableConnector = declarativeRestConnector({
3006
+ kind: "airtable",
3007
+ displayName: "Airtable",
3008
+ description: "Query and update Airtable records for lightweight operational databases.",
3009
+ auth: { kind: "api-key", hint: "Airtable personal access token." },
3010
+ category: "spreadsheet",
3011
+ defaultConsistencyModel: "authoritative",
3012
+ baseUrl: "https://api.airtable.com",
3013
+ test: { method: "GET", path: "/v0/meta/whoami" },
3014
+ capabilities: [
3015
+ {
3016
+ name: "records.list",
3017
+ class: "read",
3018
+ description: "List records in a table.",
3019
+ parameters: {
3020
+ ...baseTableParams,
3021
+ properties: {
3022
+ ...baseTableParams.properties,
3023
+ maxRecords: { type: "integer", minimum: 1, maximum: 100 },
3024
+ filterByFormula: { type: "string" }
3025
+ }
3026
+ },
3027
+ request: { method: "GET", path: "/v0/{baseId}/{tableName}", query: { maxRecords: "{maxRecords}", filterByFormula: "{filterByFormula}" } }
3028
+ },
3029
+ {
3030
+ name: "records.get",
3031
+ class: "read",
3032
+ description: "Read a single Airtable record.",
3033
+ parameters: {
3034
+ type: "object",
3035
+ properties: { baseId: { type: "string" }, tableName: { type: "string" }, recordId: { type: "string" } },
3036
+ required: ["baseId", "tableName", "recordId"]
3037
+ },
3038
+ request: { method: "GET", path: "/v0/{baseId}/{tableName}/{recordId}" }
3039
+ },
3040
+ {
3041
+ name: "records.create",
3042
+ class: "mutation",
3043
+ description: "Create an Airtable record.",
3044
+ parameters: {
3045
+ type: "object",
3046
+ properties: { baseId: { type: "string" }, tableName: { type: "string" }, fields: { type: "object" } },
3047
+ required: ["baseId", "tableName", "fields"]
3048
+ },
3049
+ request: { method: "POST", path: "/v0/{baseId}/{tableName}", body: { fields: "{fields}" } },
3050
+ cas: "native-idempotency"
3051
+ },
3052
+ {
3053
+ name: "records.update",
3054
+ class: "mutation",
3055
+ description: "Update an Airtable record.",
3056
+ parameters: {
3057
+ type: "object",
3058
+ properties: { baseId: { type: "string" }, tableName: { type: "string" }, recordId: { type: "string" }, fields: { type: "object" } },
3059
+ required: ["baseId", "tableName", "recordId", "fields"]
3060
+ },
3061
+ request: { method: "PATCH", path: "/v0/{baseId}/{tableName}/{recordId}", body: { fields: "{fields}" } },
3062
+ cas: "optimistic-read-verify"
3063
+ }
3064
+ ]
3065
+ });
3066
+
3067
+ // src/connectors/adapters/asana.ts
3068
+ var asanaConnector = declarativeRestConnector({
3069
+ kind: "asana",
3070
+ displayName: "Asana",
3071
+ description: "Search projects/tasks and create or update Asana tasks.",
3072
+ auth: { kind: "api-key", hint: "Asana personal access token." },
3073
+ category: "other",
3074
+ defaultConsistencyModel: "authoritative",
3075
+ baseUrl: "https://app.asana.com/api/1.0",
3076
+ test: { method: "GET", path: "/users/me" },
3077
+ capabilities: [
3078
+ {
3079
+ name: "projects.search",
3080
+ class: "read",
3081
+ description: "List or search projects in a workspace.",
3082
+ parameters: {
3083
+ type: "object",
3084
+ properties: { workspace: { type: "string" }, archived: { type: "boolean" }, limit: { type: "integer" } },
3085
+ required: ["workspace"]
3086
+ },
3087
+ request: { method: "GET", path: "/projects", query: { workspace: "{workspace}", archived: "{archived}", limit: "{limit}" } }
3088
+ },
3089
+ {
3090
+ name: "tasks.search",
3091
+ class: "read",
3092
+ description: "Search tasks in a workspace.",
3093
+ parameters: {
3094
+ type: "object",
3095
+ properties: { workspace: { type: "string" }, text: { type: "string" }, limit: { type: "integer" } },
3096
+ required: ["workspace"]
3097
+ },
3098
+ request: { method: "GET", path: "/workspaces/{workspace}/tasks/search", query: { text: "{text}", limit: "{limit}" } }
3099
+ },
3100
+ {
3101
+ name: "tasks.create",
3102
+ class: "mutation",
3103
+ description: "Create an Asana task.",
3104
+ parameters: {
3105
+ type: "object",
3106
+ properties: { data: { type: "object" } },
3107
+ required: ["data"]
3108
+ },
3109
+ request: { method: "POST", path: "/tasks", body: { data: "{data}" } },
3110
+ cas: "native-idempotency"
3111
+ },
3112
+ {
3113
+ name: "tasks.update",
3114
+ class: "mutation",
3115
+ description: "Update an Asana task.",
3116
+ parameters: {
3117
+ type: "object",
3118
+ properties: { taskGid: { type: "string" }, data: { type: "object" } },
3119
+ required: ["taskGid", "data"]
3120
+ },
3121
+ request: { method: "PUT", path: "/tasks/{taskGid}", body: { data: "{data}" } },
3122
+ cas: "optimistic-read-verify"
3123
+ }
3124
+ ]
3125
+ });
3126
+
3127
+ // src/connectors/adapters/salesforce.ts
3128
+ var salesforceConnector = declarativeRestConnector({
3129
+ kind: "salesforce",
3130
+ displayName: "Salesforce",
3131
+ description: "Query Salesforce records with SOQL and create or update sObjects.",
3132
+ auth: {
3133
+ kind: "oauth2",
3134
+ authorizationUrl: "https://login.salesforce.com/services/oauth2/authorize",
3135
+ tokenUrl: "https://login.salesforce.com/services/oauth2/token",
3136
+ scopes: ["api", "refresh_token"],
3137
+ clientIdEnv: "SALESFORCE_OAUTH_CLIENT_ID",
3138
+ clientSecretEnv: "SALESFORCE_OAUTH_CLIENT_SECRET"
3139
+ },
3140
+ category: "crm",
3141
+ defaultConsistencyModel: "authoritative",
3142
+ baseUrl: { metadataKey: "instanceUrl" },
3143
+ test: { method: "GET", path: "/services/data/v61.0/" },
3144
+ capabilities: [
3145
+ {
3146
+ name: "records.query",
3147
+ class: "read",
3148
+ description: "Run a SOQL query.",
3149
+ parameters: {
3150
+ type: "object",
3151
+ properties: { q: { type: "string" } },
3152
+ required: ["q"]
3153
+ },
3154
+ request: { method: "GET", path: "/services/data/v61.0/query", query: { q: "{q}" } },
3155
+ requiredScopes: ["api"]
3156
+ },
3157
+ {
3158
+ name: "records.get",
3159
+ class: "read",
3160
+ description: "Read a Salesforce sObject record.",
3161
+ parameters: {
3162
+ type: "object",
3163
+ properties: { objectName: { type: "string" }, recordId: { type: "string" } },
3164
+ required: ["objectName", "recordId"]
3165
+ },
3166
+ request: { method: "GET", path: "/services/data/v61.0/sobjects/{objectName}/{recordId}" },
3167
+ requiredScopes: ["api"]
3168
+ },
3169
+ {
3170
+ name: "records.create",
3171
+ class: "mutation",
3172
+ description: "Create a Salesforce sObject record.",
3173
+ parameters: {
3174
+ type: "object",
3175
+ properties: { objectName: { type: "string" }, fields: { type: "object" } },
3176
+ required: ["objectName", "fields"]
3177
+ },
3178
+ request: { method: "POST", path: "/services/data/v61.0/sobjects/{objectName}", body: "{fields}" },
3179
+ cas: "native-idempotency",
3180
+ requiredScopes: ["api"]
3181
+ },
3182
+ {
3183
+ name: "records.update",
3184
+ class: "mutation",
3185
+ description: "Update a Salesforce sObject record.",
3186
+ parameters: {
3187
+ type: "object",
3188
+ properties: { objectName: { type: "string" }, recordId: { type: "string" }, fields: { type: "object" } },
3189
+ required: ["objectName", "recordId", "fields"]
3190
+ },
3191
+ request: { method: "PATCH", path: "/services/data/v61.0/sobjects/{objectName}/{recordId}", body: "{fields}" },
3192
+ cas: "etag-if-match",
3193
+ requiredScopes: ["api"]
3194
+ }
3195
+ ]
3196
+ });
3197
+
2657
3198
  // src/catalog.ts
2658
3199
  var riskRank = {
2659
3200
  read: 0,
@@ -3874,6 +4415,8 @@ export {
3874
4415
  ResourceContention,
3875
4416
  StaticIntegrationPolicyEngine,
3876
4417
  _resetPendingFlowsForTests,
4418
+ airtableConnector,
4419
+ asanaConnector,
3877
4420
  assertValidConnectorManifest,
3878
4421
  buildApprovalRequest,
3879
4422
  buildIntegrationCoverageConnectors,
@@ -3884,8 +4427,11 @@ export {
3884
4427
  createDefaultIntegrationPolicyEngine,
3885
4428
  createHttpIntegrationProvider,
3886
4429
  createMockIntegrationProvider,
4430
+ declarativeRestConnector,
3887
4431
  exchangeAuthorizationCode,
3888
4432
  firstHeader,
4433
+ githubConnector,
4434
+ gitlabConnector,
3889
4435
  googleCalendar,
3890
4436
  googleSheets,
3891
4437
  hubspot,
@@ -3906,6 +4452,7 @@ export {
3906
4452
  redactCapability,
3907
4453
  redactInvocationEnvelope,
3908
4454
  refreshAccessToken,
4455
+ salesforceConnector,
3909
4456
  sanitizeConnection,
3910
4457
  searchIntegrationTools,
3911
4458
  signCapability,