flyzto пре 7 месеци
родитељ
комит
4807e712ea
100 измењених фајлова са 0 додато и 4539 уклоњено
  1. 0 15
      web/apps/backend-mock/README.md
  2. 0 14
      web/apps/backend-mock/api/auth/codes.ts
  3. 0 36
      web/apps/backend-mock/api/auth/login.post.ts
  4. 0 15
      web/apps/backend-mock/api/auth/logout.post.ts
  5. 0 33
      web/apps/backend-mock/api/auth/refresh.post.ts
  6. 0 13
      web/apps/backend-mock/api/menu/all.ts
  7. 0 5
      web/apps/backend-mock/api/status.ts
  8. 0 15
      web/apps/backend-mock/api/system/dept/.post.ts
  9. 0 15
      web/apps/backend-mock/api/system/dept/[id].delete.ts
  10. 0 15
      web/apps/backend-mock/api/system/dept/[id].put.ts
  11. 0 61
      web/apps/backend-mock/api/system/dept/list.ts
  12. 0 12
      web/apps/backend-mock/api/system/menu/list.ts
  13. 0 28
      web/apps/backend-mock/api/system/menu/name-exists.ts
  14. 0 28
      web/apps/backend-mock/api/system/menu/path-exists.ts
  15. 0 83
      web/apps/backend-mock/api/system/role/list.ts
  16. 0 73
      web/apps/backend-mock/api/table/list.ts
  17. 0 1
      web/apps/backend-mock/api/test.get.ts
  18. 0 1
      web/apps/backend-mock/api/test.post.ts
  19. 0 13
      web/apps/backend-mock/api/upload.ts
  20. 0 10
      web/apps/backend-mock/api/user/info.ts
  21. 0 7
      web/apps/backend-mock/error.ts
  22. 0 19
      web/apps/backend-mock/middleware/1.api.ts
  23. 0 20
      web/apps/backend-mock/nitro.config.ts
  24. 0 21
      web/apps/backend-mock/package.json
  25. 0 13
      web/apps/backend-mock/routes/[...].ts
  26. 0 4
      web/apps/backend-mock/tsconfig.build.json
  27. 0 3
      web/apps/backend-mock/tsconfig.json
  28. 0 26
      web/apps/backend-mock/utils/cookie-utils.ts
  29. 0 59
      web/apps/backend-mock/utils/jwt-utils.ts
  30. 0 390
      web/apps/backend-mock/utils/mock-data.ts
  31. 0 68
      web/apps/backend-mock/utils/response.ts
  32. 0 7
      web/apps/web-ele/.env.analyze
  33. 0 16
      web/apps/web-ele/.env.development
  34. 0 19
      web/apps/web-ele/.env.production
  35. 0 35
      web/apps/web-ele/index.html
  36. 0 53
      web/apps/web-ele/package.json
  37. 0 1
      web/apps/web-ele/postcss.config.mjs
  38. BIN
      web/apps/web-ele/public/favicon.ico
  39. 0 338
      web/apps/web-ele/src/adapter/component/index.ts
  40. 0 39
      web/apps/web-ele/src/adapter/form.ts
  41. 0 68
      web/apps/web-ele/src/adapter/vxe-table.ts
  42. 0 51
      web/apps/web-ele/src/api/core/auth.ts
  43. 0 3
      web/apps/web-ele/src/api/core/index.ts
  44. 0 10
      web/apps/web-ele/src/api/core/menu.ts
  45. 0 10
      web/apps/web-ele/src/api/core/user.ts
  46. 0 1
      web/apps/web-ele/src/api/index.ts
  47. 0 113
      web/apps/web-ele/src/api/request.ts
  48. 0 17
      web/apps/web-ele/src/app.vue
  49. 0 74
      web/apps/web-ele/src/bootstrap.ts
  50. 0 23
      web/apps/web-ele/src/layouts/auth.vue
  51. 0 157
      web/apps/web-ele/src/layouts/basic.vue
  52. 0 6
      web/apps/web-ele/src/layouts/index.ts
  53. 0 3
      web/apps/web-ele/src/locales/README.md
  54. 0 102
      web/apps/web-ele/src/locales/index.ts
  55. 0 13
      web/apps/web-ele/src/locales/langs/en-US/demos.json
  56. 0 14
      web/apps/web-ele/src/locales/langs/en-US/page.json
  57. 0 13
      web/apps/web-ele/src/locales/langs/zh-CN/demos.json
  58. 0 14
      web/apps/web-ele/src/locales/langs/zh-CN/page.json
  59. 0 31
      web/apps/web-ele/src/main.ts
  60. 0 13
      web/apps/web-ele/src/preferences.ts
  61. 0 42
      web/apps/web-ele/src/router/access.ts
  62. 0 133
      web/apps/web-ele/src/router/guard.ts
  63. 0 37
      web/apps/web-ele/src/router/index.ts
  64. 0 97
      web/apps/web-ele/src/router/routes/core.ts
  65. 0 37
      web/apps/web-ele/src/router/routes/index.ts
  66. 0 38
      web/apps/web-ele/src/router/routes/modules/dashboard.ts
  67. 0 36
      web/apps/web-ele/src/router/routes/modules/demos.ts
  68. 0 82
      web/apps/web-ele/src/router/routes/modules/vben.ts
  69. 0 119
      web/apps/web-ele/src/store/auth.ts
  70. 0 1
      web/apps/web-ele/src/store/index.ts
  71. 0 3
      web/apps/web-ele/src/views/_core/README.md
  72. 0 9
      web/apps/web-ele/src/views/_core/about/index.vue
  73. 0 69
      web/apps/web-ele/src/views/_core/authentication/code-login.vue
  74. 0 43
      web/apps/web-ele/src/views/_core/authentication/forget-password.vue
  75. 0 98
      web/apps/web-ele/src/views/_core/authentication/login.vue
  76. 0 10
      web/apps/web-ele/src/views/_core/authentication/qrcode-login.vue
  77. 0 96
      web/apps/web-ele/src/views/_core/authentication/register.vue
  78. 0 7
      web/apps/web-ele/src/views/_core/fallback/coming-soon.vue
  79. 0 9
      web/apps/web-ele/src/views/_core/fallback/forbidden.vue
  80. 0 9
      web/apps/web-ele/src/views/_core/fallback/internal-error.vue
  81. 0 9
      web/apps/web-ele/src/views/_core/fallback/not-found.vue
  82. 0 9
      web/apps/web-ele/src/views/_core/fallback/offline.vue
  83. 0 98
      web/apps/web-ele/src/views/dashboard/analytics/analytics-trends.vue
  84. 0 82
      web/apps/web-ele/src/views/dashboard/analytics/analytics-visits-data.vue
  85. 0 46
      web/apps/web-ele/src/views/dashboard/analytics/analytics-visits-sales.vue
  86. 0 65
      web/apps/web-ele/src/views/dashboard/analytics/analytics-visits-source.vue
  87. 0 55
      web/apps/web-ele/src/views/dashboard/analytics/analytics-visits.vue
  88. 0 90
      web/apps/web-ele/src/views/dashboard/analytics/index.vue
  89. 0 266
      web/apps/web-ele/src/views/dashboard/workspace/index.vue
  90. 0 117
      web/apps/web-ele/src/views/demos/element/index.vue
  91. 0 191
      web/apps/web-ele/src/views/demos/form/basic.vue
  92. 0 1
      web/apps/web-ele/tailwind.config.mjs
  93. 0 12
      web/apps/web-ele/tsconfig.json
  94. 0 10
      web/apps/web-ele/tsconfig.node.json
  95. 0 27
      web/apps/web-ele/vite.config.mts
  96. 0 7
      web/apps/web-naive/.env.analyze
  97. 0 16
      web/apps/web-naive/.env.development
  98. 0 19
      web/apps/web-naive/.env.production
  99. 0 35
      web/apps/web-naive/index.html
  100. 0 49
      web/apps/web-naive/package.json

+ 0 - 15
web/apps/backend-mock/README.md

@@ -1,15 +0,0 @@
-# @vben/backend-mock
-
-## Description
-
-Vben Admin 数据 mock 服务,没有对接任何的数据库,所有数据都是模拟的,用于前端开发时提供数据支持。线上环境不再提供 mock 集成,可自行部署服务或者对接真实数据,由于 `mock.js` 等工具有一些限制,比如上传文件不行、无法模拟复杂的逻辑等,所以这里使用了真实的后端服务来实现。唯一麻烦的是本地需要同时启动后端服务和前端服务,但是这样可以更好的模拟真实环境。该服务不需要手动启动,已经集成在 vite 插件内,随应用一起启用。
-
-## Running the app
-
-```bash
-# development
-$ pnpm run start
-
-# production mode
-$ pnpm run build
-```

+ 0 - 14
web/apps/backend-mock/api/auth/codes.ts

@@ -1,14 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { unAuthorizedResponse } from '~/utils/response';
-
-export default eventHandler((event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-
-  const codes =
-    MOCK_CODES.find((item) => item.username === userinfo.username)?.codes ?? [];
-
-  return useResponseSuccess(codes);
-});

+ 0 - 36
web/apps/backend-mock/api/auth/login.post.ts

@@ -1,36 +0,0 @@
-import {
-  clearRefreshTokenCookie,
-  setRefreshTokenCookie,
-} from '~/utils/cookie-utils';
-import { generateAccessToken, generateRefreshToken } from '~/utils/jwt-utils';
-import { forbiddenResponse } from '~/utils/response';
-
-export default defineEventHandler(async (event) => {
-  const { password, username } = await readBody(event);
-  if (!password || !username) {
-    setResponseStatus(event, 400);
-    return useResponseError(
-      'BadRequestException',
-      'Username and password are required',
-    );
-  }
-
-  const findUser = MOCK_USERS.find(
-    (item) => item.username === username && item.password === password,
-  );
-
-  if (!findUser) {
-    clearRefreshTokenCookie(event);
-    return forbiddenResponse(event, 'Username or password is incorrect.');
-  }
-
-  const accessToken = generateAccessToken(findUser);
-  const refreshToken = generateRefreshToken(findUser);
-
-  setRefreshTokenCookie(event, refreshToken);
-
-  return useResponseSuccess({
-    ...findUser,
-    accessToken,
-  });
-});

+ 0 - 15
web/apps/backend-mock/api/auth/logout.post.ts

@@ -1,15 +0,0 @@
-import {
-  clearRefreshTokenCookie,
-  getRefreshTokenFromCookie,
-} from '~/utils/cookie-utils';
-
-export default defineEventHandler(async (event) => {
-  const refreshToken = getRefreshTokenFromCookie(event);
-  if (!refreshToken) {
-    return useResponseSuccess('');
-  }
-
-  clearRefreshTokenCookie(event);
-
-  return useResponseSuccess('');
-});

+ 0 - 33
web/apps/backend-mock/api/auth/refresh.post.ts

@@ -1,33 +0,0 @@
-import {
-  clearRefreshTokenCookie,
-  getRefreshTokenFromCookie,
-  setRefreshTokenCookie,
-} from '~/utils/cookie-utils';
-import { verifyRefreshToken } from '~/utils/jwt-utils';
-import { forbiddenResponse } from '~/utils/response';
-
-export default defineEventHandler(async (event) => {
-  const refreshToken = getRefreshTokenFromCookie(event);
-  if (!refreshToken) {
-    return forbiddenResponse(event);
-  }
-
-  clearRefreshTokenCookie(event);
-
-  const userinfo = verifyRefreshToken(refreshToken);
-  if (!userinfo) {
-    return forbiddenResponse(event);
-  }
-
-  const findUser = MOCK_USERS.find(
-    (item) => item.username === userinfo.username,
-  );
-  if (!findUser) {
-    return forbiddenResponse(event);
-  }
-  const accessToken = generateAccessToken(findUser);
-
-  setRefreshTokenCookie(event, refreshToken);
-
-  return accessToken;
-});

+ 0 - 13
web/apps/backend-mock/api/menu/all.ts

@@ -1,13 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { unAuthorizedResponse } from '~/utils/response';
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-
-  const menus =
-    MOCK_MENUS.find((item) => item.username === userinfo.username)?.menus ?? [];
-  return useResponseSuccess(menus);
-});

+ 0 - 5
web/apps/backend-mock/api/status.ts

@@ -1,5 +0,0 @@
-export default eventHandler((event) => {
-  const { status } = getQuery(event);
-  setResponseStatus(event, Number(status));
-  return useResponseError(`${status}`);
-});

+ 0 - 15
web/apps/backend-mock/api/system/dept/.post.ts

@@ -1,15 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import {
-  sleep,
-  unAuthorizedResponse,
-  useResponseSuccess,
-} from '~/utils/response';
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-  await sleep(600);
-  return useResponseSuccess(null);
-});

+ 0 - 15
web/apps/backend-mock/api/system/dept/[id].delete.ts

@@ -1,15 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import {
-  sleep,
-  unAuthorizedResponse,
-  useResponseSuccess,
-} from '~/utils/response';
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-  await sleep(1000);
-  return useResponseSuccess(null);
-});

+ 0 - 15
web/apps/backend-mock/api/system/dept/[id].put.ts

@@ -1,15 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import {
-  sleep,
-  unAuthorizedResponse,
-  useResponseSuccess,
-} from '~/utils/response';
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-  await sleep(2000);
-  return useResponseSuccess(null);
-});

+ 0 - 61
web/apps/backend-mock/api/system/dept/list.ts

@@ -1,61 +0,0 @@
-import { faker } from '@faker-js/faker';
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { unAuthorizedResponse, useResponseSuccess } from '~/utils/response';
-
-const formatterCN = new Intl.DateTimeFormat('zh-CN', {
-  timeZone: 'Asia/Shanghai',
-  year: 'numeric',
-  month: '2-digit',
-  day: '2-digit',
-  hour: '2-digit',
-  minute: '2-digit',
-  second: '2-digit',
-});
-
-function generateMockDataList(count: number) {
-  const dataList = [];
-
-  for (let i = 0; i < count; i++) {
-    const dataItem: Record<string, any> = {
-      id: faker.string.uuid(),
-      pid: 0,
-      name: faker.commerce.department(),
-      status: faker.helpers.arrayElement([0, 1]),
-      createTime: formatterCN.format(
-        faker.date.between({ from: '2021-01-01', to: '2022-12-31' }),
-      ),
-      remark: faker.lorem.sentence(),
-    };
-    if (faker.datatype.boolean()) {
-      dataItem.children = Array.from(
-        { length: faker.number.int({ min: 1, max: 5 }) },
-        () => ({
-          id: faker.string.uuid(),
-          pid: dataItem.id,
-          name: faker.commerce.department(),
-          status: faker.helpers.arrayElement([0, 1]),
-          createTime: formatterCN.format(
-            faker.date.between({ from: '2023-01-01', to: '2023-12-31' }),
-          ),
-          remark: faker.lorem.sentence(),
-        }),
-      );
-    }
-    dataList.push(dataItem);
-  }
-
-  return dataList;
-}
-
-const mockData = generateMockDataList(10);
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-
-  const listData = structuredClone(mockData);
-
-  return useResponseSuccess(listData);
-});

+ 0 - 12
web/apps/backend-mock/api/system/menu/list.ts

@@ -1,12 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { MOCK_MENU_LIST } from '~/utils/mock-data';
-import { unAuthorizedResponse, useResponseSuccess } from '~/utils/response';
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-
-  return useResponseSuccess(MOCK_MENU_LIST);
-});

+ 0 - 28
web/apps/backend-mock/api/system/menu/name-exists.ts

@@ -1,28 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { MOCK_MENU_LIST } from '~/utils/mock-data';
-import { unAuthorizedResponse } from '~/utils/response';
-
-const namesMap: Record<string, any> = {};
-
-function getNames(menus: any[]) {
-  menus.forEach((menu) => {
-    namesMap[menu.name] = String(menu.id);
-    if (menu.children) {
-      getNames(menu.children);
-    }
-  });
-}
-getNames(MOCK_MENU_LIST);
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-  const { id, name } = getQuery(event);
-
-  return (name as string) in namesMap &&
-    (!id || namesMap[name as string] !== String(id))
-    ? useResponseSuccess(true)
-    : useResponseSuccess(false);
-});

+ 0 - 28
web/apps/backend-mock/api/system/menu/path-exists.ts

@@ -1,28 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { MOCK_MENU_LIST } from '~/utils/mock-data';
-import { unAuthorizedResponse } from '~/utils/response';
-
-const pathMap: Record<string, any> = { '/': 0 };
-
-function getPaths(menus: any[]) {
-  menus.forEach((menu) => {
-    pathMap[menu.path] = String(menu.id);
-    if (menu.children) {
-      getPaths(menu.children);
-    }
-  });
-}
-getPaths(MOCK_MENU_LIST);
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-  const { id, path } = getQuery(event);
-
-  return (path as string) in pathMap &&
-    (!id || pathMap[path as string] !== String(id))
-    ? useResponseSuccess(true)
-    : useResponseSuccess(false);
-});

+ 0 - 83
web/apps/backend-mock/api/system/role/list.ts

@@ -1,83 +0,0 @@
-import { faker } from '@faker-js/faker';
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { getMenuIds, MOCK_MENU_LIST } from '~/utils/mock-data';
-import { unAuthorizedResponse, usePageResponseSuccess } from '~/utils/response';
-
-const formatterCN = new Intl.DateTimeFormat('zh-CN', {
-  timeZone: 'Asia/Shanghai',
-  year: 'numeric',
-  month: '2-digit',
-  day: '2-digit',
-  hour: '2-digit',
-  minute: '2-digit',
-  second: '2-digit',
-});
-
-const menuIds = getMenuIds(MOCK_MENU_LIST);
-
-function generateMockDataList(count: number) {
-  const dataList = [];
-
-  for (let i = 0; i < count; i++) {
-    const dataItem: Record<string, any> = {
-      id: faker.string.uuid(),
-      name: faker.commerce.product(),
-      status: faker.helpers.arrayElement([0, 1]),
-      createTime: formatterCN.format(
-        faker.date.between({ from: '2022-01-01', to: '2025-01-01' }),
-      ),
-      permissions: faker.helpers.arrayElements(menuIds),
-      remark: faker.lorem.sentence(),
-    };
-
-    dataList.push(dataItem);
-  }
-
-  return dataList;
-}
-
-const mockData = generateMockDataList(100);
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-
-  const {
-    page = 1,
-    pageSize = 20,
-    name,
-    id,
-    remark,
-    startTime,
-    endTime,
-    status,
-  } = getQuery(event);
-  let listData = structuredClone(mockData);
-  if (name) {
-    listData = listData.filter((item) =>
-      item.name.toLowerCase().includes(String(name).toLowerCase()),
-    );
-  }
-  if (id) {
-    listData = listData.filter((item) =>
-      item.id.toLowerCase().includes(String(id).toLowerCase()),
-    );
-  }
-  if (remark) {
-    listData = listData.filter((item) =>
-      item.remark?.toLowerCase()?.includes(String(remark).toLowerCase()),
-    );
-  }
-  if (startTime) {
-    listData = listData.filter((item) => item.createTime >= startTime);
-  }
-  if (endTime) {
-    listData = listData.filter((item) => item.createTime <= endTime);
-  }
-  if (['0', '1'].includes(status as string)) {
-    listData = listData.filter((item) => item.status === Number(status));
-  }
-  return usePageResponseSuccess(page as string, pageSize as string, listData);
-});

