@commandable/mcp 0.4.0 → 0.10.0

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.
Files changed (74) hide show
  1. package/.output/nitro.json +1 -1
  2. package/.output/public/_nuxt/{Sdkz9rYy.js → BD6mASiY.js} +1 -1
  3. package/.output/public/_nuxt/{Ctwv5nxD.js → BUmYUDQu.js} +3 -3
  4. package/.output/public/_nuxt/CjAs3eBq.js +1 -0
  5. package/.output/public/_nuxt/{CBR-0oRi.js → D9wFDhac.js} +1 -1
  6. package/.output/public/_nuxt/{KqToXREt.js → DRfk9W3W.js} +1 -1
  7. package/.output/public/_nuxt/DSWYWRXT.js +59 -0
  8. package/.output/public/_nuxt/{DOIzs5t4.js → VvnbcAzZ.js} +1 -1
  9. package/.output/public/_nuxt/builds/latest.json +1 -1
  10. package/.output/public/_nuxt/builds/meta/0857a55b-f766-4fe6-86be-9bd9d857861a.json +1 -0
  11. package/.output/server/chunks/build/{_id_-Co8jGxsD.mjs → _id_-DA3Q8jun.mjs} +603 -24
  12. package/.output/server/chunks/build/_id_-DA3Q8jun.mjs.map +1 -0
  13. package/.output/server/chunks/build/client.precomputed.mjs +1 -1
  14. package/.output/server/chunks/build/error-404-D1k2kWid.mjs +3 -5
  15. package/.output/server/chunks/build/error-500-D2K2rAfl.mjs +3 -5
  16. package/.output/server/chunks/build/fetch-aDh21opM.mjs +1 -1
  17. package/.output/server/chunks/build/{index-BxsJPthj.mjs → index-F5lAFSQk.mjs} +7 -7
  18. package/.output/server/chunks/build/index-F5lAFSQk.mjs.map +1 -0
  19. package/.output/server/chunks/build/index-ycGPozML.mjs +3 -5
  20. package/.output/server/chunks/build/server.mjs +6 -8
  21. package/.output/server/chunks/nitro/nitro.mjs +4181 -2926
  22. package/.output/server/chunks/nitro/nitro.mjs.map +1 -1
  23. package/.output/server/chunks/routes/api/_commandable/status.get.mjs +3 -5
  24. package/.output/server/chunks/routes/api/_commandable/status.get.mjs.map +1 -1
  25. package/.output/server/chunks/routes/api/catalog/_type/tools.get.mjs +3 -5
  26. package/.output/server/chunks/routes/api/catalog/_type/tools.get.mjs.map +1 -1
  27. package/.output/server/chunks/routes/api/catalog/_type/toolsets.get.mjs +3 -5
  28. package/.output/server/chunks/routes/api/catalog/_type/toolsets.get.mjs.map +1 -1
  29. package/.output/server/chunks/routes/api/catalog.get.mjs +3 -5
  30. package/.output/server/chunks/routes/api/catalog.get.mjs.map +1 -1
  31. package/.output/server/chunks/routes/api/index.get.mjs +3 -5
  32. package/.output/server/chunks/routes/api/index.get.mjs.map +1 -1
  33. package/.output/server/chunks/routes/api/index.post.mjs +5 -5
  34. package/.output/server/chunks/routes/api/index.post.mjs.map +1 -1
  35. package/.output/server/chunks/routes/api/integrations/_id/credentials-config.get.mjs +3 -5
  36. package/.output/server/chunks/routes/api/integrations/_id/credentials-config.get.mjs.map +1 -1
  37. package/.output/server/chunks/routes/api/integrations/_id/credentials-status.get.mjs +3 -5
  38. package/.output/server/chunks/routes/api/integrations/_id/credentials-status.get.mjs.map +1 -1
  39. package/.output/server/chunks/routes/api/integrations/_id/credentials.delete.mjs +3 -5
  40. package/.output/server/chunks/routes/api/integrations/_id/credentials.delete.mjs.map +1 -1
  41. package/.output/server/chunks/routes/api/integrations/_id/credentials.post.mjs +3 -5
  42. package/.output/server/chunks/routes/api/integrations/_id/credentials.post.mjs.map +1 -1
  43. package/.output/server/chunks/routes/api/integrations/_id/permissions.post.mjs +3 -5
  44. package/.output/server/chunks/routes/api/integrations/_id/permissions.post.mjs.map +1 -1
  45. package/.output/server/chunks/routes/api/integrations/_id/tools.delete.mjs +3 -5
  46. package/.output/server/chunks/routes/api/integrations/_id/tools.delete.mjs.map +1 -1
  47. package/.output/server/chunks/routes/api/integrations/_id/tools.get.mjs +3 -5
  48. package/.output/server/chunks/routes/api/integrations/_id/tools.get.mjs.map +1 -1
  49. package/.output/server/chunks/routes/api/integrations/_id/toolsets.get.mjs +3 -5
  50. package/.output/server/chunks/routes/api/integrations/_id/toolsets.get.mjs.map +1 -1
  51. package/.output/server/chunks/routes/api/integrations/_id/toolsets.post.mjs +3 -5
  52. package/.output/server/chunks/routes/api/integrations/_id/toolsets.post.mjs.map +1 -1
  53. package/.output/server/chunks/routes/api/integrations/_id/variant-options.post.mjs +72 -0
  54. package/.output/server/chunks/routes/api/integrations/_id/variant-options.post.mjs.map +1 -0
  55. package/.output/server/chunks/routes/api/integrations/_id_.delete.mjs +3 -5
  56. package/.output/server/chunks/routes/api/integrations/_id_.delete.mjs.map +1 -1
  57. package/.output/server/chunks/routes/health.get.mjs +3 -5
  58. package/.output/server/chunks/routes/health.get.mjs.map +1 -1
  59. package/.output/server/chunks/routes/mcp/create.mjs +4 -6
  60. package/.output/server/chunks/routes/mcp/create.mjs.map +1 -1
  61. package/.output/server/chunks/routes/mcp/static.mjs +4 -6
  62. package/.output/server/chunks/routes/mcp/static.mjs.map +1 -1
  63. package/.output/server/chunks/routes/mcp.mjs +4 -6
  64. package/.output/server/chunks/routes/mcp.mjs.map +1 -1
  65. package/.output/server/chunks/routes/renderer.mjs +1 -1
  66. package/.output/server/index.mjs +4 -6
  67. package/.output/server/index.mjs.map +1 -1
  68. package/.output/server/package.json +1 -1
  69. package/package.json +2 -2
  70. package/.output/public/_nuxt/CYsCQznM.js +0 -59
  71. package/.output/public/_nuxt/DKO0MviJ.js +0 -1
  72. package/.output/public/_nuxt/builds/meta/dd3dc5d0-c600-485d-b098-2f5b9facdf63.json +0 -1
  73. package/.output/server/chunks/build/_id_-Co8jGxsD.mjs.map +0 -1
  74. package/.output/server/chunks/build/index-BxsJPthj.mjs.map +0 -1
