diff --git a/server/api/v1/system/sys_dictionary.go b/server/api/v1/system/sys_dictionary.go
index 5e6ca79c3..65833dee4 100644
--- a/server/api/v1/system/sys_dictionary.go
+++ b/server/api/v1/system/sys_dictionary.go
@@ -135,3 +135,57 @@ func (s *DictionaryApi) GetSysDictionaryList(c *gin.Context) {
}
response.OkWithDetailed(list, "获取成功", c)
}
+
+// ExportSysDictionary
+// @Tags SysDictionary
+// @Summary 导出字典JSON(包含字典详情)
+// @Security ApiKeyAuth
+// @accept application/json
+// @Produce application/json
+// @Param data query system.SysDictionary true "字典ID"
+// @Success 200 {object} response.Response{data=map[string]interface{},msg=string} "导出字典JSON"
+// @Router /sysDictionary/exportSysDictionary [get]
+func (s *DictionaryApi) ExportSysDictionary(c *gin.Context) {
+ var dictionary system.SysDictionary
+ err := c.ShouldBindQuery(&dictionary)
+ if err != nil {
+ response.FailWithMessage(err.Error(), c)
+ return
+ }
+ if dictionary.ID == 0 {
+ response.FailWithMessage("字典ID不能为空", c)
+ return
+ }
+ exportData, err := dictionaryService.ExportSysDictionary(dictionary.ID)
+ if err != nil {
+ global.GVA_LOG.Error("导出失败!", zap.Error(err))
+ response.FailWithMessage("导出失败", c)
+ return
+ }
+ response.OkWithDetailed(exportData, "导出成功", c)
+}
+
+// ImportSysDictionary
+// @Tags SysDictionary
+// @Summary 导入字典JSON(包含字典详情)
+// @Security ApiKeyAuth
+// @accept application/json
+// @Produce application/json
+// @Param data body map[string]interface{} true "字典JSON数据"
+// @Success 200 {object} response.Response{msg=string} "导入字典"
+// @Router /sysDictionary/importSysDictionary [post]
+func (s *DictionaryApi) ImportSysDictionary(c *gin.Context) {
+ var importData map[string]interface{}
+ err := c.ShouldBindJSON(&importData)
+ if err != nil {
+ response.FailWithMessage(err.Error(), c)
+ return
+ }
+ err = dictionaryService.ImportSysDictionary(importData)
+ if err != nil {
+ global.GVA_LOG.Error("导入失败!", zap.Error(err))
+ response.FailWithMessage("导入失败: "+err.Error(), c)
+ return
+ }
+ response.OkWithMessage("导入成功", c)
+}
diff --git a/server/router/system/sys_dictionary.go b/server/router/system/sys_dictionary.go
index 41ce85ec9..c95e8ffdd 100644
--- a/server/router/system/sys_dictionary.go
+++ b/server/router/system/sys_dictionary.go
@@ -14,6 +14,8 @@ func (s *DictionaryRouter) InitSysDictionaryRouter(Router *gin.RouterGroup) {
sysDictionaryRouter.POST("createSysDictionary", dictionaryApi.CreateSysDictionary) // 新建SysDictionary
sysDictionaryRouter.DELETE("deleteSysDictionary", dictionaryApi.DeleteSysDictionary) // 删除SysDictionary
sysDictionaryRouter.PUT("updateSysDictionary", dictionaryApi.UpdateSysDictionary) // 更新SysDictionary
+ sysDictionaryRouter.POST("importSysDictionary", dictionaryApi.ImportSysDictionary) // 导入SysDictionary
+ sysDictionaryRouter.GET("exportSysDictionary", dictionaryApi.ExportSysDictionary) // 导出SysDictionary
}
{
sysDictionaryRouterWithoutRecord.GET("findSysDictionary", dictionaryApi.FindSysDictionary) // 根据ID获取SysDictionary
diff --git a/server/service/system/sys_dictionary.go b/server/service/system/sys_dictionary.go
index 10b2d264f..90750d847 100644
--- a/server/service/system/sys_dictionary.go
+++ b/server/service/system/sys_dictionary.go
@@ -152,3 +152,166 @@ func (dictionaryService *DictionaryService) checkCircularReference(currentID uin
return nil
}
+
+//@author: [yourname]
+//@function: ExportSysDictionary
+//@description: 导出字典JSON(包含字典详情)
+//@param: id uint
+//@return: exportData map[string]interface{}, err error
+
+func (dictionaryService *DictionaryService) ExportSysDictionary(id uint) (exportData map[string]interface{}, err error) {
+ var dictionary system.SysDictionary
+ // 查询字典及其所有详情
+ err = global.GVA_DB.Where("id = ?", id).Preload("SysDictionaryDetails", func(db *gorm.DB) *gorm.DB {
+ return db.Order("sort")
+ }).First(&dictionary).Error
+ if err != nil {
+ return nil, err
+ }
+
+ // 构造导出数据
+ exportData = map[string]interface{}{
+ "name": dictionary.Name,
+ "type": dictionary.Type,
+ "status": dictionary.Status,
+ "desc": dictionary.Desc,
+ "details": dictionary.SysDictionaryDetails,
+ }
+
+ return exportData, nil
+}
+
+//@author: [yourname]
+//@function: ImportSysDictionary
+//@description: 导入字典JSON(包含字典详情)
+//@param: importData map[string]interface{}
+//@return: err error
+
+func (dictionaryService *DictionaryService) ImportSysDictionary(importData map[string]interface{}) error {
+ // 解析基本字典信息
+ name, ok := importData["name"].(string)
+ if !ok || name == "" {
+ return errors.New("字典名称不能为空")
+ }
+
+ dictType, ok := importData["type"].(string)
+ if !ok || dictType == "" {
+ return errors.New("字典类型不能为空")
+ }
+
+ // 检查字典类型是否已存在
+ if !errors.Is(global.GVA_DB.First(&system.SysDictionary{}, "type = ?", dictType).Error, gorm.ErrRecordNotFound) {
+ return errors.New("存在相同的type,不允许导入")
+ }
+
+ // 创建字典
+ dictionary := system.SysDictionary{
+ Name: name,
+ Type: dictType,
+ }
+
+ // 处理status字段
+ if status, ok := importData["status"].(bool); ok {
+ dictionary.Status = &status
+ }
+
+ // 处理desc字段
+ if desc, ok := importData["desc"].(string); ok {
+ dictionary.Desc = desc
+ }
+
+ // 开启事务
+ return global.GVA_DB.Transaction(func(tx *gorm.DB) error {
+ // 创建字典
+ if err := tx.Create(&dictionary).Error; err != nil {
+ return err
+ }
+
+ // 处理字典详情
+ if details, ok := importData["details"].([]interface{}); ok && len(details) > 0 {
+ // 创建一个映射来跟踪旧ID到新ID的对应关系
+ idMap := make(map[uint]uint)
+
+ // 第一遍:创建所有详情记录(不设置parent_id)
+ for _, detail := range details {
+ detailMap, ok := detail.(map[string]interface{})
+ if !ok {
+ continue
+ }
+
+ label, _ := detailMap["label"].(string)
+ value, _ := detailMap["value"].(string)
+
+ if label == "" || value == "" {
+ continue
+ }
+
+ detailRecord := system.SysDictionaryDetail{
+ Label: label,
+ Value: value,
+ SysDictionaryID: int(dictionary.ID),
+ }
+
+ // 处理extend字段
+ if extend, ok := detailMap["extend"].(string); ok {
+ detailRecord.Extend = extend
+ }
+
+ // 处理status字段
+ if status, ok := detailMap["status"].(bool); ok {
+ detailRecord.Status = &status
+ }
+
+ // 处理sort字段
+ if sort, ok := detailMap["sort"].(float64); ok {
+ detailRecord.Sort = int(sort)
+ }
+
+ // 创建详情记录
+ if err := tx.Create(&detailRecord).Error; err != nil {
+ return err
+ }
+
+ // 记录ID映射(如果有原始ID)
+ if oldID, ok := detailMap["ID"].(float64); ok {
+ idMap[uint(oldID)] = detailRecord.ID
+ }
+ }
+
+ // 第二遍:更新parent_id关系
+ for i, detail := range details {
+ detailMap, ok := detail.(map[string]interface{})
+ if !ok {
+ continue
+ }
+
+ // 如果有parentID,更新它
+ if oldParentID, ok := detailMap["parentID"].(float64); ok && oldParentID > 0 {
+ if newParentID, exists := idMap[uint(oldParentID)]; exists {
+ // 获取新创建的记录ID(按顺序)
+ if oldID, ok := detailMap["ID"].(float64); ok {
+ if newID, exists := idMap[uint(oldID)]; exists {
+ if err := tx.Model(&system.SysDictionaryDetail{}).Where("id = ?", newID).Update("parent_id", newParentID).Error; err != nil {
+ return err
+ }
+ }
+ } else {
+ // 如果没有ID,使用索引来查找
+ var allDetails []system.SysDictionaryDetail
+ if err := tx.Where("sys_dictionary_id = ?", dictionary.ID).Order("id").Find(&allDetails).Error; err != nil {
+ return err
+ }
+ if i < len(allDetails) {
+ if err := tx.Model(&system.SysDictionaryDetail{}).Where("id = ?", allDetails[i].ID).Update("parent_id", newParentID).Error; err != nil {
+ return err
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+
+ return nil
+ })
+}
diff --git a/server/source/system/api.go b/server/source/system/api.go
index 9500ee865..863847bd4 100644
--- a/server/source/system/api.go
+++ b/server/source/system/api.go
@@ -149,6 +149,8 @@ func (i *initApi) InitializeData(ctx context.Context) (context.Context, error) {
{ApiGroup: "系统字典", Method: "PUT", Path: "/sysDictionary/updateSysDictionary", Description: "更新字典"},
{ApiGroup: "系统字典", Method: "GET", Path: "/sysDictionary/findSysDictionary", Description: "根据ID获取字典(建议选择)"},
{ApiGroup: "系统字典", Method: "GET", Path: "/sysDictionary/getSysDictionaryList", Description: "获取字典列表"},
+ {ApiGroup: "系统字典", Method: "POST", Path: "/sysDictionary/importSysDictionary", Description: "导入字典JSON"},
+ {ApiGroup: "系统字典", Method: "GET", Path: "/sysDictionary/exportSysDictionary", Description: "导出字典JSON"},
{ApiGroup: "操作记录", Method: "POST", Path: "/sysOperationRecord/createSysOperationRecord", Description: "新增操作记录"},
{ApiGroup: "操作记录", Method: "GET", Path: "/sysOperationRecord/findSysOperationRecord", Description: "根据ID获取操作记录"},
diff --git a/server/source/system/casbin.go b/server/source/system/casbin.go
index c63dfa1b7..a7e49d757 100644
--- a/server/source/system/casbin.go
+++ b/server/source/system/casbin.go
@@ -149,6 +149,8 @@ func (i *initCasbin) InitializeData(ctx context.Context) (context.Context, error
{Ptype: "p", V0: "888", V1: "/sysDictionary/getSysDictionaryList", V2: "GET"},
{Ptype: "p", V0: "888", V1: "/sysDictionary/createSysDictionary", V2: "POST"},
{Ptype: "p", V0: "888", V1: "/sysDictionary/deleteSysDictionary", V2: "DELETE"},
+ {Ptype: "p", V0: "888", V1: "/sysDictionary/importSysDictionary", V2: "POST"},
+ {Ptype: "p", V0: "888", V1: "/sysDictionary/exportSysDictionary", V2: "GET"},
{Ptype: "p", V0: "888", V1: "/sysOperationRecord/findSysOperationRecord", V2: "GET"},
{Ptype: "p", V0: "888", V1: "/sysOperationRecord/updateSysOperationRecord", V2: "PUT"},
diff --git a/web/src/api/sysDictionary.js b/web/src/api/sysDictionary.js
index f5d6c8620..90a2583e4 100644
--- a/web/src/api/sysDictionary.js
+++ b/web/src/api/sysDictionary.js
@@ -78,3 +78,35 @@ export const getSysDictionaryList = (params) => {
params
})
}
+
+// @Tags SysDictionary
+// @Summary 导出字典JSON(包含字典详情)
+// @Security ApiKeyAuth
+// @accept application/json
+// @Produce application/json
+// @Param data query model.SysDictionary true "字典ID"
+// @Success 200 {string} string "{"success":true,"data":{},"msg":"导出成功"}"
+// @Router /sysDictionary/exportSysDictionary [get]
+export const exportSysDictionary = (params) => {
+ return service({
+ url: '/sysDictionary/exportSysDictionary',
+ method: 'get',
+ params
+ })
+}
+
+// @Tags SysDictionary
+// @Summary 导入字典JSON(包含字典详情)
+// @Security ApiKeyAuth
+// @accept application/json
+// @Produce application/json
+// @Param data body object true "字典JSON数据"
+// @Success 200 {string} string "{"success":true,"data":{},"msg":"导入成功"}"
+// @Router /sysDictionary/importSysDictionary [post]
+export const importSysDictionary = (data) => {
+ return service({
+ url: '/sysDictionary/importSysDictionary',
+ method: 'post',
+ data
+ })
+}
diff --git a/web/src/view/superAdmin/dictionary/sysDictionary.vue b/web/src/view/superAdmin/dictionary/sysDictionary.vue
index 894e8a3c1..672150cba 100644
--- a/web/src/view/superAdmin/dictionary/sysDictionary.vue
+++ b/web/src/view/superAdmin/dictionary/sysDictionary.vue
@@ -35,6 +35,8 @@
:icon="Search"
@click="showSearchInputHandler"
>
+
{{ jsonPreviewFormatted }}
+