+ 0 - 73
web/apps/backend-mock/api/table/list.ts

@@ -1,73 +0,0 @@
-import { faker } from '@faker-js/faker';
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { unAuthorizedResponse, usePageResponseSuccess } from '~/utils/response';
-
-function generateMockDataList(count: number) {
-  const dataList = [];
-
-  for (let i = 0; i < count; i++) {
-    const dataItem = {
-      id: faker.string.uuid(),
-      imageUrl: faker.image.avatar(),
-      imageUrl2: faker.image.avatar(),
-      open: faker.datatype.boolean(),
-      status: faker.helpers.arrayElement(['success', 'error', 'warning']),
-      productName: faker.commerce.productName(),
-      price: faker.commerce.price(),
-      currency: faker.finance.currencyCode(),
-      quantity: faker.number.int({ min: 1, max: 100 }),
-      available: faker.datatype.boolean(),
-      category: faker.commerce.department(),
-      releaseDate: faker.date.past(),
-      rating: faker.number.float({ min: 1, max: 5 }),
-      description: faker.commerce.productDescription(),
-      weight: faker.number.float({ min: 0.1, max: 10 }),
-      color: faker.color.human(),
-      inProduction: faker.datatype.boolean(),
-      tags: Array.from({ length: 3 }, () => faker.commerce.productAdjective()),
-    };
-
-    dataList.push(dataItem);
-  }
-
-  return dataList;
-}
-
-const mockData = generateMockDataList(100);
-
-export default eventHandler(async (event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-
-  await sleep(600);
-
-  const { page, pageSize, sortBy, sortOrder } = getQuery(event);
-  const listData = structuredClone(mockData);
-  if (sortBy && Reflect.has(listData[0], sortBy as string)) {
-    listData.sort((a, b) => {
-      if (sortOrder === 'asc') {
-        if (sortBy === 'price') {
-          return (
-            Number.parseFloat(a[sortBy as string]) -
-            Number.parseFloat(b[sortBy as string])
-          );
-        } else {
-          return a[sortBy as string] > b[sortBy as string] ? 1 : -1;
-        }
-      } else {
-        if (sortBy === 'price') {
-          return (
-            Number.parseFloat(b[sortBy as string]) -
-            Number.parseFloat(a[sortBy as string])
-          );
-        } else {
-          return a[sortBy as string] < b[sortBy as string] ? 1 : -1;
-        }
-      }
-    });
-  }
-
-  return usePageResponseSuccess(page as string, pageSize as string, listData);
-});

+ 0 - 1
web/apps/backend-mock/api/test.get.ts

@@ -1 +0,0 @@
-export default defineEventHandler(() => 'Test get handler');

+ 0 - 1
web/apps/backend-mock/api/test.post.ts

@@ -1 +0,0 @@
-export default defineEventHandler(() => 'Test post handler');

+ 0 - 13
web/apps/backend-mock/api/upload.ts

@@ -1,13 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { unAuthorizedResponse } from '~/utils/response';
-
-export default eventHandler((event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-  return useResponseSuccess({
-    url: 'https://unpkg.com/@vbenjs/static-source@0.1.7/source/logo-v1.webp',
-  });
-  // return useResponseError("test")
-});

+ 0 - 10
web/apps/backend-mock/api/user/info.ts

@@ -1,10 +0,0 @@
-import { verifyAccessToken } from '~/utils/jwt-utils';
-import { unAuthorizedResponse } from '~/utils/response';
-
-export default eventHandler((event) => {
-  const userinfo = verifyAccessToken(event);
-  if (!userinfo) {
-    return unAuthorizedResponse(event);
-  }
-  return useResponseSuccess(userinfo);
-});

+ 0 - 7
web/apps/backend-mock/error.ts

@@ -1,7 +0,0 @@
-import type { NitroErrorHandler } from 'nitropack';
-
-const errorHandler: NitroErrorHandler = function (error, event) {
-  event.node.res.end(`[Error Handler] ${error.stack}`);
-};
-
-export default errorHandler;

+ 0 - 19
web/apps/backend-mock/middleware/1.api.ts

@@ -1,19 +0,0 @@
-import { forbiddenResponse, sleep } from '~/utils/response';
-
-export default defineEventHandler(async (event) => {
-  event.node.res.setHeader(
-    'Access-Control-Allow-Origin',
-    event.headers.get('Origin') ?? '*',
-  );
-  if (event.method === 'OPTIONS') {
-    event.node.res.statusCode = 204;
-    event.node.res.statusMessage = 'No Content.';
-    return 'OK';
-  } else if (
-    ['DELETE', 'PATCH', 'POST', 'PUT'].includes(event.method) &&
-    event.path.startsWith('/api/system/')
-  ) {
-    await sleep(Math.floor(Math.random() * 2000));
-    return forbiddenResponse(event, '演示环境,禁止修改');
-  }
-});

+ 0 - 20
web/apps/backend-mock/nitro.config.ts

@@ -1,20 +0,0 @@
-import errorHandler from './error';
-
-process.env.COMPATIBILITY_DATE = new Date().toISOString();
-export default defineNitroConfig({
-  devErrorHandler: errorHandler,
-  errorHandler: '~/error',
-  routeRules: {
-    '/api/**': {
-      cors: true,
-      headers: {
-        'Access-Control-Allow-Credentials': 'true',
-        'Access-Control-Allow-Headers':
-          'Accept, Authorization, Content-Length, Content-Type, If-Match, If-Modified-Since, If-None-Match, If-Unmodified-Since, X-CSRF-TOKEN, X-Requested-With',
-        'Access-Control-Allow-Methods': 'GET,HEAD,PUT,PATCH,POST,DELETE',
-        'Access-Control-Allow-Origin': '*',
-        'Access-Control-Expose-Headers': '*',
-      },
-    },
-  },
-});

+ 0 - 21
web/apps/backend-mock/package.json

@@ -1,21 +0,0 @@
-{
-  "name": "@vben/backend-mock",
-  "version": "0.0.1",
-  "description": "",
-  "private": true,
-  "license": "MIT",
-  "author": "",
-  "scripts": {
-    "build": "nitro build",
-    "start": "nitro dev"
-  },
-  "dependencies": {
-    "@faker-js/faker": "catalog:",
-    "jsonwebtoken": "catalog:",
-    "nitropack": "catalog:"
-  },
-  "devDependencies": {
-    "@types/jsonwebtoken": "catalog:",
-    "h3": "catalog:"
-  }
-}

+ 0 - 13
web/apps/backend-mock/routes/[...].ts

@@ -1,13 +0,0 @@
-export default defineEventHandler(() => {
-  return `
-<h1>Hello Vben Admin</h1>
-<h2>Mock service is starting</h2>
-<ul>
-<li><a href="/api/user">/api/user/info</a></li>
-<li><a href="/api/menu">/api/menu/all</a></li>
-<li><a href="/api/auth/codes">/api/auth/codes</a></li>
-<li><a href="/api/auth/login">/api/auth/login</a></li>
-<li><a href="/api/upload">/api/upload</a></li>
-</ul>
-`;
-});

+ 0 - 4
web/apps/backend-mock/tsconfig.build.json

@@ -1,4 +0,0 @@
-{
-  "extends": "./tsconfig.json",
-  "exclude": ["node_modules", "test", "dist", "**/*spec.ts"]
-}

+ 0 - 3
web/apps/backend-mock/tsconfig.json

@@ -1,3 +0,0 @@
-{
-  "extends": "./.nitro/types/tsconfig.json"
-}

+ 0 - 26
web/apps/backend-mock/utils/cookie-utils.ts

@@ -1,26 +0,0 @@
-import type { EventHandlerRequest, H3Event } from 'h3';
-
-export function clearRefreshTokenCookie(event: H3Event<EventHandlerRequest>) {
-  deleteCookie(event, 'jwt', {
-    httpOnly: true,
-    sameSite: 'none',
-    secure: true,
-  });
-}
-
-export function setRefreshTokenCookie(
-  event: H3Event<EventHandlerRequest>,
-  refreshToken: string,
-) {
-  setCookie(event, 'jwt', refreshToken, {
-    httpOnly: true,
-    maxAge: 24 * 60 * 60, // unit: seconds
-    sameSite: 'none',
-    secure: true,
-  });
-}
-
-export function getRefreshTokenFromCookie(event: H3Event<EventHandlerRequest>) {
-  const refreshToken = getCookie(event, 'jwt');
-  return refreshToken;
-}

+ 0 - 59
web/apps/backend-mock/utils/jwt-utils.ts

@@ -1,59 +0,0 @@
-import type { EventHandlerRequest, H3Event } from 'h3';
-
-import jwt from 'jsonwebtoken';
-
-import { UserInfo } from './mock-data';
-
-// TODO: Replace with your own secret key
-const ACCESS_TOKEN_SECRET = 'access_token_secret';
-const REFRESH_TOKEN_SECRET = 'refresh_token_secret';
-
-export interface UserPayload extends UserInfo {
-  iat: number;
-  exp: number;
-}
-
-export function generateAccessToken(user: UserInfo) {
-  return jwt.sign(user, ACCESS_TOKEN_SECRET, { expiresIn: '7d' });
-}
-
-export function generateRefreshToken(user: UserInfo) {
-  return jwt.sign(user, REFRESH_TOKEN_SECRET, {
-    expiresIn: '30d',
-  });
-}
-
-export function verifyAccessToken(
-  event: H3Event<EventHandlerRequest>,
-): null | Omit<UserInfo, 'password'> {
-  const authHeader = getHeader(event, 'Authorization');
-  if (!authHeader?.startsWith('Bearer')) {
-    return null;
-  }
-
-  const token = authHeader.split(' ')[1];
-  try {
-    const decoded = jwt.verify(token, ACCESS_TOKEN_SECRET) as UserPayload;
-
-    const username = decoded.username;
-    const user = MOCK_USERS.find((item) => item.username === username);
-    const { password: _pwd, ...userinfo } = user;
-    return userinfo;
-  } catch {
-    return null;
-  }
-}
-
-export function verifyRefreshToken(
-  token: string,
-): null | Omit<UserInfo, 'password'> {
-  try {
-    const decoded = jwt.verify(token, REFRESH_TOKEN_SECRET) as UserPayload;
-    const username = decoded.username;
-    const user = MOCK_USERS.find((item) => item.username === username);
-    const { password: _pwd, ...userinfo } = user;
-    return userinfo;
-  } catch {
-    return null;
-  }
-}

+ 0 - 390
web/apps/backend-mock/utils/mock-data.ts

@@ -1,390 +0,0 @@
-export interface UserInfo {
-  id: number;
-  password: string;
-  realName: string;
-  roles: string[];
-  username: string;
-  homePath?: string;
-}
-
-export const MOCK_USERS: UserInfo[] = [
-  {
-    id: 0,
-    password: '123456',
-    realName: 'Vben',
-    roles: ['super'],
-    username: 'vben',
-  },
-  {
-    id: 1,
-    password: '123456',
-    realName: 'Admin',
-    roles: ['admin'],
-    username: 'admin',
-    homePath: '/workspace',
-  },
-  {
-    id: 2,
-    password: '123456',
-    realName: 'Jack',
-    roles: ['user'],
-    username: 'jack',
-    homePath: '/analytics',
-  },
-];
-
-export const MOCK_CODES = [
-  // super
-  {
-    codes: ['AC_100100', 'AC_100110', 'AC_100120', 'AC_100010'],
-    username: 'vben',
-  },
-  {
-    // admin
-    codes: ['AC_100010', 'AC_100020', 'AC_100030'],
-    username: 'admin',
-  },
-  {
-    // user
-    codes: ['AC_1000001', 'AC_1000002'],
-    username: 'jack',
-  },
-];
-
-const dashboardMenus = [
-  {
-    meta: {
-      order: -1,
-      title: 'page.dashboard.title',
-    },
-    name: 'Dashboard',
-    path: '/dashboard',
-    redirect: '/analytics',
-    children: [
-      {
-        name: 'Analytics',
-        path: '/analytics',
-        component: '/dashboard/analytics/index',
-        meta: {
-          affixTab: true,
-          title: 'page.dashboard.analytics',
-        },
-      },
-      {
-        name: 'Workspace',
-        path: '/workspace',
-        component: '/dashboard/workspace/index',
-        meta: {
-          title: 'page.dashboard.workspace',
-        },
-      },
-    ],
-  },
-];
-
-const createDemosMenus = (role: 'admin' | 'super' | 'user') => {
-  const roleWithMenus = {
-    admin: {
-      component: '/demos/access/admin-visible',
-      meta: {
-        icon: 'mdi:button-cursor',
-        title: 'demos.access.adminVisible',
-      },
-      name: 'AccessAdminVisibleDemo',
-      path: '/demos/access/admin-visible',
-    },
-    super: {
-      component: '/demos/access/super-visible',
-      meta: {
-        icon: 'mdi:button-cursor',
-        title: 'demos.access.superVisible',
-      },
-      name: 'AccessSuperVisibleDemo',
-      path: '/demos/access/super-visible',
-    },
-    user: {
-      component: '/demos/access/user-visible',
-      meta: {
-        icon: 'mdi:button-cursor',
-        title: 'demos.access.userVisible',
-      },
-      name: 'AccessUserVisibleDemo',
-      path: '/demos/access/user-visible',
-    },
-  };
-
-  return [
-    {
-      meta: {
-        icon: 'ic:baseline-view-in-ar',
-        keepAlive: true,
-        order: 1000,
-        title: 'demos.title',
-      },
-      name: 'Demos',
-      path: '/demos',
-      redirect: '/demos/access',
-      children: [
-        {
-          name: 'AccessDemos',
-          path: '/demosaccess',
-          meta: {
-            icon: 'mdi:cloud-key-outline',
-            title: 'demos.access.backendPermissions',
-          },
-          redirect: '/demos/access/page-control',
-          children: [
-            {
-              name: 'AccessPageControlDemo',
-              path: '/demos/access/page-control',
-              component: '/demos/access/index',
-              meta: {
-                icon: 'mdi:page-previous-outline',
-                title: 'demos.access.pageAccess',
-              },
-            },
-            {
-              name: 'AccessButtonControlDemo',
-              path: '/demos/access/button-control',
-              component: '/demos/access/button-control',
-              meta: {
-                icon: 'mdi:button-cursor',
-                title: 'demos.access.buttonControl',
-              },
-            },
-            {
-              name: 'AccessMenuVisible403Demo',
-              path: '/demos/access/menu-visible-403',
-              component: '/demos/access/menu-visible-403',
-              meta: {
-                authority: ['no-body'],
-                icon: 'mdi:button-cursor',
-                menuVisibleWithForbidden: true,
-                title: 'demos.access.menuVisible403',
-              },
-            },
-            roleWithMenus[role],
-          ],
-        },
-      ],
-    },
-  ];
-};
-
-export const MOCK_MENUS = [
-  {
-    menus: [...dashboardMenus, ...createDemosMenus('super')],
-    username: 'vben',
-  },
-  {
-    menus: [...dashboardMenus, ...createDemosMenus('admin')],
-    username: 'admin',
-  },
-  {
-    menus: [...dashboardMenus, ...createDemosMenus('user')],
-    username: 'jack',
-  },
-];
-
-export const MOCK_MENU_LIST = [
-  {
-    id: 1,
-    name: 'Workspace',
-    status: 1,
-    type: 'menu',
-    icon: 'mdi:dashboard',
-    path: '/workspace',
-    component: '/dashboard/workspace/index',
-    meta: {
-      icon: 'carbon:workspace',
-      title: 'page.dashboard.workspace',
-      affixTab: true,
-      order: 0,
-    },
-  },
-  {
-    id: 2,
-    meta: {
-      icon: 'carbon:settings',
-      order: 9997,
-      title: 'system.title',
-      badge: 'new',
-      badgeType: 'normal',
-      badgeVariants: 'primary',
-    },
-    status: 1,
-    type: 'catalog',
-    name: 'System',
-    path: '/system',
-    children: [
-      {
-        id: 201,
-        pid: 2,
-        path: '/system/menu',
-        name: 'SystemMenu',
-        authCode: 'System:Menu:List',
-        status: 1,
-        type: 'menu',
-        meta: {
-          icon: 'carbon:menu',
-          title: 'system.menu.title',
-        },
-        component: '/system/menu/list',
-        children: [
-          {
-            id: 20_101,
-            pid: 201,
-            name: 'SystemMenuCreate',
-            status: 1,
-            type: 'button',
-            authCode: 'System:Menu:Create',
-            meta: { title: 'common.create' },
-          },
-          {
-            id: 20_102,
-            pid: 201,
-            name: 'SystemMenuEdit',
-            status: 1,
-            type: 'button',
-            authCode: 'System:Menu:Edit',
-            meta: { title: 'common.edit' },
-          },
-          {
-            id: 20_103,
-            pid: 201,
-            name: 'SystemMenuDelete',
-            status: 1,
-            type: 'button',
-            authCode: 'System:Menu:Delete',
-            meta: { title: 'common.delete' },
-          },
-        ],
-      },
-      {
-        id: 202,
-        pid: 2,
-        path: '/system/dept',
-        name: 'SystemDept',
-        status: 1,
-        type: 'menu',
-        authCode: 'System:Dept:List',
-        meta: {
-          icon: 'carbon:container-services',
-          title: 'system.dept.title',
-        },
-        component: '/system/dept/list',
-        children: [
-          {
-            id: 20_401,
-            pid: 201,
-            name: 'SystemDeptCreate',
-            status: 1,
-            type: 'button',
-            authCode: 'System:Dept:Create',
-            meta: { title: 'common.create' },
-          },
-          {
-            id: 20_402,
-            pid: 201,
-            name: 'SystemDeptEdit',
-            status: 1,
-            type: 'button',
-            authCode: 'System:Dept:Edit',
-            meta: { title: 'common.edit' },
-          },
-          {
-            id: 20_403,
-            pid: 201,
-            name: 'SystemDeptDelete',
-            status: 1,
-            type: 'button',
-            authCode: 'System:Dept:Delete',
-            meta: { title: 'common.delete' },
-          },
-        ],
-      },
-    ],
-  },
-  {
-    id: 9,
-    meta: {
-      badgeType: 'dot',
-      order: 9998,
-      title: 'demos.vben.title',
-      icon: 'carbon:data-center',
-    },
-    name: 'Project',
-    path: '/vben-admin',
-    type: 'catalog',
-    status: 1,
-    children: [
-      {
-        id: 901,
-        pid: 9,
-        name: 'VbenDocument',
-        path: '/vben-admin/document',
-        component: 'IFrameView',
-        type: 'embedded',
-        status: 1,
-        meta: {
-          icon: 'carbon:book',
-          iframeSrc: 'https://doc.vben.pro',
-          title: 'demos.vben.document',
-        },
-      },
-      {
-        id: 902,
-        pid: 9,
-        name: 'VbenGithub',
-        path: '/vben-admin/github',
-        component: 'IFrameView',
-        type: 'link',
-        status: 1,
-        meta: {
-          icon: 'carbon:logo-github',
-          link: 'https://github.com/vbenjs/vue-vben-admin',
-          title: 'Github',
-        },
-      },
-      {
-        id: 903,
-        pid: 9,
-        name: 'VbenAntdv',
-        path: '/vben-admin/antdv',
-        component: 'IFrameView',
-        type: 'link',
-        status: 0,
-        meta: {
-          icon: 'carbon:hexagon-vertical-solid',
-          badgeType: 'dot',
-          link: 'https://ant.vben.pro',
-          title: 'demos.vben.antdv',
-        },
-      },
-    ],
-  },
-  {
-    id: 10,
-    component: '_core/about/index',
-    type: 'menu',
-    status: 1,
-    meta: {
-      icon: 'lucide:copyright',
-      order: 9999,
-      title: 'demos.vben.about',
-    },
-    name: 'About',
-    path: '/about',
-  },
-];
-
-export function getMenuIds(menus: any[]) {
-  const ids: number[] = [];
-  menus.forEach((item) => {
-    ids.push(item.id);
-    if (item.children && item.children.length > 0) {
-      ids.push(...getMenuIds(item.children));
-    }
-  });
-  return ids;
-}