@@ -1,7 +1,7 @@
1
1
  import { k as useRoute, m as _sfc_main$b, i as _sfc_main$h, a as __nuxt_component_0$1, g as _sfc_main$m, j as _sfc_main$9, _ as _export_sfc, n as navigateTo, b as useAppConfig, c as useComponentUI, d as useFormField, e as useFieldGroup, f as useComponentIcons, t as tv, h as _sfc_main$k, l as looseToNumber } from './server.mjs';
2
- import { u as useFetch, _ as _sfc_main$4, a as _sfc_main$3, b as __nuxt_component_3, c as _sfc_main$2$1, d as _sfc_main$1$1 } from './fetch-aDh21opM.mjs';
2
+ import { u as useFetch, _ as _sfc_main$4, a as _sfc_main$3$1, b as __nuxt_component_3, c as _sfc_main$2$1, d as _sfc_main$1$1 } from './fetch-aDh21opM.mjs';
3
3
  import { defineComponent, withAsyncContext, computed, ref, watch, mergeProps, withCtx, unref, createTextVNode, createVNode, toDisplayString, isRef, openBlock, createBlock, Fragment, createCommentVNode, reactive, renderList, useSlots, useTemplateRef, renderSlot, useSSRContext } from 'vue';
4
- import { ssrRenderComponent, ssrInterpolate, ssrRenderClass, ssrRenderAttrs, ssrRenderList, ssrRenderSlot } from 'vue/server-renderer';
4
+ import { ssrRenderComponent, ssrInterpolate, ssrRenderClass, ssrRenderAttrs, ssrRenderList, ssrIncludeBooleanAttr, ssrRenderSlot } from 'vue/server-renderer';
5
5
  import { Primitive } from 'reka-ui';
6
6
  import { useVModel } from '@vueuse/core';
7
7
  import { marked } from 'marked';
@@ -11,27 +11,25 @@ import '@modelcontextprotocol/sdk/server/index.js';
11
11
  import '@modelcontextprotocol/sdk/server/streamableHttp.js';
12
12
  import '@modelcontextprotocol/sdk/types.js';
13
13
  import 'fastest-levenshtein';
14
- import 'node:url';
15
- import 'node:vm';
16
14
  import 'turndown';
17
15
  import 'node:util';
18
16
  import 'node:child_process';
19
17
  import 'node:fs/promises';
20
18
  import 'node:path';
21
19
  import 'node:os';
22
- import 'node:fs';
23
20
  import 'drizzle-orm';
21
+ import 'node:url';
22
+ import 'node:vm';
24
23
  import 'node:buffer';
25
24
  import 'google-auth-library';
26
25
  import 'node:http';
27
26
  import 'node:https';
28
27
  import 'node:events';
28
+ import 'node:fs';
29
29
  import 'better-sqlite3';
30
30
  import 'drizzle-orm/better-sqlite3';
31
31
  import 'drizzle-orm/node-postgres';
32
32
  import 'pg';
33
- import 'drizzle-orm/better-sqlite3/migrator';
34
- import 'drizzle-orm/node-postgres/migrator';
35
33
  import 'drizzle-orm/sqlite-core';
36
34
  import 'drizzle-orm/pg-core';
37
35
  import 'node:process';
@@ -340,7 +338,7 @@ const theme = {
340
338
  "variant": "outline"
341
339
  }
342
340
  };
