diff --git a/README.md b/README.md
index a36f8d207..4945059cd 100644
--- a/README.md
+++ b/README.md
@@ -34,7 +34,7 @@
 * 高效率开发,使用代码生成器可以一键生成前后端代码 + 单元测试 + Swagger 接口文档 + Validator 参数校验
 * 集成微信小程序、微信公众号、企业微信、钉钉等三方登陆,集成支付宝、微信等支付与退款
 * 集成阿里云、腾讯云等短信渠道,集成 MinIO、阿里云、腾讯云、七牛云等云存储服务
-* 集成报表设计器,支持数据报表、图形报表、打印设计等
+* 集成报表设计器、大屏设计器,通过拖拽即可生成酷炫的报表与大屏
 
 | 项目名                  | 说明                     | 传送门                                                                                                                                 |
 |----------------------|------------------------|-------------------------------------------------------------------------------------------------------------------------------------|
@@ -171,10 +171,10 @@ ps:核心功能已经实现,正在对接微信小程序中...
 
 ### 数据报表
 
-|     | 功能       | 描述                                           |
-|-----|----------|----------------------------------------------|
-| 🚀  | 报表设计器     | 支持数据报表、图形报表、打印设计等       |
-| 🚀  | 大屏设计器     | 建设中... 拖拽式实现可视化数据大屏          |
+|     | 功能    | 描述                 |
+|-----|-------|--------------------|
+| 🚀  | 报表设计器 | 支持数据报表、图形报表、打印设计等  |
+| 🚀  | 大屏设计器 | 拖拽生成数据大屏,内置几十种图表组件 |
 
 ### 微信公众号
 
@@ -207,23 +207,23 @@ ps:核心功能已经实现,正在对接微信小程序中...
 
 ## 🐨 技术栈
 
-| 项目                           | 说明                 |
-|------------------------------|--------------------|
-| `yudao-dependencies`         | Maven 依赖版本管理       |
-| `yudao-framework`            | Java 框架拓展          |
-| `yudao-server`               | 管理后台 + 用户 APP 的服务端 |
-| `yudao-ui-admin`             | 管理后台的 Vue2 前端项目    |
-| `yudao-ui-admin-vue3`        | 管理后台的 Vue3 前端项目    |
-| `yudao-ui-admin-uniapp`      | 管理后台的 uni-app 多端项目 |
-| `yudao-ui-app`               | 用户 APP 的 UI 界面     |
-| `yudao-module-system`        | 系统功能的 Module 模块    |
-| `yudao-module-member`        | 会员中心的 Module 模块    |
-| `yudao-module-infra`         | 基础设施的 Module 模块    |
-| `yudao-module-bpm`           | 工作流程的 Module 模块    |
-| `yudao-module-pay`           | 支付系统的 Module 模块    |
-| `yudao-module-mall`          | 商城系统的 Module 模块    |
-| `yudao-module-mp`            | 微信公众号的 Module 模块   |
-| `yudao-module-visualization` | 大屏报表 Module 模块     |
+| 项目                      | 说明                 |
+|-------------------------|--------------------|
+| `yudao-dependencies`    | Maven 依赖版本管理       |
+| `yudao-framework`       | Java 框架拓展          |
+| `yudao-server`          | 管理后台 + 用户 APP 的服务端 |
+| `yudao-ui-admin`        | 管理后台的 Vue2 前端项目    |
+| `yudao-ui-admin-vue3`   | 管理后台的 Vue3 前端项目    |
+| `yudao-ui-admin-uniapp` | 管理后台的 uni-app 多端项目 |
+| `yudao-ui-app`          | 用户 APP 的 UI 界面     |
+| `yudao-module-system`   | 系统功能的 Module 模块    |
+| `yudao-module-member`   | 会员中心的 Module 模块    |
+| `yudao-module-infra`    | 基础设施的 Module 模块    |
+| `yudao-module-bpm`      | 工作流程的 Module 模块    |
+| `yudao-module-pay`      | 支付系统的 Module 模块    |
+| `yudao-module-mall`     | 商城系统的 Module 模块    |
+| `yudao-module-mp`       | 微信公众号的 Module 模块   |
+| `yudao-module-report`   | 大屏报表 Module 模块     |
 
 ### 后端
 
@@ -324,9 +324,10 @@ ps:核心功能已经实现,正在对接微信小程序中...
 
 ### 数据报表
 