+ 0 - 68
web/apps/backend-mock/utils/response.ts

@@ -1,68 +0,0 @@
-import type { EventHandlerRequest, H3Event } from 'h3';
-
-export function useResponseSuccess<T = any>(data: T) {
-  return {
-    code: 0,
-    data,
-    error: null,
-    message: 'ok',
-  };
-}
-
-export function usePageResponseSuccess<T = any>(
-  page: number | string,
-  pageSize: number | string,
-  list: T[],
-  { message = 'ok' } = {},
-) {
-  const pageData = pagination(
-    Number.parseInt(`${page}`),
-    Number.parseInt(`${pageSize}`),
-    list,
-  );
-
-  return {
-    ...useResponseSuccess({
-      items: pageData,
-      total: list.length,
-    }),
-    message,
-  };
-}
-
-export function useResponseError(message: string, error: any = null) {
-  return {
-    code: -1,
-    data: null,
-    error,
-    message,
-  };
-}
-
-export function forbiddenResponse(
-  event: H3Event<EventHandlerRequest>,
-  message = 'Forbidden Exception',
-) {
-  setResponseStatus(event, 403);
-  return useResponseError(message, message);
-}
-
-export function unAuthorizedResponse(event: H3Event<EventHandlerRequest>) {
-  setResponseStatus(event, 401);
-  return useResponseError('Unauthorized Exception', 'Unauthorized Exception');
-}
-
-export function sleep(ms: number) {
-  return new Promise((resolve) => setTimeout(resolve, ms));
-}
-
-export function pagination<T = any>(
-  pageNo: number,
-  pageSize: number,
-  array: T[],
-): T[] {
-  const offset = (pageNo - 1) * Number(pageSize);
-  return offset + Number(pageSize) >= array.length
-    ? array.slice(offset)
-    : array.slice(offset, offset + Number(pageSize));
-}

+ 0 - 7
web/apps/web-ele/.env.analyze

@@ -1,7 +0,0 @@
-# public path
-VITE_BASE=/
-
-# Basic interface address SPA
-VITE_GLOB_API_URL=/api
-
-VITE_VISUALIZER=true

+ 0 - 16
web/apps/web-ele/.env.development

@@ -1,16 +0,0 @@
-# 端口号
-VITE_PORT=5777
-
-VITE_BASE=/
-
-# 接口地址
-VITE_GLOB_API_URL=/api
-
-# 是否开启 Nitro Mock服务,true 为开启,false 为关闭
-VITE_NITRO_MOCK=true
-
-# 是否打开 devtools,true 为打开,false 为关闭
-VITE_DEVTOOLS=false
-
-# 是否注入全局loading
-VITE_INJECT_APP_LOADING=true

+ 0 - 19
web/apps/web-ele/.env.production

@@ -1,19 +0,0 @@
-VITE_BASE=/
-
-# 接口地址
-VITE_GLOB_API_URL=https://mock-napi.vben.pro/api
-
-# 是否开启压缩,可以设置为 none, brotli, gzip
-VITE_COMPRESS=none
-
-# 是否开启 PWA
-VITE_PWA=false
-
-# vue-router 的模式
-VITE_ROUTER_HISTORY=hash
-
-# 是否注入全局loading
-VITE_INJECT_APP_LOADING=true
-
-# 打包后是否生成dist.zip
-VITE_ARCHIVER=true

+ 0 - 35
web/apps/web-ele/index.html

@@ -1,35 +0,0 @@
-<!doctype html>
-<html lang="zh">
-  <head>
-    <meta charset="UTF-8" />
-    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
-    <meta name="renderer" content="webkit" />
-    <meta name="description" content="A Modern Back-end Management System" />
-    <meta name="keywords" content="Vben Admin Vue3 Vite" />
-    <meta name="author" content="Vben" />
-    <meta
-      name="viewport"
-      content="width=device-width,initial-scale=1.0,minimum-scale=1.0,maximum-scale=1.0,user-scalable=0"
-    />
-    <!-- 由 vite 注入 VITE_APP_TITLE 变量,在 .env 文件内配置 -->
-    <title><%= VITE_APP_TITLE %></title>
-    <link rel="icon" href="/favicon.ico" />
-    <script>
-      // 生产环境下注入百度统计
-      if (window._VBEN_ADMIN_PRO_APP_CONF_) {
-        var _hmt = _hmt || [];
-        (function () {
-          var hm = document.createElement('script');
-          hm.src =
-            'https://hm.baidu.com/hm.js?97352b16ed2df8c3860cf5a1a65fb4dd';
-          var s = document.getElementsByTagName('script')[0];
-          s.parentNode.insertBefore(hm, s);
-        })();
-      }
-    </script>
-  </head>
-  <body>
-    <div id="app"></div>
-    <script type="module" src="/src/main.ts"></script>
-  </body>
-</html>

+ 0 - 53
web/apps/web-ele/package.json

@@ -1,53 +0,0 @@
-{
-  "name": "@vben/web-ele",
-  "version": "5.5.6",
-  "homepage": "https://vben.pro",
-  "bugs": "https://github.com/vbenjs/vue-vben-admin/issues",
-  "repository": {
-    "type": "git",
-    "url": "git+https://github.com/vbenjs/vue-vben-admin.git",
-    "directory": "apps/web-ele"
-  },
-  "license": "MIT",
-  "author": {
-    "name": "vben",
-    "email": "ann.vben@gmail.com",
-    "url": "https://github.com/anncwb"
-  },
-  "type": "module",
-  "scripts": {
-    "build": "pnpm vite build --mode production",
-    "build:analyze": "pnpm vite build --mode analyze",
-    "dev": "pnpm vite --mode development",
-    "preview": "vite preview",
-    "typecheck": "vue-tsc --noEmit --skipLibCheck"
-  },
-  "imports": {
-    "#/*": "./src/*"
-  },
-  "dependencies": {
-    "@vben/access": "workspace:*",
-    "@vben/common-ui": "workspace:*",
-    "@vben/constants": "workspace:*",
-    "@vben/hooks": "workspace:*",
-    "@vben/icons": "workspace:*",
-    "@vben/layouts": "workspace:*",
-    "@vben/locales": "workspace:*",
-    "@vben/plugins": "workspace:*",
-    "@vben/preferences": "workspace:*",
-    "@vben/request": "workspace:*",
-    "@vben/stores": "workspace:*",
-    "@vben/styles": "workspace:*",
-    "@vben/types": "workspace:*",
-    "@vben/utils": "workspace:*",
-    "@vueuse/core": "catalog:",
-    "dayjs": "catalog:",
-    "element-plus": "catalog:",
-    "pinia": "catalog:",
-    "vue": "catalog:",
-    "vue-router": "catalog:"
-  },
-  "devDependencies": {
-    "unplugin-element-plus": "catalog:"
-  }
-}

+ 0 - 1
web/apps/web-ele/postcss.config.mjs

@@ -1 +0,0 @@
-export { default } from '@vben/tailwind-config/postcss';

BIN
web/apps/web-ele/public/favicon.ico


+ 0 - 338
web/apps/web-ele/src/adapter/component/index.ts

@@ -1,338 +0,0 @@
-/**
- * 通用组件共同的使用的基础组件,原先放在 adapter/form 内部,限制了使用范围,这里提取出来,方便其他地方使用
- * 可用于 vben-form、vben-modal、vben-drawer 等组件使用,
- */
-
-import type { Component } from 'vue';
-
-import type { BaseFormComponentType } from '@vben/common-ui';
-import type { Recordable } from '@vben/types';
-
-import {
-  defineAsyncComponent,
-  defineComponent,
-  getCurrentInstance,
-  h,
-  ref,
-} from 'vue';
-
-import { ApiComponent, globalShareState, IconPicker } from '@vben/common-ui';
-import { $t } from '@vben/locales';
-
-import { ElNotification } from 'element-plus';
-
-const ElButton = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/button/index'),
-    import('element-plus/es/components/button/style/css'),
-  ]).then(([res]) => res.ElButton),
-);
-const ElCheckbox = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/checkbox/index'),
-    import('element-plus/es/components/checkbox/style/css'),
-  ]).then(([res]) => res.ElCheckbox),
-);
-const ElCheckboxButton = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/checkbox/index'),
-    import('element-plus/es/components/checkbox-button/style/css'),
-  ]).then(([res]) => res.ElCheckboxButton),
-);
-const ElCheckboxGroup = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/checkbox/index'),
-    import('element-plus/es/components/checkbox-group/style/css'),
-  ]).then(([res]) => res.ElCheckboxGroup),
-);
-const ElDatePicker = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/date-picker/index'),
-    import('element-plus/es/components/date-picker/style/css'),
-  ]).then(([res]) => res.ElDatePicker),
-);
-const ElDivider = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/divider/index'),
-    import('element-plus/es/components/divider/style/css'),
-  ]).then(([res]) => res.ElDivider),
-);
-const ElInput = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/input/index'),
-    import('element-plus/es/components/input/style/css'),
-  ]).then(([res]) => res.ElInput),
-);
-const ElInputNumber = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/input-number/index'),
-    import('element-plus/es/components/input-number/style/css'),
-  ]).then(([res]) => res.ElInputNumber),
-);
-const ElRadio = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/radio/index'),
-    import('element-plus/es/components/radio/style/css'),
-  ]).then(([res]) => res.ElRadio),
-);
-const ElRadioButton = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/radio/index'),
-    import('element-plus/es/components/radio-button/style/css'),
-  ]).then(([res]) => res.ElRadioButton),
-);
-const ElRadioGroup = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/radio/index'),
-    import('element-plus/es/components/radio-group/style/css'),
-  ]).then(([res]) => res.ElRadioGroup),
-);
-const ElSelectV2 = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/select-v2/index'),
-    import('element-plus/es/components/select-v2/style/css'),
-  ]).then(([res]) => res.ElSelectV2),
-);
-const ElSpace = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/space/index'),
-    import('element-plus/es/components/space/style/css'),
-  ]).then(([res]) => res.ElSpace),
-);
-const ElSwitch = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/switch/index'),
-    import('element-plus/es/components/switch/style/css'),
-  ]).then(([res]) => res.ElSwitch),
-);
-const ElTimePicker = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/time-picker/index'),
-    import('element-plus/es/components/time-picker/style/css'),
-  ]).then(([res]) => res.ElTimePicker),
-);
-const ElTreeSelect = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/tree-select/index'),
-    import('element-plus/es/components/tree-select/style/css'),
-  ]).then(([res]) => res.ElTreeSelect),
-);
-const ElUpload = defineAsyncComponent(() =>
-  Promise.all([
-    import('element-plus/es/components/upload/index'),
-    import('element-plus/es/components/upload/style/css'),
-  ]).then(([res]) => res.ElUpload),
-);
-
-const withDefaultPlaceholder = <T extends Component>(
-  component: T,
-  type: 'input' | 'select',
-  componentProps: Recordable<any> = {},
-) => {
-  return defineComponent({
-    name: component.name,
-    inheritAttrs: false,
-    setup: (props: any, { attrs, expose, slots }) => {
-      const placeholder =
-        props?.placeholder ||
-        attrs?.placeholder ||
-        $t(`ui.placeholder.${type}`);
-      // 透传组件暴露的方法
-      const innerRef = ref();
-      const publicApi: Recordable<any> = {};
-      expose(publicApi);
-      const instance = getCurrentInstance();
-      instance?.proxy?.$nextTick(() => {
-        for (const key in innerRef.value) {
-          if (typeof innerRef.value[key] === 'function') {
-            publicApi[key] = innerRef.value[key];
-          }
-        }
-      });
-      return () =>
-        h(
-          component,
-          { ...componentProps, placeholder, ...props, ...attrs, ref: innerRef },
-          slots,
-        );
-    },
-  });
-};
-
-// 这里需要自行根据业务组件库进行适配,需要用到的组件都需要在这里类型说明
-export type ComponentType =
-  | 'ApiSelect'
-  | 'ApiTreeSelect'
-  | 'Checkbox'
-  | 'CheckboxGroup'
-  | 'DatePicker'
-  | 'Divider'
-  | 'IconPicker'
-  | 'Input'
-  | 'InputNumber'
-  | 'RadioGroup'
-  | 'Select'
-  | 'Space'
-  | 'Switch'
-  | 'TimePicker'
-  | 'TreeSelect'
-  | 'Upload'
-  | BaseFormComponentType;
-
-async function initComponentAdapter() {
-  const components: Partial<Record<ComponentType, Component>> = {
-    // 如果你的组件体积比较大,可以使用异步加载
-    // Button: () =>
-    // import('xxx').then((res) => res.Button),
-    ApiSelect: withDefaultPlaceholder(
-      {
-        ...ApiComponent,
-        name: 'ApiSelect',
-      },
-      'select',
-      {
-        component: ElSelectV2,
-        loadingSlot: 'loading',
-        visibleEvent: 'onVisibleChange',
-      },
-    ),
-    ApiTreeSelect: withDefaultPlaceholder(
-      {
-        ...ApiComponent,
-        name: 'ApiTreeSelect',
-      },
-      'select',
-      {
-        component: ElTreeSelect,
-        props: { label: 'label', children: 'children' },
-        nodeKey: 'value',
-        loadingSlot: 'loading',
-        optionsPropName: 'data',
-        visibleEvent: 'onVisibleChange',
-      },
-    ),
-    Checkbox: ElCheckbox,
-    CheckboxGroup: (props, { attrs, slots }) => {
-      let defaultSlot;
-      if (Reflect.has(slots, 'default')) {
-        defaultSlot = slots.default;
-      } else {
-        const { options, isButton } = attrs;
-        if (Array.isArray(options)) {
-          defaultSlot = () =>
-            options.map((option) =>
-              h(isButton ? ElCheckboxButton : ElCheckbox, option),
-            );
-        }
-      }
-      return h(
-        ElCheckboxGroup,
-        { ...props, ...attrs },
-        { ...slots, default: defaultSlot },
-      );
-    },
-    // 自定义默认按钮
-    DefaultButton: (props, { attrs, slots }) => {
-      return h(ElButton, { ...props, attrs, type: 'info' }, slots);
-    },
-    // 自定义主要按钮
-    PrimaryButton: (props, { attrs, slots }) => {
-      return h(ElButton, { ...props, attrs, type: 'primary' }, slots);
-    },
-    Divider: ElDivider,
-    IconPicker: withDefaultPlaceholder(IconPicker, 'select', {
-      iconSlot: 'append',
-      modelValueProp: 'model-value',
-      inputComponent: ElInput,
-    }),
-    Input: withDefaultPlaceholder(ElInput, 'input'),
-    InputNumber: withDefaultPlaceholder(ElInputNumber, 'input'),
-    RadioGroup: (props, { attrs, slots }) => {
-      let defaultSlot;
-      if (Reflect.has(slots, 'default')) {
-        defaultSlot = slots.default;
-      } else {
-        const { options } = attrs;
-        if (Array.isArray(options)) {
-          defaultSlot = () =>
-            options.map((option) =>
-              h(attrs.isButton ? ElRadioButton : ElRadio, option),
-            );
-        }
-      }
-      return h(
-        ElRadioGroup,
-        { ...props, ...attrs },
-        { ...slots, default: defaultSlot },
-      );
-    },
-    Select: (props, { attrs, slots }) => {
-      return h(ElSelectV2, { ...props, attrs }, slots);
-    },
-    Space: ElSpace,
-    Switch: ElSwitch,
-    TimePicker: (props, { attrs, slots }) => {
-      const { name, id, isRange } = props;
-      const extraProps: Recordable<any> = {};
-      if (isRange) {
-        if (name && !Array.isArray(name)) {
-          extraProps.name = [name, `${name}_end`];
-        }
-        if (id && !Array.isArray(id)) {
-          extraProps.id = [id, `${id}_end`];
-        }
-      }
-      return h(
-        ElTimePicker,
-        {
-          ...props,
-          ...attrs,
-          ...extraProps,
-        },
-        slots,
-      );
-    },
-    DatePicker: (props, { attrs, slots }) => {
-      const { name, id, type } = props;
-      const extraProps: Recordable<any> = {};
-      if (type && type.includes('range')) {
-        if (name && !Array.isArray(name)) {
-          extraProps.name = [name, `${name}_end`];
-        }
-        if (id && !Array.isArray(id)) {
-          extraProps.id = [id, `${id}_end`];
-        }
-      }
-      return h(
-        ElDatePicker,
-        {
-          ...props,
-          ...attrs,
-          ...extraProps,
-        },
-        slots,
-      );
-    },
-    TreeSelect: withDefaultPlaceholder(ElTreeSelect, 'select'),
-    Upload: ElUpload,
-  };
-
-  // 将组件注册到全局共享状态中
-  globalShareState.setComponents(components);
-
-  // 定义全局共享状态中的消息提示
-  globalShareState.defineMessage({
-    // 复制成功消息提示
-    copyPreferencesSuccess: (title, content) => {
-      ElNotification({
-        title,
-        message: content,
-        position: 'bottom-right',
-        duration: 0,
-        type: 'success',
-      });
-    },
-  });
-}
-
-export { initComponentAdapter };