343
- const _sfc_main$2 = /* @__PURE__ */ Object.assign({ inheritAttrs: false }, {
341
+ const _sfc_main$3 = /* @__PURE__ */ Object.assign({ inheritAttrs: false }, {
344
342
  __name: "UInput",
345
343
  __ssrInlineRender: true,
346
344
  props: {
@@ -565,13 +563,13 @@ const _sfc_main$2 = /* @__PURE__ */ Object.assign({ inheritAttrs: false }, {
565
563
  };
566
564
  }
567
565
  });
568
- const _sfc_setup$2 = _sfc_main$2.setup;
569
- _sfc_main$2.setup = (props, ctx) => {
566
+ const _sfc_setup$3 = _sfc_main$3.setup;
567
+ _sfc_main$3.setup = (props, ctx) => {
570
568
  const ssrContext = useSSRContext();
571
569
  (ssrContext.modules || (ssrContext.modules = /* @__PURE__ */ new Set())).add("../../node_modules/@nuxt/ui/dist/runtime/components/Input.vue");
572
- return _sfc_setup$2 ? _sfc_setup$2(props, ctx) : void 0;
570
+ return _sfc_setup$3 ? _sfc_setup$3(props, ctx) : void 0;
573
571
  };
574
- const _sfc_main$1 = /* @__PURE__ */ defineComponent({
572
+ const _sfc_main$2 = /* @__PURE__ */ defineComponent({
575
573
  __name: "IntegrationCredentials",
576
574
  __ssrInlineRender: true,
577
575
  props: {
@@ -682,7 +680,7 @@ const _sfc_main$1 = /* @__PURE__ */ defineComponent({
682
680
  const _component_UModal = _sfc_main$9;
683
681
  const _component_UFormField = _sfc_main$2$1;
684
682
  const _component_USelect = _sfc_main$1$1;
685
- const _component_UInput = _sfc_main$2;
683
+ const _component_UInput = _sfc_main$3;
686
684
  _push(`<div${ssrRenderAttrs(_attrs)} data-v-7de84f63>`);
687
685
  if (unref(loading)) {
688
686
  _push(`<div class="flex items-center gap-2 text-sm text-muted" data-v-7de84f63>`);
@@ -992,18 +990,437 @@ const _sfc_main$1 = /* @__PURE__ */ defineComponent({
992
990
  };
993
991
  }
994
992
  });
993
+ const _sfc_setup$2 = _sfc_main$2.setup;
994
+ _sfc_main$2.setup = (props, ctx) => {
995
+ const ssrContext = useSSRContext();
996
+ (ssrContext.modules || (ssrContext.modules = /* @__PURE__ */ new Set())).add("components/IntegrationCredentials.vue");
997
+ return _sfc_setup$2 ? _sfc_setup$2(props, ctx) : void 0;
998
+ };
999
+ const __nuxt_component_6 = /* @__PURE__ */ Object.assign(_export_sfc(_sfc_main$2, [["__scopeId", "data-v-7de84f63"]]), { __name: "IntegrationCredentials" });
1000
+ const _sfc_main$1 = /* @__PURE__ */ defineComponent({
1001
+ __name: "IntegrationVariantConfigDialog",
1002
+ __ssrInlineRender: true,
1003
+ props: {
1004
+ open: { type: Boolean },
1005
+ integrationId: {},
1006
+ currentType: {},
1007
+ baseType: {},
1008
+ baseName: {},
1009
+ variants: {},
1010
+ saving: { type: Boolean }
1011
+ },
1012
+ emits: ["update:open", "confirm"],
1013
+ setup(__props, { emit: __emit }) {
1014
+ const props = __props;
1015
+ const emit = __emit;
1016
+ const isOpen = computed({
1017
+ get: () => props.open,
1018
+ set: (value) => emit("update:open", value)
1019
+ });
1020
+ const selectedType = ref(props.currentType);
1021
+ const pickerOptions = reactive({});
1022
+ const singleSelections = reactive({});
1023
+ const multiSelections = reactive({});
1024
+ const loadingKeys = reactive({});
1025
+ const loadError = ref(null);
1026
+ const variantTypeItems = computed(() => [
1027
+ { label: `Full ${props.baseName}`, value: props.baseType },
1028
+ ...props.variants.map((variant) => ({
1029
+ label: variant.label || variant.type,
1030
+ value: variant.type
1031
+ }))
1032
+ ]);
1033
+ const activeVariant = computed(
1034
+ () => props.variants.find((variant) => variant.type === selectedType.value) ?? null
1035
+ );
1036
+ const activeVariantConfig = computed(() => activeVariant.value?.variantConfig ?? []);
1037
+ const selectionSignature = computed(
1038
+ () => activeVariantConfig.value.map((item) => {
1039
+ if (item.selectionMode === "multi")
1040
+ return `${item.key}:${(multiSelections[item.key] || []).join(",")}`;
1041
+ return `${item.key}:${singleSelections[item.key] || ""}`;
1042
+ }).join("|")
1043
+ );
1044
+ function clearSelections() {
1045
+ for (const key of Object.keys(singleSelections))
1046
+ delete singleSelections[key];
1047
+ for (const key of Object.keys(multiSelections))
1048
+ delete multiSelections[key];
1049
+ }
1050
+ function resetPickerState() {
1051
+ loadError.value = null;
1052
+ clearSelections();
1053
+ for (const key of Object.keys(pickerOptions))
1054
+ delete pickerOptions[key];
1055
+ for (const key of Object.keys(loadingKeys))
1056
+ delete loadingKeys[key];
1057
+ }
1058
+ function selectedOptionsFor(item) {
1059
+ const options = pickerOptions[item.key] || [];
1060
+ if (item.selectionMode === "multi")
1061
+ return options.filter((option) => (multiSelections[item.key] || []).includes(option.id));
1062
+ return options.filter((option) => option.id === singleSelections[item.key]);
1063
+ }
1064
+ function buildConfig(optionsOnly = false) {
1065
+ const config = {};
1066
+ for (const item of activeVariantConfig.value) {
1067
+ const selected = selectedOptionsFor(item);
1068
+ if (item.selectionMode === "multi") {
1069
+ if (!selected.length)
1070
+ continue;
1071
+ config[`${item.key}Ids`] = selected.map((option) => option.id);
1072
+ if (!optionsOnly)
1073
+ config[`${item.key}Names`] = selected.map((option) => option.name);
1074
+ } else {
1075
+ const option = selected[0];
1076
+ if (!option)
1077
+ continue;
1078
+ config[`${item.key}Id`] = option.id;
1079
+ if (!optionsOnly)
1080
+ config[`${item.key}Name`] = option.name;
1081
+ }
1082
+ }
1083
+ return config;
1084
+ }
1085
+ async function loadOptions() {
1086
+ if (!isOpen.value) {
1087
+ return;
1088
+ }
1089
+ if (!activeVariant.value) {
1090
+ loadError.value = null;
1091
+ return;
1092
+ }
1093
+ loadError.value = null;
1094
+ const partialConfig = {};
1095
+ for (const item of activeVariantConfig.value) {
1096
+ loadingKeys[item.key] = true;
1097
+ try {
1098
+ const response = await $fetch(`/api/integrations/${props.integrationId}/variant-options`, {
1099
+ method: "POST",
1100
+ body: {
1101
+ forIntegrationType: activeVariant.value.type,
1102
+ key: item.key,
1103
+ config: partialConfig
1104
+ }
1105
+ });
1106
+ pickerOptions[item.key] = response.options;
1107
+ } catch (error) {
1108
+ console.error(`Failed to load options for ${item.key}`, error);
1109
+ pickerOptions[item.key] = [];
1110
+ loadError.value = error instanceof Error ? error.message : `Failed to load ${item.label.toLowerCase()} options`;
1111
+ } finally {
1112
+ loadingKeys[item.key] = false;
1113
+ }
1114
+ if (item.selectionMode === "multi") {
1115
+ const validIds = new Set((pickerOptions[item.key] || []).map((option) => option.id));
1116
+ multiSelections[item.key] = (multiSelections[item.key] || []).filter((id) => validIds.has(id));
1117
+ } else if (singleSelections[item.key] && !(pickerOptions[item.key] || []).some((option) => option.id === singleSelections[item.key])) {
1118
+ singleSelections[item.key] = "";
1119
+ }
1120
+ Object.assign(partialConfig, buildConfig());
1121
+ }
1122
+ }
1123
+ function toggleMultiSelection(item, optionId) {
1124
+ const current = new Set(multiSelections[item.key] || []);
1125
+ if (current.has(optionId))
1126
+ current.delete(optionId);
1127
+ else
1128
+ current.add(optionId);
1129
+ multiSelections[item.key] = [...current];
1130
+ }
1131
+ const canConfirm = computed(() => {
1132
+ if (selectedType.value === props.baseType)
1133
+ return true;
1134
+ if (!activeVariant.value)
1135
+ return false;
1136
+ return activeVariantConfig.value.every((item) => {
1137
+ if (item.selectionMode === "multi")
1138
+ return Boolean((multiSelections[item.key] || []).length);
1139
+ return Boolean(singleSelections[item.key]);
1140
+ });
1141
+ });
1142
+ const labelSuffix = computed(
1143
+ () => activeVariantConfig.value.flatMap((item) => selectedOptionsFor(item).map((option) => option.name)).join(" / ") || null
1144
+ );
1145
+ watch(() => props.open, (open) => {
1146
+ if (!open)
1147
+ return;
1148
+ selectedType.value = props.currentType;
1149
+ resetPickerState();
1150
+ void loadOptions();
1151
+ }, { immediate: true });
1152
+ watch(selectedType, () => {
1153
+ if (!isOpen.value)
1154
+ return;
1155
+ resetPickerState();
1156
+ void loadOptions();
1157
+ });
1158
+ watch(selectionSignature, () => {
1159
+ if (!isOpen.value || selectedType.value === props.baseType)
1160
+ return;
1161
+ void loadOptions();
1162
+ });
1163
+ function submit() {
1164
+ emit("confirm", {
1165
+ type: selectedType.value,
1166
+ config: selectedType.value === props.baseType ? null : buildConfig(),
1167
+ labelSuffix: selectedType.value === props.baseType ? null : labelSuffix.value
1168
+ });
1169
+ }
1170
+ return (_ctx, _push, _parent, _attrs) => {
1171
+ const _component_UModal = _sfc_main$9;
1172
+ const _component_UFormField = _sfc_main$2$1;
1173
+ const _component_USelect = _sfc_main$1$1;
1174
+ const _component_UButton = _sfc_main$h;
1175
+ _push(ssrRenderComponent(_component_UModal, mergeProps({
1176
+ open: unref(isOpen),
1177
+ "onUpdate:open": ($event) => isRef(isOpen) ? isOpen.value = $event : null,
1178
+ title: "Reduce integration scope",
1179
+ description: "Choose a reduced scope for this integration or keep full access."
1180
+ }, _attrs), {
1181
+ body: withCtx((_, _push2, _parent2, _scopeId) => {
1182
+ if (_push2) {
1183
+ _push2(`<div class="space-y-4"${_scopeId}>`);
1184
+ _push2(ssrRenderComponent(_component_UFormField, { label: "Scope mode" }, {
1185
+ default: withCtx((_2, _push3, _parent3, _scopeId2) => {
1186
+ if (_push3) {
1187
+ _push3(ssrRenderComponent(_component_USelect, {
1188
+ modelValue: unref(selectedType),
1189
+ "onUpdate:modelValue": ($event) => isRef(selectedType) ? selectedType.value = $event : null,
1190
+ items: unref(variantTypeItems),
1191
+ class: "w-full"
1192
+ }, null, _parent3, _scopeId2));
1193
+ } else {
1194
+ return [
1195
+ createVNode(_component_USelect, {
1196
+ modelValue: unref(selectedType),
1197
+ "onUpdate:modelValue": ($event) => isRef(selectedType) ? selectedType.value = $event : null,
1198
+ items: unref(variantTypeItems),
1199
+ class: "w-full"
1200
+ }, null, 8, ["modelValue", "onUpdate:modelValue", "items"])
1201
+ ];
1202
+ }
1203
+ }),
1204
+ _: 1
1205
+ }, _parent2, _scopeId));
1206
+ if (unref(selectedType) !== __props.baseType && unref(activeVariantConfig).length) {
1207
+ _push2(`<!--[-->`);
1208
+ ssrRenderList(unref(activeVariantConfig), (item) => {
1209
+ _push2(ssrRenderComponent(_component_UFormField, {
1210
+ key: item.key,
1211
+ label: item.label,
1212
+ description: item.selectionMode === "multi" ? `Choose one or more ${item.label.toLowerCase()} values.` : `Choose a ${item.label.toLowerCase()} value.`
1213
+ }, {
1214
+ default: withCtx((_2, _push3, _parent3, _scopeId2) => {
1215
+ if (_push3) {
1216
+ if (item.selectionMode === "single") {
1217
+ _push3(ssrRenderComponent(_component_USelect, {
1218
+ modelValue: unref(singleSelections)[item.key],
1219
+ "onUpdate:modelValue": ($event) => unref(singleSelections)[item.key] = $event,
1220
+ items: (unref(pickerOptions)[item.key] || []).map((option) => ({ label: option.name, value: option.id })),
1221
+ loading: unref(loadingKeys)[item.key],
1222
+ disabled: unref(loadingKeys)[item.key],
1223
+ placeholder: `Select ${item.label.toLowerCase()}...`,
1224
+ class: "w-full"
1225
+ }, null, _parent3, _scopeId2));
1226
+ } else {
1227
+ _push3(`<div class="space-y-2"${_scopeId2}><!--[-->`);
1228
+ ssrRenderList(unref(pickerOptions)[item.key] || [], (option) => {
1229
+ _push3(`<label class="flex items-center gap-2 text-sm"${_scopeId2}><input type="checkbox"${ssrIncludeBooleanAttr((unref(multiSelections)[item.key] || []).includes(option.id)) ? " checked" : ""}${ssrIncludeBooleanAttr(unref(loadingKeys)[item.key]) ? " disabled" : ""}${_scopeId2}><span${_scopeId2}>${ssrInterpolate(option.name)}</span></label>`);
1230
+ });
1231
+ _push3(`<!--]--></div>`);
1232
+ }
1233
+ } else {
1234
+ return [
1235
+ item.selectionMode === "single" ? (openBlock(), createBlock(_component_USelect, {
1236
+ key: 0,
1237
+ modelValue: unref(singleSelections)[item.key],
1238
+ "onUpdate:modelValue": ($event) => unref(singleSelections)[item.key] = $event,
1239
+ items: (unref(pickerOptions)[item.key] || []).map((option) => ({ label: option.name, value: option.id })),
1240
+ loading: unref(loadingKeys)[item.key],
1241
+ disabled: unref(loadingKeys)[item.key],
1242
+ placeholder: `Select ${item.label.toLowerCase()}...`,
1243
+ class: "w-full"
1244
+ }, null, 8, ["modelValue", "onUpdate:modelValue", "items", "loading", "disabled", "placeholder"])) : (openBlock(), createBlock("div", {
1245
+ key: 1,
1246
+ class: "space-y-2"
1247
+ }, [
1248
+ (openBlock(true), createBlock(Fragment, null, renderList(unref(pickerOptions)[item.key] || [], (option) => {
1249
+ return openBlock(), createBlock("label", {
1250
+ key: option.id,
1251
+ class: "flex items-center gap-2 text-sm"
1252
+ }, [
1253
+ createVNode("input", {
1254
+ type: "checkbox",
1255
+ checked: (unref(multiSelections)[item.key] || []).includes(option.id),
1256
+ disabled: unref(loadingKeys)[item.key],
1257
+ onChange: ($event) => toggleMultiSelection(item, option.id)
1258
+ }, null, 40, ["checked", "disabled", "onChange"]),
1259
+ createVNode("span", null, toDisplayString(option.name), 1)
1260
+ ]);
1261
+ }), 128))
1262
+ ]))
1263
+ ];
1264
+ }
1265
+ }),
1266
+ _: 2
1267
+ }, _parent2, _scopeId));
1268
+ });
1269
+ _push2(`<!--]-->`);
1270
+ } else {
1271
+ _push2(`<!---->`);
1272
+ }
1273
+ if (unref(loadError)) {
1274
+ _push2(`<p class="text-sm text-red-600 dark:text-red-400"${_scopeId}>${ssrInterpolate(unref(loadError))}</p>`);
1275
+ } else {
1276
+ _push2(`<!---->`);
1277
+ }
1278
+ _push2(`</div>`);
1279
+ } else {
1280
+ return [
1281
+ createVNode("div", { class: "space-y-4" }, [
1282
+ createVNode(_component_UFormField, { label: "Scope mode" }, {
1283
+ default: withCtx(() => [
1284
+ createVNode(_component_USelect, {
1285
+ modelValue: unref(selectedType),
1286
+ "onUpdate:modelValue": ($event) => isRef(selectedType) ? selectedType.value = $event : null,
1287
+ items: unref(variantTypeItems),
1288
+ class: "w-full"
1289
+ }, null, 8, ["modelValue", "onUpdate:modelValue", "items"])
1290
+ ]),
1291
+ _: 1
1292
+ }),
1293
+ unref(selectedType) !== __props.baseType && unref(activeVariantConfig).length ? (openBlock(true), createBlock(Fragment, { key: 0 }, renderList(unref(activeVariantConfig), (item) => {
1294
+ return openBlock(), createBlock(_component_UFormField, {
1295
+ key: item.key,
1296
+ label: item.label,
1297
+ description: item.selectionMode === "multi" ? `Choose one or more ${item.label.toLowerCase()} values.` : `Choose a ${item.label.toLowerCase()} value.`
1298
+ }, {
1299
+ default: withCtx(() => [
1300
+ item.selectionMode === "single" ? (openBlock(), createBlock(_component_USelect, {
1301
+ key: 0,
1302
+ modelValue: unref(singleSelections)[item.key],
1303
+ "onUpdate:modelValue": ($event) => unref(singleSelections)[item.key] = $event,
1304
+ items: (unref(pickerOptions)[item.key] || []).map((option) => ({ label: option.name, value: option.id })),
1305
+ loading: unref(loadingKeys)[item.key],
1306
+ disabled: unref(loadingKeys)[item.key],
1307
+ placeholder: `Select ${item.label.toLowerCase()}...`,
1308
+ class: "w-full"
1309
+ }, null, 8, ["modelValue", "onUpdate:modelValue", "items", "loading", "disabled", "placeholder"])) : (openBlock(), createBlock("div", {
1310
+ key: 1,
1311
+ class: "space-y-2"
1312
+ }, [
1313
+ (openBlock(true), createBlock(Fragment, null, renderList(unref(pickerOptions)[item.key] || [], (option) => {
1314
+ return openBlock(), createBlock("label", {
1315
+ key: option.id,
1316
+ class: "flex items-center gap-2 text-sm"
1317
+ }, [
1318
+ createVNode("input", {
1319
+ type: "checkbox",
1320
+ checked: (unref(multiSelections)[item.key] || []).includes(option.id),
1321
+ disabled: unref(loadingKeys)[item.key],
1322
+ onChange: ($event) => toggleMultiSelection(item, option.id)
1323
+ }, null, 40, ["checked", "disabled", "onChange"]),
1324
+ createVNode("span", null, toDisplayString(option.name), 1)
1325
+ ]);
1326
+ }), 128))
1327
+ ]))
1328
+ ]),
1329
+ _: 2
1330
+ }, 1032, ["label", "description"]);
1331
+ }), 128)) : createCommentVNode("", true),
1332
+ unref(loadError) ? (openBlock(), createBlock("p", {
1333
+ key: 1,
1334
+ class: "text-sm text-red-600 dark:text-red-400"
1335
+ }, toDisplayString(unref(loadError)), 1)) : createCommentVNode("", true)
1336
+ ])
1337
+ ];
1338
+ }
1339
+ }),
1340
+ footer: withCtx((_, _push2, _parent2, _scopeId) => {
1341
+ if (_push2) {
1342
+ _push2(`<div class="flex items-center justify-end gap-2 w-full"${_scopeId}>`);
1343
+ _push2(ssrRenderComponent(_component_UButton, {
1344
+ variant: "ghost",
1345
+ color: "neutral",
1346
+ disabled: __props.saving,
1347
+ onClick: ($event) => isOpen.value = false
1348
+ }, {
1349
+ default: withCtx((_2, _push3, _parent3, _scopeId2) => {
1350
+ if (_push3) {
1351
+ _push3(` Cancel `);
1352
+ } else {
1353
+ return [
1354
+ createTextVNode(" Cancel ")
1355
+ ];
1356
+ }
1357
+ }),
1358
+ _: 1
1359
+ }, _parent2, _scopeId));
1360
+ _push2(ssrRenderComponent(_component_UButton, {
1361
+ disabled: !unref(canConfirm) || __props.saving,
1362
+ loading: __props.saving,
1363
+ onClick: submit
1364
+ }, {
1365
+ default: withCtx((_2, _push3, _parent3, _scopeId2) => {
1366
+ if (_push3) {
1367
+ _push3(` Save Scope `);
1368
+ } else {
1369
+ return [
1370
+ createTextVNode(" Save Scope ")
1371
+ ];
1372
+ }
1373
+ }),
1374
+ _: 1
1375
+ }, _parent2, _scopeId));
1376
+ _push2(`</div>`);
1377
+ } else {
1378
+ return [
1379
+ createVNode("div", { class: "flex items-center justify-end gap-2 w-full" }, [
1380
+ createVNode(_component_UButton, {
1381
+ variant: "ghost",
1382
+ color: "neutral",
1383
+ disabled: __props.saving,
1384
+ onClick: ($event) => isOpen.value = false
1385
+ }, {
1386
+ default: withCtx(() => [
1387
+ createTextVNode(" Cancel ")
1388
+ ]),
1389
+ _: 1
1390
+ }, 8, ["disabled", "onClick"]),
1391
+ createVNode(_component_UButton, {
1392
+ disabled: !unref(canConfirm) || __props.saving,
1393
+ loading: __props.saving,
1394
+ onClick: submit
1395
+ }, {
1396
+ default: withCtx(() => [
1397
+ createTextVNode(" Save Scope ")
1398
+ ]),
1399
+ _: 1
1400
+ }, 8, ["disabled", "loading"])
1401
+ ])
1402
+ ];
1403
+ }
1404
+ }),
1405
+ _: 1
1406
+ }, _parent));
1407
+ };
1408
+ }
1409
+ });
995
1410
  const _sfc_setup$1 = _sfc_main$1.setup;
996
1411
  _sfc_main$1.setup = (props, ctx) => {
997
1412
  const ssrContext = useSSRContext();
998
- (ssrContext.modules || (ssrContext.modules = /* @__PURE__ */ new Set())).add("components/IntegrationCredentials.vue");
1413
+ (ssrContext.modules || (ssrContext.modules = /* @__PURE__ */ new Set())).add("components/IntegrationVariantConfigDialog.vue");
999
1414
  return _sfc_setup$1 ? _sfc_setup$1(props, ctx) : void 0;
1000
1415
  };
1001
- const __nuxt_component_6 = /* @__PURE__ */ Object.assign(_export_sfc(_sfc_main$1, [["__scopeId", "data-v-7de84f63"]]), { __name: "IntegrationCredentials" });
1416
+ const IntegrationVariantConfigDialog = Object.assign(_sfc_main$1, { __name: "IntegrationVariantConfigDialog" });
1002
1417
  const _sfc_main = /* @__PURE__ */ defineComponent({
1003
1418
  __name: "[id]",
1004
1419
  __ssrInlineRender: true,
1005
1420
  async setup(__props) {
1006
1421
  let __temp, __restore;
1422
+ const HYPHEN_REGEX = /-/g;
1423
+ const WHITESPACE_SPLIT_REGEX = /\s+/;
1007
1424
  const route = useRoute();
1008
1425
  const integrationId = route.params.id;
1009
1426
  const { data: integrations, pending, error, refresh } = ([__temp, __restore] = withAsyncContext(() => useFetch(
@@ -1011,6 +1428,11 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1011
1428
  "$tUtKcl3GqX"
1012
1429
  /* nuxt-injected */
1013
1430
  )), __temp = await __temp, __restore(), __temp);
1431
+ const { data: catalog } = ([__temp, __restore] = withAsyncContext(() => useFetch(
1432
+ "/api/catalog",
1433
+ "$NlPmMk6-3b"
1434
+ /* nuxt-injected */
1435
+ )), __temp = await __temp, __restore(), __temp);
1014
1436
  const integration = computed(() => integrations.value?.find((i) => i.id === integrationId) ?? null);
1015
1437
  const formEnabled = ref(true);
1016
1438
  const formMaxScope = ref(null);
@@ -1019,6 +1441,54 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1019
1441
  const toolsTreeRef = ref(null);
1020
1442
  const removeModalOpen = ref(false);
1021
1443
  const saving = ref(false);
1444
+ const variantConfigDialogOpen = ref(false);
1445
+ const savingVariantConfig = ref(false);
1446
+ const connectionHealthStatus = ref(null);
1447
+ const connectionStatusLoading = ref(false);
1448
+ function humanizeType(type) {
1449
+ return type.replace(HYPHEN_REGEX, " ").split(WHITESPACE_SPLIT_REGEX).filter(Boolean).map((word) => word[0] ? `${word[0].toUpperCase()}${word.slice(1)}` : word).join(" ");
1450
+ }
1451
+ const baseCatalogEntry = computed(
1452
+ () => (catalog.value || []).find(
1453
+ (entry) => entry.type === integration.value?.type || entry.variants?.some((variant) => variant.type === integration.value?.type)
1454
+ ) ?? null
1455
+ );
1456
+ const baseType = computed(() => baseCatalogEntry.value?.type ?? integration.value?.type ?? null);
1457
+ const familyVariants = computed(
1458
+ () => baseCatalogEntry.value?.variants?.filter((variant) => (variant.variantConfig?.length ?? 0) > 0) ?? []
1459
+ );
1460
+ const showsVariantScopeAction = computed(
1461
+ () => familyVariants.value.length > 0 && Boolean(integration.value)
1462
+ );
1463
+ const isConnected = computed(() => connectionHealthStatus.value === "connected");
1464
+ const canConfigureVariantScope = computed(
1465
+ () => showsVariantScopeAction.value && isConnected.value
1466
+ );
1467
+ const baseIntegrationName = computed(() => baseCatalogEntry.value?.name || (baseType.value ? humanizeType(baseType.value) : "Integration"));
1468
+ const variantScopeBlockedMessage = computed(() => {
1469
+ if (!showsVariantScopeAction.value || canConfigureVariantScope.value)
1470
+ return null;
1471
+ if (connectionStatusLoading.value)
1472
+ return "Checking connection before enabling reduced scope...";
1473
+ if (connectionHealthStatus.value === "invalid_credentials")
1474
+ return "Reconnect this integration before choosing a reduced scope.";
1475
+ return "Connect this integration before choosing a reduced scope.";
1476
+ });
1477
+ async function refreshConnectionStatus() {
1478
+ if (!integration.value || !showsVariantScopeAction.value) {
1479
+ connectionHealthStatus.value = null;
1480
+ return;
1481
+ }
1482
+ connectionStatusLoading.value = true;
1483
+ try {
1484
+ const status = await $fetch(`/api/integrations/${integration.value.id}/credentials-status`);
1485
+ connectionHealthStatus.value = status?.health_status ?? "disconnected";
1486
+ } catch {
1487
+ connectionHealthStatus.value = "disconnected";
1488
+ } finally {
1489
+ connectionStatusLoading.value = false;
1490
+ }
1491
+ }
1022
1492
  function initForm() {
1023
1493
  if (!integration.value)
1024
1494
  return;
@@ -1030,6 +1500,9 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1030
1500
  formEnabledToolsets.value = integration.value.enabledToolsets?.length ? [...integration.value.enabledToolsets] : allKeys;
1031
1501
  }
1032
1502
  watch(integration, () => initForm(), { immediate: true });
1503
+ watch(() => integration.value?.id, () => {
1504
+ void refreshConnectionStatus();
1505
+ }, { immediate: true });
1033
1506
  watch(() => toolsTreeRef.value?.toolsets, (toolsets) => {
1034
1507
  if (!integration.value || !toolsets?.length)
1035
1508
  return;
@@ -1078,8 +1551,37 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1078
1551
  await $fetch(`/api/integrations/${integration.value.id}`, { method: "DELETE" });
1079
1552
  navigateTo("/integrations");
1080
1553
  }
1081
- function onCredentialChange() {
1082
- refresh();
1554
+ async function openVariantScopeDialog() {
1555
+ if (!canConfigureVariantScope.value)
1556
+ return;
1557
+ variantConfigDialogOpen.value = true;
1558
+ }
1559
+ async function onCredentialChange() {
1560
+ await refresh();
1561
+ await refreshConnectionStatus();
1562
+ if (canConfigureVariantScope.value)
1563
+ variantConfigDialogOpen.value = true;
1564
+ }
1565
+ async function saveVariantScope(payload) {
1566
+ if (!integration.value || !baseType.value)
1567
+ return;
1568
+ savingVariantConfig.value = true;
1569
+ try {
1570
+ const nextLabel = payload.type === baseType.value ? baseIntegrationName.value : payload.labelSuffix ? `${baseIntegrationName.value}: ${payload.labelSuffix}` : integration.value.label;
1571
+ await $fetch("/api/integrations", {
1572
+ method: "POST",
1573
+ body: {
1574
+ ...integration.value,
1575
+ type: payload.type,
1576
+ label: nextLabel,
1577
+ config: payload.config
1578
+ }
1579
+ });
1580
+ variantConfigDialogOpen.value = false;
1581
+ await refresh();
1582
+ } finally {
1583
+ savingVariantConfig.value = false;
1584
+ }
1083
1585
  }
1084
1586
  return (_ctx, _push, _parent, _attrs) => {
1085
1587
  const _component_UContainer = _sfc_main$b;
@@ -1087,7 +1589,7 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1087
1589
  const _component_NuxtLink = __nuxt_component_0$1;
1088
1590
  const _component_UIcon = _sfc_main$m;
1089
1591
  const _component_UBadge = _sfc_main$4;
1090
- const _component_USwitch = _sfc_main$3;
1592
+ const _component_USwitch = _sfc_main$3$1;
1091
1593
  const _component_IntegrationCredentials = __nuxt_component_6;
1092
1594
  const _component_IntegrationToolsTree = __nuxt_component_3;
1093
1595
  const _component_UModal = _sfc_main$9;
@@ -1164,7 +1666,32 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1164
1666
  "onUpdate:modelValue": ($event) => isRef(formEnabled) ? formEnabled.value = $event : null,
1165
1667
  size: "lg"
1166
1668
  }, null, _parent2, _scopeId));
1167
- _push2(`</div><p class="text-sm text-muted mt-1"${_scopeId}>${ssrInterpolate(unref(integration).type)} · ${ssrInterpolate(unref(integration).referenceId)}</p></div><section${_scopeId}><div class="flex items-center justify-between gap-4 mb-1"${_scopeId}><h2 class="text-lg font-medium"${_scopeId}> Connection </h2></div><div class="border border-[var(--ui-border)] rounded-lg px-4 py-3"${_scopeId}>`);
1669
+ _push2(`</div><p class="text-sm text-muted mt-1"${_scopeId}>${ssrInterpolate(unref(integration).type)} · ${ssrInterpolate(unref(integration).referenceId)}</p></div><section${_scopeId}><div class="flex items-center justify-between gap-4 mb-1"${_scopeId}><h2 class="text-lg font-medium"${_scopeId}> Connection </h2>`);
1670
+ if (unref(showsVariantScopeAction)) {
1671
+ _push2(ssrRenderComponent(_component_UButton, {
1672
+ size: "xs",
1673
+ variant: "soft",
1674
+ color: "neutral",
1675
+ icon: "i-lucide-filter",
1676
+ disabled: !unref(canConfigureVariantScope) || unref(connectionStatusLoading),
1677
+ loading: unref(connectionStatusLoading),
1678
+ onClick: openVariantScopeDialog
1679
+ }, {
1680
+ default: withCtx((_2, _push3, _parent3, _scopeId2) => {
1681
+ if (_push3) {
1682
+ _push3(` Reduce Scope `);
1683
+ } else {
1684
+ return [
1685
+ createTextVNode(" Reduce Scope ")
1686
+ ];
1687
+ }
1688
+ }),
1689
+ _: 1
1690
+ }, _parent2, _scopeId));
1691
+ } else {
1692
+ _push2(`<!---->`);
1693
+ }
1694
+ _push2(`</div><div class="border border-[var(--ui-border)] rounded-lg px-4 py-3"${_scopeId}>`);
1168
1695
  _push2(ssrRenderComponent(_component_IntegrationCredentials, {
1169
1696
  "integration-id": unref(integration).id,
1170
1697
  "integration-type": unref(integration).type,
@@ -1172,7 +1699,13 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1172
1699
  onSaved: onCredentialChange,
1173
1700
  onDisconnected: onCredentialChange
1174
1701
  }, null, _parent2, _scopeId));
1175
- _push2(`</div></section><section class="space-y-3"${_scopeId}><h2 class="text-lg font-medium"${_scopeId}> Access Level </h2><div class="flex gap-2"${_scopeId}><button type="button" class="${ssrRenderClass([unref(formMaxScope) !== "read" ? "border-green-500 bg-green-50 text-green-700 font-medium dark:bg-green-950 dark:text-green-300" : "border-[var(--ui-border)] text-muted hover:bg-[var(--ui-bg-elevated)]", "px-4 py-2 text-sm rounded-lg border transition-colors"])}"${_scopeId}> Read + Write </button><button type="button" class="${ssrRenderClass([unref(formMaxScope) === "read" ? "border-green-500 bg-green-50 text-green-700 font-medium dark:bg-green-950 dark:text-green-300" : "border-[var(--ui-border)] text-muted hover:bg-[var(--ui-bg-elevated)]", "px-4 py-2 text-sm rounded-lg border transition-colors"])}"${_scopeId}> Read-only </button></div>`);
1702
+ _push2(`</div>`);
1703
+ if (unref(variantScopeBlockedMessage)) {
1704
+ _push2(`<p class="mt-2 text-xs text-muted"${_scopeId}>${ssrInterpolate(unref(variantScopeBlockedMessage))}</p>`);
1705
+ } else {
1706
+ _push2(`<!---->`);
1707
+ }
1708
+ _push2(`</section><section class="space-y-3"${_scopeId}><h2 class="text-lg font-medium"${_scopeId}> Access Level </h2><div class="flex gap-2"${_scopeId}><button type="button" class="${ssrRenderClass([unref(formMaxScope) !== "read" ? "border-green-500 bg-green-50 text-green-700 font-medium dark:bg-green-950 dark:text-green-300" : "border-[var(--ui-border)] text-muted hover:bg-[var(--ui-bg-elevated)]", "px-4 py-2 text-sm rounded-lg border transition-colors"])}"${_scopeId}> Read + Write </button><button type="button" class="${ssrRenderClass([unref(formMaxScope) === "read" ? "border-green-500 bg-green-50 text-green-700 font-medium dark:bg-green-950 dark:text-green-300" : "border-[var(--ui-border)] text-muted hover:bg-[var(--ui-bg-elevated)]", "px-4 py-2 text-sm rounded-lg border transition-colors"])}"${_scopeId}> Read-only </button></div>`);
1176
1709
  if (unref(formMaxScope) === "read") {
1177
1710
  _push2(`<p class="text-xs text-amber-600 dark:text-amber-400"${_scopeId}> Only read tools will be available. Write and admin tools will be greyed out below. </p>`);
1178
1711
  } else {
@@ -1295,6 +1828,21 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1295
1828
  }),
1296
1829
  _: 1
1297
1830
  }, _parent2, _scopeId));
1831
+ if (unref(integration) && unref(baseType)) {
1832
+ _push2(ssrRenderComponent(IntegrationVariantConfigDialog, {
1833
+ open: unref(variantConfigDialogOpen),
1834
+ "onUpdate:open": ($event) => isRef(variantConfigDialogOpen) ? variantConfigDialogOpen.value = $event : null,
1835
+ "integration-id": unref(integration).id,
1836
+ "current-type": unref(integration).type,
1837
+ "base-type": unref(baseType),
1838
+ "base-name": unref(baseIntegrationName),
1839
+ variants: unref(familyVariants),
1840
+ saving: unref(savingVariantConfig),
1841
+ onConfirm: saveVariantScope
1842
+ }, null, _parent2, _scopeId));
1843
+ } else {
1844
+ _push2(`<!---->`);
1845
+ }
1298
1846
  _push2(`<!--]-->`);
1299
1847
  }
1300
1848
  } else {
@@ -1357,7 +1905,22 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1357
1905
  ]),
1358
1906
  createVNode("section", null, [
1359
1907
  createVNode("div", { class: "flex items-center justify-between gap-4 mb-1" }, [
1360
- createVNode("h2", { class: "text-lg font-medium" }, " Connection ")
1908
+ createVNode("h2", { class: "text-lg font-medium" }, " Connection "),
1909
+ unref(showsVariantScopeAction) ? (openBlock(), createBlock(_component_UButton, {
1910
+ key: 0,
1911
+ size: "xs",
1912
+ variant: "soft",
1913
+ color: "neutral",
1914
+ icon: "i-lucide-filter",
1915
+ disabled: !unref(canConfigureVariantScope) || unref(connectionStatusLoading),
1916
+ loading: unref(connectionStatusLoading),
1917
+ onClick: openVariantScopeDialog
1918
+ }, {
1919
+ default: withCtx(() => [
1920
+ createTextVNode(" Reduce Scope ")
1921
+ ]),
1922
+ _: 1
1923
+ }, 8, ["disabled", "loading"])) : createCommentVNode("", true)
1361
1924
  ]),
1362
1925
  createVNode("div", { class: "border border-[var(--ui-border)] rounded-lg px-4 py-3" }, [
1363
1926
  createVNode(_component_IntegrationCredentials, {
@@ -1367,7 +1930,11 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1367
1930
  onSaved: onCredentialChange,
1368
1931
  onDisconnected: onCredentialChange
1369
1932
  }, null, 8, ["integration-id", "integration-type", "current-variant"])
1370
- ])
1933
+ ]),
1934
+ unref(variantScopeBlockedMessage) ? (openBlock(), createBlock("p", {
1935
+ key: 0,
1936
+ class: "mt-2 text-xs text-muted"
1937
+ }, toDisplayString(unref(variantScopeBlockedMessage)), 1)) : createCommentVNode("", true)
1371
1938
  ]),
1372
1939
  createVNode("section", { class: "space-y-3" }, [
1373
1940
  createVNode("h2", { class: "text-lg font-medium" }, " Access Level "),
@@ -1455,7 +2022,19 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1455
2022
  ])
1456
2023
  ]),
1457
2024
  _: 1
1458
- }, 8, ["open", "onUpdate:open", "description"])
2025
+ }, 8, ["open", "onUpdate:open", "description"]),
2026
+ unref(integration) && unref(baseType) ? (openBlock(), createBlock(IntegrationVariantConfigDialog, {
2027
+ key: 0,
2028
+ open: unref(variantConfigDialogOpen),
2029
+ "onUpdate:open": ($event) => isRef(variantConfigDialogOpen) ? variantConfigDialogOpen.value = $event : null,
2030
+ "integration-id": unref(integration).id,
2031
+ "current-type": unref(integration).type,
2032
+ "base-type": unref(baseType),
2033
+ "base-name": unref(baseIntegrationName),
2034
+ variants: unref(familyVariants),
2035
+ saving: unref(savingVariantConfig),
2036
+ onConfirm: saveVariantScope
2037
+ }, null, 8, ["open", "onUpdate:open", "integration-id", "current-type", "base-type", "base-name", "variants", "saving"])) : createCommentVNode("", true)
1459
2038
  ], 64))
1460
2039
  ];
1461
2040
  }
@@ -1473,4 +2052,4 @@ _sfc_main.setup = (props, ctx) => {
1473
2052
  };
1474
2053
 
1475
2054
  export { _sfc_main as default };
1476
- //# sourceMappingURL=_id_-Co8jGxsD.mjs.map
2055
+ //# sourceMappingURL=_id_-DA3Q8jun.mjs.map