You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

192 lines
13 KiB

import { defineComponent, computed, reactive, ref, useSSRContext } from 'vue';
import { ssrRenderAttrs, ssrRenderStyle, ssrInterpolate, ssrIncludeBooleanAttr, ssrRenderAttr, ssrLooseContain, ssrLooseEqual, ssrRenderList, ssrRenderClass, ssrRenderDynamicModel } from 'vue/server-renderer';
import { u as useApi } from './useApi-B6h53Mkt.mjs';
import { u as useToast } from './useToast-C76a6bSX.mjs';
import { _ as _export_sfc, a as useRoute$1, b as useRouter } from './server.mjs';
import './auth-QFkCoU1C.mjs';
import 'pinia';
import './useLoading-D6mc40Wj.mjs';
import './state-DQnwRar-.mjs';
import '../nitro/nitro.mjs';
import 'node:http';
import 'node:https';
import 'node:events';
import 'node:buffer';
import 'node:fs';
import 'node:path';
import 'node:crypto';
import 'node:url';
import '../routes/renderer.mjs';
import 'vue-bundle-renderer/runtime';
import 'unhead/server';
import 'devalue';
import 'unhead/utils';
import 'perfect-debounce';
const _sfc_main = /* @__PURE__ */ defineComponent({
__name: "appconfig",
__ssrInlineRender: true,
setup(__props) {
useApi();
useToast();
const route = useRoute$1();
useRouter();
const appId = computed(() => Number(route.query.id) || 0);
const appName = computed(() => route.query.name || "未指定应用");
const appInitial = computed(() => (dep.app_name || appName.value || "A").charAt(0).toUpperCase());
const dep = reactive({ id: 0, app_name: "", status: "", name: "", region: "", env_id: 0, base_url: "", service_dsn: "" });
const envs = ref([]);
const envId = ref(0);
const envSaving = ref(false);
const catalog = ref([]);
const curModule = ref("");
const values = reactive({});
const dataModules = reactive(/* @__PURE__ */ new Set());
const show = reactive({});
const loading = ref(false);
const saving = ref(false);
const dbError = ref("");
const curDef = computed(() => catalog.value.find((m) => m.module === curModule.value) || null);
const cur = computed(() => values[curModule.value] || {});
const groups = computed(() => {
const order = [];
const map = /* @__PURE__ */ new Map();
for (const m of catalog.value) {
if (!map.has(m.group)) {
map.set(m.group, []);
order.push(m.group);
}
map.get(m.group).push(m);
}
return order.map((name) => ({ name, modules: map.get(name) }));
});
function dbName(dsn) {
const m = (dsn || "").match(/\/([^/?]+)\?/);
return m ? m[1] : dsn ? "(自定义)" : "—";
}
return (_ctx, _push, _parent, _attrs) => {
_push(`<div${ssrRenderAttrs(_attrs)} data-v-a2d8388e><div class="flex items-center gap-2 mb-4" data-v-a2d8388e><button class="btn btn-ghost btn-sm" data-v-a2d8388e>← 返回应用列表</button><span class="text-slate-300" data-v-a2d8388e>/</span><h2 class="text-lg font-semibold text-slate-800" data-v-a2d8388e>应用服务配置</h2></div><div class="rounded-xl px-5 py-4 mb-5" style="${ssrRenderStyle({ "background": "linear-gradient(135deg,#eef2ff,#faf5ff)", "border": "1px solid #e0e7ff" })}" data-v-a2d8388e><div class="flex items-center gap-4" data-v-a2d8388e><div class="app-avatar" data-v-a2d8388e>${ssrInterpolate(appInitial.value)}</div><div class="flex-1 min-w-0" data-v-a2d8388e><div class="flex items-center gap-2 flex-wrap" data-v-a2d8388e><span class="text-base font-bold text-slate-800" data-v-a2d8388e>${ssrInterpolate(dep.name || appName.value)}</span><span class="badge badge-sm" style="${ssrRenderStyle({ "background": "#e0e7ff", "color": "#4338ca", "border": "none" })}" data-v-a2d8388e>#${ssrInterpolate(appId.value)}</span>`);
if (dep.app_name) {
_push(`<span class="badge badge-ghost badge-sm" data-v-a2d8388e>应用:${ssrInterpolate(dep.app_name)}</span>`);
} else {
_push(`<!---->`);
}
if (dep.region) {
_push(`<span class="badge badge-ghost badge-sm" data-v-a2d8388e>${ssrInterpolate(dep.region)}</span>`);
} else {
_push(`<!---->`);
}
if (dep.status === "pending") {
_push(`<span class="badge badge-warning badge-sm text-amber-900" data-v-a2d8388e>待部署</span>`);
} else {
_push(`<span class="badge badge-success badge-sm text-white" data-v-a2d8388e>已接入</span>`);
}
_push(`</div><div class="text-[11px] text-slate-500 mt-1 flex flex-wrap gap-x-4 gap-y-0.5" data-v-a2d8388e>`);
if (dep.base_url) {
_push(`<span data-v-a2d8388e>地址:<span class="font-mono" data-v-a2d8388e>${ssrInterpolate(dep.base_url)}</span></span>`);
} else {
_push(`<!---->`);
}
_push(`<span data-v-a2d8388e>业务库:<span class="font-mono" data-v-a2d8388e>${ssrInterpolate(dbName(dep.service_dsn))}</span></span></div></div></div><div class="flex items-center gap-2 mt-3 pt-3 border-t border-indigo-100" data-v-a2d8388e><span class="text-xs text-slate-500 shrink-0" data-v-a2d8388e>部署环境</span><select class="select select-bordered select-sm w-64"${ssrIncludeBooleanAttr(envSaving.value) ? " disabled" : ""} data-v-a2d8388e><option${ssrRenderAttr("value", 0)} data-v-a2d8388e${ssrIncludeBooleanAttr(Array.isArray(envId.value) ? ssrLooseContain(envId.value, 0) : ssrLooseEqual(envId.value, 0)) ? " selected" : ""}>未绑定</option><!--[-->`);
ssrRenderList(envs.value, (e) => {
_push(`<option${ssrRenderAttr("value", e.id)} data-v-a2d8388e${ssrIncludeBooleanAttr(Array.isArray(envId.value) ? ssrLooseContain(envId.value, e.id) : ssrLooseEqual(envId.value, e.id)) ? " selected" : ""}>${ssrInterpolate(e.name)}(${ssrInterpolate(e.code || "-")})</option>`);
});
_push(`<!--]--></select>`);
if (envSaving.value) {
_push(`<span class="loading loading-spinner loading-xs text-indigo-400" data-v-a2d8388e></span>`);
} else {
_push(`<!---->`);
}
_push(`<span class="text-[11px] text-slate-400" data-v-a2d8388e>切换后即时保存。</span></div></div><div class="bg-white rounded-2xl border border-slate-100 shadow-sm p-5" data-v-a2d8388e><div class="mb-3" data-v-a2d8388e><h3 class="text-base font-semibold text-slate-800" data-v-a2d8388e>业务功能配置</h3><p class="text-[11px] text-slate-400 mt-0.5" data-v-a2d8388e> 登录 / 短信 / 邮件 / 支付等应用独立配置,保存在<b data-v-a2d8388e>该部署的业务库</b>(不进公共库)。密钥字段加密落库,显示时脱敏。 </p></div>`);
if (dbError.value) {
_push(`<div class="alert alert-warning py-2 text-sm mb-3" data-v-a2d8388e><span data-v-a2d8388e>无法连接应用业务库:${ssrInterpolate(dbError.value)}<br data-v-a2d8388e><span class="text-xs opacity-70" data-v-a2d8388e>待部署的应用先完成部署、或检查业务库 DSN 连通后再配置。</span></span></div>`);
} else {
_push(`<!---->`);
}
if (loading.value) {
_push(`<div class="py-12 text-center" data-v-a2d8388e><span class="loading loading-spinner loading-sm" data-v-a2d8388e></span></div>`);
} else {
_push(`<div class="flex gap-5" data-v-a2d8388e><aside class="w-48 shrink-0" data-v-a2d8388e><!--[-->`);
ssrRenderList(groups.value, (grp) => {
_push(`<div class="mb-3" data-v-a2d8388e><div class="text-[11px] font-semibold text-slate-400 px-2 mb-1" data-v-a2d8388e>${ssrInterpolate(grp.name)}</div><!--[-->`);
ssrRenderList(grp.modules, (m) => {
_push(`<button class="${ssrRenderClass([curModule.value === m.module ? "bg-indigo-50 text-indigo-700 font-medium" : "text-slate-600 hover:bg-slate-50", "w-full flex items-center justify-between text-left px-3 py-2 rounded-lg text-sm mb-0.5 transition-colors"])}" data-v-a2d8388e><span data-v-a2d8388e>${ssrInterpolate(m.name)}</span>`);
if (dataModules.has(m.module)) {
_push(`<span class="w-1.5 h-1.5 rounded-full bg-emerald-400 inline-block" data-v-a2d8388e></span>`);
} else {
_push(`<!---->`);
}
_push(`</button>`);
});
_push(`<!--]--></div>`);
});
_push(`<!--]--></aside><section class="flex-1 min-w-0" data-v-a2d8388e>`);
if (curDef.value) {
_push(`<!--[--><div class="flex items-center justify-between mb-3" data-v-a2d8388e><div data-v-a2d8388e><div class="text-sm font-semibold text-slate-800" data-v-a2d8388e>${ssrInterpolate(curDef.value.name)}</div>`);
if (curDef.value.desc) {
_push(`<div class="text-[11px] text-slate-400 mt-0.5" data-v-a2d8388e>${ssrInterpolate(curDef.value.desc)}</div>`);
} else {
_push(`<!---->`);
}
_push(`</div><div class="flex items-center gap-2" data-v-a2d8388e>`);
if (dataModules.has(curModule.value)) {
_push(`<button class="btn btn-ghost btn-xs text-rose-500"${ssrIncludeBooleanAttr(saving.value) ? " disabled" : ""} data-v-a2d8388e>清空</button>`);
} else {
_push(`<!---->`);
}
_push(`<button class="btn btn-primary btn-sm text-white"${ssrIncludeBooleanAttr(saving.value || dbError.value !== "") ? " disabled" : ""} data-v-a2d8388e>${ssrInterpolate(saving.value ? "保存中…" : "保存")}</button></div></div><div class="grid grid-cols-1 gap-3 max-w-2xl" data-v-a2d8388e><!--[-->`);
ssrRenderList(curDef.value.fields, (f) => {
_push(`<div class="form-control" data-v-a2d8388e><label class="label py-0.5" data-v-a2d8388e><span class="label-text text-sm" data-v-a2d8388e>${ssrInterpolate(f.label)} `);
if (f.required) {
_push(`<span class="text-rose-400" data-v-a2d8388e>*</span>`);
} else {
_push(`<!---->`);
}
if (f.secret) {
_push(`<span class="lock-tag ml-1" data-v-a2d8388e>🔒</span>`);
} else {
_push(`<!---->`);
}
_push(`<span class="text-[10px] font-normal text-slate-300 ml-1 font-mono" data-v-a2d8388e>${ssrInterpolate(f.key)}</span></span></label>`);
if (f.type === "bool") {
_push(`<label class="cursor-pointer flex items-center gap-2" data-v-a2d8388e><input type="checkbox" class="toggle toggle-sm toggle-primary"${ssrIncludeBooleanAttr(cur.value[f.key] === "true") ? " checked" : ""} data-v-a2d8388e><span class="text-xs text-slate-500" data-v-a2d8388e>${ssrInterpolate(cur.value[f.key] === "true" ? "开启" : "关闭")}</span></label>`);
} else if (f.type === "select") {
_push(`<select class="select select-bordered select-sm w-full" data-v-a2d8388e><option value="" data-v-a2d8388e${ssrIncludeBooleanAttr(Array.isArray(cur.value[f.key]) ? ssrLooseContain(cur.value[f.key], "") : ssrLooseEqual(cur.value[f.key], "")) ? " selected" : ""}>请选择</option><!--[-->`);
ssrRenderList(f.options, (o) => {
_push(`<option${ssrRenderAttr("value", o.value)} data-v-a2d8388e${ssrIncludeBooleanAttr(Array.isArray(cur.value[f.key]) ? ssrLooseContain(cur.value[f.key], o.value) : ssrLooseEqual(cur.value[f.key], o.value)) ? " selected" : ""}>${ssrInterpolate(o.label)}</option>`);
});
_push(`<!--]--></select>`);
} else if (f.type === "textarea") {
_push(`<textarea class="textarea textarea-bordered w-full font-mono text-xs" rows="3"${ssrRenderAttr("placeholder", f.secret ? "留空/保持 [encrypted] 则不变" : f.placeholder || "")} data-v-a2d8388e>${ssrInterpolate(cur.value[f.key])}</textarea>`);
} else if (f.type === "password") {
_push(`<div class="relative" data-v-a2d8388e><input${ssrRenderDynamicModel(show[f.key] ? "text" : "password", cur.value[f.key], null)}${ssrRenderAttr("type", show[f.key] ? "text" : "password")} class="input input-bordered input-sm w-full font-mono text-xs pr-14"${ssrRenderAttr("placeholder", "留空/保持 [encrypted] 则不变")} data-v-a2d8388e><button type="button" class="absolute right-3 top-1/2 -translate-y-1/2 text-xs text-slate-400 hover:text-slate-700" data-v-a2d8388e>${ssrInterpolate(show[f.key] ? "隐藏" : "显示")}</button></div>`);
} else {
_push(`<input${ssrRenderAttr("value", cur.value[f.key])} type="text" class="input input-bordered input-sm w-full font-mono text-xs"${ssrRenderAttr("placeholder", f.placeholder || "")} data-v-a2d8388e>`);
}
if (f.desc) {
_push(`<span class="text-[11px] text-slate-400 mt-0.5" data-v-a2d8388e>${ssrInterpolate(f.desc)}</span>`);
} else {
_push(`<!---->`);
}
_push(`</div>`);
});
_push(`<!--]--></div><!--]-->`);
} else {
_push(`<div class="py-10 text-center text-slate-400 text-sm" data-v-a2d8388e>暂无可配置的业务模块。</div>`);
}
_push(`</section></div>`);
}
_push(`</div></div>`);
};
}
});
const _sfc_setup = _sfc_main.setup;
_sfc_main.setup = (props, ctx) => {
const ssrContext = useSSRContext();
(ssrContext.modules || (ssrContext.modules = /* @__PURE__ */ new Set())).add("pages/appconfig.vue");
return _sfc_setup ? _sfc_setup(props, ctx) : void 0;
};
const appconfig = /* @__PURE__ */ _export_sfc(_sfc_main, [["__scopeId", "data-v-a2d8388e"]]);
export { appconfig as default };
//# sourceMappingURL=appconfig-b7qb0UVr.mjs.map