+ 0 - 39
web/apps/web-ele/src/adapter/form.ts

@@ -1,39 +0,0 @@
-import type {
-  VbenFormSchema as FormSchema,
-  VbenFormProps,
-} from '@vben/common-ui';
-
-import type { ComponentType } from './component';
-
-import { setupVbenForm, useVbenForm as useForm, z } from '@vben/common-ui';
-import { $t } from '@vben/locales';
-
-setupVbenForm<ComponentType>({
-  config: {
-    modelPropNameMap: {
-      Upload: 'fileList',
-      CheckboxGroup: 'model-value',
-    },
-  },
-  defineRules: {
-    required: (value, _params, ctx) => {
-      if (value === undefined || value === null || value.length === 0) {
-        return $t('ui.formRules.required', [ctx.label]);
-      }
-      return true;
-    },
-    selectRequired: (value, _params, ctx) => {
-      if (value === undefined || value === null) {
-        return $t('ui.formRules.selectRequired', [ctx.label]);
-      }
-      return true;
-    },
-  },
-});
-
-const useVbenForm = useForm<ComponentType>;
-
-export { useVbenForm, z };
-
-export type VbenFormSchema = FormSchema<ComponentType>;
-export type { VbenFormProps };

+ 0 - 68
web/apps/web-ele/src/adapter/vxe-table.ts

@@ -1,68 +0,0 @@
-import { h } from 'vue';
-
-import { setupVbenVxeTable, useVbenVxeGrid } from '@vben/plugins/vxe-table';
-
-import { ElButton, ElImage } from 'element-plus';
-
-import { useVbenForm } from './form';
-
-setupVbenVxeTable({
-  configVxeTable: (vxeUI) => {
-    vxeUI.setConfig({
-      grid: {
-        align: 'center',
-        border: false,
-        columnConfig: {
-          resizable: true,
-        },
-        minHeight: 180,
-        formConfig: {
-          // 全局禁用vxe-table的表单配置,使用formOptions
-          enabled: false,
-        },
-        proxyConfig: {
-          autoLoad: true,
-          response: {
-            result: 'items',
-            total: 'total',
-            list: 'items',
-          },
-          showActiveMsg: true,
-          showResponseMsg: false,
-        },
-        round: true,
-        showOverflow: true,
-        size: 'small',
-      },
-    });
-
-    // 表格配置项可以用 cellRender: { name: 'CellImage' },
-    vxeUI.renderer.add('CellImage', {
-      renderTableDefault(_renderOpts, params) {
-        const { column, row } = params;
-        const src = row[column.field];
-        return h(ElImage, { src, previewSrcList: [src] });
-      },
-    });
-
-    // 表格配置项可以用 cellRender: { name: 'CellLink' },
-    vxeUI.renderer.add('CellLink', {
-      renderTableDefault(renderOpts) {
-        const { props } = renderOpts;
-        return h(
-          ElButton,
-          { size: 'small', link: true },
-          { default: () => props?.text },
-        );
-      },
-    });
-
-    // 这里可以自行扩展 vxe-table 的全局配置,比如自定义格式化
-    // vxeUI.formats.add
-  },
-  useVbenForm,
-});
-
-export { useVbenVxeGrid };
-
-export type * from '@vben/plugins/vxe-table';

+ 0 - 51
web/apps/web-ele/src/api/core/auth.ts

@@ -1,51 +0,0 @@
-import { baseRequestClient, requestClient } from '#/api/request';
-
-export namespace AuthApi {
-  /** 登录接口参数 */
-  export interface LoginParams {
-    password?: string;
-    username?: string;
-  }
-
-  /** 登录接口返回值 */
-  export interface LoginResult {
-    accessToken: string;
-  }
-
-  export interface RefreshTokenResult {
-    data: string;
-    status: number;
-  }
-}
-
-/**
- * 登录
- */
-export async function loginApi(data: AuthApi.LoginParams) {
-  return requestClient.post<AuthApi.LoginResult>('/auth/login', data);
-}
-
-/**
- * 刷新accessToken
- */
-export async function refreshTokenApi() {
-  return baseRequestClient.post<AuthApi.RefreshTokenResult>('/auth/refresh', {
-    withCredentials: true,
-  });
-}
-
-/**
- * 退出登录
- */
-export async function logoutApi() {
-  return baseRequestClient.post('/auth/logout', {
-    withCredentials: true,
-  });
-}
-
-/**
- * 获取用户权限码
- */
-export async function getAccessCodesApi() {
-  return requestClient.get<string[]>('/auth/codes');
-}

+ 0 - 3
web/apps/web-ele/src/api/core/index.ts

@@ -1,3 +0,0 @@
-export * from './auth';
-export * from './menu';
-export * from './user';

+ 0 - 10
web/apps/web-ele/src/api/core/menu.ts

@@ -1,10 +0,0 @@
-import type { RouteRecordStringComponent } from '@vben/types';
-
-import { requestClient } from '#/api/request';
-
-/**
- * 获取用户所有菜单
- */
-export async function getAllMenusApi() {
-  return requestClient.get<RouteRecordStringComponent[]>('/menu/all');
-}

+ 0 - 10
web/apps/web-ele/src/api/core/user.ts

@@ -1,10 +0,0 @@
-import type { UserInfo } from '@vben/types';
-
-import { requestClient } from '#/api/request';
-
-/**
- * 获取用户信息
- */
-export async function getUserInfoApi() {
-  return requestClient.get<UserInfo>('/user/info');
-}

+ 0 - 1
web/apps/web-ele/src/api/index.ts

@@ -1 +0,0 @@
-export * from './core';

+ 0 - 113
web/apps/web-ele/src/api/request.ts

@@ -1,113 +0,0 @@
-/**
- * 该文件可自行根据业务逻辑进行调整
- */
-import type { RequestClientOptions } from '@vben/request';
-
-import { useAppConfig } from '@vben/hooks';
-import { preferences } from '@vben/preferences';
-import {
-  authenticateResponseInterceptor,
-  defaultResponseInterceptor,
-  errorMessageResponseInterceptor,
-  RequestClient,
-} from '@vben/request';
-import { useAccessStore } from '@vben/stores';
-
-import { ElMessage } from 'element-plus';
-
-import { useAuthStore } from '#/store';
-
-import { refreshTokenApi } from './core';
-
-const { apiURL } = useAppConfig(import.meta.env, import.meta.env.PROD);
-
-function createRequestClient(baseURL: string, options?: RequestClientOptions) {
-  const client = new RequestClient({
-    ...options,
-    baseURL,
-  });
-
-  /**
-   * 重新认证逻辑
-   */
-  async function doReAuthenticate() {
-    console.warn('Access token or refresh token is invalid or expired. ');
-    const accessStore = useAccessStore();
-    const authStore = useAuthStore();
-    accessStore.setAccessToken(null);
-    if (
-      preferences.app.loginExpiredMode === 'modal' &&
-      accessStore.isAccessChecked
-    ) {
-      accessStore.setLoginExpired(true);
-    } else {
-      await authStore.logout();
-    }
-  }
-
-  /**
-   * 刷新token逻辑
-   */
-  async function doRefreshToken() {
-    const accessStore = useAccessStore();
-    const resp = await refreshTokenApi();
-    const newToken = resp.data;
-    accessStore.setAccessToken(newToken);
-    return newToken;
-  }
-
-  function formatToken(token: null | string) {
-    return token ? `Bearer ${token}` : null;
-  }
-
-  // 请求头处理
-  client.addRequestInterceptor({
-    fulfilled: async (config) => {
-      const accessStore = useAccessStore();
-
-      config.headers.Authorization = formatToken(accessStore.accessToken);
-      config.headers['Accept-Language'] = preferences.app.locale;
-      return config;
-    },
-  });
-
-  // 处理返回的响应数据格式
-  client.addResponseInterceptor(
-    defaultResponseInterceptor({
-      codeField: 'code',
-      dataField: 'data',
-      successCode: 0,
-    }),
-  );
-
-  // token过期的处理
-  client.addResponseInterceptor(
-    authenticateResponseInterceptor({
-      client,
-      doReAuthenticate,
-      doRefreshToken,
-      enableRefreshToken: preferences.app.enableRefreshToken,
-      formatToken,
-    }),
-  );
-
-  // 通用的错误处理,如果没有进入上面的错误处理逻辑,就会进入这里
-  client.addResponseInterceptor(
-    errorMessageResponseInterceptor((msg: string, error) => {
-      // 这里可以根据业务进行定制,你可以拿到 error 内的信息进行定制化处理,根据不同的 code 做不同的提示,而不是直接使用 message.error 提示 msg
-      // 当前mock接口返回的错误字段是 error 或者 message
-      const responseData = error?.response?.data ?? {};
-      const errorMessage = responseData?.error ?? responseData?.message ?? '';
-      // 如果没有错误信息,则会根据状态码进行提示
-      ElMessage.error(errorMessage || msg);
-    }),
-  );
-
-  return client;
-}
-
-export const requestClient = createRequestClient(apiURL, {
-  responseReturn: 'data',
-});
-
-export const baseRequestClient = new RequestClient({ baseURL: apiURL });

+ 0 - 17
web/apps/web-ele/src/app.vue

@@ -1,17 +0,0 @@
-<script lang="ts" setup>
-import { useElementPlusDesignTokens } from '@vben/hooks';
-
-import { ElConfigProvider } from 'element-plus';
-
-import { elementLocale } from '#/locales';
-
-defineOptions({ name: 'App' });
-
-useElementPlusDesignTokens();
-</script>
-
-<template>
-  <ElConfigProvider :locale="elementLocale">
-    <RouterView />
-  </ElConfigProvider>
-</template>

+ 0 - 74
web/apps/web-ele/src/bootstrap.ts

@@ -1,74 +0,0 @@
-import { createApp, watchEffect } from 'vue';
-
-import { registerAccessDirective } from '@vben/access';
-import { registerLoadingDirective } from '@vben/common-ui';
-import { preferences } from '@vben/preferences';
-import { initStores } from '@vben/stores';
-import '@vben/styles';
-import '@vben/styles/ele';
-
-import { useTitle } from '@vueuse/core';
-import { ElLoading } from 'element-plus';
-
-import { $t, setupI18n } from '#/locales';
-
-import { initComponentAdapter } from './adapter/component';
-import App from './app.vue';
-import { router } from './router';
-
-async function bootstrap(namespace: string) {
-  // 初始化组件适配器
-  await initComponentAdapter();
-  // // 设置弹窗的默认配置
-  // setDefaultModalProps({
-  //   fullscreenButton: false,
-  // });
-  // // 设置抽屉的默认配置
-  // setDefaultDrawerProps({
-  //   zIndex: 2000,
-  // });
-  const app = createApp(App);
-
-  // 注册Element Plus提供的v-loading指令
-  app.directive('loading', ElLoading.directive);
-
-  // 注册Vben提供的v-loading和v-spinning指令
-  registerLoadingDirective(app, {
-    loading: false, // Vben提供的v-loading指令和Element Plus提供的v-loading指令二选一即可,此处false表示不注册Vben提供的v-loading指令
-    spinning: 'spinning',
-  });
-
-  // 国际化 i18n 配置
-  await setupI18n(app);
-
-  // 配置 pinia-tore
-  await initStores(app, { namespace });
-
-  // 安装权限指令
-  registerAccessDirective(app);
-
-  // 初始化 tippy
-  const { initTippy } = await import('@vben/common-ui/es/tippy');
-  initTippy(app);
-
-  // 配置路由及路由守卫
-  app.use(router);
-
-  // 配置Motion插件
-  const { MotionPlugin } = await import('@vben/plugins/motion');
-  app.use(MotionPlugin);
-
-  // 动态更新标题
-  watchEffect(() => {
-    if (preferences.app.dynamicTitle) {
-      const routeTitle = router.currentRoute.value.meta?.title;
-      const pageTitle =
-        (routeTitle ? `${$t(routeTitle)} - ` : '') + preferences.app.name;
-      useTitle(pageTitle);
-    }
-  });
-
-  app.mount('#app');
-}
-
-export { bootstrap };

+ 0 - 23
web/apps/web-ele/src/layouts/auth.vue

@@ -1,23 +0,0 @@
-<script lang="ts" setup>
-import { computed } from 'vue';
-
-import { AuthPageLayout } from '@vben/layouts';
-import { preferences } from '@vben/preferences';
-
-import { $t } from '#/locales';
-
-const appName = computed(() => preferences.app.name);
-const logo = computed(() => preferences.logo.source);
-</script>
-
-<template>
-  <AuthPageLayout
-    :app-name="appName"
-    :logo="logo"
-    :page-description="$t('authentication.pageDesc')"
-    :page-title="$t('authentication.pageTitle')"
-  >
-    <!-- 自定义工具栏 -->
-    <!-- <template #toolbar></template> -->
-  </AuthPageLayout>
-</template>

+ 0 - 157
web/apps/web-ele/src/layouts/basic.vue

@@ -1,157 +0,0 @@
-<script lang="ts" setup>
-import type { NotificationItem } from '@vben/layouts';
-
-import { computed, ref, watch } from 'vue';
-
-import { AuthenticationLoginExpiredModal } from '@vben/common-ui';
-import { VBEN_DOC_URL, VBEN_GITHUB_URL } from '@vben/constants';
-import { useWatermark } from '@vben/hooks';
-import { BookOpenText, CircleHelp, MdiGithub } from '@vben/icons';
-import {
-  BasicLayout,
-  LockScreen,
-  Notification,
-  UserDropdown,
-} from '@vben/layouts';
-import { preferences } from '@vben/preferences';
-import { useAccessStore, useUserStore } from '@vben/stores';
-import { openWindow } from '@vben/utils';
-
-import { $t } from '#/locales';
-import { useAuthStore } from '#/store';
-import LoginForm from '#/views/_core/authentication/login.vue';
-
-const notifications = ref<NotificationItem[]>([
-  {
-    avatar: 'https://avatar.vercel.sh/vercel.svg?text=VB',
-    date: '3小时前',
-    isRead: true,
-    message: '描述信息描述信息描述信息',
-    title: '收到了 14 份新周报',
-  },
-  {
-    avatar: 'https://avatar.vercel.sh/1',
-    date: '刚刚',
-    isRead: false,
-    message: '描述信息描述信息描述信息',
-    title: '朱偏右 回复了你',
-  },
-  {
-    avatar: 'https://avatar.vercel.sh/1',
-    date: '2024-01-01',
-    isRead: false,
-    message: '描述信息描述信息描述信息',
-    title: '曲丽丽 评论了你',
-  },
-  {
-    avatar: 'https://avatar.vercel.sh/satori',
-    date: '1天前',
-    isRead: false,
-    message: '描述信息描述信息描述信息',
-    title: '代办提醒',
-  },
-]);
-
-const userStore = useUserStore();
-const authStore = useAuthStore();
-const accessStore = useAccessStore();
-const { destroyWatermark, updateWatermark } = useWatermark();
-const showDot = computed(() =>
-  notifications.value.some((item) => !item.isRead),
-);
-
-const menus = computed(() => [
-  {
-    handler: () => {
-      openWindow(VBEN_DOC_URL, {
-        target: '_blank',
-      });
-    },
-    icon: BookOpenText,
-    text: $t('ui.widgets.document'),
-  },
-  {
-    handler: () => {
-      openWindow(VBEN_GITHUB_URL, {
-        target: '_blank',
-      });
-    },
-    icon: MdiGithub,
-    text: 'GitHub',
-  },
-  {
-    handler: () => {
-      openWindow(`${VBEN_GITHUB_URL}/issues`, {
-        target: '_blank',
-      });
-    },
-    icon: CircleHelp,
-    text: $t('ui.widgets.qa'),
-  },
-]);
-
-const avatar = computed(() => {
-  return userStore.userInfo?.avatar ?? preferences.app.defaultAvatar;
-});
-
-async function handleLogout() {
-  await authStore.logout(false);
-}
-
-function handleNoticeClear() {
-  notifications.value = [];
-}
-
-function handleMakeAll() {
-  notifications.value.forEach((item) => (item.isRead = true));
-}
-watch(
-  () => preferences.app.watermark,
-  async (enable) => {
-    if (enable) {
-      await updateWatermark({
-        content: `${userStore.userInfo?.username} - ${userStore.userInfo?.realName}`,
-      });
-    } else {
-      destroyWatermark();
-    }
-  },
-  {
-    immediate: true,
-  },
-);
-</script>
-
-<template>
-  <BasicLayout @clear-preferences-and-logout="handleLogout">
-    <template #user-dropdown>
-      <UserDropdown
-        :avatar
-        :menus
-        :text="userStore.userInfo?.realName"
-        description="ann.vben@gmail.com"
-        tag-text="Pro"
-        @logout="handleLogout"
-      />
-    </template>
-    <template #notification>
-      <Notification
-        :dot="showDot"
-        :notifications="notifications"
-        @clear="handleNoticeClear"
-        @make-all="handleMakeAll"
-      />
-    </template>
-    <template #extra>
-      <AuthenticationLoginExpiredModal
-        v-model:open="accessStore.loginExpired"
-        :avatar
-      >
-        <LoginForm />
-      </AuthenticationLoginExpiredModal>
-    </template>
-    <template #lock-screen>
-      <LockScreen :avatar @to-login="handleLogout" />
-    </template>
-  </BasicLayout>
-</template>

+ 0 - 6
web/apps/web-ele/src/layouts/index.ts

@@ -1,6 +0,0 @@
-const BasicLayout = () => import('./basic.vue');
-const AuthPageLayout = () => import('./auth.vue');
-
-const IFrameView = () => import('@vben/layouts').then((m) => m.IFrameView);
-
-export { AuthPageLayout, BasicLayout, IFrameView };

+ 0 - 3
web/apps/web-ele/src/locales/README.md

@@ -1,3 +0,0 @@
-# locale
-
-每个app使用的国际化可能不同,这里用于扩展国际化的功能,例如扩展 dayjs、antd组件库的多语言切换,以及app本身的国际化文件。

