【重要】重构 并实现新的架构
This commit is contained in:
@@ -74,6 +74,15 @@ app.get("/api/productsInfo", (req: Request, ctx: { params: { id: number; }; }) =
|
|||||||
return new Response(Res(result));
|
return new Response(Res(result));
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
// test 测试接口
|
||||||
|
app.get("/nacos", (ctx: { params: { name: any; }; }) => {
|
||||||
|
console.log("test 测试接口 被运行");
|
||||||
|
return new Response(JSON.stringify({
|
||||||
|
title: "test测试接口"
|
||||||
|
}));
|
||||||
|
});
|
||||||
|
|
||||||
const exampleLoggerMiddleware = define.middleware((ctx: { req: { method: any; url: any; }; next: () => any; }) => {
|
const exampleLoggerMiddleware = define.middleware((ctx: { req: { method: any; url: any; }; next: () => any; }) => {
|
||||||
console.log(`${ctx.req.method} ${ctx.req.url}`);
|
console.log(`${ctx.req.method} ${ctx.req.url}`);
|
||||||
return ctx.next();
|
return ctx.next();
|
||||||
|
|||||||
@@ -98,7 +98,7 @@ ufw status
|
|||||||
|
|
||||||
### 运行启动
|
### 运行启动
|
||||||
|
|
||||||
将本文件夹内所有文件上传到 1号服务器,然后执行命令:
|
将本文件夹内所有文件上传到 1号服务器,然后在文件夹内执行命令:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# 部署栈,这个过程有点慢,因为需要拉取镜像,等!
|
# 部署栈,这个过程有点慢,因为需要拉取镜像,等!
|
||||||
|
|||||||
17
docker/nginx/docker-compose.yml
Normal file
17
docker/nginx/docker-compose.yml
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
version: '3.8'
|
||||||
|
|
||||||
|
services:
|
||||||
|
nginx-proxy:
|
||||||
|
image: nginx:latest
|
||||||
|
container_name: nginx-proxy
|
||||||
|
ports:
|
||||||
|
- "80:80"
|
||||||
|
volumes:
|
||||||
|
- ./nginx.conf:/etc/nginx/nginx.conf:ro
|
||||||
|
restart: unless-stopped
|
||||||
|
networks:
|
||||||
|
- proxy-network
|
||||||
|
|
||||||
|
networks:
|
||||||
|
proxy-network:
|
||||||
|
driver: bridge
|
||||||
61
docker/nginx/nginx.conf
Normal file
61
docker/nginx/nginx.conf
Normal file
@@ -0,0 +1,61 @@
|
|||||||
|
events {
|
||||||
|
worker_connections 1024;
|
||||||
|
}
|
||||||
|
|
||||||
|
http {
|
||||||
|
include /etc/nginx/mime.types;
|
||||||
|
default_type application/octet-stream;
|
||||||
|
|
||||||
|
# 上游服务器配置
|
||||||
|
upstream nacos_cluster {
|
||||||
|
server 192.168.139.84:8848;
|
||||||
|
server 192.168.139.15:8848;
|
||||||
|
server 192.168.139.178:8848;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
upstream nacos_ui {
|
||||||
|
server 192.168.139.84:8080;
|
||||||
|
server 192.168.139.15:8080;
|
||||||
|
server 192.168.139.178:8080;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
server {
|
||||||
|
listen 80;
|
||||||
|
server_name cluster.nacos.com;
|
||||||
|
|
||||||
|
# 反向代理配置
|
||||||
|
location / {
|
||||||
|
proxy_pass http://nacos_cluster;
|
||||||
|
proxy_set_header Host $host;
|
||||||
|
proxy_set_header X-Real-IP $remote_addr;
|
||||||
|
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||||
|
proxy_set_header X-Forwarded-Proto $scheme;
|
||||||
|
|
||||||
|
# 超时设置
|
||||||
|
proxy_connect_timeout 30s;
|
||||||
|
proxy_send_timeout 30s;
|
||||||
|
proxy_read_timeout 30s;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
server {
|
||||||
|
listen 80;
|
||||||
|
server_name ui.nacos.com;
|
||||||
|
|
||||||
|
# 反向代理配置
|
||||||
|
location / {
|
||||||
|
proxy_pass http://nacos_ui;
|
||||||
|
proxy_set_header Host $host;
|
||||||
|
proxy_set_header X-Real-IP $remote_addr;
|
||||||
|
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||||
|
proxy_set_header X-Forwarded-Proto $scheme;
|
||||||
|
|
||||||
|
# 超时设置
|
||||||
|
proxy_connect_timeout 30s;
|
||||||
|
proxy_send_timeout 30s;
|
||||||
|
proxy_read_timeout 30s;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -8,8 +8,7 @@ services:
|
|||||||
- traefik-net
|
- traefik-net
|
||||||
ports:
|
ports:
|
||||||
- "80:80"
|
- "80:80"
|
||||||
- "8880:8080"
|
- "8080:8080"
|
||||||
# network_mode: "host" # 主机网络模式
|
|
||||||
volumes:
|
volumes:
|
||||||
- ./traefik.yml:/etc/traefik/traefik.yml
|
- ./traefik.yml:/etc/traefik/traefik.yml
|
||||||
- ./dynamic.yml:/etc/traefik/dynamic.yml # 动态配置文件
|
- ./dynamic.yml:/etc/traefik/dynamic.yml # 动态配置文件
|
||||||
|
|||||||
@@ -1,15 +1,13 @@
|
|||||||
# 请求协议 http or https(建议线上配置证书后,使用https)
|
# 请求协议 http or https(建议线上配置证书后,使用https)
|
||||||
VITE_PREFIX=http://
|
VITE_PREFIX=http://
|
||||||
|
|
||||||
# Nacos 配置中心ip:端口
|
# Nacos 配置中心 ip:端口 | 域名
|
||||||
VITE_NACOS_ADDRESS=192.168.31.101:8848
|
#VITE_NACOS_ADDRESS=cluster.nacos.com
|
||||||
|
VITE_NACOS_ADDRESS=192.168.139.84:8848
|
||||||
|
|
||||||
# traefik 网关的地址
|
|
||||||
VITE_TRAEFIK_ADDRESS=192.168.31.101
|
|
||||||
|
|
||||||
# 注册到 Nacos 的服务名称(微前端模块名称
|
# 注册到 Nacos 的服务名称(微前端模块名称
|
||||||
VITE_SERVER_NAME=app-product
|
VITE_SERVER_NAME=app-product
|
||||||
|
|
||||||
# 注册到 Nacos 的端口,也是前端运行的端口
|
# 注册到 Nacos 的端口,也是前端运行的端口
|
||||||
VITE_SERVER_PORT=1301
|
VITE_SERVER_PORT=1301
|
||||||
|
|
||||||
@@ -25,3 +23,4 @@ VITE_MODEL_SHARED_NAME=app-shared
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,11 +1,9 @@
|
|||||||
# 请求协议 http or https(建议线上配置证书后,使用https)
|
# 请求协议 http or https(建议线上配置证书后,使用https)
|
||||||
VITE_PREFIX=http://
|
VITE_PREFIX=http://
|
||||||
|
|
||||||
# Nacos 配置中心ip:端口
|
# Nacos 配置中心 ip:端口 | 域名
|
||||||
VITE_NACOS_ADDRESS=192.168.31.101:8848
|
VITE_NACOS_ADDRESS=192.168.139.84:8848
|
||||||
|
|
||||||
# traefik 网关的地址
|
|
||||||
VITE_TRAEFIK_ADDRESS=192.168.31.101
|
|
||||||
|
|
||||||
# 注册到 Nacos 的服务名称(微前端模块名称
|
# 注册到 Nacos 的服务名称(微前端模块名称
|
||||||
VITE_SERVER_NAME=app-product
|
VITE_SERVER_NAME=app-product
|
||||||
@@ -13,7 +11,6 @@ VITE_SERVER_NAME=app-product
|
|||||||
# 注册到 Nacos 的端口,也是前端运行的端口
|
# 注册到 Nacos 的端口,也是前端运行的端口
|
||||||
VITE_SERVER_PORT=1301
|
VITE_SERVER_PORT=1301
|
||||||
|
|
||||||
|
|
||||||
#
|
#
|
||||||
# 说明:项目要调用哪些 微前端 模块
|
# 说明:项目要调用哪些 微前端 模块
|
||||||
# 格式:VITE_MODEL_XXXX_NAME=微前端模块名称(模块 的 开发者提供)
|
# 格式:VITE_MODEL_XXXX_NAME=微前端模块名称(模块 的 开发者提供)
|
||||||
@@ -22,6 +19,3 @@ VITE_SERVER_PORT=1301
|
|||||||
|
|
||||||
# shared 共享资源模块
|
# shared 共享资源模块
|
||||||
VITE_MODEL_SHARED_NAME=app-shared
|
VITE_MODEL_SHARED_NAME=app-shared
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -14,8 +14,8 @@
|
|||||||
"type-check": "vue-tsc --build"
|
"type-check": "vue-tsc --build"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"nacos-federation": "link:../nacos-federation",
|
|
||||||
"pinia": "^3.0.3",
|
"pinia": "^3.0.3",
|
||||||
|
"vite-plugin-nacos": "link:../vite-plugin-nacos",
|
||||||
"vue": "^3.5.21",
|
"vue": "^3.5.21",
|
||||||
"vue-router": "^4.5.1"
|
"vue-router": "^4.5.1"
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -1,7 +1,12 @@
|
|||||||
import { defineComponent } from 'vue'
|
import { defineComponent, onMounted } from 'vue'
|
||||||
|
|
||||||
export default defineComponent({
|
export default defineComponent({
|
||||||
setup() {
|
setup() {
|
||||||
|
|
||||||
|
onMounted(() => {
|
||||||
|
console.log("import.meta.env: ", import.meta.env)
|
||||||
|
})
|
||||||
|
|
||||||
return () => (
|
return () => (
|
||||||
<>
|
<>
|
||||||
<div class="order-federation-placeholder">
|
<div class="order-federation-placeholder">
|
||||||
|
|||||||
@@ -22,7 +22,6 @@ export default defineComponent({
|
|||||||
|
|
||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
|
|
||||||
loadProductList()
|
loadProductList()
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|||||||
@@ -5,24 +5,18 @@ import vueDevTools from 'vite-plugin-vue-devtools'
|
|||||||
import federation from '@originjs/vite-plugin-federation';
|
import federation from '@originjs/vite-plugin-federation';
|
||||||
import { fileURLToPath, URL } from "node:url";
|
import { fileURLToPath, URL } from "node:url";
|
||||||
import { visualizer } from 'rollup-plugin-visualizer';
|
import { visualizer } from 'rollup-plugin-visualizer';
|
||||||
|
import { reg, init } from 'vite-plugin-nacos';
|
||||||
|
|
||||||
export default defineConfig(async ({ mode }) => {
|
export default defineConfig(async ({ mode }) => {
|
||||||
const env = loadEnv(mode, process.cwd());
|
const env = loadEnv(mode, process.cwd());
|
||||||
|
const { VITE_MODEL_SHARED_URL } = await init(env)
|
||||||
return {
|
return {
|
||||||
base: `${ env.VITE_PREFIX }${ env.VITE_TRAEFIK_ADDRESS }/${ env.VITE_SERVER_NAME }`,
|
|
||||||
server: {
|
|
||||||
port: Number(env.VITE_SERVER_PORT),
|
|
||||||
host: '0.0.0.0',
|
|
||||||
strictPort: true,
|
|
||||||
cors: true
|
|
||||||
},
|
|
||||||
plugins: [
|
plugins: [
|
||||||
// nacosRegVitePlugin(),
|
reg(),
|
||||||
federation({
|
federation({
|
||||||
name: env.VITE_SERVER_NAME,
|
name: env.VITE_SERVER_NAME,
|
||||||
remotes: {
|
remotes: {
|
||||||
shared: `${ env.VITE_PREFIX }${ env.VITE_TRAEFIK_ADDRESS }/${ env.VITE_MODEL_SHARED_NAME }/assets/remoteEntry.js`
|
shared: `${VITE_MODEL_SHARED_URL}/${env.VITE_MODEL_SHARED_NAME}/assets/remoteEntry.js`
|
||||||
},
|
},
|
||||||
exposes: { // 暴露给主应用的资源(按功能分组)
|
exposes: { // 暴露给主应用的资源(按功能分组)
|
||||||
'./ProductDomain': './src/domains/product/index.ts', // 领域层(实体、服务、接口等)
|
'./ProductDomain': './src/domains/product/index.ts', // 领域层(实体、服务、接口等)
|
||||||
|
|||||||
@@ -1,11 +1,10 @@
|
|||||||
# 请求协议 http or https(建议线上配置证书后,使用https)
|
# 请求协议 http or https(建议线上配置证书后,使用https)
|
||||||
VITE_PREFIX=http://
|
VITE_PREFIX=http://
|
||||||
|
|
||||||
# Nacos 配置中心ip:端口
|
# Nacos 配置中心 ip:端口 | 域名
|
||||||
VITE_NACOS_ADDRESS=192.168.31.101:8848
|
VITE_NACOS_ADDRESS=cluster.nacos.com
|
||||||
|
#VITE_NACOS_ADDRESS=192.168.139.84:8848
|
||||||
|
|
||||||
# traefik 网关的地址
|
|
||||||
VITE_TRAEFIK_ADDRESS=192.168.31.101
|
|
||||||
|
|
||||||
# 注册到 Nacos 的服务名称(微前端模块名称)
|
# 注册到 Nacos 的服务名称(微前端模块名称)
|
||||||
VITE_SERVER_NAME=app-shared
|
VITE_SERVER_NAME=app-shared
|
||||||
|
|||||||
@@ -1,11 +1,9 @@
|
|||||||
# 请求协议 http or https(建议线上配置证书后,使用https)
|
# 请求协议 http or https(建议线上配置证书后,使用https)
|
||||||
VITE_PREFIX=http://
|
VITE_PREFIX=http://
|
||||||
|
|
||||||
# Nacos 配置中心ip:端口
|
# Nacos 配置中心 ip:端口 | 域名
|
||||||
VITE_NACOS_ADDRESS=192.168.31.101:8848
|
#VITE_NACOS_ADDRESS=cluster.nacos.com
|
||||||
|
VITE_NACOS_ADDRESS=192.168.139.84:8848
|
||||||
# traefik 网关的地址
|
|
||||||
VITE_TRAEFIK_ADDRESS=192.168.31.101
|
|
||||||
|
|
||||||
# 注册到 Nacos 的服务名称(微前端模块名称)
|
# 注册到 Nacos 的服务名称(微前端模块名称)
|
||||||
VITE_SERVER_NAME=app-shared
|
VITE_SERVER_NAME=app-shared
|
||||||
|
|||||||
@@ -17,7 +17,7 @@
|
|||||||
"@originjs/vite-plugin-federation": "1.3.8",
|
"@originjs/vite-plugin-federation": "1.3.8",
|
||||||
"axios": "^1.12.2",
|
"axios": "^1.12.2",
|
||||||
"element-plus": "^2.11.3",
|
"element-plus": "^2.11.3",
|
||||||
"nacos-federation": "link:../nacos-federation",
|
"vite-plugin-nacos": "link:../vite-plugin-nacos",
|
||||||
"vue": "^3.5.21"
|
"vue": "^3.5.21"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
|
|||||||
@@ -6,21 +6,15 @@ import vueJsx from '@vitejs/plugin-vue-jsx'
|
|||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
import vue from '@vitejs/plugin-vue';
|
import vue from '@vitejs/plugin-vue';
|
||||||
import visualizer from 'rollup-plugin-visualizer';
|
import visualizer from 'rollup-plugin-visualizer';
|
||||||
|
import { reg, init } from 'vite-plugin-nacos';
|
||||||
|
|
||||||
|
|
||||||
export default defineConfig(async ({ mode }): Promise<UserConfig> => {
|
export default defineConfig(async ({ mode }): Promise<UserConfig> => {
|
||||||
const env = loadEnv(mode, process.cwd());
|
const env = loadEnv(mode, process.cwd());
|
||||||
|
init(env)
|
||||||
return {
|
return {
|
||||||
base: `${ env.VITE_PREFIX }${ env.VITE_TRAEFIK_ADDRESS }/${ env.VITE_SERVER_NAME }`,
|
|
||||||
server: {
|
|
||||||
port: Number(env.VITE_SERVER_PORT),
|
|
||||||
host: '0.0.0.0',
|
|
||||||
strictPort: true,
|
|
||||||
cors: true
|
|
||||||
},
|
|
||||||
plugins: [
|
plugins: [
|
||||||
// nacosRegVitePlugin(),
|
reg(),
|
||||||
federation({
|
federation({
|
||||||
name: env.VITE_SERVER_NAME,
|
name: env.VITE_SERVER_NAME,
|
||||||
exposes: {
|
exposes: {
|
||||||
|
|||||||
@@ -1,11 +1,17 @@
|
|||||||
# 请求协议 http or https(建议线上配置证书后,使用https)
|
# 请求协议 http or https(建议线上配置证书后,使用https)
|
||||||
VITE_PREFIX=http://
|
VITE_PREFIX=http://
|
||||||
|
|
||||||
# Nacos 配置中心ip:端口
|
#
|
||||||
VITE_NACOS_ADDRESS=192.168.139.84:8848
|
# Nacos 集群的地址
|
||||||
|
# 注意:
|
||||||
|
# 1: 内网微前端模块,直接填内网Nacos IP:端口 就行
|
||||||
|
# 2: main-app位于公网,填 网关的公网地址
|
||||||
|
#
|
||||||
|
|
||||||
|
# 网关地址
|
||||||
|
VITE_NACOS_ADDRESS=nacos.ddd.com:80
|
||||||
|
# VITE_NACOS_ADDRESS=192.168.139.84:8848
|
||||||
|
|
||||||
# traefik 网关的地址
|
|
||||||
VITE_TRAEFIK_ADDRESS=192.168.31.101
|
|
||||||
|
|
||||||
# 注册到 Nacos 的服务名称(微前端模块名称)
|
# 注册到 Nacos 的服务名称(微前端模块名称)
|
||||||
VITE_SERVER_NAME=main-app
|
VITE_SERVER_NAME=main-app
|
||||||
|
|||||||
@@ -1,8 +1,9 @@
|
|||||||
# 请求协议 http or https(建议线上配置证书后,使用https)
|
# 请求协议 http or https(建议线上配置证书后,使用https)
|
||||||
VITE_PREFIX=http://
|
VITE_PREFIX=http://
|
||||||
|
|
||||||
# Nacos 配置中心ip:端口
|
# Nacos 配置中心 ip:端口 | 域名
|
||||||
VITE_NACOS_ADDRESS=192.168.31.101:8848
|
VITE_NACOS_ADDRESS=cluster.nacos.com
|
||||||
|
#VITE_NACOS_ADDRESS=192.168.139.84:8848
|
||||||
|
|
||||||
# traefik 网关的地址
|
# traefik 网关的地址
|
||||||
VITE_TRAEFIK_ADDRESS=192.168.31.101
|
VITE_TRAEFIK_ADDRESS=192.168.31.101
|
||||||
|
|||||||
@@ -11,8 +11,8 @@
|
|||||||
"type-check": "vue-tsc --build"
|
"type-check": "vue-tsc --build"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"nacos-federation": "link:../nacos-federation",
|
|
||||||
"pinia": "^3.0.3",
|
"pinia": "^3.0.3",
|
||||||
|
"vite-plugin-nacos": "link:../vite-plugin-nacos",
|
||||||
"vue": "^3.5.21",
|
"vue": "^3.5.21",
|
||||||
"vue-facing-decorator": "^4.0.1",
|
"vue-facing-decorator": "^4.0.1",
|
||||||
"vue-router": "^4.5.1"
|
"vue-router": "^4.5.1"
|
||||||
|
|||||||
@@ -15,6 +15,7 @@ class Main {
|
|||||||
.mount('#app')
|
.mount('#app')
|
||||||
|
|
||||||
// TODO 需要解决的地方
|
// TODO 需要解决的地方
|
||||||
|
console.log("import.meta.env: ", import.meta.env)
|
||||||
window.__APP_CONFIG__ = import.meta.env;
|
window.__APP_CONFIG__ = import.meta.env;
|
||||||
|
|
||||||
elementPlus.init(app)
|
elementPlus.init(app)
|
||||||
|
|||||||
@@ -1,45 +1,22 @@
|
|||||||
import path from 'path'
|
import path from 'path'
|
||||||
|
|
||||||
import { defineConfig, loadEnv } from 'vite'
|
import { defineConfig, loadEnv, ConfigEnv, mergeConfig } from 'vite'
|
||||||
import vueJsx from '@vue3-oop/plugin-vue-jsx'
|
import vueJsx from '@vue3-oop/plugin-vue-jsx'
|
||||||
import federation from '@originjs/vite-plugin-federation';
|
import federation from '@originjs/vite-plugin-federation';
|
||||||
import { nacosRegVitePlugin } from "nacos-federation";
|
import { reg, init } from 'vite-plugin-nacos';
|
||||||
import { visualizer } from 'rollup-plugin-visualizer';
|
import { visualizer } from 'rollup-plugin-visualizer';
|
||||||
|
|
||||||
export default defineConfig(async ({ mode }) => {
|
export default defineConfig(async (config: ConfigEnv) => {
|
||||||
const env = loadEnv(mode, process.cwd());
|
const env = loadEnv(config.mode, process.cwd());
|
||||||
// const nacos-cluster = await nacosServiceManage.create({
|
|
||||||
// serverList: env.VITE_NACOS_ADDRESS,
|
|
||||||
// serviceName: env.VITE_SERVER_NAME,
|
|
||||||
// port: Number(env.VITE_SERVER_PORT)
|
|
||||||
// });
|
|
||||||
// const productUrl = await nacos-cluster.find(env.VITE_MODEL_PRODUCT_NAME)
|
|
||||||
// const sharedUrl = await nacos-cluster.find(env.VITE_MODEL_SHARED_NAME)
|
|
||||||
|
|
||||||
return {
|
return mergeConfig({
|
||||||
server: {
|
|
||||||
port: Number(env.VITE_SERVER_PORT),
|
|
||||||
host: '::',
|
|
||||||
strictPort: true,
|
|
||||||
},
|
|
||||||
plugins: [
|
plugins: [
|
||||||
nacosRegVitePlugin(),
|
reg(),
|
||||||
vueJsx(),
|
|
||||||
federation({
|
federation({
|
||||||
name: env.VITE_SERVER_NAME,
|
name: env.VITE_SERVER_NAME,
|
||||||
remotes: {
|
remotes: {
|
||||||
// 【弃用】基于 Nacos 服务发现获取 微前端模块的地址 192.168.31.101:1301
|
product: `${env.VITE_PREFIX}${env.VITE_NACOS_ADDRESS}/${env.VITE_MODEL_PRODUCT_NAME}/assets/remoteEntry.js`,
|
||||||
// product: `${ productUrl }/assets/remoteEntry.js`,
|
shared: `${env.VITE_PREFIX}${env.VITE_NACOS_ADDRESS}/${env.VITE_MODEL_SHARED_NAME}/assets/remoteEntry.js`
|
||||||
// shared: `${ sharedUrl }/assets/remoteEntry.js`
|
|
||||||
|
|
||||||
// 实现:限流与熔断,重试,IP 白名单,压缩等
|
|
||||||
// 基于 c 网关,由网关去寻找 微前端模块的地址
|
|
||||||
// 网关的地址是 nodejs脚本 定时10秒访问Nacos api 后,生成Traefik配置文件dynamic.yml,
|
|
||||||
// 并把配置实时同步到Traefik中,如果 xxx微前端模块停止运行那么就会从 Nacos服务中注销,
|
|
||||||
// 那么dynamic.yml配置文件就会自动删减被下线的网关映射
|
|
||||||
|
|
||||||
product: `${ env.VITE_PREFIX }${ env.VITE_TRAEFIK_ADDRESS }/${ env.VITE_MODEL_PRODUCT_NAME }/assets/remoteEntry.js`,
|
|
||||||
shared: `${ env.VITE_PREFIX }${ env.VITE_TRAEFIK_ADDRESS }/${ env.VITE_MODEL_SHARED_NAME }/assets/remoteEntry.js`
|
|
||||||
},
|
},
|
||||||
shared: {
|
shared: {
|
||||||
vue: { requiredVersion: '^3.5.18' },
|
vue: { requiredVersion: '^3.5.18' },
|
||||||
@@ -47,6 +24,7 @@ export default defineConfig(async ({ mode }) => {
|
|||||||
pinia: { requiredVersion: '^3.0.3' }
|
pinia: { requiredVersion: '^3.0.3' }
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
|
vueJsx(),
|
||||||
visualizer({
|
visualizer({
|
||||||
title: "主应用依赖分析",
|
title: "主应用依赖分析",
|
||||||
filename: 'dist/stats.html', // 分析文件输出路径
|
filename: 'dist/stats.html', // 分析文件输出路径
|
||||||
@@ -73,5 +51,5 @@ export default defineConfig(async ({ mode }) => {
|
|||||||
'@domains': path.resolve(__dirname, './src/domains/')
|
'@domains': path.resolve(__dirname, './src/domains/')
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}, await init(env))
|
||||||
})
|
})
|
||||||
|
|||||||
@@ -1,4 +0,0 @@
|
|||||||
// 从插件实现文件导入
|
|
||||||
export * from './vite-plugin-nacos';
|
|
||||||
export * from './nacosServiceManage';
|
|
||||||
export * from './utils';
|
|
||||||
@@ -1,36 +0,0 @@
|
|||||||
import { networkInterfaces } from "os";
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 获取本机局域网IPv4地址
|
|
||||||
* @returns 局域网IP地址(如 '192.168.1.100')
|
|
||||||
*/
|
|
||||||
export function getLocalIP(): string {
|
|
||||||
|
|
||||||
const interfaces = networkInterfaces();
|
|
||||||
for (const devName in interfaces) {
|
|
||||||
const iface = interfaces[devName];
|
|
||||||
if (!iface) continue;
|
|
||||||
|
|
||||||
for (const alias of iface) {
|
|
||||||
if (
|
|
||||||
alias.family === 'IPv4' &&
|
|
||||||
alias.address !== '127.0.0.1' &&
|
|
||||||
!alias.internal
|
|
||||||
) {
|
|
||||||
return alias.address;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return '127.0.0.1';
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 格式化服务地址
|
|
||||||
* @param ip IP地址
|
|
||||||
* @param port 端口号
|
|
||||||
* @returns 完整服务地址(如 'http://192.168.1.100:1300')
|
|
||||||
*/
|
|
||||||
export function formatServiceUrl(ip: string, port: number): string {
|
|
||||||
return `http://${ ip }:${ port }`;
|
|
||||||
}
|
|
||||||
@@ -1,123 +0,0 @@
|
|||||||
import { loadEnv, Plugin, UserConfig } from 'vite';
|
|
||||||
import { getLocalIP, nacosServiceManage, RegisterOptions } from './index';
|
|
||||||
import chalk from 'chalk';
|
|
||||||
|
|
||||||
const log = console.log;
|
|
||||||
|
|
||||||
export function nacosRegVitePlugin(options?: Partial<RegisterOptions>): Plugin {
|
|
||||||
let nacosInstance: nacosServiceManage | null = null;
|
|
||||||
|
|
||||||
return {
|
|
||||||
name: 'vite-plugin-nacos',
|
|
||||||
async config(userConfig: UserConfig, { mode }) {
|
|
||||||
// 修改base,增加资源来源地址,修复资源错误加载的问题
|
|
||||||
const env = loadEnv(mode, process.cwd());
|
|
||||||
let baseUrl = ""
|
|
||||||
// 主模块 main-app 不加 base 前缀,其他模块都加,
|
|
||||||
// 也是为了命中 traefik 路由代理
|
|
||||||
if (env.VITE_SERVER_NAME != "main-app") {
|
|
||||||
baseUrl = `${ env.VITE_SERVER_NAME }/`
|
|
||||||
}
|
|
||||||
return {
|
|
||||||
// http(https)://前端运行的服务器所在ip/前端模块名
|
|
||||||
base: `${ env.VITE_PREFIX }${ getLocalIP() }/${ baseUrl }`,
|
|
||||||
}
|
|
||||||
},
|
|
||||||
async configResolved(config) {
|
|
||||||
|
|
||||||
const env = config.env;
|
|
||||||
const registerOptions: RegisterOptions = {
|
|
||||||
serverList: env.VITE_NACOS_ADDRESS || options?.serverList!,
|
|
||||||
serviceName: env.VITE_SERVER_NAME || options?.serviceName!,
|
|
||||||
port: Number(env.VITE_SERVER_PORT || options?.port),
|
|
||||||
namespace: options?.namespace || 'public'
|
|
||||||
};
|
|
||||||
|
|
||||||
// 验证必要配置
|
|
||||||
if (!registerOptions.serverList) {
|
|
||||||
throw new Error('[nacos-cluster-federation] 缺少Nacos服务列表配置,请设置VITE_NACOS_ADDRESS环境变量或插件选项');
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!registerOptions.serviceName) {
|
|
||||||
throw new Error('[nacos-cluster-federation] 缺少服务名称配置,请设置VITE_SERVER_NAME环境变量或插件选项');
|
|
||||||
}
|
|
||||||
if (!registerOptions.port) {
|
|
||||||
throw new Error('[nacos-cluster-federation] 缺少服务端口配置,请设置VITE_SERVER_PORT环境变量或插件选项');
|
|
||||||
}
|
|
||||||
|
|
||||||
// 初始化Nacos实例
|
|
||||||
nacosInstance = await nacosServiceManage.create(registerOptions);
|
|
||||||
|
|
||||||
const baseUrl = await nacosInstance.getConfig("baseUrl", "DEFAULT_GROUP")
|
|
||||||
const baseUrlConfig = baseUrl ? JSON.parse(baseUrl) : {};
|
|
||||||
|
|
||||||
baseUrlConfig.httpTimeOut = await nacosInstance.getConfig("httpTimeOut", "DEFAULT_GROUP")
|
|
||||||
|
|
||||||
|
|
||||||
const customizeEnv: Record<string, string> = {};
|
|
||||||
Object.keys(baseUrlConfig).forEach(key => {
|
|
||||||
const envKey = `import.meta.env.VITE_${ key.toUpperCase() }`;
|
|
||||||
customizeEnv[envKey] = JSON.stringify(baseUrlConfig[key]);
|
|
||||||
});
|
|
||||||
|
|
||||||
// @ts-ignore
|
|
||||||
Object.assign(config.define, customizeEnv);
|
|
||||||
Logs(env)
|
|
||||||
},
|
|
||||||
async closeBundle() {
|
|
||||||
// // 服务关闭时注销Nacos实例
|
|
||||||
// if (nacosInstance) {
|
|
||||||
// await nacosInstance.destroy();
|
|
||||||
// }
|
|
||||||
},
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function Logs(env: Record<string, any>) {
|
|
||||||
const moduleName = []
|
|
||||||
for (const key in env) {
|
|
||||||
if (key.includes("VITE_MODEL_")) {
|
|
||||||
moduleName.push(env[key]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
moduleName.length == 0 ? moduleName.push('无') : null
|
|
||||||
const webUI = env.VITE_NACOS_ADDRESS.split(":")[0]
|
|
||||||
console.log()
|
|
||||||
|
|
||||||
console.log(dedentTemplateString(`
|
|
||||||
${ chalk.blue.bold('微服务工具:') }
|
|
||||||
${ chalk.green('➜') } Naco 配置中心: ${ env.VITE_PREFIX }${ env.VITE_NACOS_ADDRESS }
|
|
||||||
${ chalk.green('➜') } WebUi: ${ env.VITE_PREFIX }${ webUI }:8085
|
|
||||||
${ chalk.green('➜') } Prometheus 监控: ${ env.VITE_PREFIX }${ webUI }:9090
|
|
||||||
${ chalk.green('➜') } Grafana 面板: ${ env.VITE_PREFIX }${ webUI }:3000
|
|
||||||
${ chalk.green('➜') } Traefik 网关: ${ env.VITE_PREFIX }${ env.VITE_TRAEFIK_ADDRESS }
|
|
||||||
${ chalk.green('➜') } WebUi: ${ env.VITE_PREFIX }${ env.VITE_TRAEFIK_ADDRESS }:8880
|
|
||||||
|
|
||||||
${ chalk.blue.bold('微前端信息:') }
|
|
||||||
${ chalk.green('➜') } 主模块:${ chalk.green(env.VITE_SERVER_NAME) }
|
|
||||||
|
|
||||||
${ chalk.blue.bold('调用模块:') }
|
|
||||||
${ chalk.green('➜') } [ ${ chalk.yellow(moduleName) } ]
|
|
||||||
`))
|
|
||||||
console.log()
|
|
||||||
}
|
|
||||||
|
|
||||||
function dedentTemplateString(str: string) {
|
|
||||||
// 分割成行
|
|
||||||
const lines = str.split('\n');
|
|
||||||
|
|
||||||
// 移除首尾空行
|
|
||||||
if (lines[0].trim() === '') lines.shift();
|
|
||||||
if (lines[lines.length - 1].trim() === '') lines.pop();
|
|
||||||
|
|
||||||
// 找到最小缩进量
|
|
||||||
const minIndent = lines.reduce((min, line) => {
|
|
||||||
if (line.trim() === '') return min; // 跳过空行
|
|
||||||
// @ts-ignore
|
|
||||||
const indent = line.match(/^\s*/)[0].length;
|
|
||||||
return indent < min ? indent : min;
|
|
||||||
}, Infinity);
|
|
||||||
|
|
||||||
// 移除统一缩进
|
|
||||||
return lines.map(line => line.slice(minIndent)).join('\n');
|
|
||||||
}
|
|
||||||
@@ -6,6 +6,12 @@
|
|||||||
|
|
||||||
主模块:main-app -> Traefik -> ConfigServer(nacos-federation) -> Nacos
|
主模块:main-app -> Traefik -> ConfigServer(nacos-federation) -> Nacos
|
||||||
|
|
||||||
|
main-app 发送 http 请求
|
||||||
|
/nacos/reg
|
||||||
|
参数:
|
||||||
|
ip,port
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
2 获取配置
|
2 获取配置
|
||||||
@@ -15,6 +21,9 @@
|
|||||||
主模块: main-app -> Traefik -> ConfigServer(nacos-federation) -> Nacos
|
主模块: main-app -> Traefik -> ConfigServer(nacos-federation) -> Nacos
|
||||||
|
|
||||||
|
|
||||||
|
注意:
|
||||||
|
|
||||||
|
|
||||||
增加功能:
|
增加功能:
|
||||||
|
|
||||||
认证授权机制
|
认证授权机制
|
||||||
@@ -1,7 +1,7 @@
|
|||||||
{
|
{
|
||||||
"name": "nacos-federation",
|
"name": "vite-plugin-nacos",
|
||||||
"version": "1.1.0",
|
"version": "1.1.0",
|
||||||
"description": "Nacos服务注册与发现插件,用于模块联邦",
|
"description": "Vite 插件,实现Nacos服务注册与发现插件,用于模块联邦",
|
||||||
"main": "dist/index.js",
|
"main": "dist/index.js",
|
||||||
"types": "dist/index.d.ts",
|
"types": "dist/index.d.ts",
|
||||||
"files": [
|
"files": [
|
||||||
56
front-end/vite-plugin-nacos/src/index.ts
Normal file
56
front-end/vite-plugin-nacos/src/index.ts
Normal file
@@ -0,0 +1,56 @@
|
|||||||
|
// 从插件实现文件导入
|
||||||
|
export * from './vite-plugin-nacos';
|
||||||
|
export * from './utils';
|
||||||
|
import { log } from 'console';
|
||||||
|
import { nacosServiceManage } from './nacosServiceManage';
|
||||||
|
import { mergeConfig } from 'vite';
|
||||||
|
|
||||||
|
export const init = async (env: Record<string, string>) => {
|
||||||
|
const nacos = await nacosServiceManage.create({
|
||||||
|
serverList: env.VITE_NACOS_ADDRESS,
|
||||||
|
serviceName: env.VITE_SERVER_NAME,
|
||||||
|
port: Number(env.VITE_SERVER_PORT)
|
||||||
|
});
|
||||||
|
|
||||||
|
if (env.VITE_SERVER_NAME === "main-app") {
|
||||||
|
log("不需要服务发现,进行配置发现...")
|
||||||
|
|
||||||
|
const baseUrl = await nacos.getConfig("baseUrl", "DEFAULT_GROUP")
|
||||||
|
const baseUrlConfig = baseUrl ? JSON.parse(baseUrl) : {};
|
||||||
|
baseUrlConfig.httpTimeOut = await nacos.getConfig("httpTimeOut", "DEFAULT_GROUP")
|
||||||
|
|
||||||
|
// 将新配置处理一下,需要 JSON.stringify
|
||||||
|
const customizeEnv: Record<string, Record<string, string>> = { define: {} };
|
||||||
|
Object.keys(baseUrlConfig).forEach(key => {
|
||||||
|
customizeEnv.define[`import.meta.env.VITE_${key.toUpperCase()}`] = JSON.stringify(baseUrlConfig[key]);
|
||||||
|
});
|
||||||
|
|
||||||
|
// 将老配置处理一下,需要 JSON.stringify
|
||||||
|
const existingDefine: Record<string, Record<string, string>> = { define: {} }
|
||||||
|
Object.keys(env).forEach(key => {
|
||||||
|
existingDefine.define[`import.meta.env.${key}`] = JSON.stringify(env[key])
|
||||||
|
})
|
||||||
|
|
||||||
|
return mergeConfig(existingDefine, customizeEnv)
|
||||||
|
|
||||||
|
} else {
|
||||||
|
log("进行服务发现,获取依赖模块的地址...")
|
||||||
|
let modelName = []
|
||||||
|
for (const key in env) {
|
||||||
|
if (key.includes("VITE_MODEL_")) modelName.push(env[key])
|
||||||
|
}
|
||||||
|
|
||||||
|
const modelUrl: Record<string, string> = {}
|
||||||
|
|
||||||
|
if (modelName.length !== 0) {
|
||||||
|
for (const val of modelName) modelUrl[`VITE_MODEL_${val.replace("app-", "").toUpperCase()}_URL`] = await nacos.find(val)
|
||||||
|
}
|
||||||
|
|
||||||
|
log("modelUrl: ", modelUrl)
|
||||||
|
return modelUrl
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
@@ -4,7 +4,7 @@ import chalk from 'chalk';
|
|||||||
|
|
||||||
const logger = console;
|
const logger = console;
|
||||||
|
|
||||||
export interface RegisterOptions {
|
interface RegisterOptions {
|
||||||
serverList: string;
|
serverList: string;
|
||||||
/** 服务名称(如 'main-app') */
|
/** 服务名称(如 'main-app') */
|
||||||
serviceName: string;
|
serviceName: string;
|
||||||
@@ -42,21 +42,13 @@ export class nacosServiceManage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
const instance = new nacosServiceManage(option);
|
const instance = new nacosServiceManage(option);
|
||||||
// await instance.initClient();
|
await instance.initClient();
|
||||||
// await instance.initConfig();
|
await instance.initConfig();
|
||||||
|
|
||||||
this.instanceMap.set(configKey, instance);
|
this.instanceMap.set(configKey, instance);
|
||||||
return instance;
|
return instance;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* 生成配置唯一标识:基于 serverList + namespace + serviceName(确保不同配置对应不同实例)
|
|
||||||
*/
|
|
||||||
private static getConfigKey(option: RegisterOptions): string {
|
|
||||||
const namespace = option.namespace || 'public';
|
|
||||||
return `${ option.serverList }-${ namespace }-${ option.serviceName }`;
|
|
||||||
}
|
|
||||||
|
|
||||||
// 服务注册
|
// 服务注册
|
||||||
public async initClient() {
|
public async initClient() {
|
||||||
this.nacosClient = new NacosNamingClient({
|
this.nacosClient = new NacosNamingClient({
|
||||||
@@ -69,15 +61,11 @@ export class nacosServiceManage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取配置
|
* 生成配置唯一标识:基于 serverList + namespace + serviceName(确保不同配置对应不同实例)
|
||||||
* @param dataId
|
|
||||||
* @param group
|
|
||||||
*/
|
*/
|
||||||
async getConfig(dataId: string, group: string = "DEFAULT_GROUP") {
|
private static getConfigKey(option: RegisterOptions): string {
|
||||||
const res = await this.configClient.getConfig(dataId, group)
|
const namespace = option.namespace || 'public';
|
||||||
console.log()
|
return `${ option.serverList }-${ namespace }-${ option.serviceName }`;
|
||||||
console.log(`${ chalk.blue('[nacos-cluster-federation] 配置发现:') }\n ${ chalk.green('➜') } ${ chalk.green(dataId) } 的配置为: ${ chalk.green(res) }`)
|
|
||||||
return res;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -93,16 +81,18 @@ export class nacosServiceManage {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* 初始化配置服务
|
|
||||||
* @private
|
|
||||||
*/
|
|
||||||
private async initConfig() {
|
|
||||||
this.configClient = new NacosConfigClient({
|
|
||||||
serverAddr: this.initOptions.serverList,
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取配置
|
||||||
|
* @param dataId
|
||||||
|
* @param group
|
||||||
|
*/
|
||||||
|
async getConfig(dataId: string, group: string = "DEFAULT_GROUP") {
|
||||||
|
const res = await this.configClient.getConfig(dataId, group)
|
||||||
|
console.log()
|
||||||
|
console.log(`${ chalk.blue('[nacos-cluster-federation] 配置发现:') }\n ${ chalk.green('➜') } ${ chalk.green(dataId) } 的配置为: ${ chalk.green(res) }`)
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 从Nacos发现服务地址
|
* 从Nacos发现服务地址
|
||||||
@@ -118,6 +108,29 @@ export class nacosServiceManage {
|
|||||||
return formatServiceUrl(instances[0].ip, instances[0].port);
|
return formatServiceUrl(instances[0].ip, instances[0].port);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 初始化配置服务
|
||||||
|
* @private
|
||||||
|
*/
|
||||||
|
private async initConfig() {
|
||||||
|
this.configClient = new NacosConfigClient({
|
||||||
|
serverAddr: this.initOptions.serverList,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 注册服务到Nacos并返回客户端实例
|
||||||
|
*/
|
||||||
|
private async reg() {
|
||||||
|
const { serviceName, port } = this.initOptions;
|
||||||
|
const ip = getLocalIP();
|
||||||
|
// @ts-ignore
|
||||||
|
await this.nacosClient.registerInstance(serviceName, { port, ip })
|
||||||
|
logger.log()
|
||||||
|
logger.log(chalk.blue("[nacos-cluster-federation] 服务注册:"))
|
||||||
|
logger.log(` ${ chalk.green('➜') } ${ chalk.green(serviceName) } (${ formatServiceUrl(ip, port) }) 已注册到配置中心!`);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 手动销毁实例(如服务下线时)
|
* 手动销毁实例(如服务下线时)
|
||||||
*/
|
*/
|
||||||
@@ -134,18 +147,5 @@ export class nacosServiceManage {
|
|||||||
nacosServiceManage.instanceMap.delete(configKey);
|
nacosServiceManage.instanceMap.delete(configKey);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* 注册服务到Nacos并返回客户端实例
|
|
||||||
*/
|
|
||||||
private async reg() {
|
|
||||||
const { serviceName, port } = this.initOptions;
|
|
||||||
const ip = getLocalIP();
|
|
||||||
// @ts-ignore
|
|
||||||
await this.nacosClient.registerInstance(serviceName, { port, ip })
|
|
||||||
logger.log()
|
|
||||||
logger.log(chalk.blue("[nacos-cluster-federation] 服务注册:"))
|
|
||||||
logger.log(` ${ chalk.green('➜') } ${ chalk.green(serviceName) } (${ formatServiceUrl(ip, port) }) 已注册到配置中心!`);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
52
front-end/vite-plugin-nacos/src/utils.ts
Normal file
52
front-end/vite-plugin-nacos/src/utils.ts
Normal file
@@ -0,0 +1,52 @@
|
|||||||
|
import { networkInterfaces } from "os";
|
||||||
|
|
||||||
|
|
||||||
|
class Utils {
|
||||||
|
/**
|
||||||
|
* 获取本机局域网IPv4地址
|
||||||
|
* @returns 局域网IP地址(如 '192.168.1.100')
|
||||||
|
*/
|
||||||
|
static getLocalIP(): string {
|
||||||
|
const interfaces = networkInterfaces();
|
||||||
|
for (const devName in interfaces) {
|
||||||
|
const iface = interfaces[devName];
|
||||||
|
if (!iface) continue;
|
||||||
|
|
||||||
|
for (const alias of iface) {
|
||||||
|
if (
|
||||||
|
alias.family === 'IPv4' &&
|
||||||
|
alias.address !== '127.0.0.1' &&
|
||||||
|
!alias.internal
|
||||||
|
) {
|
||||||
|
return alias.address;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return '127.0.0.1';
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 格式化服务地址
|
||||||
|
* @param ip IP地址
|
||||||
|
* @param port 端口号
|
||||||
|
* @returns 完整服务地址(如 'http://192.168.1.100:1300')
|
||||||
|
*/
|
||||||
|
static formatServiceUrl(ip: string, port: number): string {
|
||||||
|
return `http://${ ip }:${ port }`;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* VITE_DEPEND_MODEL_NAME_LIST 配置 格式化成数组
|
||||||
|
* app-shared,app-test
|
||||||
|
* @param arg ["app-shared", "app-test"]
|
||||||
|
*/
|
||||||
|
static dependModel(arg: string): string[] {
|
||||||
|
return arg.split(',').map(name => name.trim()).filter(Boolean) || [];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export const {
|
||||||
|
getLocalIP, formatServiceUrl,
|
||||||
|
dependModel
|
||||||
|
} = Utils
|
||||||
144
front-end/vite-plugin-nacos/src/vite-plugin-nacos.ts
Normal file
144
front-end/vite-plugin-nacos/src/vite-plugin-nacos.ts
Normal file
@@ -0,0 +1,144 @@
|
|||||||
|
import { loadEnv, Plugin, UserConfig } from 'vite';
|
||||||
|
import { NacosConfigClient, NacosNamingClient } from 'nacos';
|
||||||
|
import { getLocalIP, dependModel, formatServiceUrl } from './utils';
|
||||||
|
import chalk from 'chalk';
|
||||||
|
|
||||||
|
const logger = console;
|
||||||
|
|
||||||
|
export interface RegisterOptions {
|
||||||
|
serverList: string;
|
||||||
|
/** 服务名称(如 'main-app') */
|
||||||
|
serviceName: string;
|
||||||
|
/** 服务端口号 */
|
||||||
|
port: number;
|
||||||
|
/** 命名空间(用于环境隔离,默认 'public') */
|
||||||
|
namespace?: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function reg(options?: Partial<RegisterOptions>): Plugin {
|
||||||
|
return {
|
||||||
|
name: 'vite-plugin-nacos',
|
||||||
|
async config(config: UserConfig, { mode }) {
|
||||||
|
// 修改base,增加资源来源地址,修复资源错误加载的问题
|
||||||
|
const env = loadEnv(mode, process.cwd());
|
||||||
|
let baseUrl = ""
|
||||||
|
|
||||||
|
// 主模块 main-app 不加 base 前缀,其他模块都加,
|
||||||
|
// 也是为了命中 traefik 路由代理
|
||||||
|
if (env.VITE_SERVER_NAME != "main-app") {
|
||||||
|
baseUrl = `${env.VITE_SERVER_NAME}/`
|
||||||
|
}
|
||||||
|
|
||||||
|
return {
|
||||||
|
server: {
|
||||||
|
allowedHosts: [
|
||||||
|
'.ddd.com',
|
||||||
|
],
|
||||||
|
port: Number(env.VITE_SERVER_PORT),
|
||||||
|
host: '::',
|
||||||
|
strictPort: true,
|
||||||
|
cors: true
|
||||||
|
},
|
||||||
|
// TODO dist 上线到服务器后,http://192.168.31.101:1301/ 会出问题
|
||||||
|
// http(https)://前端运行的服务器所在ip/前端模块名
|
||||||
|
base: `${env.VITE_PREFIX}${getLocalIP()}:${env.VITE_SERVER_PORT}/${baseUrl}`
|
||||||
|
};
|
||||||
|
},
|
||||||
|
async configResolved(config) {
|
||||||
|
const env = config.env;
|
||||||
|
|
||||||
|
// const registerOptions: RegisterOptions = {
|
||||||
|
// serverList: env.VITE_NACOS_ADDRESS || options?.serverList!,
|
||||||
|
// serviceName: env.VITE_SERVER_NAME || options?.serviceName!,
|
||||||
|
// port: Number(env.VITE_SERVER_PORT || options?.port),
|
||||||
|
// namespace: options?.namespace || 'public'
|
||||||
|
// };
|
||||||
|
//
|
||||||
|
// // 验证必要配置
|
||||||
|
// if (!registerOptions.serverList) {
|
||||||
|
// throw new Error('[nacos-cluster-federation] 缺少Nacos服务列表配置,请设置VITE_NACOS_ADDRESS环境变量或插件选项');
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// if (!registerOptions.serviceName) {
|
||||||
|
// throw new Error('[nacos-cluster-federation] 缺少服务名称配置,请设置VITE_SERVER_NAME环境变量或插件选项');
|
||||||
|
// }
|
||||||
|
// if (!registerOptions.port) {
|
||||||
|
// throw new Error('[nacos-cluster-federation] 缺少服务端口配置,请设置VITE_SERVER_PORT环境变量或插件选项');
|
||||||
|
// }
|
||||||
|
|
||||||
|
// // 初始化Nacos实例
|
||||||
|
// nacosInstance = await nacosServiceManage.create(registerOptions);
|
||||||
|
//
|
||||||
|
// const baseUrl = await nacosInstance.getConfig("baseUrl", "DEFAULT_GROUP")
|
||||||
|
// const baseUrlConfig = baseUrl ? JSON.parse(baseUrl) : {};
|
||||||
|
//
|
||||||
|
// baseUrlConfig.httpTimeOut = await nacosInstance.getConfig("httpTimeOut", "DEFAULT_GROUP")
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// const customizeEnv: Record<string, string> = {};
|
||||||
|
// Object.keys(baseUrlConfig).forEach(key => {
|
||||||
|
// const envKey = `import.meta.env.VITE_${ key.toUpperCase() }`;
|
||||||
|
// customizeEnv[envKey] = JSON.stringify(baseUrlConfig[key]);
|
||||||
|
// });
|
||||||
|
//
|
||||||
|
// // @ts-ignore
|
||||||
|
// Object.assign(config.define, customizeEnv);
|
||||||
|
// Logs(env)
|
||||||
|
},
|
||||||
|
async closeBundle() {
|
||||||
|
// // 服务关闭时注销Nacos实例
|
||||||
|
// if (nacosInstance) {
|
||||||
|
// await nacosInstance.destroy();
|
||||||
|
// }
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function Logs(env: Record<string, any>) {
|
||||||
|
const moduleName = []
|
||||||
|
for (const key in env) {
|
||||||
|
if (key.includes("VITE_MODEL_")) {
|
||||||
|
moduleName.push(env[key]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
moduleName.length == 0 ? moduleName.push('无') : null
|
||||||
|
const webUI = env.VITE_NACOS_ADDRESS.split(":")[0]
|
||||||
|
console.log()
|
||||||
|
|
||||||
|
console.log(dedentTemplateString(`
|
||||||
|
${chalk.blue.bold('微服务工具:')}
|
||||||
|
${chalk.green('➜')} Naco 配置中心: ${env.VITE_PREFIX}${env.VITE_NACOS_ADDRESS}
|
||||||
|
${chalk.green('➜')} WebUi: ${env.VITE_PREFIX}${webUI}:8085
|
||||||
|
${chalk.green('➜')} Prometheus 监控: ${env.VITE_PREFIX}${webUI}:9090
|
||||||
|
${chalk.green('➜')} Grafana 面板: ${env.VITE_PREFIX}${webUI}:3000
|
||||||
|
${chalk.green('➜')} Traefik 网关: ${env.VITE_PREFIX}${env.VITE_TRAEFIK_ADDRESS}
|
||||||
|
${chalk.green('➜')} WebUi: ${env.VITE_PREFIX}${env.VITE_TRAEFIK_ADDRESS}:8880
|
||||||
|
|
||||||
|
${chalk.blue.bold('微前端信息:')}
|
||||||
|
${chalk.green('➜')} 主模块:${chalk.green(env.VITE_SERVER_NAME)}
|
||||||
|
|
||||||
|
${chalk.blue.bold('调用模块:')}
|
||||||
|
${chalk.green('➜')} [ ${chalk.yellow(moduleName)} ]
|
||||||
|
`))
|
||||||
|
console.log()
|
||||||
|
}
|
||||||
|
|
||||||
|
function dedentTemplateString(str: string) {
|
||||||
|
// 分割成行
|
||||||
|
const lines = str.split('\n');
|
||||||
|
|
||||||
|
// 移除首尾空行
|
||||||
|
if (lines[0].trim() === '') lines.shift();
|
||||||
|
if (lines[lines.length - 1].trim() === '') lines.pop();
|
||||||
|
|
||||||
|
// 找到最小缩进量
|
||||||
|
const minIndent = lines.reduce((min, line) => {
|
||||||
|
if (line.trim() === '') return min; // 跳过空行
|
||||||
|
// @ts-ignore
|
||||||
|
const indent = line.match(/^\s*/)[0].length;
|
||||||
|
return indent < min ? indent : min;
|
||||||
|
}, Infinity);
|
||||||
|
|
||||||
|
// 移除统一缩进
|
||||||
|
return lines.map(line => line.slice(minIndent)).join('\n');
|
||||||
|
}
|
||||||
5
front-end/vite-plugin-nacos/test.ts
Normal file
5
front-end/vite-plugin-nacos/test.ts
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
import { nacosServiceManage } from "./src";
|
||||||
|
|
||||||
|
const main = async () => {
|
||||||
|
const nacos = new nacosServiceManage.create({})
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user