-| 模块      | biu                                                              | biu                                                                    | biu                                                                    |
-|---------|------------------------------------------------------------------|------------------------------------------------------------------------|------------------------------------------------------------------------|
+| 模块    | biu                                                                                                    | biu                                                                                                    | biu                                                                                                          |
+|-------|--------------------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------------------------------------|
 | 报表设计器 | ![数据报表](https://static.iocoder.cn/images/ruoyi-vue-pro/报表设计器-数据报表.jpg?imageView2/2/format/webp/w/1280) | ![图形报表](https://static.iocoder.cn/images/ruoyi-vue-pro/报表设计器-图形报表.jpg?imageView2/2/format/webp/w/1280) | ![报表设计器-打印设计](https://static.iocoder.cn/images/ruoyi-vue-pro/报表设计器-打印设计.jpg?imageView2/2/format/webp/w/1280) |
+| 大屏设计器 | ![大屏列表](https://static.iocoder.cn/images/ruoyi-vue-pro/大屏设计器-列表.jpg?imageView2/2/format/webp/w/1280)   | ![大屏预览](https://static.iocoder.cn/images/ruoyi-vue-pro/大屏设计器-预览.jpg?imageView2/2/format/webp/w/1280)   | ![大屏编辑](https://static.iocoder.cn/images/ruoyi-vue-pro/大屏设计器-编辑.jpg?imageView2/2/format/webp/w/1280)         |
 
 ### 移动端(管理后台)
 
diff --git a/pom.xml b/pom.xml
index 9a2cf0e72..123797c2d 100644
--- a/pom.xml
+++ b/pom.xml
@@ -18,7 +18,7 @@
         <module>yudao-module-infra</module>
         <module>yudao-module-pay</module>
 <!--        <module>yudao-module-bpm</module>-->
-<!--        <module>yudao-module-visualization</module>-->
+<!--        <module>yudao-module-report</module>-->
 <!--        <module>yudao-module-mp</module>-->
 <!--        <module>yudao-module-mall</module>-->
         <!-- 示例项目 -->
diff --git a/sql/mysql/optional/go-view.sql b/sql/mysql/optional/go-view.sql
new file mode 100644
index 000000000..210cff3f9
--- /dev/null
+++ b/sql/mysql/optional/go-view.sql
@@ -0,0 +1,47 @@
+/*
+ Navicat Premium Data Transfer
+
+ Source Server         : 127.0.0.1 MySQL
+ Source Server Type    : MySQL
+ Source Server Version : 80026
+ Source Host           : localhost:3306
+ Source Schema         : ruoyi-vue-pro
+
+ Target Server Type    : MySQL
+ Target Server Version : 80026
+ File Encoding         : 65001
+
+ Date: 07/02/2023 22:00:03
+*/
+
+SET NAMES utf8mb4;
+SET FOREIGN_KEY_CHECKS = 0;
+
+-- ----------------------------
+-- Table structure for report_go_view_project
+-- ----------------------------
+DROP TABLE IF EXISTS `report_go_view_project`;
+CREATE TABLE `report_go_view_project`  (
+  `id` bigint NOT NULL AUTO_INCREMENT COMMENT '编号',
+  `name` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '项目名称',
+  `pic_url` varchar(1024) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NULL DEFAULT NULL COMMENT '预览图片 URL',
+  `content` text CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NULL COMMENT '报表内容',
+  `status` tinyint NOT NULL COMMENT '发布状态',
+  `remark` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NULL DEFAULT NULL COMMENT '项目备注',
+  `creator` varchar(64) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NULL DEFAULT '' COMMENT '创建者',
+  `create_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
+  `updater` varchar(64) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NULL DEFAULT '' COMMENT '更新者',
+  `update_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
+  `deleted` bit(1) NOT NULL DEFAULT b'0' COMMENT '是否删除',
+  `tenant_id` bigint NOT NULL DEFAULT 0 COMMENT '租户编号',
+  PRIMARY KEY (`id`) USING BTREE
+) ENGINE = InnoDB AUTO_INCREMENT = 9 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_unicode_ci COMMENT = 'GoView 项目表';
+
+-- ----------------------------
+-- Records of report_go_view_project
+-- ----------------------------
+BEGIN;
+INSERT INTO `report_go_view_project` (`id`, `name`, `pic_url`, `content`, `status`, `remark`, `creator`, `create_time`, `updater`, `update_time`, `deleted`, `tenant_id`) VALUES (6, 'HTTP示例', 'http://test.yudao.iocoder.cn/7c0cb26b09cfa97cae0b3e5d19b210978eed0ab184dd0bff1b66b3daf70a01fc.png', '{\n  \"editCanvasConfig\": {\n    \"projectName\": \"HTTP示例\",\n    \"width\": 1920,\n    \"height\": 1080,\n    \"filterShow\": false,\n    \"hueRotate\": 0,\n    \"saturate\": 1,\n    \"contrast\": 1,\n    \"brightness\": 1,\n    \"opacity\": 1,\n    \"rotateZ\": 0,\n    \"rotateX\": 0,\n    \"rotateY\": 0,\n    \"skewX\": 0,\n    \"skewY\": 0,\n    \"blendMode\": \"normal\",\n    \"background\": null,\n    \"backgroundImage\": null,\n    \"selectColor\": true,\n    \"chartThemeColor\": \"dark\",\n    \"chartThemeSetting\": {\n      \"title\": {\n        \"show\": true,\n        \"textStyle\": {\n          \"color\": \"#BFBFBF\",\n          \"fontSize\": 18\n        },\n        \"subtextStyle\": {\n          \"color\": \"#A2A2A2\",\n          \"fontSize\": 14\n        }\n      },\n      \"xAxis\": {\n        \"show\": true,\n        \"name\": \"\",\n        \"nameGap\": 15,\n        \"nameTextStyle\": {\n          \"color\": \"#B9B8CE\",\n          \"fontSize\": 12\n        },\n        \"inverse\": false,\n        \"axisLabel\": {\n          \"show\": true,\n          \"fontSize\": 12,\n          \"color\": \"#B9B8CE\",\n          \"rotate\": 0\n        },\n        \"position\": \"bottom\",\n        \"axisLine\": {\n          \"show\": true,\n          \"lineStyle\": {\n            \"color\": \"#B9B8CE\",\n            \"width\": 1\n          },\n          \"onZero\": true\n        },\n        \"axisTick\": {\n          \"show\": true,\n          \"length\": 5\n        },\n        \"splitLine\": {\n          \"show\": false,\n          \"lineStyle\": {\n            \"color\": \"#484753\",\n            \"width\": 1,\n            \"type\": \"solid\"\n          }\n        }\n      },\n      \"yAxis\": {\n        \"show\": true,\n        \"name\": \"\",\n        \"nameGap\": 15,\n        \"nameTextStyle\": {\n          \"color\": \"#B9B8CE\",\n          \"fontSize\": 12\n        },\n        \"inverse\": false,\n        \"axisLabel\": {\n          \"show\": true,\n          \"fontSize\": 12,\n          \"color\": \"#B9B8CE\",\n          \"rotate\": 0\n        },\n        \"position\": \"left\",\n        \"axisLine\": {\n          \"show\": true,\n          \"lineStyle\": {\n            \"color\": \"#B9B8CE\",\n            \"width\": 1\n          },\n          \"onZero\": true\n        },\n        \"axisTick\": {\n          \"show\": true,\n          \"length\": 5\n        },\n        \"splitLine\": {\n          \"show\": true,\n          \"lineStyle\": {\n            \"color\": \"#484753\",\n            \"width\": 1,\n            \"type\": \"solid\"\n          }\n        }\n      },\n      \"legend\": {\n        \"show\": true,\n        \"top\": \"5%\",\n        \"textStyle\": {\n          \"color\": \"#B9B8CE\"\n        }\n      },\n      \"grid\": {\n        \"show\": false,\n        \"left\": \"10%\",\n        \"top\": \"60\",\n        \"right\": \"10%\",\n        \"bottom\": \"60\"\n      },\n      \"dataset\": null\n    },\n    \"previewScaleType\": \"fit\"\n  },\n  \"componentList\": [\n    {\n      \"id\": \"4vxgys8nh6g000\",\n      \"isGroup\": false,\n      \"attr\": {\n        \"x\": 7,\n        \"y\": 11,\n        \"w\": 1898,\n        \"h\": 1066,\n        \"offsetX\": 0,\n        \"offsetY\": 0,\n        \"zIndex\": -1\n      },\n      \"styles\": {\n        \"filterShow\": false,\n        \"hueRotate\": 0,\n        \"saturate\": 1,\n        \"contrast\": 1,\n        \"brightness\": 1,\n        \"opacity\": 1,\n        \"rotateZ\": 0,\n        \"rotateX\": 0,\n        \"rotateY\": 0,\n        \"skewX\": 0,\n        \"skewY\": 0,\n        \"blendMode\": \"normal\",\n        \"animations\": []\n      },\n      \"status\": {\n        \"lock\": false,\n        \"hide\": false\n      },\n      \"request\": {\n        \"requestDataType\": 1,\n        \"requestHttpType\": \"get\",\n        \"requestUrl\": \"http://127.0.0.1:48080/admin-api/report/go-view/data/get-by-http\",\n        \"requestInterval\": null,\n        \"requestIntervalUnit\": \"second\",\n        \"requestContentType\": 0,\n        \"requestParamsBodyType\": \"none\",\n        \"requestSQLContent\": {\n          \"sql\": \"select * from  where\"\n        },\n        \"requestParams\": {\n          \"Body\": {\n            \"form-data\": {},\n            \"x-www-form-urlencoded\": {},\n            \"json\": \"\",\n            \"xml\": \"\"\n          },\n          \"Header\": {},\n          \"Params\": {}\n        }\n      },\n      \"filter\": null,\n      \"events\": {\n        \"baseEvent\": {\n          \"click\": null,\n          \"dblclick\": null,\n          \"mouseenter\": null,\n          \"mouseleave\": null\n        },\n        \"advancedEvents\": {\n          \"vnodeMounted\": null,\n          \"vnodeBeforeMount\": null\n        }\n      },\n      \"key\": \"LineCommon\",\n      \"chartConfig\": {\n        \"key\": \"LineCommon\",\n        \"chartKey\": \"VLineCommon\",\n        \"conKey\": \"VCLineCommon\",\n        \"title\": \"折线图\",\n        \"category\": \"Lines\",\n        \"categoryName\": \"折线图\",\n        \"package\": \"Charts\",\n        \"chartFrame\": \"echarts\",\n        \"image\": \"line.png\"\n      },\n      \"option\": {\n        \"legend\": {\n          \"show\": true,\n          \"top\": \"5%\",\n          \"textStyle\": {\n            \"color\": \"#B9B8CE\"\n          }\n        },\n        \"xAxis\": {\n          \"show\": true,\n          \"name\": \"\",\n          \"nameGap\": 15,\n          \"nameTextStyle\": {\n            \"color\": \"#B9B8CE\",\n            \"fontSize\": 12\n          },\n          \"inverse\": false,\n          \"axisLabel\": {\n            \"show\": true,\n            \"fontSize\": 12,\n            \"color\": \"#B9B8CE\",\n            \"rotate\": 0\n          },\n          \"position\": \"bottom\",\n          \"axisLine\": {\n            \"show\": true,\n            \"lineStyle\": {\n              \"color\": \"#B9B8CE\",\n              \"width\": 1\n            },\n            \"onZero\": true\n          },\n          \"axisTick\": {\n            \"show\": true,\n            \"length\": 5\n          },\n          \"splitLine\": {\n            \"show\": false,\n            \"lineStyle\": {\n              \"color\": \"#484753\",\n              \"width\": 1,\n              \"type\": \"solid\"\n            }\n          },\n          \"type\": \"category\"\n        },\n        \"yAxis\": {\n          \"show\": true,\n          \"name\": \"\",\n          \"nameGap\": 15,\n          \"nameTextStyle\": {\n            \"color\": \"#B9B8CE\",\n            \"fontSize\": 12\n          },\n          \"inverse\": false,\n          \"axisLabel\": {\n            \"show\": true,\n            \"fontSize\": 12,\n            \"color\": \"#B9B8CE\",\n            \"rotate\": 0\n          },\n          \"position\": \"left\",\n          \"axisLine\": {\n            \"show\": true,\n            \"lineStyle\": {\n              \"color\": \"#B9B8CE\",\n              \"width\": 1\n            },\n            \"onZero\": true\n          },\n          \"axisTick\": {\n            \"show\": true,\n            \"length\": 5\n          },\n          \"splitLine\": {\n            \"show\": true,\n            \"lineStyle\": {\n              \"color\": \"#484753\",\n              \"width\": 1,\n              \"type\": \"solid\"\n            }\n          },\n          \"type\": \"value\"\n        },\n        \"grid\": {\n          \"show\": false,\n          \"left\": \"10%\",\n          \"top\": \"60\",\n          \"right\": \"10%\",\n          \"bottom\": \"60\"\n        },\n        \"tooltip\": {\n          \"show\": true,\n          \"trigger\": \"axis\",\n          \"axisPointer\": {\n            \"type\": \"line\"\n          }\n        },\n        \"dataset\": {\n          \"dimensions\": [\n            \"日期\",\n            \"PV\",\n            \"UV\"\n          ],\n          \"source\": [\n            {\n              \"UV\": 518,\n              \"日期\": \"2021-01\",\n              \"PV\": 7954\n            },\n            {\n              \"UV\": 135,\n              \"日期\": \"2021-02\",\n              \"PV\": 9402\n            },\n            {\n              \"UV\": 905,\n              \"日期\": \"2021-03\",\n              \"PV\": 1665\n            },\n            {\n              \"UV\": 157,\n              \"日期\": \"2021-04\",\n              \"PV\": 2633\n            },\n            {\n              \"UV\": 849,\n              \"日期\": \"2021-05\",\n              \"PV\": 7650\n            },\n            {\n              \"UV\": 563,\n              \"日期\": \"2021-06\",\n              \"PV\": 2399\n            },\n            {\n              \"UV\": 427,\n              \"日期\": \"2021-07\",\n              \"PV\": 9952\n            },\n            {\n              \"UV\": 158,\n              \"日期\": \"2021-08\",\n              \"PV\": 9232\n            },\n            {\n              \"UV\": 894,\n              \"日期\": \"2021-09\",\n              \"PV\": 3013\n            },\n            {\n              \"UV\": 343,\n              \"日期\": \"2021-10\",\n              \"PV\": 6181\n            },\n            {\n              \"UV\": 294,\n              \"日期\": \"2021-11\",\n              \"PV\": 8949\n            },\n            {\n              \"UV\": 452,\n              \"日期\": \"2021-12\",\n              \"PV\": 8730\n            }\n          ]\n        },\n        \"series\": [\n          {\n            \"type\": \"line\",\n            \"label\": {\n              \"show\": true,\n              \"position\": \"top\",\n              \"color\": \"#fff\",\n              \"fontSize\": 12\n            },\n            \"symbolSize\": 5,\n            \"itemStyle\": {\n              \"color\": null,\n              \"borderRadius\": 0\n            },\n            \"lineStyle\": {\n              \"type\": \"solid\",\n              \"width\": 3,\n              \"color\": null\n            }\n          },\n          {\n            \"type\": \"line\",\n            \"label\": {\n              \"show\": true,\n              \"position\": \"top\",\n              \"color\": \"#fff\",\n              \"fontSize\": 12\n            },\n            \"symbolSize\": 5,\n            \"itemStyle\": {\n              \"color\": null,\n              \"borderRadius\": 0\n            },\n            \"lineStyle\": {\n              \"type\": \"solid\",\n              \"width\": 3,\n              \"color\": null\n            }\n          }\n        ],\n        \"backgroundColor\": \"rgba(0,0,0,0)\"\n      }\n    }\n  ],\n  \"requestGlobalConfig\": {\n    \"requestDataPond\": [],\n    \"requestOriginUrl\": \"\",\n    \"requestInterval\": 30,\n    \"requestIntervalUnit\": \"second\",\n    \"requestParams\": {\n      \"Body\": {\n        \"form-data\": {},\n        \"x-www-form-urlencoded\": {},\n        \"json\": \"\",\n        \"xml\": \"\"\n      },\n      \"Header\": {},\n      \"Params\": {}\n    }\n  }\n}', 0, NULL, '1', '2023-02-07 11:38:22', '1', '2023-02-07 17:27:43', b'0', 1), (7, 'SQL示例', 'http://test.yudao.iocoder.cn/c1f570bad6ec7e7fa4a0a7c8f563da4ea158fde6e731da4dd1abe8ba9b6baeed.png', '{\n  \"editCanvasConfig\": {\n    \"projectName\": \"SQL示例\",\n    \"width\": 1920,\n    \"height\": 1080,\n    \"filterShow\": false,\n    \"hueRotate\": 0,\n    \"saturate\": 1,\n    \"contrast\": 1,\n    \"brightness\": 1,\n    \"opacity\": 1,\n    \"rotateZ\": 0,\n    \"rotateX\": 0,\n    \"rotateY\": 0,\n    \"skewX\": 0,\n    \"skewY\": 0,\n    \"blendMode\": \"normal\",\n    \"background\": null,\n    \"backgroundImage\": null,\n    \"selectColor\": true,\n    \"chartThemeColor\": \"dark\",\n    \"chartThemeSetting\": {\n      \"title\": {\n        \"show\": true,\n        \"textStyle\": {\n          \"color\": \"#BFBFBF\",\n          \"fontSize\": 18\n        },\n        \"subtextStyle\": {\n          \"color\": \"#A2A2A2\",\n          \"fontSize\": 14\n        }\n      },\n      \"xAxis\": {\n        \"show\": true,\n        \"name\": \"\",\n        \"nameGap\": 15,\n        \"nameTextStyle\": {\n          \"color\": \"#B9B8CE\",\n          \"fontSize\": 12\n        },\n        \"inverse\": false,\n        \"axisLabel\": {\n          \"show\": true,\n          \"fontSize\": 12,\n          \"color\": \"#B9B8CE\",\n          \"rotate\": 0\n        },\n        \"position\": \"bottom\",\n        \"axisLine\": {\n          \"show\": true,\n          \"lineStyle\": {\n            \"color\": \"#B9B8CE\",\n            \"width\": 1\n          },\n          \"onZero\": true\n        },\n        \"axisTick\": {\n          \"show\": true,\n          \"length\": 5\n        },\n        \"splitLine\": {\n          \"show\": false,\n          \"lineStyle\": {\n            \"color\": \"#484753\",\n            \"width\": 1,\n            \"type\": \"solid\"\n          }\n        }\n      },\n      \"yAxis\": {\n        \"show\": true,\n        \"name\": \"\",\n        \"nameGap\": 15,\n        \"nameTextStyle\": {\n          \"color\": \"#B9B8CE\",\n          \"fontSize\": 12\n        },\n        \"inverse\": false,\n        \"axisLabel\": {\n          \"show\": true,\n          \"fontSize\": 12,\n          \"color\": \"#B9B8CE\",\n          \"rotate\": 0\n        },\n        \"position\": \"left\",\n        \"axisLine\": {\n          \"show\": true,\n          \"lineStyle\": {\n            \"color\": \"#B9B8CE\",\n            \"width\": 1\n          },\n          \"onZero\": true\n        },\n        \"axisTick\": {\n          \"show\": true,\n          \"length\": 5\n        },\n        \"splitLine\": {\n          \"show\": true,\n          \"lineStyle\": {\n            \"color\": \"#484753\",\n            \"width\": 1,\n            \"type\": \"solid\"\n          }\n        }\n      },\n      \"legend\": {\n        \"show\": true,\n        \"top\": \"5%\",\n        \"textStyle\": {\n          \"color\": \"#B9B8CE\"\n        }\n      },\n      \"grid\": {\n        \"show\": false,\n        \"left\": \"10%\",\n        \"top\": \"60\",\n        \"right\": \"10%\",\n        \"bottom\": \"60\"\n      },\n      \"dataset\": null\n    },\n    \"previewScaleType\": \"fit\"\n  },\n  \"componentList\": [\n    {\n      \"id\": \"5cqrghfle9g000\",\n      \"isGroup\": false,\n      \"attr\": {\n        \"x\": 27,\n        \"y\": 3,\n        \"w\": 1870,\n        \"h\": 1051,\n        \"offsetX\": 0,\n        \"offsetY\": 0,\n        \"zIndex\": -1\n      },\n      \"styles\": {\n        \"filterShow\": false,\n        \"hueRotate\": 0,\n        \"saturate\": 1,\n        \"contrast\": 1,\n        \"brightness\": 1,\n        \"opacity\": 1,\n        \"rotateZ\": 0,\n        \"rotateX\": 0,\n        \"rotateY\": 0,\n        \"skewX\": 0,\n        \"skewY\": 0,\n        \"blendMode\": \"normal\",\n        \"animations\": [\n          \"headShake\"\n        ]\n      },\n      \"status\": {\n        \"lock\": false,\n        \"hide\": false\n      },\n      \"request\": {\n        \"requestDataType\": 1,\n        \"requestHttpType\": \"post\",\n        \"requestUrl\": \"http://127.0.0.1:48080/admin-api/report/go-view/data/get-by-sql\",\n        \"requestInterval\": null,\n        \"requestIntervalUnit\": \"second\",\n        \"requestContentType\": 0,\n        \"requestParamsBodyType\": \"none\",\n        \"requestSQLContent\": {\n          \"sql\": \"SELECT DATE_FORMAT(create_time, \\\"%Y-%m\\\") AS time, COUNT(*) AS \'次数\', COUNT(DISTINCT(user_id)) AS \'人数\' FROM system_login_log GROUP BY DATE_FORMAT(create_time, \\\"%Y-%m\\\")\"\n        },\n        \"requestParams\": {\n          \"Body\": {\n            \"form-data\": {},\n            \"x-www-form-urlencoded\": {},\n            \"json\": \"\",\n            \"xml\": \"\"\n          },\n          \"Header\": {},\n          \"Params\": {}\n        }\n      },\n      \"filter\": null,\n      \"events\": {\n        \"baseEvent\": {\n          \"click\": null,\n          \"dblclick\": null,\n          \"mouseenter\": null,\n          \"mouseleave\": null\n        },\n        \"advancedEvents\": {\n          \"vnodeMounted\": null,\n          \"vnodeBeforeMount\": null\n        }\n      },\n      \"key\": \"LineCommon\",\n      \"chartConfig\": {\n        \"key\": \"LineCommon\",\n        \"chartKey\": \"VLineCommon\",\n        \"conKey\": \"VCLineCommon\",\n        \"title\": \"折线图\",\n        \"category\": \"Lines\",\n        \"categoryName\": \"折线图\",\n        \"package\": \"Charts\",\n        \"chartFrame\": \"echarts\",\n        \"image\": \"line.png\"\n      },\n      \"option\": {\n        \"legend\": {\n          \"show\": true,\n          \"top\": \"5%\",\n          \"textStyle\": {\n            \"color\": \"#B9B8CE\"\n          }\n        },\n        \"xAxis\": {\n          \"show\": true,\n          \"name\": \"\",\n          \"nameGap\": 15,\n          \"nameTextStyle\": {\n            \"color\": \"#B9B8CE\",\n            \"fontSize\": 12\n          },\n          \"inverse\": false,\n          \"axisLabel\": {\n            \"show\": true,\n            \"fontSize\": 12,\n            \"color\": \"#B9B8CE\",\n            \"rotate\": 0\n          },\n          \"position\": \"bottom\",\n          \"axisLine\": {\n            \"show\": true,\n            \"lineStyle\": {\n              \"color\": \"#B9B8CE\",\n              \"width\": 1\n            },\n            \"onZero\": true\n          },\n          \"axisTick\": {\n            \"show\": true,\n            \"length\": 5\n          },\n          \"splitLine\": {\n            \"show\": false,\n            \"lineStyle\": {\n              \"color\": \"#484753\",\n              \"width\": 1,\n              \"type\": \"solid\"\n            }\n          },\n          \"type\": \"category\"\n        },\n        \"yAxis\": {\n          \"show\": true,\n          \"name\": \"\",\n          \"nameGap\": 15,\n          \"nameTextStyle\": {\n            \"color\": \"#B9B8CE\",\n            \"fontSize\": 12\n          },\n          \"inverse\": false,\n          \"axisLabel\": {\n            \"show\": true,\n            \"fontSize\": 12,\n            \"color\": \"#B9B8CE\",\n            \"rotate\": 0\n          },\n          \"position\": \"left\",\n          \"axisLine\": {\n            \"show\": true,\n            \"lineStyle\": {\n              \"color\": \"#B9B8CE\",\n              \"width\": 1\n            },\n            \"onZero\": true\n          },\n          \"axisTick\": {\n            \"show\": true,\n            \"length\": 5\n          },\n          \"splitLine\": {\n            \"show\": true,\n            \"lineStyle\": {\n              \"color\": \"#484753\",\n              \"width\": 1,\n              \"type\": \"solid\"\n            }\n          },\n          \"type\": \"value\"\n        },\n        \"grid\": {\n          \"show\": false,\n          \"left\": \"10%\",\n          \"top\": \"60\",\n          \"right\": \"10%\",\n          \"bottom\": \"60\"\n        },\n        \"tooltip\": {\n          \"show\": true,\n          \"trigger\": \"axis\",\n          \"axisPointer\": {\n            \"type\": \"line\"\n          }\n        },\n        \"dataset\": {\n          \"dimensions\": [\n            \"time\",\n            \"次数\",\n            \"人数\"\n          ],\n          \"source\": [\n            {\n              \"次数\": 94,\n              \"time\": \"2022-05\",\n              \"人数\": 5\n            },\n            {\n              \"次数\": 120,\n              \"time\": \"2022-06\",\n              \"人数\": 2\n            },\n            {\n              \"次数\": 118,\n              \"time\": \"2022-07\",\n              \"人数\": 5\n            },\n            {\n              \"次数\": 37,\n              \"time\": \"2022-08\",\n              \"人数\": 2\n            },\n            {\n              \"次数\": 65,\n              \"time\": \"2022-09\",\n              \"人数\": 2\n            },\n            {\n              \"次数\": 35,\n              \"time\": \"2022-10\",\n              \"人数\": 2\n            },\n            {\n              \"次数\": 86,\n              \"time\": \"2022-11\",\n              \"人数\": 1\n            },\n            {\n              \"次数\": 49,\n              \"time\": \"2022-12\",\n              \"人数\": 3\n            },\n            {\n              \"次数\": 45,\n              \"time\": \"2023-01\",\n              \"人数\": 1\n            },\n            {\n              \"次数\": 70,\n              \"time\": \"2023-02\",\n              \"人数\": 1\n            }\n          ]\n        },\n        \"series\": [\n          {\n            \"type\": \"line\",\n            \"label\": {\n              \"show\": true,\n              \"position\": \"top\",\n              \"color\": \"#fff\",\n              \"fontSize\": 12\n            },\n            \"symbolSize\": 5,\n            \"itemStyle\": {\n              \"color\": null,\n              \"borderRadius\": 0\n            },\n            \"lineStyle\": {\n              \"type\": \"solid\",\n              \"width\": 3,\n              \"color\": null\n            }\n          },\n          {\n            \"type\": \"line\",\n            \"label\": {\n              \"show\": true,\n              \"position\": \"top\",\n              \"color\": \"#fff\",\n              \"fontSize\": 12\n            },\n            \"symbolSize\": 5,\n            \"itemStyle\": {\n              \"color\": null,\n              \"borderRadius\": 0\n            },\n            \"lineStyle\": {\n              \"type\": \"solid\",\n              \"width\": 3,\n              \"color\": null\n            }\n          }\n        ],\n        \"backgroundColor\": \"rgba(0,0,0,0)\"\n      }\n    }\n  ],\n  \"requestGlobalConfig\": {\n    \"requestDataPond\": [],\n    \"requestOriginUrl\": \"\",\n    \"requestInterval\": 30,\n    \"requestIntervalUnit\": \"second\",\n    \"requestParams\": {\n      \"Body\": {\n        \"form-data\": {},\n        \"x-www-form-urlencoded\": {},\n        \"json\": \"\",\n        \"xml\": \"\"\n      },\n      \"Header\": {},\n      \"Params\": {}\n    }\n  }\n}', 0, NULL, '1', '2023-02-07 11:43:57', '1', '2023-02-07 17:27:40', b'0', 1), (8, '57q2gor533g000', NULL, NULL, 1, NULL, '1', '2023-02-07 19:27:09', '1', '2023-02-07 19:27:09', b'0', 1);
+COMMIT;
+
+SET FOREIGN_KEY_CHECKS = 1;
diff --git a/yudao-framework/yudao-common/src/main/java/cn/iocoder/yudao/framework/common/exception/enums/ServiceErrorCodeRange.java b/yudao-framework/yudao-common/src/main/java/cn/iocoder/yudao/framework/common/exception/enums/ServiceErrorCodeRange.java
index e3cfc453f..c3e504a7c 100644
--- a/yudao-framework/yudao-common/src/main/java/cn/iocoder/yudao/framework/common/exception/enums/ServiceErrorCodeRange.java
+++ b/yudao-framework/yudao-common/src/main/java/cn/iocoder/yudao/framework/common/exception/enums/ServiceErrorCodeRange.java
@@ -31,6 +31,7 @@ public class ServiceErrorCodeRange {
 
     // 模块 infra 错误码区间 [1-001-000-000 ~ 1-002-000-000)
     // 模块 system 错误码区间 [1-002-000-000 ~ 1-003-000-000)
+    // 模块 report 错误码区间 [1-003-000-000 ~ 1-004-000-000)
     // 模块 member 错误码区间 [1-004-000-000 ~ 1-005-000-000)
     // 模块 pay 错误码区间 [1-007-000-000 ~ 1-008-000-000)
     // 模块 bpm 错误码区间 [1-009-000-000 ~ 1-010-000-000)
diff --git a/yudao-framework/yudao-spring-boot-starter-banner/src/main/java/cn/iocoder/yudao/framework/banner/core/BannerApplicationRunner.java b/yudao-framework/yudao-spring-boot-starter-banner/src/main/java/cn/iocoder/yudao/framework/banner/core/BannerApplicationRunner.java
index c01d419f4..9809cdc27 100644
--- a/yudao-framework/yudao-spring-boot-starter-banner/src/main/java/cn/iocoder/yudao/framework/banner/core/BannerApplicationRunner.java
+++ b/yudao-framework/yudao-spring-boot-starter-banner/src/main/java/cn/iocoder/yudao/framework/banner/core/BannerApplicationRunner.java
@@ -33,8 +33,8 @@ public class BannerApplicationRunner implements ApplicationRunner {
                     "https://t.zsxq.com/02B6ujIee");
 
             // 数据报表
-            if (isNotPresent("cn.iocoder.yudao.module.visualization.framework.security.config.SecurityConfiguration")) {
-                System.out.println("[报表模块 yudao-module-visualization - 已禁用][参考 https://doc.iocoder.cn/report/ 开启]");
+            if (isNotPresent("cn.iocoder.yudao.module.report.framework.security.config.SecurityConfiguration")) {
+                System.out.println("[报表模块 yudao-module-report - 已禁用][参考 https://doc.iocoder.cn/report/ 开启]");
             }
             // 工作流
             if (isNotPresent("cn.iocoder.yudao.framework.flowable.config.YudaoFlowableConfiguration")) {
@@ -44,9 +44,9 @@ public class BannerApplicationRunner implements ApplicationRunner {
             if (isNotPresent("cn.iocoder.yudao.module.mp.framework.mp.config.MpConfiguration")) {
                 System.out.println("[微信公众号 yudao-module-mp - 已禁用][参考 https://doc.iocoder.cn/mp/build/ 开启]");
             }
-            // 微信公众号
+            // 商城
             if (isNotPresent("cn.iocoder.yudao.module.trade.framework.web.config.TradeWebConfiguration")) {
-                System.out.println("[商城 yudao-module-mall - 已禁用][参考 https://doc.iocoder.cn/mall/build/ 开启]");
+                System.out.println("[商城系统 yudao-module-mall - 已禁用][参考 https://doc.iocoder.cn/mall/build/ 开启]");
             }
         });
     }
diff --git a/yudao-module-bpm/yudao-module-bpm-biz/src/test/java/cn/iocoder/yudao/module/bpm/service/definition/BpmTaskAssignRuleServiceImplTest.java b/yudao-module-bpm/yudao-module-bpm-biz/src/test/java/cn/iocoder/yudao/module/bpm/service/definition/BpmTaskAssignRuleServiceImplTest.java
index 7c1eb0f84..a00bbbf86 100644
--- a/yudao-module-bpm/yudao-module-bpm-biz/src/test/java/cn/iocoder/yudao/module/bpm/service/definition/BpmTaskAssignRuleServiceImplTest.java
+++ b/yudao-module-bpm/yudao-module-bpm-biz/src/test/java/cn/iocoder/yudao/module/bpm/service/definition/BpmTaskAssignRuleServiceImplTest.java
@@ -103,7 +103,7 @@ public class BpmTaskAssignRuleServiceImplTest extends BaseDbUnitTest {
         // mock 方法
         DeptRespDTO dept1 = randomPojo(DeptRespDTO.class, o -> o.setLeaderUserId(11L));
         DeptRespDTO dept2 = randomPojo(DeptRespDTO.class, o -> o.setLeaderUserId(22L));
-        when(deptApi.getDepts(eq(rule.getOptions()))).thenReturn(Arrays.asList(dept1, dept2));
+        when(deptApi.getDeptList(eq(rule.getOptions()))).thenReturn(Arrays.asList(dept1, dept2));
         mockGetUserMap(asSet(11L, 22L));
 
         // 调用
diff --git a/yudao-module-visualization/pom.xml b/yudao-module-report/pom.xml
similarity index 69%
rename from yudao-module-visualization/pom.xml
rename to yudao-module-report/pom.xml
index 63c2c6f4a..fadb0740b 100644
--- a/yudao-module-visualization/pom.xml
+++ b/yudao-module-report/pom.xml
@@ -9,15 +9,15 @@
     </parent>
     <modelVersion>4.0.0</modelVersion>
     <modules>
-        <module>yudao-module-visualization-api</module>
-        <module>yudao-module-visualization-biz</module>
+        <module>yudao-module-report-api</module>
+        <module>yudao-module-report-biz</module>
     </modules>
-    <artifactId>yudao-module-visualization</artifactId>
+    <artifactId>yudao-module-report</artifactId>
     <packaging>pom</packaging>
 
     <name>${project.artifactId}</name>
     <description>
-        visualization 模块,主要实现数据可视化报表等功能。
+        report 模块,主要实现数据可视化报表等功能。
     </description>
 
-</project>
\ No newline at end of file
+</project>
diff --git a/yudao-module-visualization/yudao-module-visualization-api/pom.xml b/yudao-module-report/yudao-module-report-api/pom.xml
similarity index 78%
rename from yudao-module-visualization/yudao-module-visualization-api/pom.xml
rename to yudao-module-report/yudao-module-report-api/pom.xml
index 0b5217d1b..3effa4323 100644
--- a/yudao-module-visualization/yudao-module-visualization-api/pom.xml
+++ b/yudao-module-report/yudao-module-report-api/pom.xml
@@ -4,17 +4,17 @@
          xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
     <parent>
         <groupId>cn.iocoder.boot</groupId>
-        <artifactId>yudao-module-visualization</artifactId>
+        <artifactId>yudao-module-report</artifactId>
         <version>${revision}</version>
     </parent>
     <modelVersion>4.0.0</modelVersion>
 
-    <artifactId>yudao-module-visualization-api</artifactId>
+    <artifactId>yudao-module-report-api</artifactId>
     <packaging>jar</packaging>
 
     <name>${project.artifactId}</name>
     <description>
-        visualization 模块 API,暴露给其它模块调用
+        report 模块 API,暴露给其它模块调用
     </description>
 
     <dependencies>
@@ -23,4 +23,4 @@
             <artifactId>yudao-common</artifactId>
         </dependency>
     </dependencies>
-</project>
\ No newline at end of file
+</project>
diff --git a/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/api/package-info.java b/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/api/package-info.java
new file mode 100644
index 000000000..827bef3fd
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/api/package-info.java
@@ -0,0 +1,4 @@
+/**
+ * 占位,避免 api 目录无文件时,git 无法提交
+ */
+package cn.iocoder.yudao.module.report.api;
diff --git a/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/enums/ErrorCodeConstants.java b/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/enums/ErrorCodeConstants.java
new file mode 100644
index 000000000..d90bed398
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/enums/ErrorCodeConstants.java
@@ -0,0 +1,15 @@
+package cn.iocoder.yudao.module.report.enums;
+
+import cn.iocoder.yudao.framework.common.exception.ErrorCode;
+
+/**
+ * Report 错误码枚举类
+ *
+ * system 系统,使用 1-003-000-000 段
+ */
+public interface ErrorCodeConstants {
+
+    // ========== AUTH 模块 1003000000 ==========
+    ErrorCode GO_VIEW_PROJECT_NOT_EXISTS = new ErrorCode(1003000000, "GoView 项目不存在");
+
+}
diff --git a/yudao-module-visualization/yudao-module-visualization-biz/pom.xml b/yudao-module-report/yudao-module-report-biz/pom.xml
similarity index 90%
rename from yudao-module-visualization/yudao-module-visualization-biz/pom.xml
rename to yudao-module-report/yudao-module-report-biz/pom.xml
index a2e4818de..9308fc386 100644
--- a/yudao-module-visualization/yudao-module-visualization-biz/pom.xml
+++ b/yudao-module-report/yudao-module-report-biz/pom.xml
@@ -4,23 +4,23 @@
          xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
     <parent>
         <groupId>cn.iocoder.boot</groupId>
-        <artifactId>yudao-module-visualization</artifactId>
+        <artifactId>yudao-module-report</artifactId>
         <version>${revision}</version>
     </parent>
     <modelVersion>4.0.0</modelVersion>
 
-    <artifactId>yudao-module-visualization-biz</artifactId>
+    <artifactId>yudao-module-report-biz</artifactId>
     <packaging>jar</packaging>
 
     <name>${project.artifactId}</name>
     <description>
-        visualization 模块,主要实现数据可视化报表等功能:
+        report 模块,主要实现数据可视化报表等功能:
         1. 基于「积木报表」实现,打印设计、报表设计、图形设计、大屏设计等。
     </description>
     <dependencies>
         <dependency>
             <groupId>cn.iocoder.boot</groupId>
-            <artifactId>yudao-module-visualization-api</artifactId>
+            <artifactId>yudao-module-report-api</artifactId>
             <version>${revision}</version>
         </dependency>
 
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/ajreport/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/ajreport/package-info.java
new file mode 100644
index 000000000..e32b8b916
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/ajreport/package-info.java
@@ -0,0 +1 @@
+package cn.iocoder.yudao.module.report.controller.admin.ajreport;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewDataController.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewDataController.java
new file mode 100644
index 000000000..ee0b69225
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewDataController.java
@@ -0,0 +1,66 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview;
+
+import cn.hutool.core.map.MapUtil;
+import cn.hutool.core.util.RandomUtil;
+import cn.iocoder.yudao.framework.common.pojo.CommonResult;
+import cn.iocoder.yudao.framework.operatelog.core.annotations.OperateLog;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.data.GoViewDataGetBySqlReqVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.data.GoViewDataRespVO;
+import cn.iocoder.yudao.module.report.service.goview.GoViewDataService;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestParam;
+import org.springframework.web.bind.annotation.RestController;
+
+import javax.annotation.Resource;
+import javax.validation.Valid;
+
+import java.util.*;
+
+import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
+
+@Tag(name = "管理后台 - GoView 数据", description = "提供 SQL、HTTP 等数据查询的能力")
+@RestController
+@RequestMapping("/report/go-view/data")
+@Validated
+public class GoViewDataController {
+
+    @Resource
+    private GoViewDataService goViewDataService;
+
+    @RequestMapping("/get-by-sql")
+    @Operation(summary = "使用 SQL 查询数据")
+    @PreAuthorize("@ss.hasPermission('report:go-view-data:get-by-sql')")
+    @OperateLog(enable = false) // 不记录操作日志,因为不需要
+    public CommonResult<GoViewDataRespVO> getDataBySQL(@Valid @RequestBody GoViewDataGetBySqlReqVO reqVO) {
+        return success(goViewDataService.getDataBySQL(reqVO.getSql()));
+    }
+
+    @RequestMapping("/get-by-http")
+    @Operation(summary = "使用 HTTP 查询数据", description = "这个只是示例接口,实际应该每个查询,都要写一个接口")
+    @PreAuthorize("@ss.hasPermission('report:go-view-data:get-by-http')")
+    @OperateLog(enable = false) // 不记录操作日志,因为不需要
+    public CommonResult<GoViewDataRespVO> getDataByHttp(
+            @RequestParam(required = false) Map<String, String> params,
+            @RequestBody(required = false) String body) { // params、body 按照需要去接收,这里仅仅是示例
+        GoViewDataRespVO respVO = new GoViewDataRespVO();
+        // 1. 数据维度
+        respVO.setDimensions(Arrays.asList("日期", "PV", "UV")); // PV 是每天访问次数;UV 是每天访问人数
+        // 2. 明细数据列表
+        // 目前通过随机的方式生成。一般来说,这里你可以写逻辑来实现数据的返回
+        respVO.setSource(new LinkedList<>());
+        for (int i = 1; i <= 12; i++) {
+            String date = "2021-" + (i < 10 ? "0" + i : i);
+            Integer pv = RandomUtil.randomInt(1000, 10000);
+            Integer uv = RandomUtil.randomInt(100, 1000);
+            respVO.getSource().add(MapUtil.<String, Object>builder().put("日期", date)
+                    .put("PV", pv).put("UV", uv).build());
+        }
+        return success(respVO);
+    }
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewProjectController.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewProjectController.java
new file mode 100644
index 000000000..8cc5f7e1f
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewProjectController.java
@@ -0,0 +1,77 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview;
+
+import cn.iocoder.yudao.framework.common.pojo.CommonResult;
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectCreateReqVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectRespVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectUpdateReqVO;
+import cn.iocoder.yudao.module.report.convert.goview.GoViewProjectConvert;
+import cn.iocoder.yudao.module.report.dal.dataobject.goview.GoViewProjectDO;
+import cn.iocoder.yudao.module.report.service.goview.GoViewProjectService;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import org.springframework.jdbc.core.JdbcTemplate;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.validation.Valid;
+
+import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
+import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId;
+
+@Tag(name = "管理后台 - GoView 项目")
+@RestController
+@RequestMapping("/report/go-view/project")
+@Validated
+public class GoViewProjectController {
+
+    @Resource
+    private GoViewProjectService goViewProjectService;
+
+    @PostMapping("/create")
+    @Operation(summary = "创建项目")
+    @PreAuthorize("@ss.hasPermission('report:go-view-project:create')")
+    public CommonResult<Long> createProject(@Valid @RequestBody GoViewProjectCreateReqVO createReqVO) {
+        return success(goViewProjectService.createProject(createReqVO));
+    }
+
+    @PutMapping("/update")
+    @Operation(summary = "更新项目")
+    @PreAuthorize("@ss.hasPermission('report:go-view-project:update')")
+    public CommonResult<Boolean> updateProject(@Valid @RequestBody GoViewProjectUpdateReqVO updateReqVO) {
+        goViewProjectService.updateProject(updateReqVO);
+        return success(true);
+    }
+
+    @DeleteMapping("/delete")
+    @Operation(summary = "删除 GoView 项目")
+    @Parameter(name = "id", description = "编号", required = true, example = "1024")
+    @PreAuthorize("@ss.hasPermission('report:go-view-project:delete')")
+    public CommonResult<Boolean> deleteProject(@RequestParam("id") Long id) {
+        goViewProjectService.deleteProject(id);
+        return success(true);
+    }
+
+    @GetMapping("/get")
+    @Operation(summary = "获得项目")
+    @Parameter(name = "id", description = "编号", required = true, example = "1024")
+    @PreAuthorize("@ss.hasPermission('report:go-view-project:query')")
+    public CommonResult<GoViewProjectRespVO> getProject(@RequestParam("id") Long id) {
+        GoViewProjectDO project = goViewProjectService.getProject(id);
+        return success(GoViewProjectConvert.INSTANCE.convert(project));
+    }
+
+    @GetMapping("/my-page")
+    @Operation(summary = "获得我的项目分页")
+    @PreAuthorize("@ss.hasPermission('report:go-view-project:query')")
+    public CommonResult<PageResult<GoViewProjectRespVO>> getMyProjectPage(@Valid PageParam pageVO) {
+        PageResult<GoViewProjectDO> pageResult = goViewProjectService.getMyProjectPage(
+                pageVO, getLoginUserId());
+        return success(GoViewProjectConvert.INSTANCE.convertPage(pageResult));
+    }
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataGetBySqlReqVO.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataGetBySqlReqVO.java
new file mode 100644
index 000000000..598d7539f
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataGetBySqlReqVO.java
@@ -0,0 +1,16 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview.vo.data;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import javax.validation.constraints.NotEmpty;
+
+@Schema(description = "管理后台 - GoView 使用 SQL 查询数据 Request VO")
+@Data
+public class GoViewDataGetBySqlReqVO {
+
+    @Schema(description = "SQL 语句", required = true, example = "SELECT * FROM user")
+    @NotEmpty(message = "SQL 语句不能为空")
+    private String sql;
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataRespVO.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataRespVO.java
new file mode 100644
index 000000000..0d7b86138
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataRespVO.java
@@ -0,0 +1,19 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview.vo.data;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import java.util.List;
+import java.util.Map;
+
+@Schema(description = "管理后台 - GoView 数据 Response VO")
+@Data
+public class GoViewDataRespVO {
+
+    @Schema(description = "数据维度", required = true, example = "['product', 'data1', 'data2']")
+    private List<String> dimensions;
+
+    @Schema(description = "数据明细列表", required = true)
+    private List<Map<String, Object>> source;
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/project/GoViewProjectCreateReqVO.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/project/GoViewProjectCreateReqVO.java
new file mode 100644
index 000000000..ac5c21019
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/project/GoViewProjectCreateReqVO.java
@@ -0,0 +1,15 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview.vo.project;
+
+import lombok.*;
+import io.swagger.v3.oas.annotations.media.Schema;
+import javax.validation.constraints.*;
+
+@Schema(description = "管理后台 - GoView 项目创建 Request VO")
+@Data
+public class GoViewProjectCreateReqVO {
+
+    @Schema(description = "项目名称", required = true, example = "王五")
+    @NotEmpty(message = "项目名称不能为空")
+    private String name;
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/project/GoViewProjectRespVO.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/project/GoViewProjectRespVO.java
new file mode 100644
index 000000000..8c1be5844
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/project/GoViewProjectRespVO.java
@@ -0,0 +1,36 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview.vo.project;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.*;
+
+import java.time.LocalDateTime;
+
+@Schema(description = "管理后台 - GoView 项目 Response VO")
+@Data
+public class GoViewProjectRespVO {
+
+    @Schema(description = "编号", required = true, example = "18993")
+    private Long id;
+
+    @Schema(description = "项目名称", required = true, example = "王五")
+    private String name;
+
+    @Schema(description = "发布状态", required = true, example = "1")
+    private Integer status;
+
+    @Schema(description = "报表内容") // JSON 格式
+    private String content;
+
+    @Schema(description = "预览图片 URL", example = "https://www.iocoder.cn")
+    private String picUrl;
+
+    @Schema(description = "项目备注", example = "你猜")
+    private String remark;
+
+    @Schema(description = "创建人编号", required = true, example = "1024")
+    private String creator;
+
+    @Schema(description = "创建时间", required = true)
+    private LocalDateTime createTime;
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/project/GoViewProjectUpdateReqVO.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/project/GoViewProjectUpdateReqVO.java
new file mode 100644
index 000000000..d8bda04f0
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/project/GoViewProjectUpdateReqVO.java
@@ -0,0 +1,34 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview.vo.project;
+
+import cn.iocoder.yudao.framework.common.enums.CommonStatusEnum;
+import cn.iocoder.yudao.framework.common.validation.InEnum;
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.*;
+
+import javax.validation.constraints.*;
+
+@Schema(description = "管理后台 - GoView 项目更新 Request VO")
+@Data
+public class GoViewProjectUpdateReqVO {
+
+    @Schema(description = "编号", required = true, example = "18993")
+    @NotNull(message = "编号不能为空")
+    private Long id;
+
+    @Schema(description = "项目名称", required = true, example = "王五")
+    private String name;
+
+    @Schema(description = "发布状态", required = true, example = "1")
+    @InEnum(value = CommonStatusEnum.class, message = "发布状态必须是 {value}")
+    private Integer status;
+
+    @Schema(description = "报表内容") // JSON 格式
+    private String content;
+
+    @Schema(description = "预览图片 URL", example = "https://www.iocoder.cn")
+    private String picUrl;
+
+    @Schema(description = "项目备注", example = "你猜")
+    private String remark;
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/package-info.java
new file mode 100644
index 000000000..ccbf9bb19
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/package-info.java
@@ -0,0 +1,6 @@
+/**
+ * 提供 RESTful API 给前端:
+ * 1. admin 包:提供给管理后台 yudao-ui-admin 前端项目
+ * 2. app 包:提供给用户 APP yudao-ui-app 前端项目,它的 Controller 和 VO 都要添加 App 前缀,用于和管理后台进行区分
+ */
+package cn.iocoder.yudao.module.report.controller;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/convert/ajreport/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/convert/ajreport/package-info.java
new file mode 100644
index 000000000..72860791f
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/convert/ajreport/package-info.java
@@ -0,0 +1,4 @@
+/**
+ * TODO 占位,后续删除
+ */
+package cn.iocoder.yudao.module.report.convert.ajreport;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/convert/goview/GoViewProjectConvert.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/convert/goview/GoViewProjectConvert.java
new file mode 100644
index 000000000..9c993a19c
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/convert/goview/GoViewProjectConvert.java
@@ -0,0 +1,24 @@
+package cn.iocoder.yudao.module.report.convert.goview;
+
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectCreateReqVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectRespVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectUpdateReqVO;
+import cn.iocoder.yudao.module.report.dal.dataobject.goview.GoViewProjectDO;
+import org.mapstruct.Mapper;
+import org.mapstruct.factory.Mappers;
+
+@Mapper
+public interface GoViewProjectConvert {
+
+    GoViewProjectConvert INSTANCE = Mappers.getMapper(GoViewProjectConvert.class);
+
+    GoViewProjectDO convert(GoViewProjectCreateReqVO bean);
+
+    GoViewProjectDO convert(GoViewProjectUpdateReqVO bean);
+
+    GoViewProjectRespVO convert(GoViewProjectDO bean);
+
+    PageResult<GoViewProjectRespVO> convertPage(PageResult<GoViewProjectDO> page);
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/dataobject/ajreport/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/dataobject/ajreport/package-info.java
new file mode 100644
index 000000000..922ec6fd4
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/dataobject/ajreport/package-info.java
@@ -0,0 +1,4 @@
+/**
+ * TODO 芋艿:占位,待删除
+ */
+package cn.iocoder.yudao.module.report.dal.dataobject.ajreport;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/dataobject/goview/GoViewProjectDO.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/dataobject/goview/GoViewProjectDO.java
new file mode 100644
index 000000000..38730d29e
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/dataobject/goview/GoViewProjectDO.java
@@ -0,0 +1,57 @@
+package cn.iocoder.yudao.module.report.dal.dataobject.goview;
+
+import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
+import com.baomidou.mybatisplus.annotation.KeySequence;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.*;
+
+/**
+ * GoView 项目表
+ *
+ * 每个大屏图标,对应一个项目
+ *
+ * @author 芋道源码
+ */
+@TableName(value = "report_go_view_project", autoResultMap = true) // 由于 SQL Server 的 system_user 是关键字,所以使用 system_users
+@KeySequence("report_go_view_project_seq") // 用于 Oracle、PostgreSQL、Kingbase、DB2、H2 数据库的主键自增。如果是 MySQL 等数据库,可不写。
+@Data
+@EqualsAndHashCode(callSuper = true)
+@Builder
+@NoArgsConstructor
+@AllArgsConstructor
+public class GoViewProjectDO extends BaseDO {
+
+    /**
+     * 编号,数据库自增
+     */
+    @TableId
+    private Long id;
+    /**
+     * 项目名称
+     */
+    private String name;
+    /**
+     * 预览图片 URL
+     */
+    private String picUrl;
+    /**
+     * 报表内容
+     *
+     * JSON 配置,使用字符串存储
+     */
+    private String content;
+    /**
+     * 发布状态
+     *
+     * 0 - 已发布
+     * 1 - 未发布
+     *
+     * 枚举 {@link cn.iocoder.yudao.framework.common.enums.CommonStatusEnum}
+     */
+    private Integer status;
+    /**
+     * 项目备注
+     */
+    private String remark;
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/mysql/ajreport/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/mysql/ajreport/package-info.java
new file mode 100644
index 000000000..0fb86173d
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/mysql/ajreport/package-info.java
@@ -0,0 +1,4 @@
+/**
+ * TODO 芋艿:占位,待删除
+ */
+package cn.iocoder.yudao.module.report.dal.mysql.ajreport;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/mysql/goview/GoViewProjectMapper.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/mysql/goview/GoViewProjectMapper.java
new file mode 100644
index 000000000..af1ca6345
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/dal/mysql/goview/GoViewProjectMapper.java
@@ -0,0 +1,19 @@
+package cn.iocoder.yudao.module.report.dal.mysql.goview;
+
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX;
+import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
+import cn.iocoder.yudao.module.report.dal.dataobject.goview.GoViewProjectDO;
+import org.apache.ibatis.annotations.Mapper;
+
+@Mapper
+public interface GoViewProjectMapper extends BaseMapperX<GoViewProjectDO> {
+
+    default PageResult<GoViewProjectDO> selectPage(PageParam reqVO, Long userId) {
+        return selectPage(reqVO, new LambdaQueryWrapperX<GoViewProjectDO>()
+                .eq(GoViewProjectDO::getCreator, userId)
+                .orderByDesc(GoViewProjectDO::getId));
+    }
+
+}
diff --git a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/jmreport/config/JmReportConfiguration.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/jmreport/config/JmReportConfiguration.java
similarity index 83%
rename from yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/jmreport/config/JmReportConfiguration.java
rename to yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/jmreport/config/JmReportConfiguration.java
index c679d1112..3c99b2858 100644
--- a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/jmreport/config/JmReportConfiguration.java
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/jmreport/config/JmReportConfiguration.java
@@ -1,8 +1,8 @@
-package cn.iocoder.yudao.module.visualization.framework.jmreport.config;
+package cn.iocoder.yudao.module.report.framework.jmreport.config;
 
 import cn.iocoder.yudao.framework.security.config.SecurityProperties;
 import cn.iocoder.yudao.module.system.api.oauth2.OAuth2TokenApi;
-import cn.iocoder.yudao.module.visualization.framework.jmreport.core.service.JmReportTokenServiceImpl;
+import cn.iocoder.yudao.module.report.framework.jmreport.core.service.JmReportTokenServiceImpl;
 import org.jeecg.modules.jmreport.api.JmReportTokenServiceI;
 import org.springframework.context.annotation.Bean;
 import org.springframework.context.annotation.ComponentScan;
diff --git a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/jmreport/core/service/JmReportTokenServiceImpl.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/jmreport/core/service/JmReportTokenServiceImpl.java
similarity index 98%
rename from yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/jmreport/core/service/JmReportTokenServiceImpl.java
rename to yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/jmreport/core/service/JmReportTokenServiceImpl.java
index 22c4a19c8..e2c272d2c 100644
--- a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/jmreport/core/service/JmReportTokenServiceImpl.java
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/jmreport/core/service/JmReportTokenServiceImpl.java
@@ -1,4 +1,4 @@
-package cn.iocoder.yudao.module.visualization.framework.jmreport.core.service;
+package cn.iocoder.yudao.module.report.framework.jmreport.core.service;
 
 import cn.hutool.core.util.ObjectUtil;
 import cn.hutool.core.util.StrUtil;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/jmreport/core/web/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/jmreport/core/web/package-info.java
new file mode 100644
index 000000000..e082e3bdc
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/jmreport/core/web/package-info.java
@@ -0,0 +1,4 @@
+/**
+ * 占位,后续会基于 Filter 实现积木报表的认证等功能,替代 {@link cn.iocoder.yudao.module.report.framework.jmreport.core.service.JmReportTokenServiceImpl}
+ */
+package cn.iocoder.yudao.module.report.framework.jmreport.core.web;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/package-info.java
new file mode 100644
index 000000000..c2163d8cd
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/package-info.java
@@ -0,0 +1,6 @@
+/**
+ * 属于 report 模块的 framework 封装
+ *
+ * @author 芋道源码
+ */
+package cn.iocoder.yudao.module.report.framework;
diff --git a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/security/config/SecurityConfiguration.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/security/config/SecurityConfiguration.java
similarity index 78%
rename from yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/security/config/SecurityConfiguration.java
rename to yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/security/config/SecurityConfiguration.java
index 7e1567dff..5b73cd274 100644
--- a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/security/config/SecurityConfiguration.java
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/security/config/SecurityConfiguration.java
@@ -1,4 +1,4 @@
-package cn.iocoder.yudao.module.visualization.framework.security.config;
+package cn.iocoder.yudao.module.report.framework.security.config;
 
 import cn.iocoder.yudao.framework.security.config.AuthorizeRequestsCustomizer;
 import org.springframework.context.annotation.Bean;
@@ -7,12 +7,12 @@ import org.springframework.security.config.annotation.web.builders.HttpSecurity;
 import org.springframework.security.config.annotation.web.configurers.ExpressionUrlAuthorizationConfigurer;
 
 /**
- * Visualization 模块的 Security 配置
+ * Report 模块的 Security 配置
  */
-@Configuration("visualizationSecurityConfiguration")
+@Configuration("reportSecurityConfiguration")
 public class SecurityConfiguration {
 
-    @Bean("visualizationAuthorizeRequestsCustomizer")
+    @Bean("reportAuthorizeRequestsCustomizer")
     public AuthorizeRequestsCustomizer authorizeRequestsCustomizer() {
         return new AuthorizeRequestsCustomizer() {
 
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/security/core/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/security/core/package-info.java
new file mode 100644
index 000000000..61083268f
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/security/core/package-info.java
@@ -0,0 +1,4 @@
+/**
+ * 占位
+ */
+package cn.iocoder.yudao.module.report.framework.security.core;
diff --git a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/ureport/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/ureport/package-info.java
similarity index 79%
rename from yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/ureport/package-info.java
rename to yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/ureport/package-info.java
index 1d825674b..a4e2e8bf1 100644
--- a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/ureport/package-info.java
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/framework/ureport/package-info.java
@@ -4,4 +4,4 @@
  * ureport2 和 jimurepot 是相同类型的产品,不过停更了,最好发布时间是 2018 年。
  * 它们之间的功能对比,可见 https://juejin.cn/post/6939836480269320200 地址
  */
-package cn.iocoder.yudao.module.visualization.framework.ureport;
+package cn.iocoder.yudao.module.report.framework.ureport;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/package-info.java
new file mode 100644
index 000000000..3306c0ebb
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/package-info.java
@@ -0,0 +1,9 @@
+/**
+ * report 模块,主要实现数据可视化报表等功能:
+ * 1. 基于「积木报表」实现,打印设计、报表设计、图形设计、大屏设计等。URL 前缀是 /jmreport,表名前缀是 jimu_
+ *
+ * 由于「积木报表」的大屏设计器需要收费,后续会自研,对应的是:
+ * 1. Controller URL:以 /report/ 开头,避免和其它 Module 冲突
+ * 2. DataObject 表名:以 report_ 开头,方便在数据库中区分
+ */
+package cn.iocoder.yudao.module.report;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/ajreport/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/ajreport/package-info.java
new file mode 100644
index 000000000..2512e50ed
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/ajreport/package-info.java
@@ -0,0 +1,4 @@
+/**
+ * TODO 芋艿:占位,待删除
+ */
+package cn.iocoder.yudao.module.report.service.ajreport;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewDataService.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewDataService.java
new file mode 100644
index 000000000..b912373b1
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewDataService.java
@@ -0,0 +1,20 @@
+package cn.iocoder.yudao.module.report.service.goview;
+
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.data.GoViewDataRespVO;
+
+/**
+ * GoView 数据 Service 接口
+ *
+ * @author 芋道源码
+ */
+public interface GoViewDataService {
+
+    /**
+     * 使用 SQL 查询数据
+     *
+     * @param sql SQL 语句
+     * @return 数据
+     */
+    GoViewDataRespVO getDataBySQL(String sql);
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewDataServiceImpl.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewDataServiceImpl.java
new file mode 100644
index 000000000..8938d3e74
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewDataServiceImpl.java
@@ -0,0 +1,55 @@
+package cn.iocoder.yudao.module.report.service.goview;
+
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.data.GoViewDataRespVO;
+import com.google.common.collect.Maps;
+import org.springframework.jdbc.core.JdbcTemplate;
+import org.springframework.jdbc.support.rowset.SqlRowSet;
+import org.springframework.jdbc.support.rowset.SqlRowSetMetaData;
+import org.springframework.stereotype.Service;
+import org.springframework.validation.annotation.Validated;
+
+import javax.annotation.Resource;
+import java.util.Arrays;
+import java.util.LinkedList;
+import java.util.Map;
+
+/**
+ * GoView 数据 Service 实现类
+ *
+ * 补充说明:
+ * 1. 目前默认使用 jdbcTemplate 查询项目配置的数据源。如果你想查询其它数据源,可以新建对应数据源的 jdbcTemplate 来实现。
+ * 2. 默认数据源是 MySQL 关系数据源,可能数据量比较大的情况下,会比较慢,可以考虑后续使用 Click House 等等。
+ *
+ * @author 芋道源码
+ */
+@Service
+@Validated
+public class GoViewDataServiceImpl implements GoViewDataService {
+
+    @Resource
+    private JdbcTemplate jdbcTemplate;
+
+    @Override
+    public GoViewDataRespVO getDataBySQL(String sql) {
+        // 1. 执行查询
+        SqlRowSet sqlRowSet = jdbcTemplate.queryForRowSet(sql);
+
+        // 2. 构建返回结果
+        GoViewDataRespVO respVO = new GoViewDataRespVO();
+        // 2.1 解析元数据
+        SqlRowSetMetaData metaData = sqlRowSet.getMetaData();
+        String[] columnNames = metaData.getColumnNames();
+        respVO.setDimensions(Arrays.asList(columnNames));
+        // 2.2 解析数据明细
+        respVO.setSource(new LinkedList<>()); // 由于数据量不确认,使用 LinkedList 虽然内存占用大一点,但是不存在扩容复制的问题
+        while (sqlRowSet.next()) {
+            Map<String, Object> data = Maps.newHashMapWithExpectedSize(columnNames.length);
+            for (String columnName : columnNames) {
+                data.put(columnName, sqlRowSet.getObject(columnName));
+            }
+            respVO.getSource().add(data);
+        }
+        return respVO;
+    }
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewProjectService.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewProjectService.java
new file mode 100644
index 000000000..b171c5905
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewProjectService.java
@@ -0,0 +1,57 @@
+package cn.iocoder.yudao.module.report.service.goview;
+
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectCreateReqVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectUpdateReqVO;
+import cn.iocoder.yudao.module.report.dal.dataobject.goview.GoViewProjectDO;
+
+import javax.validation.Valid;
+
+/**
+ * GoView 项目 Service 接口
+ *
+ * @author 芋道源码
+ */
+public interface GoViewProjectService {
+
+    /**
+     * 创建项目
+     *
+     * @param createReqVO 创建信息
+     * @return 编号
+     */
+    Long createProject(@Valid GoViewProjectCreateReqVO createReqVO);
+
+    /**
+     * 更新项目
+     *
+     * @param updateReqVO 更新信息
+     */
+    void updateProject(@Valid GoViewProjectUpdateReqVO updateReqVO);
+
+    /**
+     * 删除项目
+     *
+     * @param id 编号
+     */
+    void deleteProject(Long id);
+
+    /**
+     * 获得项目
+     *
+     * @param id 编号
+     * @return 项目
+     */
+    GoViewProjectDO getProject(Long id);
+
+    /**
+     * 获得我的项目分页
+     *
+     * @param pageReqVO 分页查询
+     * @param userId 用户编号
+     * @return GoView 项目分页
+     */
+    PageResult<GoViewProjectDO> getMyProjectPage(PageParam pageReqVO, Long userId);
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewProjectServiceImpl.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewProjectServiceImpl.java
new file mode 100644
index 000000000..2b05052f7
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/service/goview/GoViewProjectServiceImpl.java
@@ -0,0 +1,74 @@
+package cn.iocoder.yudao.module.report.service.goview;
+
+import cn.iocoder.yudao.framework.common.enums.CommonStatusEnum;
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectCreateReqVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectUpdateReqVO;
+import cn.iocoder.yudao.module.report.convert.goview.GoViewProjectConvert;
+import cn.iocoder.yudao.module.report.dal.dataobject.goview.GoViewProjectDO;
+import cn.iocoder.yudao.module.report.dal.mysql.goview.GoViewProjectMapper;
+import org.springframework.stereotype.Service;
+import org.springframework.validation.annotation.Validated;
+
+import javax.annotation.Resource;
+
+import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
+import static cn.iocoder.yudao.module.report.enums.ErrorCodeConstants.GO_VIEW_PROJECT_NOT_EXISTS;
+
+/**
+ * GoView 项目 Service 实现类
+ *
+ * @author 芋道源码
+ */
+@Service
+@Validated
+public class GoViewProjectServiceImpl implements GoViewProjectService {
+
+    @Resource
+    private GoViewProjectMapper goViewProjectMapper;
+
+    @Override
+    public Long createProject(GoViewProjectCreateReqVO createReqVO) {
+        // 插入
+        GoViewProjectDO goViewProject = GoViewProjectConvert.INSTANCE.convert(createReqVO)
+                .setStatus(CommonStatusEnum.DISABLE.getStatus());
+        goViewProjectMapper.insert(goViewProject);
+        // 返回
+        return goViewProject.getId();
+    }
+
+    @Override
+    public void updateProject(GoViewProjectUpdateReqVO updateReqVO) {
+        // 校验存在
+        validateProjectExists(updateReqVO.getId());
+        // 更新
+        GoViewProjectDO updateObj = GoViewProjectConvert.INSTANCE.convert(updateReqVO);
+        goViewProjectMapper.updateById(updateObj);
+    }
+
+    @Override
+    public void deleteProject(Long id) {
+        // 校验存在
+        validateProjectExists(id);
+        // 删除
+        goViewProjectMapper.deleteById(id);
+    }
+
+    private void validateProjectExists(Long id) {
+        if (goViewProjectMapper.selectById(id) == null) {
+            throw exception(GO_VIEW_PROJECT_NOT_EXISTS);
+        }
+    }
+
+    @Override
+    public GoViewProjectDO getProject(Long id) {
+        return goViewProjectMapper.selectById(id);
+    }
+
+    @Override
+    public PageResult<GoViewProjectDO> getMyProjectPage(PageParam pageReqVO, Long userId) {
+        return goViewProjectMapper.selectPage(pageReqVO, userId);
+    }
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/test/java/cn/iocoder/yudao/module/report/service/goview/GoViewDataServiceImplTest.java b/yudao-module-report/yudao-module-report-biz/src/test/java/cn/iocoder/yudao/module/report/service/goview/GoViewDataServiceImplTest.java
new file mode 100644
index 000000000..87b78b8b8
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/test/java/cn/iocoder/yudao/module/report/service/goview/GoViewDataServiceImplTest.java
@@ -0,0 +1,58 @@
+package cn.iocoder.yudao.module.report.service.goview;
+
+import cn.iocoder.yudao.framework.test.core.ut.BaseDbUnitTest;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.data.GoViewDataRespVO;
+import org.junit.jupiter.api.Test;
+import org.springframework.boot.test.mock.mockito.MockBean;
+import org.springframework.context.annotation.Import;
+import org.springframework.jdbc.core.JdbcTemplate;
+import org.springframework.jdbc.support.rowset.SqlRowSet;
+import org.springframework.jdbc.support.rowset.SqlRowSetMetaData;
+
+import javax.annotation.Resource;
+import java.util.Arrays;
+
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.mockito.ArgumentMatchers.eq;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+
+@Import(GoViewDataServiceImpl.class)
+public class GoViewDataServiceImplTest extends BaseDbUnitTest {
+
+    @Resource
+    private GoViewDataServiceImpl goViewDataService;
+
+    @MockBean
+    private JdbcTemplate jdbcTemplate;
+
+    @Test
+    public void testGetDataBySQL() {
+        // 准备参数
+        String sql = "SELECT id, name FROM system_users";
+        // mock 方法
+        SqlRowSet sqlRowSet = mock(SqlRowSet.class);
+        when(jdbcTemplate.queryForRowSet(eq(sql))).thenReturn(sqlRowSet);
+        // mock 元数据
+        SqlRowSetMetaData metaData = mock(SqlRowSetMetaData.class);
+        when(sqlRowSet.getMetaData()).thenReturn(metaData);
+        when(metaData.getColumnNames()).thenReturn(new String[]{"id", "name"});
+        // mock 数据明细
+        when(sqlRowSet.next()).thenReturn(true).thenReturn(true).thenReturn(false);
+        when(sqlRowSet.getObject("id")).thenReturn(1L).thenReturn(2L);
+        when(sqlRowSet.getObject("name")).thenReturn("芋道源码").thenReturn("芋道");
+
+        // 调用
+        GoViewDataRespVO dataBySQL = goViewDataService.getDataBySQL(sql);
+        // 断言
+        assertEquals(Arrays.asList("id", "name"), dataBySQL.getDimensions());
+        assertEquals(2, dataBySQL.getDimensions().size());
+        assertEquals(2, dataBySQL.getSource().get(0).size());
+        assertEquals(1L, dataBySQL.getSource().get(0).get("id"));
+        assertEquals("芋道源码", dataBySQL.getSource().get(0).get("name"));
+        assertEquals(2, dataBySQL.getSource().get(1).size());
+        assertEquals(2L, dataBySQL.getSource().get(1).get("id"));
+        assertEquals("芋道", dataBySQL.getSource().get(1).get("name"));
+    }
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/test/java/cn/iocoder/yudao/module/report/service/goview/GoViewProjectServiceImplTest.java b/yudao-module-report/yudao-module-report-biz/src/test/java/cn/iocoder/yudao/module/report/service/goview/GoViewProjectServiceImplTest.java
new file mode 100644
index 000000000..2f6bfae7b
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/test/java/cn/iocoder/yudao/module/report/service/goview/GoViewProjectServiceImplTest.java
@@ -0,0 +1,135 @@
+package cn.iocoder.yudao.module.report.service.goview;
+
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.framework.test.core.ut.BaseDbUnitTest;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectCreateReqVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectUpdateReqVO;
+import cn.iocoder.yudao.module.report.dal.dataobject.goview.GoViewProjectDO;
+import cn.iocoder.yudao.module.report.dal.mysql.goview.GoViewProjectMapper;
+import org.junit.jupiter.api.Test;
+import org.springframework.context.annotation.Import;
+
+import javax.annotation.Resource;
+
+import static cn.iocoder.yudao.framework.common.util.object.ObjectUtils.cloneIgnoreId;
+import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertPojoEquals;
+import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertServiceException;
+import static cn.iocoder.yudao.framework.test.core.util.RandomUtils.*;
+import static cn.iocoder.yudao.module.report.enums.ErrorCodeConstants.GO_VIEW_PROJECT_NOT_EXISTS;
+import static org.junit.jupiter.api.Assertions.*;
+
+/**
+ * {@link GoViewProjectServiceImpl} 的单元测试类
+ *
+ * @author 芋道源码
+ */
+@Import(GoViewProjectServiceImpl.class)
+public class GoViewProjectServiceImplTest extends BaseDbUnitTest {
+
+    @Resource
+    private GoViewProjectServiceImpl goViewProjectService;
+
+    @Resource
+    private GoViewProjectMapper goViewProjectMapper;
+
+    @Test
+    public void testCreateProject_success() {
+        // 准备参数
+        GoViewProjectCreateReqVO reqVO = randomPojo(GoViewProjectCreateReqVO.class);
+
+        // 调用
+        Long goViewProjectId = goViewProjectService.createProject(reqVO);
+        // 断言
+        assertNotNull(goViewProjectId);
+        // 校验记录的属性是否正确
+        GoViewProjectDO goViewProject = goViewProjectMapper.selectById(goViewProjectId);
+        assertPojoEquals(reqVO, goViewProject);
+    }
+
+    @Test
+    public void testUpdateProject_success() {
+        // mock 数据
+        GoViewProjectDO dbGoViewProject = randomPojo(GoViewProjectDO.class);
+        goViewProjectMapper.insert(dbGoViewProject);// @Sql: 先插入出一条存在的数据
+        // 准备参数
+        GoViewProjectUpdateReqVO reqVO = randomPojo(GoViewProjectUpdateReqVO.class, o -> {
+            o.setId(dbGoViewProject.getId()); // 设置更新的 ID
+            o.setStatus(randomCommonStatus());
+        });
+
+        // 调用
+        goViewProjectService.updateProject(reqVO);
+        // 校验是否更新正确
+        GoViewProjectDO goViewProject = goViewProjectMapper.selectById(reqVO.getId()); // 获取最新的
+        assertPojoEquals(reqVO, goViewProject);
+    }
+
+    @Test
+    public void testUpdateProject_notExists() {
+        // 准备参数
+        GoViewProjectUpdateReqVO reqVO = randomPojo(GoViewProjectUpdateReqVO.class);
+
+        // 调用, 并断言异常
+        assertServiceException(() -> goViewProjectService.updateProject(reqVO), GO_VIEW_PROJECT_NOT_EXISTS);
+    }
+
+    @Test
+    public void testDeleteProject_success() {
+        // mock 数据
+        GoViewProjectDO dbGoViewProject = randomPojo(GoViewProjectDO.class);
+        goViewProjectMapper.insert(dbGoViewProject);// @Sql: 先插入出一条存在的数据
+        // 准备参数
+        Long id = dbGoViewProject.getId();
+
+        // 调用
+        goViewProjectService.deleteProject(id);
+        // 校验数据不存在了
+        assertNull(goViewProjectMapper.selectById(id));
+    }
+
+    @Test
+    public void testDeleteProject_notExists() {
+        // 准备参数
+        Long id = randomLongId();
+
+        // 调用, 并断言异常
+        assertServiceException(() -> goViewProjectService.deleteProject(id), GO_VIEW_PROJECT_NOT_EXISTS);
+    }
+
+    @Test
+    public void testGetProject() {
+        // mock 数据
+        GoViewProjectDO dbGoViewProject = randomPojo(GoViewProjectDO.class);
+        goViewProjectMapper.insert(dbGoViewProject);// @Sql: 先插入出一条存在的数据
+        // 准备参数
+        Long id = dbGoViewProject.getId();
+
+        // 调用
+        GoViewProjectDO goViewProject = goViewProjectService.getProject(id);
+        // 断言
+        assertPojoEquals(dbGoViewProject, goViewProject);
+    }
+
+    @Test
+    public void testGetMyGoViewProjectPage() {
+        // mock 数据
+        GoViewProjectDO dbGoViewProject = randomPojo(GoViewProjectDO.class, o -> { // 等会查询到
+            o.setCreator("1");
+        });
+        goViewProjectMapper.insert(dbGoViewProject);
+        // 测试 userId 不匹配
+        goViewProjectMapper.insert(cloneIgnoreId(dbGoViewProject, o -> o.setCreator("2")));
+        // 准备参数
+        PageParam reqVO = new PageParam();
+        Long userId = 1L;
+
+        // 调用
+        PageResult<GoViewProjectDO> pageResult = goViewProjectService.getMyProjectPage(reqVO, userId);
+        // 断言
+        assertEquals(1, pageResult.getTotal());
+        assertEquals(1, pageResult.getList().size());
+        assertPojoEquals(dbGoViewProject, pageResult.getList().get(0));
+    }
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/test/resources/application-unit-test.yaml b/yudao-module-report/yudao-module-report-biz/src/test/resources/application-unit-test.yaml
new file mode 100644
index 000000000..460d4a250
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/test/resources/application-unit-test.yaml
@@ -0,0 +1,55 @@
+spring:
+  main:
+    lazy-initialization: true # 开启懒加载,加快速度
+    banner-mode: off # 单元测试,禁用 Banner
+
+--- #################### 数据库相关配置 ####################
+
+spring:
+  # 数据源配置项
+  datasource:
+    name: ruoyi-vue-pro
+    url: jdbc:h2:mem:testdb;MODE=MYSQL;DATABASE_TO_UPPER=false;NON_KEYWORDS=value; # MODE 使用 MySQL 模式;DATABASE_TO_UPPER 配置表和字段使用小写
+    driver-class-name: org.h2.Driver
+    username: sa
+    password:
+    druid:
+      async-init: true # 单元测试,异步初始化 Druid 连接池,提升启动速度
+      initial-size: 1 # 单元测试,配置为 1,提升启动速度
+  sql:
+    init:
+      schema-locations: classpath:/sql/create_tables.sql
+
+  # Redis 配置。Redisson 默认的配置足够使用,一般不需要进行调优
+  redis:
+    host: 127.0.0.1 # 地址
+    port: 16379 # 端口(单元测试,使用 16379 端口)
+    database: 0 # 数据库索引
+
+
+mybatis:
+  lazy-initialization: true # 单元测试,设置 MyBatis Mapper 延迟加载,加速每个单元测试
+
+--- #################### 定时任务相关配置 ####################
+
+--- #################### 配置中心相关配置 ####################
+
+--- #################### 服务保障相关配置 ####################
+
+# Lock4j 配置项(单元测试,禁用 Lock4j)
+
+# Resilience4j 配置项
+
+--- #################### 监控相关配置 ####################
+
+--- #################### 芋道相关配置 ####################
+
+# 芋道配置项,设置当前项目所有自定义的配置
+yudao:
+  info:
+    base-package: cn.iocoder.yudao.module
+  captcha:
+    timeout: 5m
+    width: 160
+    height: 60
+    enable: true
diff --git a/yudao-module-report/yudao-module-report-biz/src/test/resources/logback.xml b/yudao-module-report/yudao-module-report-biz/src/test/resources/logback.xml
new file mode 100644
index 000000000..daf756bff
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/test/resources/logback.xml
@@ -0,0 +1,4 @@
+<configuration>
+    <!-- 引用 Spring Boot 的 logback 基础配置 -->
+    <include resource="org/springframework/boot/logging/logback/defaults.xml" />
+</configuration>
diff --git a/yudao-module-report/yudao-module-report-biz/src/test/resources/sql/clean.sql b/yudao-module-report/yudao-module-report-biz/src/test/resources/sql/clean.sql
new file mode 100644
index 000000000..4a0268afc
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/test/resources/sql/clean.sql
@@ -0,0 +1 @@
+DELETE FROM "report_go_view_project";
diff --git a/yudao-module-report/yudao-module-report-biz/src/test/resources/sql/create_tables.sql b/yudao-module-report/yudao-module-report-biz/src/test/resources/sql/create_tables.sql
new file mode 100644
index 000000000..a77397fea
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/test/resources/sql/create_tables.sql
@@ -0,0 +1,14 @@
+CREATE TABLE IF NOT EXISTS "report_go_view_project" (
+    "id" bigint NOT NULL GENERATED BY DEFAULT AS IDENTITY,
+    "name" varchar NOT NULL,
+    "pic_url" varchar,
+    "content" varchar,
+    "status" varchar NOT NULL,
+    "remark" varchar,
+    "creator" varchar DEFAULT '',
+    "create_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
+    "updater" varchar DEFAULT '',
+    "update_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
+    "deleted" bit NOT NULL DEFAULT FALSE,
+    PRIMARY KEY ("id")
+) COMMENT 'GoView 项目表';
diff --git a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/jmreport/core/web/package-info.java b/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/jmreport/core/web/package-info.java
deleted file mode 100644
index 140fce2a2..000000000
--- a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/jmreport/core/web/package-info.java
+++ /dev/null
@@ -1,4 +0,0 @@
-/**
- * 占位,后续会基于 Filter 实现积木报表的认证等功能,替代 {@link cn.iocoder.yudao.module.visualization.framework.jmreport.core.service.JmReportTokenServiceImpl}
- */
-package cn.iocoder.yudao.module.visualization.framework.jmreport.core.web;
diff --git a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/package-info.java b/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/package-info.java
deleted file mode 100644
index af863b522..000000000
--- a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/package-info.java
+++ /dev/null
@@ -1,6 +0,0 @@
-/**
- * 属于 visualization 模块的 framework 封装
- *
- * @author 芋道源码
- */
-package cn.iocoder.yudao.module.visualization.framework;
diff --git a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/security/core/package-info.java b/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/security/core/package-info.java
deleted file mode 100644
index 21585321c..000000000
--- a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/framework/security/core/package-info.java
+++ /dev/null
@@ -1,4 +0,0 @@
-/**
- * 占位
- */
-package cn.iocoder.yudao.module.visualization.framework.security.core;
diff --git a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/package-info.java b/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/package-info.java
deleted file mode 100644
index cc501dcb8..000000000
--- a/yudao-module-visualization/yudao-module-visualization-biz/src/main/java/cn/iocoder/yudao/module/visualization/package-info.java
+++ /dev/null
@@ -1,9 +0,0 @@
-/**
- * visualization 模块,主要实现数据可视化报表等功能:
- * 1. 基于「积木报表」实现,打印设计、报表设计、图形设计、大屏设计等。URL 前缀是 /jmreport,表名前缀是 jimu_
- *
- * 由于「积木报表」的大屏设计器需要收费,后续会自研,对应的是:
- * 1. Controller URL:以 /visualization/ 开头,避免和其它 Module 冲突
- * 2. DataObject 表名:以 visualization_ 开头,方便在数据库中区分
- */
-package cn.iocoder.yudao.module.visualization;
diff --git a/yudao-server/pom.xml b/yudao-server/pom.xml
index 40b35b9cb..86399b2f1 100644
--- a/yudao-server/pom.xml
+++ b/yudao-server/pom.xml
@@ -44,7 +44,7 @@
         <!-- 数据报表 -->
 <!--        <dependency>-->
 <!--            <groupId>cn.iocoder.boot</groupId>-->
-<!--            <artifactId>yudao-module-visualization-biz</artifactId>-->
+<!--            <artifactId>yudao-module-report-biz</artifactId>-->
 <!--            <version>${revision}</version>-->
 <!--        </dependency>-->
         <!-- 工作流 -->
diff --git a/yudao-server/src/main/java/cn/iocoder/yudao/server/controller/DefaultController.java b/yudao-server/src/main/java/cn/iocoder/yudao/server/controller/DefaultController.java
index ab328b429..3a7cd3bfa 100644
--- a/yudao-server/src/main/java/cn/iocoder/yudao/server/controller/DefaultController.java
+++ b/yudao-server/src/main/java/cn/iocoder/yudao/server/controller/DefaultController.java
@@ -32,7 +32,13 @@ public class DefaultController {
             "/admin-api/promotion/**"})  // 营销中心
     public CommonResult<Boolean> mall404() {
         return CommonResult.error(NOT_IMPLEMENTED.getCode(),
-                "[商城 yudao-module-mp - 已禁用][参考 https://doc.iocoder.cn/mall/build/ 开启]");
+                "[商城系统 yudao-module-mall - 已禁用][参考 https://doc.iocoder.cn/mall/build/ 开启]");
+    }
+
+    @RequestMapping(value = {"/admin-api/report/**"})
+    public CommonResult<Boolean> report404() {
+        return CommonResult.error(NOT_IMPLEMENTED.getCode(),
+                "[报表模块 yudao-module-report - 已禁用][参考 https://doc.iocoder.cn/report/ 开启]");
     }
 
 }
diff --git a/yudao-ui-admin-vue3/.env.dev b/yudao-ui-admin-vue3/.env.dev
index 658a4f62d..3b85e4819 100644
--- a/yudao-ui-admin-vue3/.env.dev
+++ b/yudao-ui-admin-vue3/.env.dev
@@ -4,10 +4,10 @@ NODE_ENV=production
 VITE_DEV=false
 
 # 请求路径
-VITE_BASE_URL='http://localhost:58080'
+VITE_BASE_URL='http://localhost:48080'
 
 # 上传路径
-VITE_UPLOAD_URL='http://localhost:58080/admin-api/infra/file/upload'
+VITE_UPLOAD_URL='http://localhost:48080/admin-api/infra/file/upload'
 
 # 接口前缀
 VITE_API_BASEPATH=/dev-api
diff --git a/yudao-ui-admin-vue3/.env.pro b/yudao-ui-admin-vue3/.env.pro
index 0c91638b0..8348e02e3 100644
--- a/yudao-ui-admin-vue3/.env.pro
+++ b/yudao-ui-admin-vue3/.env.pro
@@ -4,10 +4,10 @@ NODE_ENV=production
 VITE_DEV=false
 
 # 请求路径
-VITE_BASE_URL='http://localhost:58080'
+VITE_BASE_URL='http://localhost:48080'
 
 # 上传路径
-VITE_UPLOAD_URL='http://localhost:58080/admin-api/infra/file/upload'
+VITE_UPLOAD_URL='http://localhost:48080/admin-api/infra/file/upload'
 
 # 接口前缀
 VITE_API_BASEPATH=
diff --git a/yudao-ui-admin-vue3/.env.test b/yudao-ui-admin-vue3/.env.test
index 72b1c47cd..85e2cf545 100644
--- a/yudao-ui-admin-vue3/.env.test
+++ b/yudao-ui-admin-vue3/.env.test
@@ -4,10 +4,10 @@ NODE_ENV=production
 VITE_DEV=false
 
 # 请求路径
-VITE_BASE_URL='http://localhost:58080'
+VITE_BASE_URL='http://localhost:48080'
 
 # 上传路径
-VITE_UPLOAD_URL='http://localhost:58080/admin-api/infra/file/upload'
+VITE_UPLOAD_URL='http://localhost:48080/admin-api/infra/file/upload'
 
 # 接口前缀
 VITE_API_BASEPATH=
diff --git a/yudao-ui-admin-vue3/pnpm-lock.yaml b/yudao-ui-admin-vue3/pnpm-lock.yaml
index ad10d25bf..d185c1539 100644
--- a/yudao-ui-admin-vue3/pnpm-lock.yaml
+++ b/yudao-ui-admin-vue3/pnpm-lock.yaml
@@ -1,4 +1,4 @@
-lockfileVersion: 5.4
+lockfileVersion: 5.3
 
 specifiers:
   '@commitlint/cli': ^17.4.2
@@ -103,7 +103,7 @@ dependencies:
   '@iconify/iconify': 3.1.0
   '@vueuse/core': 9.12.0_vue@3.2.47
   '@wangeditor/editor': 5.1.23
-  '@wangeditor/editor-for-vue': 5.1.12_77ywgcaevzgjoxs6yixvgo4fve
+  '@wangeditor/editor-for-vue': 5.1.12_fff1630804ae4c975e5ec22f533b85a9
   '@zxcvbn-ts/core': 2.2.0
   animate.css: 4.1.1
   axios: 1.3.2
@@ -124,7 +124,7 @@ dependencies:
   min-dash: 4.0.0
   mitt: 3.0.0
   nprogress: 0.2.0
-  pinia: 2.0.30_hmuptsblhheur2tugfgucj7gc4
+  pinia: 2.0.30_typescript@4.9.5+vue@3.2.47
   qrcode: 1.5.1
   qs: 6.11.0
   steady-xml: 0.1.0
@@ -151,8 +151,8 @@ devDependencies:
   '@types/nprogress': 0.2.0
   '@types/qrcode': 1.5.0
   '@types/qs': 6.9.7
-  '@typescript-eslint/eslint-plugin': 5.50.0_go4drrxstycfikanvu45pi4vgq
-  '@typescript-eslint/parser': 5.50.0_4vsywjlpuriuw3tl5oq6zy5a64
+  '@typescript-eslint/eslint-plugin': 5.50.0_33b838c6f29e0454280dad39d7a39534
+  '@typescript-eslint/parser': 5.50.0_eslint@8.33.0+typescript@4.9.5
   '@vitejs/plugin-legacy': 4.0.1_terser@5.16.3+vite@4.1.1
   '@vitejs/plugin-vue': 4.0.0_vite@4.1.1+vue@3.2.47
   '@vitejs/plugin-vue-jsx': 3.0.0_vite@4.1.1+vue@3.2.47
@@ -163,7 +163,7 @@ devDependencies:
   eslint: 8.33.0
   eslint-config-prettier: 8.6.0_eslint@8.33.0
   eslint-define-config: 1.15.0
-  eslint-plugin-prettier: 4.2.1_jqplj6qf3uqpxpu4gdyhwwasnq
+  eslint-plugin-prettier: 4.2.1_4c1eb4fa05dd20fbbe9c30f07b58126c
   eslint-plugin-vue: 9.9.0_eslint@8.33.0
   lint-staged: 13.1.0
   postcss: 8.4.21
@@ -174,17 +174,17 @@ devDependencies:
   rollup: 3.14.0
   sass: 1.58.0
   stylelint: 14.16.1
-  stylelint-config-html: 1.1.0_kbto3rg3njmczth2rrsgfnlsqa
+  stylelint-config-html: 1.1.0_5066edc4db6a582cccfa8c6462b57280
   stylelint-config-prettier: 9.0.4_stylelint@14.16.1
   stylelint-config-recommended: 9.0.0_stylelint@14.16.1
   stylelint-config-standard: 29.0.0_stylelint@14.16.1
   stylelint-order: 6.0.1_stylelint@14.16.1
   terser: 5.16.3
   typescript: 4.9.5
-  unplugin-auto-import: 0.13.0_z2glzmrjcar3r3i7v53oix2lwa
+  unplugin-auto-import: 0.13.0_ce8cbcb2291023b8ed1faf76e45f4bb0
   unplugin-element-plus: 0.6.0_rollup@3.14.0
   unplugin-vue-components: 0.23.0_rollup@3.14.0+vue@3.2.47
-  vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+  vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
   vite-plugin-compression: 0.5.1_vite@4.1.1
   vite-plugin-ejs: 1.6.4
   vite-plugin-eslint: 1.8.1_eslint@8.33.0+vite@4.1.1
@@ -1732,12 +1732,12 @@ packages:
       '@types/node': 18.11.19
       chalk: 4.1.2
       cosmiconfig: 8.0.0
-      cosmiconfig-typescript-loader: 4.2.0_q6dimmvgduffavfq3obt6abtea
+      cosmiconfig-typescript-loader: 4.2.0_87868632a61d0a5054b0db833f003320
       lodash.isplainobject: 4.0.6
       lodash.merge: 4.6.2
       lodash.uniq: 4.5.0
       resolve-from: 5.0.0
-      ts-node: 10.9.1_qqdszkrtcshgbphghj7vnvrrby
+      ts-node: 10.9.1_84072caa33148e60bce63a7f56d6310e
       typescript: 4.9.5
     transitivePeerDependencies:
       - '@swc/core'
@@ -1818,7 +1818,7 @@ packages:
       '@jridgewell/trace-mapping': 0.3.9
     dev: true
 
-  /@csstools/selector-specificity/2.0.2_wajs5nedgkikc5pcuwett7legi:
+  /@csstools/selector-specificity/2.0.2_b0132eb4833290a175e2a58939fd6432:
     resolution: {integrity: sha512-IkpVW/ehM1hWKln4fCA3NzJU8KwD+kIOvPZA4cqxoJHtE21CCzjyp+Kxbu0i5I4tBNOlXPL9mjwnWlL0VEG4Fg==}
     engines: {node: ^12 || ^14 || >=16}
     peerDependencies:
@@ -2232,12 +2232,14 @@ packages:
       '@intlify/message-compiler': 9.2.2
       '@intlify/shared': 9.2.2
       '@intlify/vue-devtools': 9.2.2
+    dev: false
 
   /@intlify/devtools-if/9.2.2:
     resolution: {integrity: sha512-4ttr/FNO29w+kBbU7HZ/U0Lzuh2cRDhP8UlWOtV9ERcjHzuyXVZmjyleESK6eVP60tGC9QtQW9yZE+JeRhDHkg==}
     engines: {node: '>= 14'}
     dependencies:
       '@intlify/shared': 9.2.2
+    dev: false
 
   /@intlify/message-compiler/9.2.2:
     resolution: {integrity: sha512-IUrQW7byAKN2fMBe8z6sK6riG1pue95e5jfokn8hA5Q3Bqy4MBJ5lJAofUsawQJYHeoPJ7svMDyBaVJ4d0GTtA==}
@@ -2245,6 +2247,7 @@ packages:
     dependencies:
       '@intlify/shared': 9.2.2
       source-map: 0.6.1
+    dev: false
 
   /@intlify/message-compiler/9.3.0-beta.16:
     resolution: {integrity: sha512-CGQI3xRcs1ET75eDQ0DUy3MRYOqTauRIIgaMoISKiF83gqRWg93FqN8lGMKcpBqaF4tI0JhsfosCaGiBL9+dnw==}
@@ -2257,6 +2260,7 @@ packages:
   /@intlify/shared/9.2.2:
     resolution: {integrity: sha512-wRwTpsslgZS5HNyM7uDQYZtxnbI12aGiBZURX3BTR9RFIKKRWpllTsgzHWvj3HKm3Y2Sh5LPC1r0PDCKEhVn9Q==}
     engines: {node: '>= 14'}
+    dev: false
 
   /@intlify/shared/9.3.0-beta.16:
     resolution: {integrity: sha512-kXbm4svALe3lX+EjdJxfnabOphqS4yQ1Ge/iIlR8tvUiYRCoNz3hig1M4336iY++Dfx5ytEQJPNjIcknNIuvig==}
@@ -2301,6 +2305,7 @@ packages:
     dependencies:
       '@intlify/core-base': 9.2.2
       '@intlify/shared': 9.2.2
+    dev: false
 
   /@jridgewell/gen-mapping/0.1.1:
     resolution: {integrity: sha512-sQXCasFk+U8lWYEe66WxRDOE9PjVz4vSM51fTu3Hw+ClTpUSQb718772vH3pyS5pShp6lvQM7SxgIDXXXmOX7w==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npm.taobao.org/@jridgewell/gen-mapping/-/gen-mapping-0.1.1.tgz}
@@ -2572,8 +2577,9 @@ packages:
 
   /@types/web-bluetooth/0.0.16:
     resolution: {integrity: sha512-oh8q2Zc32S6gd/j50GowEjKLoOVOwHP/bWVjKJInBwQqdOYMdPrf1oVlelTlyfFK3CKxL1uahMDAr+vy8T7yMQ==}
+    dev: false
 
-  /@typescript-eslint/eslint-plugin/5.50.0_go4drrxstycfikanvu45pi4vgq:
+  /@typescript-eslint/eslint-plugin/5.50.0_33b838c6f29e0454280dad39d7a39534:
     resolution: {integrity: sha512-vwksQWSFZiUhgq3Kv7o1Jcj0DUNylwnIlGvKvLLYsq8pAWha6/WCnXUeaSoNNha/K7QSf2+jvmkxggC1u3pIwQ==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
@@ -2584,10 +2590,10 @@ packages:
       typescript:
         optional: true
     dependencies:
-      '@typescript-eslint/parser': 5.50.0_4vsywjlpuriuw3tl5oq6zy5a64
+      '@typescript-eslint/parser': 5.50.0_eslint@8.33.0+typescript@4.9.5
       '@typescript-eslint/scope-manager': 5.50.0
-      '@typescript-eslint/type-utils': 5.50.0_4vsywjlpuriuw3tl5oq6zy5a64
-      '@typescript-eslint/utils': 5.50.0_4vsywjlpuriuw3tl5oq6zy5a64
+      '@typescript-eslint/type-utils': 5.50.0_eslint@8.33.0+typescript@4.9.5
+      '@typescript-eslint/utils': 5.50.0_eslint@8.33.0+typescript@4.9.5
       debug: 4.3.4
       eslint: 8.33.0
       grapheme-splitter: 1.0.4
@@ -2601,7 +2607,7 @@ packages:
       - supports-color
     dev: true
 
-  /@typescript-eslint/parser/5.50.0_4vsywjlpuriuw3tl5oq6zy5a64:
+  /@typescript-eslint/parser/5.50.0_eslint@8.33.0+typescript@4.9.5:
     resolution: {integrity: sha512-KCcSyNaogUDftK2G9RXfQyOCt51uB5yqC6pkUYqhYh8Kgt+DwR5M0EwEAxGPy/+DH6hnmKeGsNhiZRQxjH71uQ==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
@@ -2629,7 +2635,7 @@ packages:
       '@typescript-eslint/visitor-keys': 5.50.0
     dev: true
 
-  /@typescript-eslint/type-utils/5.50.0_4vsywjlpuriuw3tl5oq6zy5a64:
+  /@typescript-eslint/type-utils/5.50.0_eslint@8.33.0+typescript@4.9.5:
     resolution: {integrity: sha512-dcnXfZ6OGrNCO7E5UY/i0ktHb7Yx1fV6fnQGGrlnfDhilcs6n19eIRcvLBqx6OQkrPaFlDPk3OJ0WlzQfrV0bQ==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
@@ -2640,7 +2646,7 @@ packages:
         optional: true
     dependencies:
       '@typescript-eslint/typescript-estree': 5.50.0_typescript@4.9.5
-      '@typescript-eslint/utils': 5.50.0_4vsywjlpuriuw3tl5oq6zy5a64
+      '@typescript-eslint/utils': 5.50.0_eslint@8.33.0+typescript@4.9.5
       debug: 4.3.4
       eslint: 8.33.0
       tsutils: 3.21.0_typescript@4.9.5
@@ -2675,7 +2681,7 @@ packages:
       - supports-color
     dev: true
 
-  /@typescript-eslint/utils/5.50.0_4vsywjlpuriuw3tl5oq6zy5a64:
+  /@typescript-eslint/utils/5.50.0_eslint@8.33.0+typescript@4.9.5:
     resolution: {integrity: sha512-v/AnUFImmh8G4PH0NDkf6wA8hujNNcrwtecqW4vtQ1UOSNBaZl49zP1SHoZ/06e+UiwzHpgb5zP5+hwlYYWYAw==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
@@ -2759,7 +2765,7 @@ packages:
       regenerator-runtime: 0.13.11
       systemjs: 6.13.0
       terser: 5.16.3
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
     transitivePeerDependencies:
       - supports-color
     dev: true
@@ -2774,7 +2780,7 @@ packages:
       '@babel/core': 7.20.5
       '@babel/plugin-transform-typescript': 7.20.2_@babel+core@7.20.5
       '@vue/babel-plugin-jsx': 1.1.1_@babel+core@7.20.5
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
       vue: 3.2.47
     transitivePeerDependencies:
       - supports-color
@@ -2787,7 +2793,7 @@ packages:
       vite: ^4.0.0
       vue: ^3.2.25
     dependencies:
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
       vue: 3.2.47
     dev: true
 
@@ -2867,6 +2873,7 @@ packages:
       '@vue/shared': 3.2.47
       estree-walker: 2.0.2
       source-map: 0.6.1
+    dev: false
 
   /@vue/compiler-dom/3.2.45:
     resolution: {integrity: sha512-tyYeUEuKqqZO137WrZkpwfPCdiiIeXYCcJ8L4gWz9vqaxzIQRccTSwSWZ/Axx5YR2z+LvpUbmPNXxuBU45lyRw==}
@@ -2880,6 +2887,7 @@ packages:
     dependencies:
       '@vue/compiler-core': 3.2.47
       '@vue/shared': 3.2.47
+    dev: false
 
   /@vue/compiler-sfc/3.2.45:
     resolution: {integrity: sha512-1jXDuWah1ggsnSAOGsec8cFjT/K6TMZ0sPL3o3d84Ft2AYZi2jWJgRMjw4iaK0rBfA89L5gw427H4n1RZQBu6Q==}
@@ -2909,6 +2917,7 @@ packages:
       magic-string: 0.25.9
       postcss: 8.4.21
       source-map: 0.6.1
+    dev: false
 
   /@vue/compiler-ssr/3.2.45:
     resolution: {integrity: sha512-6BRaggEGqhWht3lt24CrIbQSRD5O07MTmd+LjAn5fJj568+R9eUD2F7wMQJjX859seSlrYog7sUtrZSd7feqrQ==}
@@ -2922,9 +2931,11 @@ packages:
     dependencies:
       '@vue/compiler-dom': 3.2.47
       '@vue/shared': 3.2.47
+    dev: false
 
   /@vue/devtools-api/6.4.5:
     resolution: {integrity: sha512-JD5fcdIuFxU4fQyXUu3w2KpAJHzTVdN+p4iOX2lMWSHMOoQdMAcpFLZzm9Z/2nmsoZ1a96QEhZ26e50xLBsgOQ==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npm.taobao.org/@vue/devtools-api/-/devtools-api-6.4.5.tgz}
+    dev: false
 
   /@vue/reactivity-transform/3.2.45:
     resolution: {integrity: sha512-BHVmzYAvM7vcU5WmuYqXpwaBHjsS8T63jlKGWVtHxAHIoMIlmaMyurUSEs1Zcg46M4AYT5MtB1U274/2aNzjJQ==}
@@ -2944,6 +2955,7 @@ packages:
       '@vue/shared': 3.2.47
       estree-walker: 2.0.2
       magic-string: 0.25.9
+    dev: false
 
   /@vue/reactivity/3.2.45:
     resolution: {integrity: sha512-PRvhCcQcyEVohW0P8iQ7HDcIOXRjZfAsOds3N99X/Dzewy8TVhTCT4uXpAHfoKjVTJRA0O0K+6QNkDIZAxNi3A==}
@@ -2955,12 +2967,14 @@ packages:
     resolution: {integrity: sha512-7khqQ/75oyyg+N/e+iwV6lpy1f5wq759NdlS1fpAhFXa8VeAIKGgk2E/C4VF59lx5b+Ezs5fpp/5WsRYXQiKxQ==}
     dependencies:
       '@vue/shared': 3.2.47
+    dev: false
 
   /@vue/runtime-core/3.2.47:
     resolution: {integrity: sha512-RZxbLQIRB/K0ev0K9FXhNbBzT32H9iRtYbaXb0ZIz2usLms/D55dJR2t6cIEUn6vyhS3ALNvNthI+Q95C+NOpA==}
     dependencies:
       '@vue/reactivity': 3.2.47
       '@vue/shared': 3.2.47
+    dev: false
 
   /@vue/runtime-dom/3.2.47:
     resolution: {integrity: sha512-ArXrFTjS6TsDei4qwNvgrdmHtD930KgSKGhS5M+j8QxXrDJYLqYw4RRcDy1bz1m1wMmb6j+zGLifdVHtkXA7gA==}
@@ -2968,6 +2982,7 @@ packages:
       '@vue/runtime-core': 3.2.47
       '@vue/shared': 3.2.47
       csstype: 2.6.21
+    dev: false
 
   /@vue/server-renderer/3.2.47_vue@3.2.47:
     resolution: {integrity: sha512-dN9gc1i8EvmP9RCzvneONXsKfBRgqFeFZLurmHOveL7oH6HiFXJw5OGu294n1nHc/HMgTy6LulU/tv5/A7f/LA==}
@@ -2977,6 +2992,7 @@ packages:
       '@vue/compiler-ssr': 3.2.47
       '@vue/shared': 3.2.47
       vue: 3.2.47
+    dev: false
 
   /@vue/shared/3.2.45:
     resolution: {integrity: sha512-Ewzq5Yhimg7pSztDV+RH1UDKBzmtqieXQlpTVm2AwraoRL/Rks96mvd8Vgi7Lj+h+TH8dv7mXD3FRZR3TUvbSg==}
@@ -2984,6 +3000,7 @@ packages:
 
   /@vue/shared/3.2.47:
     resolution: {integrity: sha512-BHGyyGN3Q97EZx0taMQ+OLNuZcW3d37ZEVmEAyeoA9ERdGvm9Irc/0Fua8SNyOtV1w6BS4q25wbMzJujO9HIfQ==}
+    dev: false
 
   /@vueuse/core/9.12.0_vue@3.2.47:
     resolution: {integrity: sha512-h/Di8Bvf6xRcvS/PvUVheiMYYz3U0tH3X25YxONSaAUBa841ayMwxkuzx/DGUMCW/wHWzD8tRy2zYmOC36r4sg==}
@@ -2995,9 +3012,11 @@ packages:
     transitivePeerDependencies:
       - '@vue/composition-api'
       - vue
+    dev: false
 
   /@vueuse/metadata/9.12.0:
     resolution: {integrity: sha512-9oJ9MM9lFLlmvxXUqsR1wLt1uF7EVbP5iYaHJYqk+G2PbMjY6EXvZeTjbdO89HgoF5cI6z49o2zT/jD9SVoNpQ==}
+    dev: false
 
   /@vueuse/shared/9.12.0_vue@3.2.47:
     resolution: {integrity: sha512-TWuJLACQ0BVithVTRbex4Wf1a1VaRuSpVeyEd4vMUWl54PzlE0ciFUshKCXnlLuD0lxIaLK4Ypj3NXYzZh4+SQ==}
@@ -3006,8 +3025,9 @@ packages:
     transitivePeerDependencies:
       - '@vue/composition-api'
       - vue
+    dev: false
 
-  /@wangeditor/basic-modules/1.1.7_j7icpicfeimtkldwmemjnpdjs4:
+  /@wangeditor/basic-modules/1.1.7_4fd027a0452219352c76611896bc6997:
     resolution: {integrity: sha512-cY9CPkLJaqF05STqfpZKWG4LpxTMeGSIIF1fHvfm/mz+JXatCagjdkbxdikOuKYlxDdeqvOeBmsUBItufDLXZg==}
     peerDependencies:
       '@wangeditor/core': 1.x
@@ -3017,7 +3037,7 @@ packages:
       slate: ^0.72.0
       snabbdom: ^3.1.0
     dependencies:
-      '@wangeditor/core': 1.1.19_qokc4m5r26t2nkvzejrgzroa7e
+      '@wangeditor/core': 1.1.19_83942e33b1d7a7a6aab922626cc5c0f9
       dom7: 3.0.0
       is-url: 1.2.4
       lodash.throttle: 4.1.1
@@ -3026,7 +3046,7 @@ packages:
       snabbdom: 3.5.1
     dev: false
 
-  /@wangeditor/code-highlight/1.0.3_tztyh2vh7kwzpeloifaekkk3my:
+  /@wangeditor/code-highlight/1.0.3_9e6783eaa7faad97916e414045295b66:
     resolution: {integrity: sha512-iazHwO14XpCuIWJNTQTikqUhGKyqj+dUNWJ9288Oym9M2xMVHvnsOmDU2sgUDWVy+pOLojReMPgXCsvvNlOOhw==}
     peerDependencies:
       '@wangeditor/core': 1.x
@@ -3034,14 +3054,14 @@ packages:
       slate: ^0.72.0
       snabbdom: ^3.1.0
     dependencies:
-      '@wangeditor/core': 1.1.19_qokc4m5r26t2nkvzejrgzroa7e
+      '@wangeditor/core': 1.1.19_83942e33b1d7a7a6aab922626cc5c0f9
       dom7: 3.0.0
       prismjs: 1.29.0
       slate: 0.72.8
       snabbdom: 3.5.1
     dev: false
 
-  /@wangeditor/core/1.1.19_qokc4m5r26t2nkvzejrgzroa7e:
+  /@wangeditor/core/1.1.19_83942e33b1d7a7a6aab922626cc5c0f9:
     resolution: {integrity: sha512-KevkB47+7GhVszyYF2pKGKtCSj/YzmClsD03C3zTt+9SR2XWT5T0e3yQqg8baZpcMvkjs1D8Dv4fk8ok/UaS2Q==}
     peerDependencies:
       '@uppy/core': ^2.1.1
@@ -3081,7 +3101,7 @@ packages:
       snabbdom: 3.5.1
     dev: false
 
-  /@wangeditor/editor-for-vue/5.1.12_77ywgcaevzgjoxs6yixvgo4fve:
+  /@wangeditor/editor-for-vue/5.1.12_fff1630804ae4c975e5ec22f533b85a9:
     resolution: {integrity: sha512-0Ds3D8I+xnpNWezAeO7HmPRgTfUxHLMd9JKcIw+QzvSmhC5xUHbpCcLU+KLmeBKTR/zffnS5GQo6qi3GhTMJWQ==}
     peerDependencies:
       '@wangeditor/editor': '>=5.1.0'
@@ -3096,13 +3116,13 @@ packages:
     dependencies:
       '@uppy/core': 2.3.4
       '@uppy/xhr-upload': 2.1.3_@uppy+core@2.3.4
-      '@wangeditor/basic-modules': 1.1.7_j7icpicfeimtkldwmemjnpdjs4
-      '@wangeditor/code-highlight': 1.0.3_tztyh2vh7kwzpeloifaekkk3my
-      '@wangeditor/core': 1.1.19_qokc4m5r26t2nkvzejrgzroa7e
-      '@wangeditor/list-module': 1.0.5_tztyh2vh7kwzpeloifaekkk3my
-      '@wangeditor/table-module': 1.1.4_2dde2uzwslfxq2cqrl35sl4erm
-      '@wangeditor/upload-image-module': 1.0.2_dwqga4onuah5imhngzkgmw6t5a
-      '@wangeditor/video-module': 1.1.4_i6gxywmu7tvxmjxypclnjlcil4
+      '@wangeditor/basic-modules': 1.1.7_4fd027a0452219352c76611896bc6997
+      '@wangeditor/code-highlight': 1.0.3_9e6783eaa7faad97916e414045295b66
+      '@wangeditor/core': 1.1.19_83942e33b1d7a7a6aab922626cc5c0f9
+      '@wangeditor/list-module': 1.0.5_9e6783eaa7faad97916e414045295b66
+      '@wangeditor/table-module': 1.1.4_d0c64d533692cb7868508af7d92f848b
+      '@wangeditor/upload-image-module': 1.0.2_1da06071cda00fd430ed3654665bd3e8
+      '@wangeditor/video-module': 1.1.4_478d7c5994fceb7626f87896d4ac485f
       dom7: 3.0.0
       is-hotkey: 0.2.0
       lodash.camelcase: 4.3.0
@@ -3117,7 +3137,7 @@ packages:
       snabbdom: 3.5.1
     dev: false
 
-  /@wangeditor/list-module/1.0.5_tztyh2vh7kwzpeloifaekkk3my:
+  /@wangeditor/list-module/1.0.5_9e6783eaa7faad97916e414045295b66:
     resolution: {integrity: sha512-uDuYTP6DVhcYf7mF1pTlmNn5jOb4QtcVhYwSSAkyg09zqxI1qBqsfUnveeDeDqIuptSJhkh81cyxi+MF8sEPOQ==}
     peerDependencies:
       '@wangeditor/core': 1.x
@@ -3125,13 +3145,13 @@ packages:
       slate: ^0.72.0
       snabbdom: ^3.1.0
     dependencies:
-      '@wangeditor/core': 1.1.19_qokc4m5r26t2nkvzejrgzroa7e
+      '@wangeditor/core': 1.1.19_83942e33b1d7a7a6aab922626cc5c0f9
       dom7: 3.0.0
       slate: 0.72.8
       snabbdom: 3.5.1
     dev: false
 
-  /@wangeditor/table-module/1.1.4_2dde2uzwslfxq2cqrl35sl4erm:
+  /@wangeditor/table-module/1.1.4_d0c64d533692cb7868508af7d92f848b:
     resolution: {integrity: sha512-5saanU9xuEocxaemGdNi9t8MCDSucnykEC6jtuiT72kt+/Hhh4nERYx1J20OPsTCCdVr7hIyQenFD1iSRkIQ6w==}
     peerDependencies:
       '@wangeditor/core': 1.x
@@ -3142,7 +3162,7 @@ packages:
       slate: ^0.72.0
       snabbdom: ^3.1.0
     dependencies:
-      '@wangeditor/core': 1.1.19_qokc4m5r26t2nkvzejrgzroa7e
+      '@wangeditor/core': 1.1.19_83942e33b1d7a7a6aab922626cc5c0f9
       dom7: 3.0.0
       lodash.isequal: 4.5.0
       lodash.throttle: 4.1.1
@@ -3151,7 +3171,7 @@ packages:
       snabbdom: 3.5.1
     dev: false
 
-  /@wangeditor/upload-image-module/1.0.2_dwqga4onuah5imhngzkgmw6t5a:
+  /@wangeditor/upload-image-module/1.0.2_1da06071cda00fd430ed3654665bd3e8:
     resolution: {integrity: sha512-z81lk/v71OwPDYeQDxj6cVr81aDP90aFuywb8nPD6eQeECtOymrqRODjpO6VGvCVxVck8nUxBHtbxKtjgcwyiA==}
     peerDependencies:
       '@uppy/core': ^2.0.3
@@ -3165,15 +3185,15 @@ packages:
     dependencies:
       '@uppy/core': 2.3.4
       '@uppy/xhr-upload': 2.1.3_@uppy+core@2.3.4
-      '@wangeditor/basic-modules': 1.1.7_j7icpicfeimtkldwmemjnpdjs4
-      '@wangeditor/core': 1.1.19_qokc4m5r26t2nkvzejrgzroa7e
+      '@wangeditor/basic-modules': 1.1.7_4fd027a0452219352c76611896bc6997
+      '@wangeditor/core': 1.1.19_83942e33b1d7a7a6aab922626cc5c0f9
       dom7: 3.0.0
       lodash.foreach: 4.5.0
       slate: 0.72.8
       snabbdom: 3.5.1
     dev: false
 
-  /@wangeditor/video-module/1.1.4_i6gxywmu7tvxmjxypclnjlcil4:
+  /@wangeditor/video-module/1.1.4_478d7c5994fceb7626f87896d4ac485f:
     resolution: {integrity: sha512-ZdodDPqKQrgx3IwWu4ZiQmXI8EXZ3hm2/fM6E3t5dB8tCaIGWQZhmqd6P5knfkRAd3z2+YRSRbxOGfoRSp/rLg==}
     peerDependencies:
       '@uppy/core': ^2.1.4
@@ -3186,7 +3206,7 @@ packages:
     dependencies:
       '@uppy/core': 2.3.4
       '@uppy/xhr-upload': 2.1.3_@uppy+core@2.3.4
-      '@wangeditor/core': 1.1.19_qokc4m5r26t2nkvzejrgzroa7e
+      '@wangeditor/core': 1.1.19_83942e33b1d7a7a6aab922626cc5c0f9
       dom7: 3.0.0
       nanoid: 3.3.4
       slate: 0.72.8
@@ -3608,8 +3628,6 @@ packages:
       snapdragon-node: 2.1.1
       split-string: 3.1.0
       to-regex: 3.0.2
-    transitivePeerDependencies:
-      - supports-color
     dev: true
 
   /braces/3.0.2:
@@ -3957,8 +3975,8 @@ packages:
     engines: {node: '>=10'}
     hasBin: true
     dependencies:
-      JSONStream: 1.3.5
       is-text-path: 1.0.1
+      JSONStream: 1.3.5
       lodash: 4.17.21
       meow: 8.1.2
       split2: 3.2.2
@@ -4002,7 +4020,7 @@ packages:
       vary: 1.1.2
     dev: true
 
-  /cosmiconfig-typescript-loader/4.2.0_q6dimmvgduffavfq3obt6abtea:
+  /cosmiconfig-typescript-loader/4.2.0_87868632a61d0a5054b0db833f003320:
     resolution: {integrity: sha512-NkANeMnaHrlaSSlpKGyvn2R4rqUDeE/9E5YHx+b4nwo0R8dZyAqcih8/gxpCZvqWP9Vf6xuLpMSzSgdVEIM78g==}
     engines: {node: '>=12', npm: '>=6'}
     peerDependencies:
@@ -4013,7 +4031,7 @@ packages:
     dependencies:
       '@types/node': 18.11.19
       cosmiconfig: 8.0.0
-      ts-node: 10.9.1_qqdszkrtcshgbphghj7vnvrrby
+      ts-node: 10.9.1_84072caa33148e60bce63a7f56d6310e
       typescript: 4.9.5
     dev: true
 
@@ -4113,6 +4131,7 @@ packages:
 
   /csstype/2.6.21:
     resolution: {integrity: sha512-Z1PhmomIfypOpoMjRQB70jfvy/wxT50qW08YXO5lMIJkrdq4yOTR+AW7FqutScmB9NkLwxo+jU+kZLbofZZq/w==}
+    dev: false
 
   /d/1.0.1:
     resolution: {integrity: sha512-m62ShEObQ39CfralilEQRjH6oAMtNCV1xJyEx5LpRYUVN+EviphDgUc/F3hnYbADmkiNs67Y+3ylmlG7Lnu+FA==}
@@ -4136,11 +4155,6 @@ packages:
 
   /debug/2.6.9:
     resolution: {integrity: sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==}
-    peerDependencies:
-      supports-color: '*'
-    peerDependenciesMeta:
-      supports-color:
-        optional: true
     dependencies:
       ms: 2.0.0
     dev: true
@@ -4427,7 +4441,7 @@ packages:
       escape-html: 1.0.3
       lodash: 4.17.21
       lodash-es: 4.17.21
-      lodash-unified: 1.0.3_3ib2ivapxullxkx3xftsimdk7u
+      lodash-unified: 1.0.3_da03a4540fbd16bbaafbb96724306afd
       memoize-one: 6.0.0
       normalize-wheel-es: 1.2.0
       vue: 3.2.47
@@ -4583,7 +4597,7 @@ packages:
     engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0, npm: '>=6.14.13', pnpm: '>= 7.0.0'}
     dev: true
 
-  /eslint-plugin-prettier/4.2.1_jqplj6qf3uqpxpu4gdyhwwasnq:
+  /eslint-plugin-prettier/4.2.1_4c1eb4fa05dd20fbbe9c30f07b58126c:
     resolution: {integrity: sha512-f/0rXLXUt0oFYs8ra4w49wYZBG5GKZpAYsJSm6rnYL5uVDjd+zowwMwVZHnAjf4edNrKpCDYfXDgmRE/Ak7QyQ==}
     engines: {node: '>=12.0.0'}
     peerDependencies:
@@ -4823,8 +4837,6 @@ packages:
       regex-not: 1.0.2
       snapdragon: 0.8.2
       to-regex: 3.0.2
-    transitivePeerDependencies:
-      - supports-color
     dev: true
 
   /ext/1.7.0:
@@ -4860,8 +4872,6 @@ packages:
       regex-not: 1.0.2
       snapdragon: 0.8.2
       to-regex: 3.0.2
-    transitivePeerDependencies:
-      - supports-color
     dev: true
 
   /fast-deep-equal/3.1.3:
@@ -5876,7 +5886,7 @@ packages:
     resolution: {integrity: sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw==}
     dev: false
 
-  /lodash-unified/1.0.3_3ib2ivapxullxkx3xftsimdk7u:
+  /lodash-unified/1.0.3_da03a4540fbd16bbaafbb96724306afd:
     resolution: {integrity: sha512-WK9qSozxXOD7ZJQlpSqOT+om2ZfcT4yO+03FuzAHD0wF6S0l0090LRPDx3vhTTLZ8cFKpBn+IOcVXK6qOcIlfQ==}
     peerDependencies:
       '@types/lodash-es': '*'
@@ -6134,8 +6144,6 @@ packages:
       regex-not: 1.0.2
       snapdragon: 0.8.2
       to-regex: 3.0.2
-    transitivePeerDependencies:
-      - supports-color
     dev: true
 
   /micromatch/4.0.5:
@@ -6355,8 +6363,6 @@ packages:
       regex-not: 1.0.2
       snapdragon: 0.8.2
       to-regex: 3.0.2
-    transitivePeerDependencies:
-      - supports-color
     dev: true
 
   /natural-compare-lite/1.4.0:
@@ -6630,7 +6636,7 @@ packages:
     hasBin: true
     dev: true
 
-  /pinia/2.0.30_hmuptsblhheur2tugfgucj7gc4:
+  /pinia/2.0.30_typescript@4.9.5+vue@3.2.47:
     resolution: {integrity: sha512-q6DUmxWwe/mQgg+55QQjykpKC+aGeGdaJV3niminl19V08dE+LRTvSEuqi6/NLSGCKHI49KGL6tMNEOssFiMyA==}
     peerDependencies:
       '@vue/composition-api': ^1.4.0
@@ -7337,8 +7343,6 @@ packages:
       source-map: 0.5.7
       source-map-resolve: 0.5.3
       use: 3.1.1
-    transitivePeerDependencies:
-      - supports-color
     dev: true
 
   /sortablejs/1.14.0:
@@ -7541,7 +7545,7 @@ packages:
     resolution: {integrity: sha512-Dj1Okke1C3uKKwQcetra4jSuk0DqbzbYtXipzFlFMZtowbF1x7BKJwB9AayVMyFARvU8EDrZdcax4At/452cAg==}
     dev: true
 
-  /stylelint-config-html/1.1.0_kbto3rg3njmczth2rrsgfnlsqa:
+  /stylelint-config-html/1.1.0_5066edc4db6a582cccfa8c6462b57280:
     resolution: {integrity: sha512-IZv4IVESjKLumUGi+HWeb7skgO6/g4VMuAYrJdlqQFndgbj6WJAXPhaysvBiXefX79upBdQVumgYcdd17gCpjQ==}
     engines: {node: ^12 || >=14}
     peerDependencies:
@@ -7594,7 +7598,7 @@ packages:
     engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0}
     hasBin: true
     dependencies:
-      '@csstools/selector-specificity': 2.0.2_wajs5nedgkikc5pcuwett7legi
+      '@csstools/selector-specificity': 2.0.2_b0132eb4833290a175e2a58939fd6432
       balanced-match: 2.0.0
       colord: 2.9.3
       cosmiconfig: 7.1.0
@@ -7691,8 +7695,6 @@ packages:
       posthtml-svg-mode: 1.0.3
       query-string: 4.3.4
       traverse: 0.6.7
-    transitivePeerDependencies:
-      - supports-color
     dev: true
 
   /svg-tags/1.0.0:
@@ -7840,7 +7842,7 @@ packages:
     engines: {node: '>=8'}
     dev: true
 
-  /ts-node/10.9.1_qqdszkrtcshgbphghj7vnvrrby:
+  /ts-node/10.9.1_84072caa33148e60bce63a7f56d6310e:
     resolution: {integrity: sha512-NtVysVPkxxrwFGUUxGYhfux8k78pQB3JqYBXlLRZgdGUqTO5wU/UyHop5p70iEbGhB7q5KmiZiU0Y3KlJrScEw==}
     hasBin: true
     peerDependencies:
@@ -7936,6 +7938,7 @@ packages:
     resolution: {integrity: sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g==}
     engines: {node: '>=4.2.0'}
     hasBin: true
+    dev: true
 
   /ufo/1.0.1:
     resolution: {integrity: sha512-boAm74ubXHY7KJQZLlXrtMz52qFvpsbOxDcZOnw/Wf+LS4Mmyu7JxmzD4tDLtUQtmZECypJ0FrCz4QIe6dvKRA==}
@@ -8006,7 +8009,7 @@ packages:
     engines: {node: '>= 10.0.0'}
     dev: true
 
-  /unplugin-auto-import/0.13.0_z2glzmrjcar3r3i7v53oix2lwa:
+  /unplugin-auto-import/0.13.0_ce8cbcb2291023b8ed1faf76e45f4bb0:
     resolution: {integrity: sha512-nKMxDbkjM4FRPInFfm7sWrJOKgxfKKwb5yLPP+DEGl/SG0/FtBoW1LnZL4PQfx0FXjertoHO1P/5nDf+RSip2Q==}
     engines: {node: '>=14'}
     peerDependencies:
@@ -8159,7 +8162,7 @@ packages:
       chalk: 4.1.2
       debug: 4.3.4
       fs-extra: 10.1.0
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
     transitivePeerDependencies:
       - supports-color
     dev: true
@@ -8180,7 +8183,7 @@ packages:
       '@types/eslint': 8.4.10
       eslint: 8.33.0
       rollup: 2.79.1
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
     dev: true
 
   /vite-plugin-progress/0.0.6_vite@4.1.1:
@@ -8192,7 +8195,7 @@ packages:
       picocolors: 1.0.0
       progress: 2.0.3
       rd: 2.0.1
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
     dev: true
 
   /vite-plugin-purge-icons/0.9.2_vite@4.1.1:
@@ -8204,7 +8207,7 @@ packages:
       '@purge-icons/core': 0.9.1
       '@purge-icons/generated': 0.9.0
       rollup-plugin-purge-icons: 0.9.1
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
     transitivePeerDependencies:
       - encoding
       - supports-color
@@ -8223,7 +8226,7 @@ packages:
       pathe: 0.2.0
       svg-baker: 1.7.0
       svgo: 2.8.0
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
     transitivePeerDependencies:
       - supports-color
     dev: true
@@ -8235,7 +8238,7 @@ packages:
     dependencies:
       '@vue/compiler-sfc': 3.2.45
       magic-string: 0.25.9
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
     dev: true
 
   /vite-plugin-windicss/1.8.10_vite@4.1.1:
@@ -8246,13 +8249,13 @@ packages:
       '@windicss/plugin-utils': 1.8.10
       debug: 4.3.4
       kolorist: 1.6.0
-      vite: 4.1.1_sf2ihp5jwkcy5ypowegsyojpbq
+      vite: 4.1.1_917483bfa9b2858ee1eeb10d2c392f0c
       windicss: 3.5.6
     transitivePeerDependencies:
       - supports-color
     dev: true
 
-  /vite/4.1.1_sf2ihp5jwkcy5ypowegsyojpbq:
+  /vite/4.1.1_917483bfa9b2858ee1eeb10d2c392f0c:
     resolution: {integrity: sha512-LM9WWea8vsxhr782r9ntg+bhSFS06FJgCvvB0+8hf8UWtvaiDagKYWXndjfX6kGl74keHJUcpzrQliDXZlF5yg==}
     engines: {node: ^14.18.0 || >=16.0.0}
     hasBin: true
@@ -8301,6 +8304,7 @@ packages:
         optional: true
     dependencies:
       vue: 3.2.47
+    dev: false
 
   /vue-eslint-parser/9.1.0_eslint@8.33.0:
     resolution: {integrity: sha512-NGn/iQy8/Wb7RrRa4aRkokyCZfOUWk19OP5HP6JEozQFX5AoS/t+Z0ZN7FY4LlmWc4FNI922V7cvX28zctN8dQ==}
@@ -8331,6 +8335,7 @@ packages:
       '@intlify/vue-devtools': 9.2.2
       '@vue/devtools-api': 6.4.5
       vue: 3.2.47
+    dev: false
 
   /vue-router/4.1.6_vue@3.2.47:
     resolution: {integrity: sha512-DYWYwsG6xNPmLq/FmZn8Ip+qrhFEzA14EI12MsMgVxvHFDYvlr4NXpVF5hrRH1wVcDP8fGi5F4rxuJSl8/r+EQ==}
@@ -8380,6 +8385,7 @@ packages:
       '@vue/runtime-dom': 3.2.47
       '@vue/server-renderer': 3.2.47_vue@3.2.47
       '@vue/shared': 3.2.47
+    dev: false
 
   /vuedraggable/4.1.0_vue@3.2.47:
     resolution: {integrity: sha512-FU5HCWBmsf20GpP3eudURW3WdWTKIbEIQxh9/8GE806hydR9qZqRRxRE3RjqX7PkuLuMQG/A7n3cfj9rCEchww==}
diff --git a/yudao-ui-admin-vue3/src/views/report/goview/index.vue b/yudao-ui-admin-vue3/src/views/report/goview/index.vue
new file mode 100644
index 000000000..7267085e7
--- /dev/null
+++ b/yudao-ui-admin-vue3/src/views/report/goview/index.vue
@@ -0,0 +1,8 @@
+<template>
+  <ContentWrap>
+    <IFrame :src="src" />
+  </ContentWrap>
+</template>
+<script setup lang="ts" name="GoView">
+const src = 'http://127.0.0.1:3000'
+</script>
diff --git a/yudao-ui-admin-vue3/src/views/visualization/jmreport/index.vue b/yudao-ui-admin-vue3/src/views/report/jmreport/index.vue
similarity index 100%
rename from yudao-ui-admin-vue3/src/views/visualization/jmreport/index.vue
rename to yudao-ui-admin-vue3/src/views/report/jmreport/index.vue
diff --git a/yudao-ui-admin/src/views/report/goview/index.vue b/yudao-ui-admin/src/views/report/goview/index.vue
new file mode 100644
index 000000000..5cbce7ff0
--- /dev/null
+++ b/yudao-ui-admin/src/views/report/goview/index.vue
@@ -0,0 +1,18 @@
+<template>
+  <div>
+    <doc-alert title="大屏设计器" url="https://doc.iocoder.cn/report/screen/" />
+    <i-frame :src="url" />
+  </div>
+</template>
+<script>
+import iFrame from "@/components/iFrame/index";
+export default {
+  name: "GoView",
+  components: { iFrame },
+  data() {
+    return {
+      url: 'http://127.0.0.1:3000',
+    };
+  },
+};
+</script>
diff --git a/yudao-ui-admin/src/views/visualization/jmreport/index.vue b/yudao-ui-admin/src/views/report/jmreport/index.vue
similarity index 100%
rename from yudao-ui-admin/src/views/visualization/jmreport/index.vue
rename to yudao-ui-admin/src/views/report/jmreport/index.vue