+ 0 - 102
web/apps/web-ele/src/locales/index.ts

@@ -1,102 +0,0 @@
-import type { Language } from 'element-plus/es/locale';
-
-import type { App } from 'vue';
-
-import type { LocaleSetupOptions, SupportedLanguagesType } from '@vben/locales';
-
-import { ref } from 'vue';
-
-import {
-  $t,
-  setupI18n as coreSetup,
-  loadLocalesMapFromDir,
-} from '@vben/locales';
-import { preferences } from '@vben/preferences';
-
-import dayjs from 'dayjs';
-import enLocale from 'element-plus/es/locale/lang/en';
-import defaultLocale from 'element-plus/es/locale/lang/zh-cn';
-
-const elementLocale = ref<Language>(defaultLocale);
-
-const modules = import.meta.glob('./langs/**/*.json');
-
-const localesMap = loadLocalesMapFromDir(
-  /\.\/langs\/([^/]+)\/(.*)\.json$/,
-  modules,
-);
-/**
- * 加载应用特有的语言包
- * 这里也可以改造为从服务端获取翻译数据
- * @param lang
- */
-async function loadMessages(lang: SupportedLanguagesType) {
-  const [appLocaleMessages] = await Promise.all([
-    localesMap[lang]?.(),
-    loadThirdPartyMessage(lang),
-  ]);
-  return appLocaleMessages?.default;
-}
-
-/**
- * 加载第三方组件库的语言包
- * @param lang
- */
-async function loadThirdPartyMessage(lang: SupportedLanguagesType) {
-  await Promise.all([loadElementLocale(lang), loadDayjsLocale(lang)]);
-}
-
-/**
- * 加载dayjs的语言包
- * @param lang
- */
-async function loadDayjsLocale(lang: SupportedLanguagesType) {
-  let locale;
-  switch (lang) {
-    case 'en-US': {
-      locale = await import('dayjs/locale/en');
-      break;
-    }
-    case 'zh-CN': {
-      locale = await import('dayjs/locale/zh-cn');
-      break;
-    }
-    // 默认使用英语
-    default: {
-      locale = await import('dayjs/locale/en');
-    }
-  }
-  if (locale) {
-    dayjs.locale(locale);
-  } else {
-    console.error(`Failed to load dayjs locale for ${lang}`);
-  }
-}
-
-/**
- * 加载element-plus的语言包
- * @param lang
- */
-async function loadElementLocale(lang: SupportedLanguagesType) {
-  switch (lang) {
-    case 'en-US': {
-      elementLocale.value = enLocale;
-      break;
-    }
-    case 'zh-CN': {
-      elementLocale.value = defaultLocale;
-      break;
-    }
-  }
-}
-
-async function setupI18n(app: App, options: LocaleSetupOptions = {}) {
-  await coreSetup(app, {
-    defaultLocale: preferences.app.locale,
-    loadMessages,
-    missingWarn: !import.meta.env.PROD,
-    ...options,
-  });
-}
-
-export { $t, elementLocale, setupI18n };

+ 0 - 13
web/apps/web-ele/src/locales/langs/en-US/demos.json

@@ -1,13 +0,0 @@
-{
-  "title": "Demos",
-  "elementPlus": "Element Plus",
-  "form": "Form",
-  "vben": {
-    "title": "Project",
-    "about": "About",
-    "document": "Document",
-    "antdv": "Ant Design Vue Version",
-    "naive-ui": "Naive UI Version",
-    "element-plus": "Element Plus Version"
-  }
-}

+ 0 - 14
web/apps/web-ele/src/locales/langs/en-US/page.json

@@ -1,14 +0,0 @@
-{
-  "auth": {
-    "login": "Login",
-    "register": "Register",
-    "codeLogin": "Code Login",
-    "qrcodeLogin": "Qr Code Login",
-    "forgetPassword": "Forget Password"
-  },
-  "dashboard": {
-    "title": "Dashboard",
-    "analytics": "Analytics",
-    "workspace": "Workspace"
-  }
-}

+ 0 - 13
web/apps/web-ele/src/locales/langs/zh-CN/demos.json

@@ -1,13 +0,0 @@
-{
-  "title": "演示",
-  "elementPlus": "Element Plus",
-  "form": "表单演示",
-  "vben": {
-    "title": "项目",
-    "about": "关于",
-    "document": "文档",
-    "antdv": "Ant Design Vue 版本",
-    "naive-ui": "Naive UI 版本",
-    "element-plus": "Element Plus 版本"
-  }
-}

+ 0 - 14
web/apps/web-ele/src/locales/langs/zh-CN/page.json

@@ -1,14 +0,0 @@
-{
-  "auth": {
-    "login": "登录",
-    "register": "注册",
-    "codeLogin": "验证码登录",
-    "qrcodeLogin": "二维码登录",
-    "forgetPassword": "忘记密码"
-  },
-  "dashboard": {
-    "title": "概览",
-    "analytics": "分析页",
-    "workspace": "工作台"
-  }
-}

+ 0 - 31
web/apps/web-ele/src/main.ts

@@ -1,31 +0,0 @@
-import { initPreferences } from '@vben/preferences';
-import { unmountGlobalLoading } from '@vben/utils';
-
-import { overridesPreferences } from './preferences';
-
-/**
- * 应用初始化完成之后再进行页面加载渲染
- */
-async function initApplication() {
-  // name用于指定项目唯一标识
-  // 用于区分不同项目的偏好设置以及存储数据的key前缀以及其他一些需要隔离的数据
-  const env = import.meta.env.PROD ? 'prod' : 'dev';
-  const appVersion = import.meta.env.VITE_APP_VERSION;
-  const namespace = `${import.meta.env.VITE_APP_NAMESPACE}-${appVersion}-${env}`;
-
-  // app偏好设置初始化
-  await initPreferences({
-    namespace,
-    overrides: overridesPreferences,
-  });
-
-  // 启动应用并挂载
-  // vue应用主要逻辑及视图
-  const { bootstrap } = await import('./bootstrap');
-  await bootstrap(namespace);
-
-  // 移除并销毁loading
-  unmountGlobalLoading();
-}
-
-initApplication();

+ 0 - 13
web/apps/web-ele/src/preferences.ts

@@ -1,13 +0,0 @@
-import { defineOverridesPreferences } from '@vben/preferences';
-
-/**
- * @description 项目配置文件
- * 只需要覆盖项目中的一部分配置,不需要的配置不用覆盖,会自动使用默认配置
- * !!! 更改配置后请清空缓存,否则可能不生效
- */
-export const overridesPreferences = defineOverridesPreferences({
-  // overrides
-  app: {
-    name: import.meta.env.VITE_APP_TITLE,
-  },
-});

+ 0 - 42
web/apps/web-ele/src/router/access.ts

@@ -1,42 +0,0 @@
-import type {
-  ComponentRecordType,
-  GenerateMenuAndRoutesOptions,
-} from '@vben/types';
-
-import { generateAccessible } from '@vben/access';
-import { preferences } from '@vben/preferences';
-
-import { ElMessage } from 'element-plus';
-
-import { getAllMenusApi } from '#/api';
-import { BasicLayout, IFrameView } from '#/layouts';
-import { $t } from '#/locales';
-
-const forbiddenComponent = () => import('#/views/_core/fallback/forbidden.vue');
-
-async function generateAccess(options: GenerateMenuAndRoutesOptions) {
-  const pageMap: ComponentRecordType = import.meta.glob('../views/**/*.vue');
-
-  const layoutMap: ComponentRecordType = {
-    BasicLayout,
-    IFrameView,
-  };
-
-  return await generateAccessible(preferences.app.accessMode, {
-    ...options,
-    fetchMenuListAsync: async () => {
-      ElMessage({
-        duration: 1500,
-        message: `${$t('common.loadingMenu')}...`,
-      });
-      return await getAllMenusApi();
-    },
-    // 可以指定没有权限跳转403页面
-    forbiddenComponent,
-    // 如果 route.meta.menuVisibleWithForbidden = true
-    layoutMap,
-    pageMap,
-  });
-}
-
-export { generateAccess };

+ 0 - 133
web/apps/web-ele/src/router/guard.ts

@@ -1,133 +0,0 @@
-import type { Router } from 'vue-router';
-
-import { LOGIN_PATH } from '@vben/constants';
-import { preferences } from '@vben/preferences';
-import { useAccessStore, useUserStore } from '@vben/stores';
-import { startProgress, stopProgress } from '@vben/utils';
-
-import { accessRoutes, coreRouteNames } from '#/router/routes';
-import { useAuthStore } from '#/store';
-
-import { generateAccess } from './access';
-
-/**
- * 通用守卫配置
- * @param router
- */
-function setupCommonGuard(router: Router) {
-  // 记录已经加载的页面
-  const loadedPaths = new Set<string>();
-
-  router.beforeEach((to) => {
-    to.meta.loaded = loadedPaths.has(to.path);
-
-    // 页面加载进度条
-    if (!to.meta.loaded && preferences.transition.progress) {
-      startProgress();
-    }
-    return true;
-  });
-
-  router.afterEach((to) => {
-    // 记录页面是否加载,如果已经加载,后续的页面切换动画等效果不在重复执行
-
-    loadedPaths.add(to.path);
-
-    // 关闭页面加载进度条
-    if (preferences.transition.progress) {
-      stopProgress();
-    }
-  });
-}
-
-/**
- * 权限访问守卫配置
- * @param router
- */
-function setupAccessGuard(router: Router) {
-  router.beforeEach(async (to, from) => {
-    const accessStore = useAccessStore();
-    const userStore = useUserStore();
-    const authStore = useAuthStore();
-
-    // 基本路由,这些路由不需要进入权限拦截
-    if (coreRouteNames.includes(to.name as string)) {
-      if (to.path === LOGIN_PATH && accessStore.accessToken) {
-        return decodeURIComponent(
-          (to.query?.redirect as string) ||
-            userStore.userInfo?.homePath ||
-            preferences.app.defaultHomePath,
-        );
-      }
-      return true;
-    }
-
-    // accessToken 检查
-    if (!accessStore.accessToken) {
-      // 明确声明忽略权限访问权限,则可以访问
-      if (to.meta.ignoreAccess) {
-        return true;
-      }
-
-      // 没有访问权限,跳转登录页面
-      if (to.fullPath !== LOGIN_PATH) {
-        return {
-          path: LOGIN_PATH,
-          // 如不需要,直接删除 query
-          query:
-            to.fullPath === preferences.app.defaultHomePath
-              ? {}
-              : { redirect: encodeURIComponent(to.fullPath) },
-          // 携带当前跳转的页面,登录后重新跳转该页面
-          replace: true,
-        };
-      }
-      return to;
-    }
-
-    // 是否已经生成过动态路由
-    if (accessStore.isAccessChecked) {
-      return true;
-    }
-
-    // 生成路由表
-    // 当前登录用户拥有的角色标识列表
-    const userInfo = userStore.userInfo || (await authStore.fetchUserInfo());
-    const userRoles = userInfo.roles ?? [];
-
-    // 生成菜单和路由
-    const { accessibleMenus, accessibleRoutes } = await generateAccess({
-      roles: userRoles,
-      router,
-      // 则会在菜单中显示,但是访问会被重定向到403
-      routes: accessRoutes,
-    });
-
-    // 保存菜单信息和路由信息
-    accessStore.setAccessMenus(accessibleMenus);
-    accessStore.setAccessRoutes(accessibleRoutes);
-    accessStore.setIsAccessChecked(true);
-    const redirectPath = (from.query.redirect ??
-      (to.path === preferences.app.defaultHomePath
-        ? userInfo.homePath || preferences.app.defaultHomePath
-        : to.fullPath)) as string;
-
-    return {
-      ...router.resolve(decodeURIComponent(redirectPath)),
-      replace: true,
-    };
-  });
-}
-
-/**
- * 项目守卫配置
- * @param router
- */
-function createRouterGuard(router: Router) {
-  /** 通用 */
-  setupCommonGuard(router);
-  /** 权限访问 */
-  setupAccessGuard(router);
-}
-
-export { createRouterGuard };

+ 0 - 37
web/apps/web-ele/src/router/index.ts

@@ -1,37 +0,0 @@
-import {
-  createRouter,
-  createWebHashHistory,
-  createWebHistory,
-} from 'vue-router';
-
-import { resetStaticRoutes } from '@vben/utils';
-
-import { createRouterGuard } from './guard';
-import { routes } from './routes';
-
-/**
- *  @zh_CN 创建vue-router实例
- */
-const router = createRouter({
-  history:
-    import.meta.env.VITE_ROUTER_HISTORY === 'hash'
-      ? createWebHashHistory(import.meta.env.VITE_BASE)
-      : createWebHistory(import.meta.env.VITE_BASE),
-  // 应该添加到路由的初始路由列表。
-  routes,
-  scrollBehavior: (to, _from, savedPosition) => {
-    if (savedPosition) {
-      return savedPosition;
-    }
-    return to.hash ? { behavior: 'smooth', el: to.hash } : { left: 0, top: 0 };
-  },
-  // 是否应该禁止尾部斜杠。
-  // strict: true,
-});
-
-const resetRoutes = () => resetStaticRoutes(router, routes);
-
-// 创建路由守卫
-createRouterGuard(router);
-
-export { resetRoutes, router };

+ 0 - 97
web/apps/web-ele/src/router/routes/core.ts

@@ -1,97 +0,0 @@
-import type { RouteRecordRaw } from 'vue-router';
-
-import { LOGIN_PATH } from '@vben/constants';
-import { preferences } from '@vben/preferences';
-
-import { $t } from '#/locales';
-
-const BasicLayout = () => import('#/layouts/basic.vue');
-const AuthPageLayout = () => import('#/layouts/auth.vue');
-/** 全局404页面 */
-const fallbackNotFoundRoute: RouteRecordRaw = {
-  component: () => import('#/views/_core/fallback/not-found.vue'),
-  meta: {
-    hideInBreadcrumb: true,
-    hideInMenu: true,
-    hideInTab: true,
-    title: '404',
-  },
-  name: 'FallbackNotFound',
-  path: '/:path(.*)*',
-};
-
-/** 基本路由,这些路由是必须存在的 */
-const coreRoutes: RouteRecordRaw[] = [
-  /**
-   * 根路由
-   * 使用基础布局,作为所有页面的父级容器,子级就不必配置BasicLayout。
-   * 此路由必须存在,且不应修改
-   */
-  {
-    component: BasicLayout,
-    meta: {
-      hideInBreadcrumb: true,
-      title: 'Root',
-    },
-    name: 'Root',
-    path: '/',
-    redirect: preferences.app.defaultHomePath,
-    children: [],
-  },
-  {
-    component: AuthPageLayout,
-    meta: {
-      hideInTab: true,
-      title: 'Authentication',
-    },
-    name: 'Authentication',
-    path: '/auth',
-    redirect: LOGIN_PATH,
-    children: [
-      {
-        name: 'Login',
-        path: 'login',
-        component: () => import('#/views/_core/authentication/login.vue'),
-        meta: {
-          title: $t('page.auth.login'),
-        },
-      },
-      {
-        name: 'CodeLogin',
-        path: 'code-login',
-        component: () => import('#/views/_core/authentication/code-login.vue'),
-        meta: {
-          title: $t('page.auth.codeLogin'),
-        },
-      },
-      {
-        name: 'QrCodeLogin',
-        path: 'qrcode-login',
-        component: () =>
-          import('#/views/_core/authentication/qrcode-login.vue'),
-        meta: {
-          title: $t('page.auth.qrcodeLogin'),
-        },
-      },
-      {
-        name: 'ForgetPassword',
-        path: 'forget-password',
-        component: () =>
-          import('#/views/_core/authentication/forget-password.vue'),
-        meta: {
-          title: $t('page.auth.forgetPassword'),
-        },
-      },
-      {
-        name: 'Register',
-        path: 'register',
-        component: () => import('#/views/_core/authentication/register.vue'),
-        meta: {
-          title: $t('page.auth.register'),
-        },
-      },
-    ],
-  },
-];
-
-export { coreRoutes, fallbackNotFoundRoute };

+ 0 - 37
web/apps/web-ele/src/router/routes/index.ts

@@ -1,37 +0,0 @@
-import type { RouteRecordRaw } from 'vue-router';
-
-import { mergeRouteModules, traverseTreeValues } from '@vben/utils';
-
-import { coreRoutes, fallbackNotFoundRoute } from './core';
-
-const dynamicRouteFiles = import.meta.glob('./modules/**/*.ts', {
-  eager: true,
-});
-
-// 有需要可以自行打开注释,并创建文件夹
-// const externalRouteFiles = import.meta.glob('./external/**/*.ts', { eager: true });
-// const staticRouteFiles = import.meta.glob('./static/**/*.ts', { eager: true });
-
-/** 动态路由 */
-const dynamicRoutes: RouteRecordRaw[] = mergeRouteModules(dynamicRouteFiles);
-
-/** 外部路由列表,访问这些页面可以不需要Layout,可能用于内嵌在别的系统(不会显示在菜单中) */
-// const externalRoutes: RouteRecordRaw[] = mergeRouteModules(externalRouteFiles);
-// const staticRoutes: RouteRecordRaw[] = mergeRouteModules(staticRouteFiles);
-const staticRoutes: RouteRecordRaw[] = [];
-const externalRoutes: RouteRecordRaw[] = [];
-
-/** 路由列表,由基本路由、外部路由和404兜底路由组成
- *  无需走权限验证(会一直显示在菜单中) */
-const routes: RouteRecordRaw[] = [
-  ...coreRoutes,
-  ...externalRoutes,
-  fallbackNotFoundRoute,
-];
-
-/** 基本路由列表,这些路由不需要进入权限拦截 */
-const coreRouteNames = traverseTreeValues(coreRoutes, (route) => route.name);
-
-/** 有权限校验的路由列表,包含动态路由和静态路由 */
-const accessRoutes = [...dynamicRoutes, ...staticRoutes];
-export { accessRoutes, coreRouteNames, routes };

+ 0 - 38
web/apps/web-ele/src/router/routes/modules/dashboard.ts

@@ -1,38 +0,0 @@
-import type { RouteRecordRaw } from 'vue-router';
-
-import { $t } from '#/locales';
-
-const routes: RouteRecordRaw[] = [
-  {
-    meta: {
-      icon: 'lucide:layout-dashboard',
-      order: -1,
-      title: $t('page.dashboard.title'),
-    },
-    name: 'Dashboard',
-    path: '/dashboard',
-    children: [
-      {
-        name: 'Analytics',
-        path: '/analytics',
-        component: () => import('#/views/dashboard/analytics/index.vue'),
-        meta: {
-          affixTab: true,
-          icon: 'lucide:area-chart',
-          title: $t('page.dashboard.analytics'),
-        },
-      },
-      {
-        name: 'Workspace',
-        path: '/workspace',
-        component: () => import('#/views/dashboard/workspace/index.vue'),
-        meta: {
-          icon: 'carbon:workspace',
-          title: $t('page.dashboard.workspace'),
-        },
-      },
-    ],
-  },
-];
-
-export default routes;

+ 0 - 36
web/apps/web-ele/src/router/routes/modules/demos.ts

@@ -1,36 +0,0 @@
-import type { RouteRecordRaw } from 'vue-router';
-
-import { $t } from '#/locales';
-
-const routes: RouteRecordRaw[] = [
-  {
-    meta: {
-      icon: 'ic:baseline-view-in-ar',
-      keepAlive: true,
-      order: 1000,
-      title: $t('demos.title'),
-    },
-    name: 'Demos',
-    path: '/demos',
-    children: [
-      {
-        meta: {
-          title: $t('demos.elementPlus'),
-        },
-        name: 'NaiveDemos',
-        path: '/demos/element',
-        component: () => import('#/views/demos/element/index.vue'),
-      },
-      {
-        meta: {
-          title: $t('demos.form'),
-        },
-        name: 'BasicForm',
-        path: '/demos/form',
-        component: () => import('#/views/demos/form/basic.vue'),
-      },
-    ],
-  },
-];
-
-export default routes;

+ 0 - 82
web/apps/web-ele/src/router/routes/modules/vben.ts

@@ -1,82 +0,0 @@
-import type { RouteRecordRaw } from 'vue-router';
-
-import {
-  VBEN_ANT_PREVIEW_URL,
-  VBEN_DOC_URL,
-  VBEN_GITHUB_URL,
-  VBEN_LOGO_URL,
-  VBEN_NAIVE_PREVIEW_URL,
-} from '@vben/constants';
-import { SvgAntdvLogoIcon } from '@vben/icons';
-
-import { IFrameView } from '#/layouts';
-import { $t } from '#/locales';
-
-const routes: RouteRecordRaw[] = [
-  {
-    meta: {
-      badgeType: 'dot',
-      icon: VBEN_LOGO_URL,
-      order: 9998,
-      title: $t('demos.vben.title'),
-    },
-    name: 'VbenProject',
-    path: '/vben-admin',
-    children: [
-      {
-        name: 'VbenDocument',
-        path: '/vben-admin/document',
-        component: IFrameView,
-        meta: {
-          icon: 'lucide:book-open-text',
-          link: VBEN_DOC_URL,
-          title: $t('demos.vben.document'),
-        },
-      },
-      {
-        name: 'VbenGithub',
-        path: '/vben-admin/github',
-        component: IFrameView,
-        meta: {
-          icon: 'mdi:github',
-          link: VBEN_GITHUB_URL,
-          title: 'Github',
-        },
-      },
-      {
-        name: 'VbenNaive',
-        path: '/vben-admin/naive',
-        component: IFrameView,
-        meta: {
-          badgeType: 'dot',
-          icon: 'logos:naiveui',
-          link: VBEN_NAIVE_PREVIEW_URL,
-          title: $t('demos.vben.naive-ui'),
-        },
-      },
-      {
-        name: 'VbenAntd',
-        path: '/vben-admin/antd',
-        component: IFrameView,
-        meta: {
-          badgeType: 'dot',
-          icon: SvgAntdvLogoIcon,
-          link: VBEN_ANT_PREVIEW_URL,
-          title: $t('demos.vben.antdv'),
-        },
-      },
-    ],
-  },
-  {
-    name: 'VbenAbout',
-    path: '/vben-admin/about',
-    component: () => import('#/views/_core/about/index.vue'),
-    meta: {
-      icon: 'lucide:copyright',
-      title: $t('demos.vben.about'),
-      order: 9999,
-    },
-  },
-];
-
-export default routes;

+ 0 - 119
web/apps/web-ele/src/store/auth.ts

@@ -1,119 +0,0 @@
-import type { Recordable, UserInfo } from '@vben/types';
-
-import { ref } from 'vue';
-import { useRouter } from 'vue-router';
-
-import { LOGIN_PATH } from '@vben/constants';
-import { preferences } from '@vben/preferences';
-import { resetAllStores, useAccessStore, useUserStore } from '@vben/stores';
-
-import { ElNotification } from 'element-plus';
-import { defineStore } from 'pinia';
-
-import { getAccessCodesApi, getUserInfoApi, loginApi, logoutApi } from '#/api';
-import { $t } from '#/locales';
-
-export const useAuthStore = defineStore('auth', () => {
-  const accessStore = useAccessStore();
-  const userStore = useUserStore();
-  const router = useRouter();
-
-  const loginLoading = ref(false);
-
-  /**
-   * 异步处理登录操作
-   * Asynchronously handle the login process
-   * @param params 登录表单数据
-   */
-  async function authLogin(
-    params: Recordable<any>,
-    onSuccess?: () => Promise<void> | void,
-  ) {
-    // 异步处理用户登录操作并获取 accessToken
-    let userInfo: null | UserInfo = null;
-    try {
-      loginLoading.value = true;
-      const { accessToken } = await loginApi(params);
-
-      // 如果成功获取到 accessToken
-      if (accessToken) {
-        // 将 accessToken 存储到 accessStore 中
-        accessStore.setAccessToken(accessToken);
-
-        // 获取用户信息并存储到 accessStore 中
-        const [fetchUserInfoResult, accessCodes] = await Promise.all([
-          fetchUserInfo(),
-          getAccessCodesApi(),
-        ]);
-
-        userInfo = fetchUserInfoResult;
-
-        userStore.setUserInfo(userInfo);
-        accessStore.setAccessCodes(accessCodes);
-
-        if (accessStore.loginExpired) {
-          accessStore.setLoginExpired(false);
-        } else {
-          onSuccess
-            ? await onSuccess?.()
-            : await router.push(
-                userInfo.homePath || preferences.app.defaultHomePath,
-              );
-        }
-
-        if (userInfo?.realName) {
-          ElNotification({
-            message: `${$t('authentication.loginSuccessDesc')}:${userInfo?.realName}`,
-            title: $t('authentication.loginSuccess'),
-            type: 'success',
-          });
-        }
-      }
-    } finally {
-      loginLoading.value = false;
-    }
-
-    return {
-      userInfo,
-    };
-  }
-
-  async function logout(redirect: boolean = true) {
-    try {
-      await logoutApi();
-    } catch {
-      // 不做任何处理
-    }
-    resetAllStores();
-    accessStore.setLoginExpired(false);
-
-    // 回登录页带上当前路由地址
-    await router.replace({
-      path: LOGIN_PATH,
-      query: redirect
-        ? {
-            redirect: encodeURIComponent(router.currentRoute.value.fullPath),
-          }
-        : {},
-    });
-  }
-
-  async function fetchUserInfo() {
-    let userInfo: null | UserInfo = null;
-    userInfo = await getUserInfoApi();
-    userStore.setUserInfo(userInfo);
-    return userInfo;
-  }
-
-  function $reset() {
-    loginLoading.value = false;
-  }
-
-  return {
-    $reset,
-    authLogin,
-    fetchUserInfo,
-    loginLoading,
-    logout,
-  };
-});

+ 0 - 1
web/apps/web-ele/src/store/index.ts

@@ -1 +0,0 @@
-export * from './auth';

+ 0 - 3
web/apps/web-ele/src/views/_core/README.md

@@ -1,3 +0,0 @@
-# \_core
-
-此目录包含应用程序正常运行所需的基本视图。这些视图是应用程序布局中使用的视图。

+ 0 - 9
web/apps/web-ele/src/views/_core/about/index.vue

@@ -1,9 +0,0 @@
-<script lang="ts" setup>
-import { About } from '@vben/common-ui';
-
-defineOptions({ name: 'About' });
-</script>
-
-<template>
-  <About />
-</template>

+ 0 - 69
web/apps/web-ele/src/views/_core/authentication/code-login.vue

@@ -1,69 +0,0 @@
-<script lang="ts" setup>
-import type { VbenFormSchema } from '@vben/common-ui';
-import type { Recordable } from '@vben/types';
-
-import { computed, ref } from 'vue';
-
-import { AuthenticationCodeLogin, z } from '@vben/common-ui';
-import { $t } from '@vben/locales';
-
-defineOptions({ name: 'CodeLogin' });
-
-const loading = ref(false);
-const CODE_LENGTH = 6;
-
-const formSchema = computed((): VbenFormSchema[] => {
-  return [
-    {
-      component: 'VbenInput',
-      componentProps: {
-        placeholder: $t('authentication.mobile'),
-      },
-      fieldName: 'phoneNumber',
-      label: $t('authentication.mobile'),
-      rules: z
-        .string()
-        .min(1, { message: $t('authentication.mobileTip') })
-        .refine((v) => /^\d{11}$/.test(v), {
-          message: $t('authentication.mobileErrortip'),
-        }),
-    },
-    {
-      component: 'VbenPinInput',
-      componentProps: {
-        codeLength: CODE_LENGTH,
-        createText: (countdown: number) => {
-          const text =
-            countdown > 0
-              ? $t('authentication.sendText', [countdown])
-              : $t('authentication.sendCode');
-          return text;
-        },
-        placeholder: $t('authentication.code'),
-      },
-      fieldName: 'code',
-      label: $t('authentication.code'),
-      rules: z.string().length(CODE_LENGTH, {
-        message: $t('authentication.codeTip', [CODE_LENGTH]),
-      }),
-    },
-  ];
-});
-/**
- * 异步处理登录操作
- * Asynchronously handle the login process
- * @param values 登录表单数据
- */
-async function handleLogin(values: Recordable<any>) {
-  // eslint-disable-next-line no-console
-  console.log(values);
-}
-</script>
-
-<template>
-  <AuthenticationCodeLogin
-    :form-schema="formSchema"
-    :loading="loading"
-    @submit="handleLogin"
-  />
-</template>

+ 0 - 43
web/apps/web-ele/src/views/_core/authentication/forget-password.vue

@@ -1,43 +0,0 @@
-<script lang="ts" setup>
-import type { VbenFormSchema } from '@vben/common-ui';
-import type { Recordable } from '@vben/types';
-
-import { computed, ref } from 'vue';
-
-import { AuthenticationForgetPassword, z } from '@vben/common-ui';
-import { $t } from '@vben/locales';
-
-defineOptions({ name: 'ForgetPassword' });
-
-const loading = ref(false);
-
-const formSchema = computed((): VbenFormSchema[] => {
-  return [
-    {
-      component: 'VbenInput',
-      componentProps: {
-        placeholder: 'example@example.com',
-      },
-      fieldName: 'email',
-      label: $t('authentication.email'),
-      rules: z
-        .string()
-        .min(1, { message: $t('authentication.emailTip') })
-        .email($t('authentication.emailValidErrorTip')),
-    },
-  ];
-});
-
-function handleSubmit(value: Recordable<any>) {
-  // eslint-disable-next-line no-console
-  console.log('reset email:', value);
-}
-</script>
-
-<template>
-  <AuthenticationForgetPassword
-    :form-schema="formSchema"
-    :loading="loading"
-    @submit="handleSubmit"
-  />
-</template>

+ 0 - 98
web/apps/web-ele/src/views/_core/authentication/login.vue

@@ -1,98 +0,0 @@
-<script lang="ts" setup>
-import type { VbenFormSchema } from '@vben/common-ui';
-import type { BasicOption } from '@vben/types';
-
-import { computed, markRaw } from 'vue';
-
-import { AuthenticationLogin, SliderCaptcha, z } from '@vben/common-ui';
-import { $t } from '@vben/locales';
-
-import { useAuthStore } from '#/store';
-
-defineOptions({ name: 'Login' });
-
-const authStore = useAuthStore();
-
-const MOCK_USER_OPTIONS: BasicOption[] = [
-  {
-    label: 'Super',
-    value: 'vben',
-  },
-  {
-    label: 'Admin',
-    value: 'admin',
-  },
-  {
-    label: 'User',
-    value: 'jack',
-  },
-];
-
-const formSchema = computed((): VbenFormSchema[] => {
-  return [
-    {
-      component: 'VbenSelect',
-      componentProps: {
-        options: MOCK_USER_OPTIONS,
-        placeholder: $t('authentication.selectAccount'),
-      },
-      fieldName: 'selectAccount',
-      label: $t('authentication.selectAccount'),
-      rules: z
-        .string()
-        .min(1, { message: $t('authentication.selectAccount') })
-        .optional()
-        .default('vben'),
-    },
-    {
-      component: 'VbenInput',
-      componentProps: {
-        placeholder: $t('authentication.usernameTip'),
-      },
-      dependencies: {
-        trigger(values, form) {
-          if (values.selectAccount) {
-            const findUser = MOCK_USER_OPTIONS.find(
-              (item) => item.value === values.selectAccount,
-            );
-            if (findUser) {
-              form.setValues({
-                password: '123456',
-                username: findUser.value,
-              });
-            }
-          }
-        },
-        triggerFields: ['selectAccount'],
-      },
-      fieldName: 'username',
-      label: $t('authentication.username'),
-      rules: z.string().min(1, { message: $t('authentication.usernameTip') }),
-    },
-    {
-      component: 'VbenInputPassword',
-      componentProps: {
-        placeholder: $t('authentication.password'),
-      },
-      fieldName: 'password',
-      label: $t('authentication.password'),
-      rules: z.string().min(1, { message: $t('authentication.passwordTip') }),
-    },
-    {
-      component: markRaw(SliderCaptcha),
-      fieldName: 'captcha',
-      rules: z.boolean().refine((value) => value, {
-        message: $t('authentication.verifyRequiredTip'),
-      }),
-    },
-  ];
-});
-</script>
-
-<template>
-  <AuthenticationLogin
-    :form-schema="formSchema"
-    :loading="authStore.loginLoading"
-    @submit="authStore.authLogin"
-  />
-</template>

+ 0 - 10
web/apps/web-ele/src/views/_core/authentication/qrcode-login.vue

@@ -1,10 +0,0 @@
-<script lang="ts" setup>
-import { AuthenticationQrCodeLogin } from '@vben/common-ui';
-import { LOGIN_PATH } from '@vben/constants';
-
-defineOptions({ name: 'QrCodeLogin' });
-</script>
-
-<template>
-  <AuthenticationQrCodeLogin :login-path="LOGIN_PATH" />
-</template>

+ 0 - 96
web/apps/web-ele/src/views/_core/authentication/register.vue

@@ -1,96 +0,0 @@
-<script lang="ts" setup>
-import type { VbenFormSchema } from '@vben/common-ui';
-import type { Recordable } from '@vben/types';
-
-import { computed, h, ref } from 'vue';
-
-import { AuthenticationRegister, z } from '@vben/common-ui';
-import { $t } from '@vben/locales';
-
-defineOptions({ name: 'Register' });
-
-const loading = ref(false);
-
-const formSchema = computed((): VbenFormSchema[] => {
-  return [
-    {
-      component: 'VbenInput',
-      componentProps: {
-        placeholder: $t('authentication.usernameTip'),
-      },
-      fieldName: 'username',
-      label: $t('authentication.username'),
-      rules: z.string().min(1, { message: $t('authentication.usernameTip') }),
-    },
-    {
-      component: 'VbenInputPassword',
-      componentProps: {
-        passwordStrength: true,
-        placeholder: $t('authentication.password'),
-      },
-      fieldName: 'password',
-      label: $t('authentication.password'),
-      renderComponentContent() {
-        return {
-          strengthText: () => $t('authentication.passwordStrength'),
-        };
-      },
-      rules: z.string().min(1, { message: $t('authentication.passwordTip') }),
-    },
-    {
-      component: 'VbenInputPassword',
-      componentProps: {
-        placeholder: $t('authentication.confirmPassword'),
-      },
-      dependencies: {
-        rules(values) {
-          const { password } = values;
-          return z
-            .string({ required_error: $t('authentication.passwordTip') })
-            .min(1, { message: $t('authentication.passwordTip') })
-            .refine((value) => value === password, {
-              message: $t('authentication.confirmPasswordTip'),
-            });
-        },
-        triggerFields: ['password'],
-      },
-      fieldName: 'confirmPassword',
-      label: $t('authentication.confirmPassword'),
-    },
-    {
-      component: 'VbenCheckbox',
-      fieldName: 'agreePolicy',
-      renderComponentContent: () => ({
-        default: () =>
-          h('span', [
-            $t('authentication.agree'),
-            h(
-              'a',
-              {
-                class: 'vben-link ml-1 ',
-                href: '',
-              },
-              `${$t('authentication.privacyPolicy')} & ${$t('authentication.terms')}`,
-            ),
-          ]),
-      }),
-      rules: z.boolean().refine((value) => !!value, {
-        message: $t('authentication.agreeTip'),
-      }),
-    },
-  ];
-});
-
-function handleSubmit(value: Recordable<any>) {
-  // eslint-disable-next-line no-console
-  console.log('register submit:', value);
-}
-</script>
-
-<template>
-  <AuthenticationRegister
-    :form-schema="formSchema"
-    :loading="loading"
-    @submit="handleSubmit"
-  />
-</template>

+ 0 - 7
web/apps/web-ele/src/views/_core/fallback/coming-soon.vue

@@ -1,7 +0,0 @@
-<script lang="ts" setup>
-import { Fallback } from '@vben/common-ui';
-</script>
-
-<template>
-  <Fallback status="coming-soon" />
-</template>

+ 0 - 9
web/apps/web-ele/src/views/_core/fallback/forbidden.vue

@@ -1,9 +0,0 @@
-<script lang="ts" setup>
-import { Fallback } from '@vben/common-ui';
-
-defineOptions({ name: 'Fallback403Demo' });
-</script>
-
-<template>
-  <Fallback status="403" />
-</template>

+ 0 - 9
web/apps/web-ele/src/views/_core/fallback/internal-error.vue

@@ -1,9 +0,0 @@
-<script lang="ts" setup>
-import { Fallback } from '@vben/common-ui';
-
-defineOptions({ name: 'Fallback500Demo' });
-</script>
-
-<template>
-  <Fallback status="500" />
-</template>

+ 0 - 9
web/apps/web-ele/src/views/_core/fallback/not-found.vue

@@ -1,9 +0,0 @@
-<script lang="ts" setup>
-import { Fallback } from '@vben/common-ui';
-
-defineOptions({ name: 'Fallback404Demo' });
-</script>
-
-<template>
-  <Fallback status="404" />
-</template>

+ 0 - 9
web/apps/web-ele/src/views/_core/fallback/offline.vue

@@ -1,9 +0,0 @@
-<script lang="ts" setup>
-import { Fallback } from '@vben/common-ui';
-
-defineOptions({ name: 'FallbackOfflineDemo' });
-</script>
-
-<template>
-  <Fallback status="offline" />
-</template>

+ 0 - 98
web/apps/web-ele/src/views/dashboard/analytics/analytics-trends.vue

@@ -1,98 +0,0 @@
-<script lang="ts" setup>
-import type { EchartsUIType } from '@vben/plugins/echarts';
-
-import { onMounted, ref } from 'vue';
-
-import { EchartsUI, useEcharts } from '@vben/plugins/echarts';
-
-const chartRef = ref<EchartsUIType>();
-const { renderEcharts } = useEcharts(chartRef);
-
-onMounted(() => {
-  renderEcharts({
-    grid: {
-      bottom: 0,
-      containLabel: true,
-      left: '1%',
-      right: '1%',
-      top: '2 %',
-    },
-    series: [
-      {
-        areaStyle: {},
-        data: [
-          111, 2000, 6000, 16_000, 33_333, 55_555, 64_000, 33_333, 18_000,
-          36_000, 70_000, 42_444, 23_222, 13_000, 8000, 4000, 1200, 333, 222,
-          111,
-        ],
-        itemStyle: {
-          color: '#5ab1ef',
-        },
-        smooth: true,
-        type: 'line',
-      },
-      {
-        areaStyle: {},
-        data: [
-          33, 66, 88, 333, 3333, 6200, 20_000, 3000, 1200, 13_000, 22_000,
-          11_000, 2221, 1201, 390, 198, 60, 30, 22, 11,
-        ],
-        itemStyle: {
-          color: '#019680',
-        },
-        smooth: true,
-        type: 'line',
-      },
-    ],
-    tooltip: {
-      axisPointer: {
-        lineStyle: {
-          color: '#019680',
-          width: 1,
-        },
-      },
-      trigger: 'axis',
-    },
-    // xAxis: {
-    //   axisTick: {
-    //     show: false,
-    //   },
-    //   boundaryGap: false,
-    //   data: Array.from({ length: 18 }).map((_item, index) => `${index + 6}:00`),
-    //   type: 'category',
-    // },
-    xAxis: {
-      axisTick: {
-        show: false,
-      },
-      boundaryGap: false,
-      data: Array.from({ length: 18 }).map((_item, index) => `${index + 6}:00`),
-      splitLine: {
-        lineStyle: {
-          type: 'solid',
-          width: 1,
-        },
-        show: true,
-      },
-      type: 'category',
-    },
-    yAxis: [
-      {
-        axisTick: {
-          show: false,
-        },
-        max: 80_000,
-        splitArea: {
-          show: true,
-        },
-        splitNumber: 4,
-        type: 'value',
-      },
-    ],
-  });
-});
-</script>
-
-<template>
-  <EchartsUI ref="chartRef" />
-</template>

+ 0 - 82
web/apps/web-ele/src/views/dashboard/analytics/analytics-visits-data.vue

@@ -1,82 +0,0 @@
-<script lang="ts" setup>
-import type { EchartsUIType } from '@vben/plugins/echarts';
-
-import { onMounted, ref } from 'vue';
-
-import { EchartsUI, useEcharts } from '@vben/plugins/echarts';
-
-const chartRef = ref<EchartsUIType>();
-const { renderEcharts } = useEcharts(chartRef);
-
-onMounted(() => {
-  renderEcharts({
-    legend: {
-      bottom: 0,
-      data: ['访问', '趋势'],
-    },
-    radar: {
-      indicator: [
-        {
-          name: '网页',
-        },
-        {
-          name: '移动端',
-        },
-        {
-          name: 'Ipad',
-        },
-        {
-          name: '客户端',
-        },
-        {
-          name: '第三方',
-        },
-        {
-          name: '其它',
-        },
-      ],
-      radius: '60%',
-      splitNumber: 8,
-    },
-    series: [
-      {
-        areaStyle: {
-          opacity: 1,
-          shadowBlur: 0,
-          shadowColor: 'rgba(0,0,0,.2)',
-          shadowOffsetX: 0,
-          shadowOffsetY: 10,
-        },
-        data: [
-          {
-            itemStyle: {
-              color: '#b6a2de',
-            },
-            name: '访问',
-            value: [90, 50, 86, 40, 50, 20],
-          },
-          {
-            itemStyle: {
-              color: '#5ab1ef',
-            },
-            name: '趋势',
-            value: [70, 75, 70, 76, 20, 85],
-          },
-        ],
-        itemStyle: {
-          // borderColor: '#fff',
-          borderRadius: 10,
-          borderWidth: 2,
-        },
-        symbolSize: 0,
-        type: 'radar',
-      },
-    ],
-    tooltip: {},
-  });
-});
-</script>
-
-<template>
-  <EchartsUI ref="chartRef" />
-</template>

+ 0 - 46
web/apps/web-ele/src/views/dashboard/analytics/analytics-visits-sales.vue

@@ -1,46 +0,0 @@
-<script lang="ts" setup>
-import type { EchartsUIType } from '@vben/plugins/echarts';
-
-import { onMounted, ref } from 'vue';
-
-import { EchartsUI, useEcharts } from '@vben/plugins/echarts';
-
-const chartRef = ref<EchartsUIType>();
-const { renderEcharts } = useEcharts(chartRef);
-
-onMounted(() => {
-  renderEcharts({
-    series: [
-      {
-        animationDelay() {
-          return Math.random() * 400;
-        },
-        animationEasing: 'exponentialInOut',
-        animationType: 'scale',
-        center: ['50%', '50%'],
-        color: ['#5ab1ef', '#b6a2de', '#67e0e3', '#2ec7c9'],
-        data: [
-          { name: '外包', value: 500 },
-          { name: '定制', value: 310 },
-          { name: '技术支持', value: 274 },
-          { name: '远程', value: 400 },
-        ].sort((a, b) => {
-          return a.value - b.value;
-        }),
-        name: '商业占比',
-        radius: '80%',
-        roseType: 'radius',
-        type: 'pie',
-      },
-    ],
-
-    tooltip: {
-      trigger: 'item',
-    },
-  });
-});
-</script>
-
-<template>
-  <EchartsUI ref="chartRef" />
-</template>

+ 0 - 65
web/apps/web-ele/src/views/dashboard/analytics/analytics-visits-source.vue

@@ -1,65 +0,0 @@
-<script lang="ts" setup>
-import type { EchartsUIType } from '@vben/plugins/echarts';
-
-import { onMounted, ref } from 'vue';
-
-import { EchartsUI, useEcharts } from '@vben/plugins/echarts';
-
-const chartRef = ref<EchartsUIType>();
-const { renderEcharts } = useEcharts(chartRef);
-
-onMounted(() => {
-  renderEcharts({
-    legend: {
-      bottom: '2%',
-      left: 'center',
-    },
-    series: [
-      {
-        animationDelay() {
-          return Math.random() * 100;
-        },
-        animationEasing: 'exponentialInOut',
-        animationType: 'scale',
-        avoidLabelOverlap: false,
-        color: ['#5ab1ef', '#b6a2de', '#67e0e3', '#2ec7c9'],
-        data: [
-          { name: '搜索引擎', value: 1048 },
-          { name: '直接访问', value: 735 },
-          { name: '邮件营销', value: 580 },
-          { name: '联盟广告', value: 484 },
-        ],
-        emphasis: {
-          label: {
-            fontSize: '12',
-            fontWeight: 'bold',
-            show: true,
-          },
-        },
-        itemStyle: {
-          // borderColor: '#fff',
-          borderRadius: 10,
-          borderWidth: 2,
-        },
-        label: {
-          position: 'center',
-          show: false,
-        },
-        labelLine: {
-          show: false,
-        },
-        name: '访问来源',
-        radius: ['40%', '65%'],
-        type: 'pie',
-      },
-    ],
-    tooltip: {
-      trigger: 'item',
-    },
-  });
-});
-</script>
-
-<template>
-  <EchartsUI ref="chartRef" />
-</template>

+ 0 - 55
web/apps/web-ele/src/views/dashboard/analytics/analytics-visits.vue

@@ -1,55 +0,0 @@
-<script lang="ts" setup>
-import type { EchartsUIType } from '@vben/plugins/echarts';
-
-import { onMounted, ref } from 'vue';
-
-import { EchartsUI, useEcharts } from '@vben/plugins/echarts';
-
-const chartRef = ref<EchartsUIType>();
-const { renderEcharts } = useEcharts(chartRef);
-
-onMounted(() => {
-  renderEcharts({
-    grid: {
-      bottom: 0,
-      containLabel: true,
-      left: '1%',
-      right: '1%',
-      top: '2 %',
-    },
-    series: [
-      {
-        barMaxWidth: 80,
-        // color: '#4f69fd',
-        data: [
-          3000, 2000, 3333, 5000, 3200, 4200, 3200, 2100, 3000, 5100, 6000,
-          3200, 4800,
-        ],
-        type: 'bar',
-      },
-    ],
-    tooltip: {
-      axisPointer: {
-        lineStyle: {
-          // color: '#4f69fd',
-          width: 1,
-        },
-      },
-      trigger: 'axis',
-    },
-    xAxis: {
-      data: Array.from({ length: 12 }).map((_item, index) => `${index + 1}月`),
-      type: 'category',
-    },
-    yAxis: {
-      max: 8000,
-      splitNumber: 4,
-      type: 'value',
-    },
-  });
-});
-</script>
-
-<template>
-  <EchartsUI ref="chartRef" />
-</template>

+ 0 - 90
web/apps/web-ele/src/views/dashboard/analytics/index.vue

@@ -1,90 +0,0 @@
-<script lang="ts" setup>
-import type { AnalysisOverviewItem } from '@vben/common-ui';
-import type { TabOption } from '@vben/types';
-
-import {
-  AnalysisChartCard,
-  AnalysisChartsTabs,
-  AnalysisOverview,
-} from '@vben/common-ui';
-import {
-  SvgBellIcon,
-  SvgCakeIcon,
-  SvgCardIcon,
-  SvgDownloadIcon,
-} from '@vben/icons';
-
-import AnalyticsTrends from './analytics-trends.vue';
-import AnalyticsVisitsData from './analytics-visits-data.vue';
-import AnalyticsVisitsSales from './analytics-visits-sales.vue';
-import AnalyticsVisitsSource from './analytics-visits-source.vue';
-import AnalyticsVisits from './analytics-visits.vue';
-
-const overviewItems: AnalysisOverviewItem[] = [
-  {
-    icon: SvgCardIcon,
-    title: '用户量',
-    totalTitle: '总用户量',
-    totalValue: 120_000,
-    value: 2000,
-  },
-  {
-    icon: SvgCakeIcon,
-    title: '访问量',
-    totalTitle: '总访问量',
-    totalValue: 500_000,
-    value: 20_000,
-  },
-  {
-    icon: SvgDownloadIcon,
-    title: '下载量',
-    totalTitle: '总下载量',
-    totalValue: 120_000,
-    value: 8000,
-  },
-  {
-    icon: SvgBellIcon,
-    title: '使用量',
-    totalTitle: '总使用量',
-    totalValue: 50_000,
-    value: 5000,
-  },
-];
-
-const chartTabs: TabOption[] = [
-  {
-    label: '流量趋势',
-    value: 'trends',
-  },
-  {
-    label: '月访问量',
-    value: 'visits',
-  },
-];
-</script>
-
-<template>
-  <div class="p-5">
-    <AnalysisOverview :items="overviewItems" />
-    <AnalysisChartsTabs :tabs="chartTabs" class="mt-5">
-      <template #trends>
-        <AnalyticsTrends />
-      </template>
-      <template #visits>
-        <AnalyticsVisits />
-      </template>
-    </AnalysisChartsTabs>
-
-    <div class="mt-5 w-full md:flex">
-      <AnalysisChartCard class="mt-5 md:mr-4 md:mt-0 md:w-1/3" title="访问数量">
-        <AnalyticsVisitsData />
-      </AnalysisChartCard>
-      <AnalysisChartCard class="mt-5 md:mr-4 md:mt-0 md:w-1/3" title="访问来源">
-        <AnalyticsVisitsSource />
-      </AnalysisChartCard>
-      <AnalysisChartCard class="mt-5 md:mt-0 md:w-1/3" title="访问来源">
-        <AnalyticsVisitsSales />
-      </AnalysisChartCard>
-    </div>
-  </div>
-</template>

+ 0 - 266
web/apps/web-ele/src/views/dashboard/workspace/index.vue

@@ -1,266 +0,0 @@
-<script lang="ts" setup>
-import type {
-  WorkbenchProjectItem,
-  WorkbenchQuickNavItem,
-  WorkbenchTodoItem,
-  WorkbenchTrendItem,
-} from '@vben/common-ui';
-
-import { ref } from 'vue';
-import { useRouter } from 'vue-router';
-
-import {
-  AnalysisChartCard,
-  WorkbenchHeader,
-  WorkbenchProject,
-  WorkbenchQuickNav,
-  WorkbenchTodo,
-  WorkbenchTrends,
-} from '@vben/common-ui';
-import { preferences } from '@vben/preferences';
-import { useUserStore } from '@vben/stores';
-import { openWindow } from '@vben/utils';
-
-import AnalyticsVisitsSource from '../analytics/analytics-visits-source.vue';
-
-const userStore = useUserStore();
-
-// 这是一个示例数据,实际项目中需要根据实际情况进行调整
-// url 也可以是内部路由,在 navTo 方法中识别处理,进行内部跳转
-// 例如:url: /dashboard/workspace
-const projectItems: WorkbenchProjectItem[] = [
-  {
-    color: '',
-    content: '不要等待机会,而要创造机会。',
-    date: '2021-04-01',
-    group: '开源组',
-    icon: 'carbon:logo-github',
-    title: 'Github',
-    url: 'https://github.com',
-  },
-  {
-    color: '#3fb27f',
-    content: '现在的你决定将来的你。',
-    date: '2021-04-01',
-    group: '算法组',
-    icon: 'ion:logo-vue',
-    title: 'Vue',
-    url: 'https://vuejs.org',
-  },
-  {
-    color: '#e18525',
-    content: '没有什么才能比努力更重要。',
-    date: '2021-04-01',
-    group: '上班摸鱼',
-    icon: 'ion:logo-html5',
-    title: 'Html5',
-    url: 'https://developer.mozilla.org/zh-CN/docs/Web/HTML',
-  },
-  {
-    color: '#bf0c2c',
-    content: '热情和欲望可以突破一切难关。',
-    date: '2021-04-01',
-    group: 'UI',
-    icon: 'ion:logo-angular',
-    title: 'Angular',
-    url: 'https://angular.io',
-  },
-  {
-    color: '#00d8ff',
-    content: '健康的身体是实现目标的基石。',
-    date: '2021-04-01',
-    group: '技术牛',
-    icon: 'bx:bxl-react',
-    title: 'React',
-    url: 'https://reactjs.org',
-  },
-  {
-    color: '#EBD94E',
-    content: '路是走出来的,而不是空想出来的。',
-    date: '2021-04-01',
-    group: '架构组',
-    icon: 'ion:logo-javascript',
-    title: 'Js',
-    url: 'https://developer.mozilla.org/zh-CN/docs/Web/JavaScript',
-  },
-];
-
-// 同样,这里的 url 也可以使用以 http 开头的外部链接
-const quickNavItems: WorkbenchQuickNavItem[] = [
-  {
-    color: '#1fdaca',
-    icon: 'ion:home-outline',
-    title: '首页',
-    url: '/',
-  },
-  {
-    color: '#bf0c2c',
-    icon: 'ion:grid-outline',
-    title: '仪表盘',
-    url: '/dashboard',
-  },
-  {
-    color: '#e18525',
-    icon: 'ion:layers-outline',
-    title: '组件',
-    url: '/demos/features/icons',
-  },
-  {
-    color: '#3fb27f',
-    icon: 'ion:settings-outline',
-    title: '系统管理',
-    url: '/demos/features/login-expired', // 这里的 URL 是示例,实际项目中需要根据实际情况进行调整
-  },
-  {
-    color: '#4daf1bc9',
-    icon: 'ion:key-outline',
-    title: '权限管理',
-    url: '/demos/access/page-control',
-  },
-  {
-    color: '#00d8ff',
-    icon: 'ion:bar-chart-outline',
-    title: '图表',
-    url: '/analytics',
-  },
-];
-
-const todoItems = ref<WorkbenchTodoItem[]>([
-  {
-    completed: false,
-    content: `审查最近提交到Git仓库的前端代码,确保代码质量和规范。`,
-    date: '2024-07-30 11:00:00',
-    title: '审查前端代码提交',
-  },
-  {
-    completed: true,
-    content: `检查并优化系统性能,降低CPU使用率。`,
-    date: '2024-07-30 11:00:00',
-    title: '系统性能优化',
-  },
-  {
-    completed: false,
-    content: `进行系统安全检查,确保没有安全漏洞或未授权的访问。 `,
-    date: '2024-07-30 11:00:00',
-    title: '安全检查',
-  },
-  {
-    completed: false,
-    content: `更新项目中的所有npm依赖包,确保使用最新版本。`,
-    date: '2024-07-30 11:00:00',
-    title: '更新项目依赖',
-  },
-  {
-    completed: false,
-    content: `修复用户报告的页面UI显示问题,确保在不同浏览器中显示一致。 `,
-    date: '2024-07-30 11:00:00',
-    title: '修复UI显示问题',
-  },
-]);
-const trendItems: WorkbenchTrendItem[] = [
-  {
-    avatar: 'svg:avatar-1',
-    content: `在 <a>开源组</a> 创建了项目 <a>Vue</a>`,
-    date: '刚刚',
-    title: '威廉',
-  },
-  {
-    avatar: 'svg:avatar-2',
-    content: `关注了 <a>威廉</a> `,
-    date: '1个小时前',
-    title: '艾文',
-  },
-  {
-    avatar: 'svg:avatar-3',
-    content: `发布了 <a>个人动态</a> `,
-    date: '1天前',
-    title: '克里斯',
-  },
-  {
-    avatar: 'svg:avatar-4',
-    content: `发表文章 <a>如何编写一个Vite插件</a> `,
-    date: '2天前',
-    title: 'Vben',
-  },
-  {
-    avatar: 'svg:avatar-1',
-    content: `回复了 <a>杰克</a> 的问题 <a>如何进行项目优化?</a>`,
-    date: '3天前',
-    title: '皮特',
-  },
-  {
-    avatar: 'svg:avatar-2',
-    content: `关闭了问题 <a>如何运行项目</a> `,
-    date: '1周前',
-    title: '杰克',
-  },
-  {
-    avatar: 'svg:avatar-3',
-    content: `发布了 <a>个人动态</a> `,
-    date: '1周前',
-    title: '威廉',
-  },
-  {
-    avatar: 'svg:avatar-4',
-    content: `推送了代码到 <a>Github</a>`,
-    date: '2021-04-01 20:00',
-    title: '威廉',
-  },
-  {
-    avatar: 'svg:avatar-4',
-    content: `发表文章 <a>如何编写使用 Admin Vben</a> `,
-    date: '2021-03-01 20:00',
-    title: 'Vben',
-  },
-];
-
-const router = useRouter();
-
-// 这是一个示例方法,实际项目中需要根据实际情况进行调整
-// This is a sample method, adjust according to the actual project requirements
-function navTo(nav: WorkbenchProjectItem | WorkbenchQuickNavItem) {
-  if (nav.url?.startsWith('http')) {
-    openWindow(nav.url);
-    return;
-  }
-  if (nav.url?.startsWith('/')) {
-    router.push(nav.url).catch((error) => {
-      console.error('Navigation failed:', error);
-    });
-  } else {
-    console.warn(`Unknown URL for navigation item: ${nav.title} -> ${nav.url}`);
-  }
-}
-</script>
-
-<template>
-  <div class="p-5">
-    <WorkbenchHeader
-      :avatar="userStore.userInfo?.avatar || preferences.app.defaultAvatar"
-    >
-      <template #title>
-        早安, {{ userStore.userInfo?.realName }}, 开始您一天的工作吧!
-      </template>
-      <template #description> 今日晴,20℃ - 32℃! </template>
-    </WorkbenchHeader>
-
-    <div class="mt-5 flex flex-col lg:flex-row">
-      <div class="mr-4 w-full lg:w-3/5">
-        <WorkbenchProject :items="projectItems" title="项目" @click="navTo" />
-        <WorkbenchTrends :items="trendItems" class="mt-5" title="最新动态" />
-      </div>
-      <div class="w-full lg:w-2/5">
-        <WorkbenchQuickNav
-          :items="quickNavItems"
-          class="mt-5 lg:mt-0"
-          title="快捷导航"
-          @click="navTo"
-        />
-        <WorkbenchTodo :items="todoItems" class="mt-5" title="待办事项" />
-        <AnalysisChartCard class="mt-5" title="访问来源">
-          <AnalyticsVisitsSource />
-        </AnalysisChartCard>
-      </div>
-    </div>
-  </div>
-</template>

+ 0 - 117
web/apps/web-ele/src/views/demos/element/index.vue

@@ -1,117 +0,0 @@
-<script lang="ts" setup>
-import { ref } from 'vue';
-
-import { Page } from '@vben/common-ui';
-
-import {
-  ElButton,
-  ElCard,
-  ElMessage,
-  ElNotification,
-  ElSegmented,
-  ElSpace,
-  ElTable,
-} from 'element-plus';
-
-type NotificationType = 'error' | 'info' | 'success' | 'warning';
-
-function info() {
-  ElMessage.info('How many roads must a man walk down');
-}
-
-function error() {
-  ElMessage.error({
-    duration: 2500,
-    message: 'Once upon a time you dressed so fine',
-  });
-}
-
-function warning() {
-  ElMessage.warning('How many roads must a man walk down');
-}
-function success() {
-  ElMessage.success(
-    'Cause you walked hand in hand With another man in my place',
-  );
-}
-
-function notify(type: NotificationType) {
-  ElNotification({
-    duration: 2500,
-    message: '说点啥呢',
-    type,
-  });
-}
-const tableData = [
-  { prop1: '1', prop2: 'A' },
-  { prop1: '2', prop2: 'B' },
-  { prop1: '3', prop2: 'C' },
-  { prop1: '4', prop2: 'D' },
-  { prop1: '5', prop2: 'E' },
-  { prop1: '6', prop2: 'F' },
-];
-
-const segmentedValue = ref('Mon');
-
-const segmentedOptions = ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'];
-</script>
-
-<template>
-  <Page
-    description="支持多语言,主题功能集成切换等"
-    title="Element Plus组件使用演示"
-  >
-    <div class="flex flex-wrap gap-5">
-      <ElCard class="mb-5 w-auto">
-        <template #header> 按钮 </template>
-        <ElSpace>
-          <ElButton text>Text</ElButton>
-          <ElButton>Default</ElButton>
-          <ElButton type="primary"> Primary </ElButton>
-          <ElButton type="info"> Info </ElButton>
-          <ElButton type="success"> Success </ElButton>
-          <ElButton type="warning"> Warning </ElButton>
-          <ElButton type="danger"> Error </ElButton>
-        </ElSpace>
-      </ElCard>
-      <ElCard class="mb-5 w-80">
-        <template #header> Message </template>
-        <ElSpace>
-          <ElButton type="info" @click="info"> 信息 </ElButton>
-          <ElButton type="danger" @click="error"> 错误 </ElButton>
-          <ElButton type="warning" @click="warning"> 警告 </ElButton>
-          <ElButton type="success" @click="success"> 成功 </ElButton>
-        </ElSpace>
-      </ElCard>
-      <ElCard class="mb-5 w-80">
-        <template #header> Notification </template>
-        <ElSpace>
-          <ElButton type="info" @click="notify('info')"> 信息 </ElButton>
-          <ElButton type="danger" @click="notify('error')"> 错误 </ElButton>
-          <ElButton type="warning" @click="notify('warning')"> 警告 </ElButton>
-          <ElButton type="success" @click="notify('success')"> 成功 </ElButton>
-        </ElSpace>
-      </ElCard>
-      <ElCard class="mb-5 w-auto">
-        <template #header> Segmented </template>
-        <ElSegmented
-          v-model="segmentedValue"
-          :options="segmentedOptions"
-          size="large"
-        />
-      </ElCard>
-      <ElCard class="mb-5 w-80">
-        <template #header> V-Loading </template>
-        <div class="flex size-72 items-center justify-center" v-loading="true">
-          一些演示的内容
-        </div>
-      </ElCard>
-      <ElCard class="mb-5 w-80">
-        <ElTable :data="tableData" stripe>
-          <ElTable.TableColumn label="测试列1" prop="prop1" />
-          <ElTable.TableColumn label="测试列2" prop="prop2" />
-        </ElTable>
-      </ElCard>
-    </div>
-  </Page>
-</template>

+ 0 - 191
web/apps/web-ele/src/views/demos/form/basic.vue

@@ -1,191 +0,0 @@
-<script lang="ts" setup>
-import { h } from 'vue';
-
-import { Page, useVbenDrawer } from '@vben/common-ui';
-
-import { ElButton, ElCard, ElCheckbox, ElMessage } from 'element-plus';
-
-import { useVbenForm } from '#/adapter/form';
-import { getAllMenusApi } from '#/api';
-
-const [Form, formApi] = useVbenForm({
-  commonConfig: {
-    // 所有表单项
-    componentProps: {
-      class: 'w-full',
-    },
-  },
-  layout: 'horizontal',
-  // 大屏一行显示3个,中屏一行显示2个,小屏一行显示1个
-  // wrapperClass: 'grid-cols-1 md:grid-cols-2 lg:grid-cols-3',
-  handleSubmit: (values) => {
-    ElMessage.success(`表单数据:${JSON.stringify(values)}`);
-  },
-  schema: [
-    {
-      component: 'IconPicker',
-      fieldName: 'icon',
-      label: 'IconPicker',
-    },
-    {
-      // 组件需要在 #/adapter.ts内注册,并加上类型
-      component: 'ApiSelect',
-      // 对应组件的参数
-      componentProps: {
-        // 菜单接口转options格式
-        afterFetch: (data: { name: string; path: string }[]) => {
-          return data.map((item: any) => ({
-            label: item.name,
-            value: item.path,
-          }));
-        },
-        // 菜单接口
-        api: getAllMenusApi,
-      },
-      // 字段名
-      fieldName: 'api',
-      // 界面显示的label
-      label: 'ApiSelect',
-    },
-    {
-      component: 'ApiTreeSelect',
-      // 对应组件的参数
-      componentProps: {
-        // 菜单接口
-        api: getAllMenusApi,
-        childrenField: 'children',
-        // 菜单接口转options格式
-        labelField: 'name',
-        valueField: 'path',
-      },
-      // 字段名
-      fieldName: 'apiTree',
-      // 界面显示的label
-      label: 'ApiTreeSelect',
-    },
-    {
-      component: 'Input',
-      fieldName: 'string',
-      label: 'String',
-    },
-    {
-      component: 'InputNumber',
-      fieldName: 'number',
-      label: 'Number',
-    },
-    {
-      component: 'RadioGroup',
-      fieldName: 'radio',
-      label: 'Radio',
-      componentProps: {
-        options: [
-          { value: 'A', label: 'A' },
-          { value: 'B', label: 'B' },
-          { value: 'C', label: 'C' },
-          { value: 'D', label: 'D' },
-          { value: 'E', label: 'E' },
-        ],
-      },
-    },
-    {
-      component: 'RadioGroup',
-      fieldName: 'radioButton',
-      label: 'RadioButton',
-      componentProps: {
-        isButton: true,
-        options: ['A', 'B', 'C', 'D', 'E', 'F'].map((v) => ({
-          value: v,
-          label: `选项${v}`,
-        })),
-      },
-    },
-    {
-      component: 'CheckboxGroup',
-      fieldName: 'checkbox',
-      label: 'Checkbox',
-      componentProps: {
-        options: ['A', 'B', 'C'].map((v) => ({ value: v, label: `选项${v}` })),
-      },
-    },
-    {
-      component: 'CheckboxGroup',
-      fieldName: 'checkbox1',
-      label: 'Checkbox1',
-      renderComponentContent: () => {
-        return {
-          default: () => {
-            return ['A', 'B', 'C', 'D'].map((v) =>
-              h(ElCheckbox, { label: v, value: v }),
-            );
-          },
-        };
-      },
-    },
-    {
-      component: 'CheckboxGroup',
-      fieldName: 'checkbotton',
-      label: 'CheckBotton',
-      componentProps: {
-        isButton: true,
-        options: [
-          { value: 'A', label: '选项A' },
-          { value: 'B', label: '选项B' },
-          { value: 'C', label: '选项C' },
-        ],
-      },
-    },
-    {
-      component: 'DatePicker',
-      fieldName: 'date',
-      label: 'Date',
-    },
-    {
-      component: 'Select',
-      fieldName: 'select',
-      label: 'Select',
-      componentProps: {
-        filterable: true,
-        options: [
-          { value: 'A', label: '选项A' },
-          { value: 'B', label: '选项B' },
-          { value: 'C', label: '选项C' },
-        ],
-      },
-    },
-  ],
-});
-
-const [Drawer, drawerApi] = useVbenDrawer();
-function setFormValues() {
-  formApi.setValues({
-    string: 'string',
-    number: 123,
-    radio: 'B',
-    radioButton: 'C',
-    checkbox: ['A', 'C'],
-    checkbotton: ['B', 'C'],
-    checkbox1: ['A', 'B'],
-    date: new Date(),
-    select: 'B',
-  });
-}
-</script>
-<template>
-  <Page
-    description="我们重新包装了CheckboxGroup、RadioGroup、Select,可以通过options属性传入选项属性数组以自动生成选项"
-    title="表单演示"
-  >
-    <Drawer class="w-[600px]" title="基础表单示例">
-      <Form />
-    </Drawer>
-    <ElCard>
-      <template #header>
-        <div class="flex items-center">
-          <span class="flex-auto">基础表单演示</span>
-          <ElButton type="primary" @click="setFormValues">设置表单值</ElButton>
-        </div>
-      </template>
-      <ElButton type="primary" @click="drawerApi.open"> 打开抽屉 </ElButton>
-    </ElCard>
-  </Page>
-</template>

+ 0 - 1
web/apps/web-ele/tailwind.config.mjs

@@ -1 +0,0 @@
-export { default } from '@vben/tailwind-config';

+ 0 - 12
web/apps/web-ele/tsconfig.json

@@ -1,12 +0,0 @@
-{
-  "$schema": "https://json.schemastore.org/tsconfig",
-  "extends": "@vben/tsconfig/web-app.json",
-  "compilerOptions": {
-    "baseUrl": ".",
-    "paths": {
-      "#/*": ["./src/*"]
-    }
-  },
-  "references": [{ "path": "./tsconfig.node.json" }],
-  "include": ["src/**/*.ts", "src/**/*.tsx", "src/**/*.vue"]
-}

+ 0 - 10
web/apps/web-ele/tsconfig.node.json

@@ -1,10 +0,0 @@
-{
-  "$schema": "https://json.schemastore.org/tsconfig",
-  "extends": "@vben/tsconfig/node.json",
-  "compilerOptions": {
-    "composite": true,
-    "tsBuildInfoFile": "./node_modules/.tmp/tsconfig.node.tsbuildinfo",
-    "noEmit": false
-  },
-  "include": ["vite.config.mts"]
-}

+ 0 - 27
web/apps/web-ele/vite.config.mts

@@ -1,27 +0,0 @@
-import { defineConfig } from '@vben/vite-config';
-
-import ElementPlus from 'unplugin-element-plus/vite';
-
-export default defineConfig(async () => {
-  return {
-    application: {},
-    vite: {
-      plugins: [
-        ElementPlus({
-          format: 'esm',
-        }),
-      ],
-      server: {
-        proxy: {
-          '/api': {
-            changeOrigin: true,
-            rewrite: (path) => path.replace(/^\/api/, ''),
-            // mock代理目标地址
-            target: 'http://localhost:5320/api',
-            ws: true,
-          },
-        },
-      },
-    },
-  };
-});

+ 0 - 7
web/apps/web-naive/.env.analyze

@@ -1,7 +0,0 @@
-# public path
-VITE_BASE=/
-
-# Basic interface address SPA
-VITE_GLOB_API_URL=/api
-
-VITE_VISUALIZER=true

+ 0 - 16
web/apps/web-naive/.env.development

@@ -1,16 +0,0 @@
-# 端口号
-VITE_PORT=5888
-
-VITE_BASE=/
-
-# 接口地址
-VITE_GLOB_API_URL=/api
-
-# 是否开启 Nitro Mock服务,true 为开启,false 为关闭
-VITE_NITRO_MOCK=true
-
-# 是否打开 devtools,true 为打开,false 为关闭
-VITE_DEVTOOLS=false
-
-# 是否注入全局loading
-VITE_INJECT_APP_LOADING=true

+ 0 - 19
web/apps/web-naive/.env.production

@@ -1,19 +0,0 @@
-VITE_BASE=/
-
-# 接口地址
-VITE_GLOB_API_URL=https://mock-napi.vben.pro/api
-
-# 是否开启压缩,可以设置为 none, brotli, gzip
-VITE_COMPRESS=none
-
-# 是否开启 PWA
-VITE_PWA=false
-
-# vue-router 的模式
-VITE_ROUTER_HISTORY=hash
-
-# 是否注入全局loading
-VITE_INJECT_APP_LOADING=true
-
-# 打包后是否生成dist.zip
-VITE_ARCHIVER=true

+ 0 - 35
web/apps/web-naive/index.html

@@ -1,35 +0,0 @@
-<!doctype html>
-<html lang="zh">
-  <head>
-    <meta charset="UTF-8" />
-    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
-    <meta name="renderer" content="webkit" />
-    <meta name="description" content="A Modern Back-end Management System" />
-    <meta name="keywords" content="Vben Admin Vue3 Vite" />
-    <meta name="author" content="Vben" />
-    <meta
-      name="viewport"
-      content="width=device-width,initial-scale=1.0,minimum-scale=1.0,maximum-scale=1.0,user-scalable=0"
-    />
-    <!-- 由 vite 注入 VITE_APP_TITLE 变量,在 .env 文件内配置 -->
-    <title><%= VITE_APP_TITLE %></title>
-    <link rel="icon" href="/favicon.ico" />
-    <script>
-      // 生产环境下注入百度统计
-      if (window._VBEN_ADMIN_PRO_APP_CONF_) {
-        var _hmt = _hmt || [];
-        (function () {
-          var hm = document.createElement('script');
-          hm.src =
-            'https://hm.baidu.com/hm.js?24bb3eb91dfe4ebfcbcee6952a107cb6';
-          var s = document.getElementsByTagName('script')[0];
-          s.parentNode.insertBefore(hm, s);
-        })();
-      }
-    </script>
-  </head>
-  <body>
-    <div id="app"></div>
-    <script type="module" src="/src/main.ts"></script>
-  </body>
-</html>

+ 0 - 49
web/apps/web-naive/package.json

@@ -1,49 +0,0 @@
-{
-  "name": "@vben/web-naive",
-  "version": "5.5.6",
-  "homepage": "https://vben.pro",
-  "bugs": "https://github.com/vbenjs/vue-vben-admin/issues",
-  "repository": {
-    "type": "git",
-    "url": "git+https://github.com/vbenjs/vue-vben-admin.git",
-    "directory": "apps/web-naive"
-  },
-  "license": "MIT",
-  "author": {
-    "name": "vben",
-    "email": "ann.vben@gmail.com",
-    "url": "https://github.com/anncwb"
-  },
-  "type": "module",
-  "scripts": {
-    "build": "pnpm vite build --mode production",
-    "build:analyze": "pnpm vite build --mode analyze",
-    "dev": "pnpm vite --mode development",
-    "preview": "vite preview",
-    "typecheck": "vue-tsc --noEmit --skipLibCheck"
-  },
-  "imports": {
-    "#/*": "./src/*"
-  },
-  "dependencies": {
-    "@vben/access": "workspace:*",
-    "@vben/common-ui": "workspace:*",
-    "@vben/constants": "workspace:*",
-    "@vben/hooks": "workspace:*",
-    "@vben/icons": "workspace:*",
-    "@vben/layouts": "workspace:*",
-    "@vben/locales": "workspace:*",
-    "@vben/plugins": "workspace:*",
-    "@vben/preferences": "workspace:*",
-    "@vben/request": "workspace:*",
-    "@vben/stores": "workspace:*",
-    "@vben/styles": "workspace:*",
-    "@vben/types": "workspace:*",
-    "@vben/utils": "workspace:*",
-    "@vueuse/core": "catalog:",
-    "naive-ui": "catalog:",
-    "pinia": "catalog:",
-    "vue": "catalog:",
-    "vue-router": "catalog:"
-  }
-}

Неке датотеке нису приказане због велике количине промена