Explorar o código

初始化项目

LIJIAN hai 1 mes
pai
achega
e977bcfe00
Modificáronse 40 ficheiros con 867 adicións e 269 borrados
  1. 10 0
      .idea/.gitignore
  2. 21 0
      .idea/compiler.xml
  3. 9 0
      .idea/ema_project.iml
  4. 10 0
      .idea/encodings.xml
  5. 30 0
      .idea/jarRepositories.xml
  6. 12 0
      .idea/material_theme_project_new.xml
  7. 14 0
      .idea/misc.xml
  8. 6 0
      .idea/vcs.xml
  9. 1 1
      ema-admin/src/main/java/com/ema/admin/codegen/MybatisFlexCodegen.java
  10. 15 5
      ema-admin/src/main/java/com/ema/admin/handler/OperLoggerHandler.java
  11. 105 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/controller/AssetStatusHistoryController.java
  12. 106 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/controller/AssetsInfoController.java
  13. 119 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/entity/AssetStatusHistory.java
  14. 132 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/entity/AssetsInfo.java
  15. 14 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/mapper/AssetStatusHistoryMapper.java
  16. 14 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/mapper/AssetsInfoMapper.java
  17. 23 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/service/AssetStatusHistoryService.java
  18. 24 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/service/AssetsInfoService.java
  19. 27 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/service/impl/AssetStatusHistoryServiceImpl.java
  20. 34 0
      ema-admin/src/main/java/com/ema/admin/modules/assets/service/impl/AssetsInfoServiceImpl.java
  21. 4 1
      ema-admin/src/main/java/com/ema/admin/modules/system/controller/SysOperLogController.java
  22. 3 1
      ema-admin/src/main/java/com/ema/admin/modules/system/controller/SysUserController.java
  23. 1 1
      ema-admin/src/main/java/com/ema/admin/modules/system/converter/SysOperLogConverter.java
  24. 5 0
      ema-admin/src/main/java/com/ema/admin/modules/system/entity/SysOperLog.java
  25. 0 29
      ema-admin/src/main/java/com/ema/admin/modules/system/enums/SysOperLogEnum.java
  26. 7 1
      ema-admin/src/main/java/com/ema/admin/modules/system/service/impl/SysOperLogServiceImpl.java
  27. 1 1
      ema-admin/src/main/resources/web/css/login.css
  28. 10 0
      ema-admin/src/main/resources/web/js/config.js
  29. 15 42
      ema-admin/src/main/resources/web/pages/department/department_form.html
  30. 3 14
      ema-admin/src/main/resources/web/pages/department/department_list.html
  31. 1 1
      ema-admin/src/main/resources/web/pages/dict/dict_data_form.html
  32. 3 3
      ema-admin/src/main/resources/web/pages/dict/dict_data_list.html
  33. 19 19
      ema-admin/src/main/resources/web/pages/log/log_detail.html
  34. 11 14
      ema-admin/src/main/resources/web/pages/log/log_list.html
  35. 7 0
      ema-admin/src/main/resources/web/pages/menu/menu_form.html
  36. 6 11
      ema-admin/src/main/resources/web/pages/menu/menu_list.html
  37. 18 6
      ema-admin/src/main/resources/web/pages/user/user_form.html
  38. 22 3
      ema-admin/src/main/resources/web/pages/user/user_info.html
  39. 5 5
      ema-admin/src/main/resources/web/pages/user/user_list.html
  40. 0 111
      ema-web/README.md

+ 10 - 0
.idea/.gitignore

@@ -0,0 +1,10 @@
+# 默认忽略的文件
+/shelf/
+/workspace.xml
+# 基于编辑器的 HTTP 客户端请求
+/httpRequests/
+# 已忽略包含查询文件的默认文件夹
+/queries/
+# Datasource local storage ignored files
+/dataSources/
+/dataSources.local.xml

+ 21 - 0
.idea/compiler.xml

@@ -0,0 +1,21 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project version="4">
+  <component name="CompilerConfiguration">
+    <annotationProcessing>
+      <profile default="true" name="Default" enabled="true" />
+      <profile name="Maven default annotation processors profile" enabled="true">
+        <sourceOutputDir name="target/generated-sources/annotations" />
+        <sourceTestOutputDir name="target/generated-test-sources/test-annotations" />
+        <outputRelativeToContentRoot value="true" />
+        <module name="ema-common" />
+        <module name="ema-admin" />
+      </profile>
+    </annotationProcessing>
+  </component>
+  <component name="JavacSettings">
+    <option name="ADDITIONAL_OPTIONS_OVERRIDE">
+      <module name="ema-admin" options="-parameters" />
+      <module name="ema-common" options="-parameters" />
+    </option>
+  </component>
+</project>

+ 9 - 0
.idea/ema_project.iml

@@ -0,0 +1,9 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<module type="JAVA_MODULE" version="4">
+  <component name="NewModuleRootManager" inherit-compiler-output="true">
+    <exclude-output />
+    <content url="file://$MODULE_DIR$" />
+    <orderEntry type="inheritedJdk" />
+    <orderEntry type="sourceFolder" forTests="false" />
+  </component>
+</module>

+ 10 - 0
.idea/encodings.xml

@@ -0,0 +1,10 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project version="4">
+  <component name="Encoding">
+    <file url="file://$PROJECT_DIR$/ema-admin/src/main/java" charset="UTF-8" />
+    <file url="file://$PROJECT_DIR$/ema-admin/src/main/resources" charset="UTF-8" />
+    <file url="file://$PROJECT_DIR$/ema-common/src/main/java" charset="UTF-8" />
+    <file url="file://$PROJECT_DIR$/src/main/java" charset="UTF-8" />
+    <file url="file://$PROJECT_DIR$/src/main/resources" charset="UTF-8" />
+  </component>
+</project>

+ 30 - 0
.idea/jarRepositories.xml

@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project version="4">
+  <component name="RemoteRepositoriesConfiguration">
+    <remote-repository>
+      <option name="id" value="spring-snapshot" />
+      <option name="name" value="Spring Snapshot Repository" />
+      <option name="url" value="https://maven.aliyun.com/repository/public" />
+    </remote-repository>
+    <remote-repository>
+      <option name="id" value="central" />
+      <option name="name" value="Maven Central repository" />
+      <option name="url" value="https://repo1.maven.org/maven2" />
+    </remote-repository>
+    <remote-repository>
+      <option name="id" value="jboss.community" />
+      <option name="name" value="JBoss Community repository" />
+      <option name="url" value="https://repository.jboss.org/nexus/content/repositories/public/" />
+    </remote-repository>
+    <remote-repository>
+      <option name="id" value="central" />
+      <option name="name" value="Central Repository" />
+      <option name="url" value="https://maven.aliyun.com/repository/public" />
+    </remote-repository>
+    <remote-repository>
+      <option name="id" value="spring-milestone" />
+      <option name="name" value="Spring Milestone Repository" />
+      <option name="url" value="https://maven.aliyun.com/repository/public" />
+    </remote-repository>
+  </component>
+</project>

+ 12 - 0
.idea/material_theme_project_new.xml

@@ -0,0 +1,12 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project version="4">
+  <component name="MaterialThemeProjectNewConfig">
+    <option name="metadata">
+      <MTProjectMetadataState>
+        <option name="migrated" value="true" />
+        <option name="pristineConfig" value="false" />
+        <option name="userId" value="-6058a98e:19c4175be21:-7ffe" />
+      </MTProjectMetadataState>
+    </option>
+  </component>
+</project>

+ 14 - 0
.idea/misc.xml

@@ -0,0 +1,14 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project version="4">
+  <component name="ExternalStorageConfigurationManager" enabled="true" />
+  <component name="MavenProjectsManager">
+    <option name="originalFiles">
+      <list>
+        <option value="$PROJECT_DIR$/pom.xml" />
+      </list>
+    </option>
+  </component>
+  <component name="ProjectRootManager" version="2" languageLevel="JDK_21" default="true" project-jdk-name="ms-21" project-jdk-type="JavaSDK">
+    <output url="file://$PROJECT_DIR$/out" />
+  </component>
+</project>

+ 6 - 0
.idea/vcs.xml

@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project version="4">
+  <component name="VcsDirectoryMappings">
+    <mapping directory="" vcs="Git" />
+  </component>
+</project>

+ 1 - 1
ema-admin/src/main/java/com/ema/admin/codegen/MybatisFlexCodegen.java

@@ -17,7 +17,7 @@ public class MybatisFlexCodegen {
         public static void main(String[] args) {
             //配置数据源
             HikariDataSource dataSource = new HikariDataSource();
-            dataSource.setJdbcUrl("jdbc:mysql://172.16.0.212:3306/ema_project?useUnicode=true&characterEncoding=UTF-8&&serverTimezone=GMT%2B8&allowMultiQueries=true&nullCatalogMeansCurrent=true");
+            dataSource.setJdbcUrl("jdbc:mysql://172.16.0.212:3306/ema_projet?useUnicode=true&characterEncoding=UTF-8&&serverTimezone=GMT%2B8&allowMultiQueries=true&nullCatalogMeansCurrent=true");
             dataSource.setUsername("root");
             dataSource.setPassword("Xcsz@2024");
             String module = "assets";

+ 15 - 5
ema-admin/src/main/java/com/ema/admin/handler/OperLoggerHandler.java

@@ -2,7 +2,9 @@ package com.ema.admin.handler;
 
 import cn.dev33.satoken.stp.StpUtil;
 import com.ema.admin.modules.system.converter.SysOperLogConverter;
+import com.ema.admin.modules.system.service.SysAuthService;
 import com.ema.admin.modules.system.service.SysOperLogService;
+import com.ema.admin.modules.system.vo.SysUserVo;
 import com.ema.common.aspect.logger.LoggerHandler;
 import com.ema.common.aspect.logger.LoggerVo;
 import com.ema.common.consts.CommonConst;
@@ -11,6 +13,7 @@ import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
 import org.springframework.stereotype.Component;
 
 import javax.annotation.Resource;
+
 /**
  * 操作日志处理器
  */
@@ -21,7 +24,8 @@ public class OperLoggerHandler implements LoggerHandler {
 
     @Resource(name = CommonConst.ASYNC_POOL)
     private ThreadPoolTaskExecutor threadPoolExecutor;
-
+    @Resource
+    private SysAuthService sysAuthService;
     @Resource
     private SysOperLogService sysOperLogService;
     @Resource
@@ -29,9 +33,15 @@ public class OperLoggerHandler implements LoggerHandler {
 
     @Override
     public void handler(LoggerVo loggerVo) {
-        String userId = StpUtil.isLogin() ? StpUtil.getLoginIdAsString() : null;
-        threadPoolExecutor.execute(() -> {
-            sysOperLogService.save(sysOperLogConverter.toSysOperLog(userId, loggerVo));
-        });
+        if (StpUtil.isLogin()) {
+            SysUserVo userVo = sysAuthService.getCurrentUser();
+            threadPoolExecutor.execute(() -> {
+                sysOperLogService.save(sysOperLogConverter.toSysOperLog(userVo.getId(), userVo.getName(), loggerVo));
+            });
+        } else {
+            threadPoolExecutor.execute(() -> {
+                sysOperLogService.save(sysOperLogConverter.toSysOperLog(null, null, loggerVo));
+            });
+        }
     }
 }

+ 105 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/controller/AssetStatusHistoryController.java

@@ -0,0 +1,105 @@
+package com.ema.admin.modules.assets.controller;
+
+import com.mybatisflex.core.paginate.Page;
+import org.springframework.web.bind.annotation.DeleteMapping;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.PathVariable;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.PutMapping;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.beans.factory.annotation.Autowired;
+import com.ema.admin.modules.assets.entity.AssetStatusHistory;
+import com.ema.admin.modules.assets.service.AssetStatusHistoryService;
+import org.springframework.web.bind.annotation.RestController;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import io.swagger.annotations.ApiParam;
+import java.util.List;
+
+/**
+ *  资产状态历史表控制层。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+@RestController
+@Api("资产状态历史表接口")
+@RequestMapping("/assetStatusHistory")
+public class AssetStatusHistoryController {
+
+    @Autowired
+    private AssetStatusHistoryService assetStatusHistoryService;
+
+    /**
+     * 添加。
+     *
+     * @param assetStatusHistory 
+     * @return {@code true} 添加成功,{@code false} 添加失败
+     */
+    @PostMapping("save")
+    @ApiOperation("保存")
+    public boolean save(@RequestBody @ApiParam("") AssetStatusHistory assetStatusHistory) {
+        return assetStatusHistoryService.save(assetStatusHistory);
+    }
+
+    /**
+     * 根据主键删除。
+     *
+     * @param id 主键
+     * @return {@code true} 删除成功,{@code false} 删除失败
+     */
+    @DeleteMapping("remove/{id}")
+    @ApiOperation("根据主键")
+    public boolean remove(@PathVariable @ApiParam("主键") String id) {
+        return assetStatusHistoryService.removeById(id);
+    }
+
+    /**
+     * 根据主键更新。
+     *
+     * @param assetStatusHistory 
+     * @return {@code true} 更新成功,{@code false} 更新失败
+     */
+    @PutMapping("update")
+    @ApiOperation("根据主键更新")
+    public boolean update(@RequestBody @ApiParam("主键") AssetStatusHistory assetStatusHistory) {
+        return assetStatusHistoryService.updateById(assetStatusHistory);
+    }
+
+    /**
+     * 查询所有。
+     *
+     * @return 所有数据
+     */
+    @GetMapping("list")
+    @ApiOperation("查询所有")
+    public List<AssetStatusHistory> list() {
+        return assetStatusHistoryService.list();
+    }
+
+    /**
+     * 根据资产ID查询历史记录。
+     *
+     * @param assetId 资产ID
+     * @return 历史记录列表
+     */
+    @GetMapping("listByAssetId/{assetId}")
+    @ApiOperation("根据资产ID查询历史记录")
+    public List<AssetStatusHistory> listByAssetId(@PathVariable @ApiParam("资产ID") String assetId) {
+        return assetStatusHistoryService.listByAssetId(assetId);
+    }
+
+    /**
+     * 根据主键获取详细信息。
+     *
+     * @param id 主键
+     * @return 详情
+     */
+    @GetMapping("getInfo/{id}")
+    @ApiOperation("根据主键获取")
+    public AssetStatusHistory getInfo(@PathVariable @ApiParam("主键") String id) {
+        return assetStatusHistoryService.getById(id);
+    }
+
+}

+ 106 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/controller/AssetsInfoController.java

@@ -0,0 +1,106 @@
+package com.ema.admin.modules.assets.controller;
+
+import com.mybatisflex.core.paginate.Page;
+import org.springframework.web.bind.annotation.DeleteMapping;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.PathVariable;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.PutMapping;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.beans.factory.annotation.Autowired;
+import com.ema.admin.modules.assets.entity.AssetsInfo;
+import com.ema.admin.modules.assets.vo.AssetsInfoQueryVo;
+import com.ema.admin.modules.assets.service.AssetsInfoService;
+import org.springframework.web.bind.annotation.RestController;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import io.swagger.annotations.ApiParam;
+import java.util.List;
+
+/**
+ *  资产信息表 控制层。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+@RestController
+@Api("资产信息表接口")
+@RequestMapping("/assetsInfo")
+public class AssetsInfoController {
+
+    @Autowired
+    private AssetsInfoService assetsInfoService;
+
+    /**
+     * 添加。
+     *
+     * @param assetsInfo 
+     * @return {@code true} 添加成功,{@code false} 添加失败
+     */
+    @PostMapping("save")
+    @ApiOperation("保存")
+    public boolean save(@RequestBody @ApiParam("") AssetsInfo assetsInfo) {
+        return assetsInfoService.save(assetsInfo);
+    }
+
+    /**
+     * 根据主键删除。
+     *
+     * @param id 主键
+     * @return {@code true} 删除成功,{@code false} 删除失败
+     */
+    @DeleteMapping("remove/{id}")
+    @ApiOperation("根据主键")
+    public boolean remove(@PathVariable @ApiParam("主键") String id) {
+        return assetsInfoService.removeById(id);
+    }
+
+    /**
+     * 根据主键更新。
+     *
+     * @param assetsInfo 
+     * @return {@code true} 更新成功,{@code false} 更新失败
+     */
+    @PutMapping("update")
+    @ApiOperation("根据主键更新")
+    public boolean update(@RequestBody @ApiParam("主键") AssetsInfo assetsInfo) {
+        return assetsInfoService.updateById(assetsInfo);
+    }
+
+    /**
+     * 查询所有。
+     *
+     * @return 所有数据
+     */
+    @GetMapping("list")
+    @ApiOperation("查询所有")
+    public List<AssetsInfo> list() {
+        return assetsInfoService.list();
+    }
+
+    /**
+     * 根据主键获取详细信息。
+     *
+     * @param id 主键
+     * @return 详情
+     */
+    @GetMapping("getInfo/{id}")
+    @ApiOperation("根据主键获取")
+    public AssetsInfo getInfo(@PathVariable @ApiParam("主键") String id) {
+        return assetsInfoService.getById(id);
+    }
+
+    /**
+     * 分页查询(带查询条件)。
+     *
+     * @param queryVo 查询条件
+     * @return 分页对象
+     */
+    @PostMapping("page")
+    @ApiOperation("分页查询")
+    public Page<AssetsInfo> page(@RequestBody @ApiParam("查询条件") AssetsInfoQueryVo queryVo) {
+        return assetsInfoService.page(queryVo);
+    }
+
+}

+ 119 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/entity/AssetStatusHistory.java

@@ -0,0 +1,119 @@
+package com.ema.admin.modules.assets.entity;
+
+import com.ema.common.domain.base.BaseEntity;
+import com.mybatisflex.annotation.Id;
+import com.mybatisflex.annotation.KeyType;
+import com.mybatisflex.annotation.Table;
+import java.io.Serializable;
+import java.sql.Date;
+import java.time.LocalDateTime;
+
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.AllArgsConstructor;
+import lombok.Builder;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+import lombok.EqualsAndHashCode;
+
+/**
+ *  资产状态历史表实体类。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+@Data
+@Builder
+@NoArgsConstructor
+@AllArgsConstructor
+@EqualsAndHashCode(callSuper = true)
+@ApiModel("资产状态历史表")
+@Table("asset_status_history")
+public class AssetStatusHistory extends BaseEntity implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * 主键
+     */
+    @Id(keyType = KeyType.Generator, value = "snowFlakeId")
+    @ApiModelProperty("主键")
+    private String id;
+
+    /**
+     * 资产信息id
+     */
+    @ApiModelProperty("资产信息id")
+    private String assetId;
+
+    /**
+     * 使用公司
+     */
+    @ApiModelProperty("使用公司")
+    private String useCompany;
+
+    /**
+     * 使用部门
+     */
+    @ApiModelProperty("使用部门")
+    private String useDept;
+
+    /**
+     * 使用人
+     */
+    @ApiModelProperty("使用人")
+    private String useUser;
+
+    /**
+     * 使用状态 在库、正常使用、已转移、报废中、维修中等
+     */
+    @ApiModelProperty("使用状态 在库、正常使用、已转移、报废中、维修中等")
+    private String useStatus;
+
+    /**
+     * 当前位置
+     */
+    @ApiModelProperty("当前位置")
+    private String curLocation;
+
+    /**
+     * 生效开始日期
+     */
+    @ApiModelProperty("生效开始日期")
+    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
+    private Date startDate;
+
+    /**
+     * 生效结束日期(当前有效为4712-12-31)
+     */
+    @ApiModelProperty("生效结束日期(当前有效为4712-12-31)")
+    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
+    private Date endDate;
+
+    /**
+     * 操作人
+     */
+    @ApiModelProperty("操作人")
+    private String operatorName;
+
+    /**
+     * 操作时间
+     */
+    @ApiModelProperty("操作时间")
+    private LocalDateTime operatorDate;
+
+    /**
+     * 协管员
+     */
+    @ApiModelProperty("协管员")
+    private String assistantName;
+
+    /**
+     * 备注
+     */
+    @ApiModelProperty("备注")
+    private String remark;
+
+}

+ 132 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/entity/AssetsInfo.java

@@ -0,0 +1,132 @@
+package com.ema.admin.modules.assets.entity;
+
+import com.ema.common.domain.base.BaseEntity;
+import com.mybatisflex.annotation.Id;
+import com.mybatisflex.annotation.KeyType;
+import com.mybatisflex.annotation.Table;
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.sql.Date;
+import java.time.LocalDateTime;
+
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.AllArgsConstructor;
+import lombok.Builder;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+import lombok.EqualsAndHashCode;
+
+/**
+ *  资产信息表 实体类。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+@Data
+@Builder
+@NoArgsConstructor
+@AllArgsConstructor
+@EqualsAndHashCode(callSuper = true)
+@ApiModel("资产信息表")
+@Table("assets_info")
+public class AssetsInfo extends BaseEntity implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * 主键
+     */
+    @Id(keyType = KeyType.Generator, value = "snowFlakeId")
+    @ApiModelProperty("主键")
+    private String id;
+
+    /**
+     * 资产管理部门
+     */
+    @ApiModelProperty("资产管理部门")
+    private String deptName;
+
+    /**
+     * 资产编码
+     */
+    @ApiModelProperty("资产编码")
+    private String assetCode;
+
+    /**
+     * 资产类型
+     */
+    @ApiModelProperty("资产类型")
+    private String assetType;
+
+    /**
+     * 品牌
+     */
+    @ApiModelProperty("品牌")
+    private String brand;
+
+    /**
+     * 型号
+     */
+    @ApiModelProperty("型号")
+    private String model;
+
+    /**
+     * 购买日期
+     */
+    @ApiModelProperty("购买日期")
+    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
+    private Date purchaseDate;
+
+    /**
+     * 采购价值(元)
+     */
+    @ApiModelProperty("采购价值(元)")
+    private BigDecimal purchaseValue;
+
+    /**
+     * 盘点状态
+     */
+    @ApiModelProperty("盘点状态")
+    private String invstkStatus;
+
+    /**
+     * 最后一次盘点时间
+     */
+    @ApiModelProperty("最后一次盘点时间")
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
+    private LocalDateTime lastInvstkTime;
+
+    /**
+     * 扩展字段1
+     */
+    @ApiModelProperty("扩展字段1")
+    private String attribute1;
+
+    /**
+     * 扩展字段2
+     */
+    @ApiModelProperty("扩展字段2")
+    private String attribute2;
+
+    /**
+     * 扩展字段3
+     */
+    @ApiModelProperty("扩展字段3")
+    private String attribute3;
+
+    /**
+     * 扩展字段4
+     */
+    @ApiModelProperty("扩展字段4")
+    private String attribute4;
+
+    /**
+     * 备注
+     */
+    @ApiModelProperty("备注")
+    private String remark;
+
+}

+ 14 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/mapper/AssetStatusHistoryMapper.java

@@ -0,0 +1,14 @@
+package com.ema.admin.modules.assets.mapper;
+
+import com.mybatisflex.core.BaseMapper;
+import com.ema.admin.modules.assets.entity.AssetStatusHistory;
+
+/**
+ *  资产状态历史表映射层。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+public interface AssetStatusHistoryMapper extends BaseMapper<AssetStatusHistory> {
+
+}

+ 14 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/mapper/AssetsInfoMapper.java

@@ -0,0 +1,14 @@
+package com.ema.admin.modules.assets.mapper;
+
+import com.mybatisflex.core.BaseMapper;
+import com.ema.admin.modules.assets.entity.AssetsInfo;
+
+/**
+ *  资产信息表 映射层。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+public interface AssetsInfoMapper extends BaseMapper<AssetsInfo> {
+
+}

+ 23 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/service/AssetStatusHistoryService.java

@@ -0,0 +1,23 @@
+package com.ema.admin.modules.assets.service;
+
+import com.mybatisflex.core.service.IService;
+import com.ema.admin.modules.assets.entity.AssetStatusHistory;
+import java.util.List;
+
+/**
+ *  资产状态历史表服务层。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+public interface AssetStatusHistoryService extends IService<AssetStatusHistory> {
+
+    /**
+     * 根据资产ID查询历史记录
+     *
+     * @param assetId 资产ID
+     * @return 历史记录列表
+     */
+    List<AssetStatusHistory> listByAssetId(String assetId);
+
+}

+ 24 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/service/AssetsInfoService.java

@@ -0,0 +1,24 @@
+package com.ema.admin.modules.assets.service;
+
+import com.mybatisflex.core.paginate.Page;
+import com.mybatisflex.core.service.IService;
+import com.ema.admin.modules.assets.entity.AssetsInfo;
+import com.ema.admin.modules.assets.vo.AssetsInfoQueryVo;
+
+/**
+ *  资产信息表 服务层。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+public interface AssetsInfoService extends IService<AssetsInfo> {
+
+    /**
+     * 分页查询(带查询条件)
+     *
+     * @param queryVo 查询条件
+     * @return 分页对象
+     */
+    Page<AssetsInfo> page(AssetsInfoQueryVo queryVo);
+
+}

+ 27 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/service/impl/AssetStatusHistoryServiceImpl.java

@@ -0,0 +1,27 @@
+package com.ema.admin.modules.assets.service.impl;
+
+import com.mybatisflex.core.query.QueryWrapper;
+import com.mybatisflex.spring.service.impl.ServiceImpl;
+import com.ema.admin.modules.assets.entity.AssetStatusHistory;
+import com.ema.admin.modules.assets.mapper.AssetStatusHistoryMapper;
+import com.ema.admin.modules.assets.service.AssetStatusHistoryService;
+import org.springframework.stereotype.Service;
+import java.util.List;
+
+/**
+ *  资产状态历史表服务层实现。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+@Service
+public class AssetStatusHistoryServiceImpl extends ServiceImpl<AssetStatusHistoryMapper, AssetStatusHistory> implements AssetStatusHistoryService {
+
+    @Override
+    public List<AssetStatusHistory> listByAssetId(String assetId) {
+        QueryWrapper queryWrapper = QueryWrapper.create()
+                .eq(AssetStatusHistory::getAssetId, assetId)
+                .orderBy(AssetStatusHistory::getOperatorDate, false);
+        return list(queryWrapper);
+    }
+}

+ 34 - 0
ema-admin/src/main/java/com/ema/admin/modules/assets/service/impl/AssetsInfoServiceImpl.java

@@ -0,0 +1,34 @@
+package com.ema.admin.modules.assets.service.impl;
+
+import cn.hutool.core.util.StrUtil;
+import com.ema.admin.modules.assets.entity.AssetsInfo;
+import com.ema.admin.modules.assets.vo.AssetsInfoQueryVo;
+import com.ema.admin.modules.assets.mapper.AssetsInfoMapper;
+import com.ema.admin.modules.assets.service.AssetsInfoService;
+import com.mybatisflex.core.paginate.Page;
+import com.mybatisflex.core.query.QueryWrapper;
+import com.mybatisflex.spring.service.impl.ServiceImpl;
+import org.springframework.stereotype.Service;
+
+/**
+ *  资产信息表 服务层实现。
+ *
+ * @author LIJIAN
+ * @since 2026-05-13
+ */
+@Service
+public class AssetsInfoServiceImpl extends ServiceImpl<AssetsInfoMapper, AssetsInfo> implements AssetsInfoService {
+
+    @Override
+    public Page<AssetsInfo> page(AssetsInfoQueryVo queryVo) {
+        QueryWrapper queryWrapper = QueryWrapper.create();
+        queryWrapper.like(AssetsInfo::getDeptName, queryVo.getDeptName(), StrUtil.isNotBlank(queryVo.getDeptName()));
+        queryWrapper.like(AssetsInfo::getAssetCode, queryVo.getAssetCode(), StrUtil.isNotBlank(queryVo.getAssetCode()));
+        queryWrapper.eq(AssetsInfo::getAssetType, queryVo.getAssetType(), StrUtil.isNotBlank(queryVo.getAssetType()));
+        queryWrapper.like(AssetsInfo::getBrand, queryVo.getBrand(), StrUtil.isNotBlank(queryVo.getBrand()));
+        queryWrapper.like(AssetsInfo::getModel, queryVo.getModel(), StrUtil.isNotBlank(queryVo.getModel()));
+        queryWrapper.eq(AssetsInfo::getInvstkStatus, queryVo.getInvstkStatus(), StrUtil.isNotBlank(queryVo.getInvstkStatus()));
+        queryWrapper.orderBy(AssetsInfo::getCreateTime, false);
+        return this.page(new Page<>(queryVo.getPageNumber(), queryVo.getPageSize()), queryWrapper);
+    }
+}

+ 4 - 1
ema-admin/src/main/java/com/ema/admin/modules/system/controller/SysOperLogController.java

@@ -1,5 +1,6 @@
 package com.ema.admin.modules.system.controller;
 
+import com.ema.common.aspect.logger.LogTypeEnum;
 import com.mybatisflex.core.paginate.Page;
 import com.ema.admin.modules.system.entity.SysOperLog;
 import com.ema.admin.modules.system.entity.SysOperLogQueryVo;
@@ -33,7 +34,9 @@ public class SysOperLogController {
     @GetMapping("getInfo/{id}")
     @ApiOperation("根据主键获取操作日志记录")
     public SysOperLog getInfo(@PathVariable @ApiParam("操作日志记录主键") String id) {
-        return sysOperLogService.getById(id);
+        SysOperLog operLog = sysOperLogService.getById(id);
+        operLog.setType(LogTypeEnum.getDescribe(operLog.getType()));
+        return operLog;
     }
 
     /**

+ 3 - 1
ema-admin/src/main/java/com/ema/admin/modules/system/controller/SysUserController.java

@@ -83,7 +83,9 @@ public class SysUserController {
         if(StrUtil.isNotBlank(sysUser.getPassword())){
             sysUser.setPassword(SaSecureUtil.md5(sysUser.getPassword()));
         }
-        sysUserService.assignRolesToUser(sysUser.getId(),sysUser.getRoleIds());
+        if(CollUtil.isNotEmpty(sysUser.getRoleIds())){
+            sysUserService.assignRolesToUser(sysUser.getId(),sysUser.getRoleIds());
+        }
         return sysUserService.updateById(sysUserConverter.toSysUser(sysUser));
     }
 

+ 1 - 1
ema-admin/src/main/java/com/ema/admin/modules/system/converter/SysOperLogConverter.java

@@ -7,5 +7,5 @@ import org.mapstruct.Mapper;
 
 @Mapper(componentModel = "spring", uses = MyMapStructMapper.class)
 public interface SysOperLogConverter {
-    SysOperLog toSysOperLog(String userId, LoggerVo loggerVo);
+    SysOperLog toSysOperLog(String userId, String userName, LoggerVo loggerVo);
 }

+ 5 - 0
ema-admin/src/main/java/com/ema/admin/modules/system/entity/SysOperLog.java

@@ -97,6 +97,11 @@ public class SysOperLog implements Serializable {
      */
     @ApiModelProperty("用户ID")
     private String userId;
+    /**
+     * 用户名称
+     */
+    @ApiModelProperty("用户名称")
+    private String userName;
 
     /**
      * 请求IP

+ 0 - 29
ema-admin/src/main/java/com/ema/admin/modules/system/enums/SysOperLogEnum.java

@@ -1,29 +0,0 @@
-package com.ema.admin.modules.system.enums;
-
-import lombok.Data;
-
-@Data
-public class SysOperLogEnum {
-    /**
-     * 日志类型枚举
-     */
-    public enum Type {
-
-        LOGIN("1","登录日志"),
-        OPER("1","操作日志"),
-        ;
-        private String value;
-        private String describe;
-
-        Type(String describe, String value) {
-            this.describe = describe;
-            this.value = value;
-        }
-        public String getValue() {
-            return value;
-        }
-        public String getDescribe() {
-            return describe;
-        }
-    }
-}

+ 7 - 1
ema-admin/src/main/java/com/ema/admin/modules/system/service/impl/SysOperLogServiceImpl.java

@@ -1,6 +1,7 @@
 package com.ema.admin.modules.system.service.impl;
 
 import cn.hutool.core.util.StrUtil;
+import com.ema.common.aspect.logger.LogTypeEnum;
 import com.mybatisflex.core.paginate.Page;
 import com.mybatisflex.core.query.QueryWrapper;
 import com.mybatisflex.spring.service.impl.ServiceImpl;
@@ -30,6 +31,11 @@ public class SysOperLogServiceImpl extends ServiceImpl<SysOperLogMapper, SysOper
         queryWrapper.eq(SysOperLog::getStatus, queryVo.getStatus(), StrUtil.isNotBlank(queryVo.getStatus()));
         queryWrapper.eq(SysOperLog::getUserId, queryVo.getUserId(), StrUtil.isNotBlank(queryVo.getUserId()));
         queryWrapper.orderBy(SysOperLog::getOperTime, false);
-        return this.page(new Page<>(queryVo.getPageNumber(), queryVo.getPageSize()), queryWrapper);
+        Page<SysOperLog> page = this.page(new Page<>(queryVo.getPageNumber(), queryVo.getPageSize()), queryWrapper);
+        page.getRecords().forEach(operLog -> {
+            operLog.setUserName(operLog.getUserName());
+            operLog.setType(LogTypeEnum.getDescribe(operLog.getType()));
+        });
+        return page;
     }
 }

+ 1 - 1
ema-admin/src/main/resources/web/css/login.css

@@ -77,7 +77,7 @@ body {
 }
 
 .captcha-img {
-    height: 40px;
+    height: 47px;
     width: 100%;
     border-radius: 4px;
     cursor: pointer;

+ 10 - 0
ema-admin/src/main/resources/web/js/config.js

@@ -105,6 +105,16 @@ var Config = {
             getInfo: '/sysTimersJob/getInfo',
             stop: '/sysTimersJob/stop',
             start: '/sysTimersJob/start'
+        },
+
+        // 资产管理
+        assets: {
+            list: '/assetsInfo/list',
+            page: '/assetsInfo/page',
+            save: '/assetsInfo/save',
+            update: '/assetsInfo/update',
+            remove: '/assetsInfo/remove',
+            getInfo: '/assetsInfo/getInfo'
         }
     },
 

+ 15 - 42
ema-admin/src/main/resources/web/pages/department/department_form.html

@@ -17,7 +17,7 @@
         <div class="layui-form-item">
             <label class="layui-form-label"><span class="required">*</span>部门名称</label>
             <div class="layui-input-block">
-                <input type="text" name="departmentName" lay-verify="required" placeholder="请输入部门名称" class="layui-input" style="width: 300px;">
+                <input type="text" name="deptName" lay-verify="required" placeholder="请输入部门名称" class="layui-input" style="width: 300px;">
             </div>
         </div>
         
@@ -33,21 +33,7 @@
         <div class="layui-form-item">
             <label class="layui-form-label">部门编码</label>
             <div class="layui-input-block">
-                <input type="text" name="departmentCode" placeholder="请输入部门编码" class="layui-input" style="width: 200px;">
-            </div>
-        </div>
-        
-        <div class="layui-form-item">
-            <label class="layui-form-label">负责人</label>
-            <div class="layui-input-block">
-                <input type="text" name="leader" placeholder="请输入负责人" class="layui-input" style="width: 200px;">
-            </div>
-        </div>
-        
-        <div class="layui-form-item">
-            <label class="layui-form-label">联系电话</label>
-            <div class="layui-input-block">
-                <input type="text" name="phone" placeholder="请输入联系电话" class="layui-input" style="width: 200px;">
+                <input type="text" name="deptCode" placeholder="请输入部门编码" class="layui-input" style="width: 200px;">
             </div>
         </div>
         
@@ -58,21 +44,6 @@
             </div>
         </div>
         
-        <div class="layui-form-item">
-            <label class="layui-form-label">状态</label>
-            <div class="layui-input-block">
-                <input type="radio" name="status" value="1" title="正常" checked>
-                <input type="radio" name="status" value="0" title="停用">
-            </div>
-        </div>
-        
-        <div class="layui-form-item">
-            <label class="layui-form-label">备注</label>
-            <div class="layui-input-block">
-                <textarea name="remark" placeholder="请输入备注" class="layui-textarea" style="width: 350px; height: 80px;"></textarea>
-            </div>
-        </div>
-        
         <div class="layui-form-item">
             <div class="layui-input-block">
                 <button type="submit" class="layui-btn" lay-submit lay-filter="submitForm">提交</button>
@@ -92,28 +63,30 @@
             var id = Common.getQueryString('id');
             var isEdit = !!id;
             
-            loadDeptTree();
-            
-            if (isEdit) {
-                Common.get(Config.api.department.getInfo + '/' + id, function(res) {
-                    if (res.code === 200) {
-                        form.val('deptForm', res.data);
-                    }
-                });
-            }
+            loadDeptTree(function() {
+                if (isEdit) {
+                    Common.get(Config.api.department.getInfo + '/' + id, function(res) {
+                        if (res.code === 200) {
+                            form.val('deptForm', res.data);
+                            form.render('select');
+                        }
+                    });
+                }
+            });
             
-            function loadDeptTree() {
+            function loadDeptTree(callback) {
                 Common.get(Config.api.department.tree, function(res) {
                     if (res.code === 200) {
                         var depts = res.data || [];
                         var html = '<option value="0">顶级部门</option>';
                         depts.forEach(function(dept) {
                             if (dept.id !== id) {
-                                html += '<option value="' + dept.id + '">' + dept.departmentName + '</option>';
+                                html += '<option value="' + dept.id + '">' + dept.deptName + '</option>';
                             }
                         });
                         $('#parentSelect').html(html);
                         form.render('select');
+                        if (callback) callback();
                     }
                 });
             }

+ 3 - 14
ema-admin/src/main/resources/web/pages/department/department_list.html

@@ -23,14 +23,6 @@
         <a class="layui-btn layui-btn-danger layui-btn-xs" lay-event="del"><i class="layui-icon layui-icon-delete"></i> 删除</a>
     </script>
     
-    <script type="text/html" id="statusTpl">
-        {{# if(d.status === '1') { }}
-            <span class="status-green"><i class="layui-icon layui-icon-ok-circle"></i> 正常</span>
-        {{# } else { }}
-            <span class="status-red"><i class="layui-icon layui-icon-close-fill"></i> 停用</span>
-        {{# } }}
-    </script>
-    
     <script src="../../lib/jquery.min.js"></script>
     <script src="../../lib/layui/layui.js"></script>
     <script src="../../js/config.js"></script>
@@ -55,12 +47,9 @@
                     dataName: 'data'
                 },
                 cols: [[
-                    { field: 'departmentName', title: '部门名称', width: 250 },
-                    { field: 'departmentCode', title: '部门编码', width: 150 },
-                    { field: 'leader', title: '负责人', width: 120 },
-                    { field: 'phone', title: '联系电话', width: 140 },
+                    { field: 'deptName', title: '部门名称', width: 250 },
+                    { field: 'deptCode', title: '部门编码', width: 150 },
                     { field: 'sort', title: '排序', width: 80 },
-                    { field: 'status', title: '状态', width: 100, templet: '#statusTpl' },
                     { fixed: 'right', title: '操作', width: 150, align: 'center', toolbar: '#toolbar' }
                 ]],
                 parseData: function(res) {
@@ -90,7 +79,7 @@
                         content: 'department_form.html?id=' + data.id
                     });
                 } else if (event === 'del') {
-                    Common.confirm('确定要删除部门 【' + data.departmentName + '】 吗?', function() {
+                    Common.confirm('确定要删除部门 【' + data.deptName + '】 吗?', function() {
                         Common.del(Config.api.department.remove + '/' + data.id, function(res) {
                             Common.success('删除成功', function() {
                                 obj.del();

+ 1 - 1
ema-admin/src/main/resources/web/pages/dict/dict_data_form.html

@@ -18,7 +18,7 @@
         <div class="layui-form-item">
             <label class="layui-form-label"><span class="required">*</span>字典标签</label>
             <div class="layui-input-block">
-                <input type="text" name="label" lay-verify="required" placeholder="请输入字典标签" class="layui-input" style="width: 250px;">
+                <input type="text" name="value" lay-verify="required" placeholder="请输入字典标签" class="layui-input" style="width: 250px;">
             </div>
         </div>
         

+ 3 - 3
ema-admin/src/main/resources/web/pages/dict/dict_data_list.html

@@ -17,7 +17,7 @@
                 <div class="layui-inline">
                     <label class="layui-form-label">字典标签</label>
                     <div class="layui-input-inline">
-                        <input type="text" name="label" placeholder="请输入字典标签" class="layui-input">
+                        <input type="text" name="value" placeholder="请输入字典标签" class="layui-input">
                     </div>
                 </div>
                 <div class="layui-inline">
@@ -71,8 +71,8 @@
                 where: { typeCode: typeCode },
                 cols: [[
                     { type: 'checkbox', fixed: 'left' },
-                    { field: 'label', title: '字典标签', width: 150 },
-                    { field: 'value', title: '字典值', width: 150 },
+                    { field: 'value', title: '字典标签', width: 150 },
+                    { field: 'code', title: '字典编码', width: 150 },
                     { field: 'code', title: '字典编码', width: 120 },
                     { field: 'sort', title: '排序', width: 80 },
                     { field: 'status', title: '状态', width: 100, templet: '#statusTpl' },

+ 19 - 19
ema-admin/src/main/resources/web/pages/log/log_detail.html

@@ -16,17 +16,17 @@
 <body>
     <table class="detail-table" id="detailTable">
         <tr><td>操作模块</td><td id="title"></td></tr>
-        <tr><td>操作类型</td><td id="businessType"></td></tr>
-        <tr><td>操作人</td><td id="operator"></td></tr>
+        <tr><td>操作类型</td><td id="type"></td></tr>
+        <tr><td>操作人</td><td id="userName"></td></tr>
         <tr><td>IP地址</td><td id="ip"></td></tr>
-        <tr><td>操作地点</td><td id="location"></td></tr>
+        <tr><td>操作地点</td><td id="region"></td></tr>
         <tr><td>操作URL</td><td id="url"></td></tr>
-        <tr><td>请求方式</td><td id="requestMethod"></td></tr>
+        <tr><td>请求方式</td><td id="method"></td></tr>
         <tr><td>操作状态</td><td id="status"></td></tr>
-        <tr><td>操作时间</td><td id="createTime"></td></tr>
-        <tr><td>操作说明</td><td id="operationName"></td></tr>
-        <tr><td>请求参数</td><td id="param"></td></tr>
-        <tr><td>返回结果</td><td id="result"></td></tr>
+        <tr><td>操作时间</td><td id="operTime"></td></tr>
+        <tr><td>请求耗时</td><td id="duration"></td></tr>
+        <tr><td>请求参数</td><td id="params"></td></tr>
+        <tr><td>错误信息</td><td id="errorMsg"></td></tr>
     </table>
     
     <script src="../../lib/jquery.min.js"></script>
@@ -34,7 +34,7 @@
     <script src="../../js/config.js"></script>
     <script src="../../js/common.js"></script>
     <script>
-        layui.use([], function() {
+        layui.use(['jquery'], function() {
             var $ = layui.jquery;
             
             var id = Common.getQueryString('id');
@@ -46,19 +46,19 @@
                     var types = ['其他', '新增', '修改', '删除', '查询', '登录'];
                     
                     $('#title').text(data.title || '-');
-                    $('#businessType').text(types[data.businessType] || '其他');
-                    $('#operator').text(data.operator || '-');
+                    $('#type').text(types[data.type] || '其他');
+                    $('#userName').text(data.userName || '-');
                     $('#ip').text(data.ip || '-');
-                    $('#location').text(data.location || '-');
+                    $('#region').text(data.region || '-');
                     $('#url').text(data.url || '-');
-                    $('#requestMethod').text(data.requestMethod || '-');
-                    $('#status').html(data.status === 0 
-                        ? '<span class="layui-badge layui-bg-green">成功</span>' 
+                    $('#method').text(data.method || '-');
+                    $('#status').html(data.status === '1'
+                        ? '<span class="layui-badge layui-bg-green">成功</span>'
                         : '<span class="layui-badge layui-bg-red">失败</span>');
-                    $('#createTime').text(Common.formatDate(data.createTime));
-                    $('#operationName').text(data.operationName || '-');
-                    $('#param').text(data.param || '-');
-                    $('#result').text(data.result || '-');
+                    $('#operTime').text(Common.formatDate(data.operTime));
+                    $('#duration').text(data.duration ? data.duration + 'ms' : '-');
+                    $('#params').text(data.params || '-');
+                    $('#errorMsg').text(data.errorMsg || '-');
                 }
             });
         });

+ 11 - 14
ema-admin/src/main/resources/web/pages/log/log_list.html

@@ -29,7 +29,7 @@
                 <div class="layui-inline">
                     <label class="layui-form-label">操作类型</label>
                     <div class="layui-input-inline">
-                        <select name="businessType" class="layui-select">
+                        <select name="type" class="layui-select">
                             <option value="">全部</option>
                             <option value="0">其他</option>
                             <option value="1">新增</option>
@@ -54,13 +54,8 @@
         <a class="layui-btn layui-btn-xs layui-btn-primary" lay-event="detail"><i class="layui-icon layui-icon-about"></i> 详情</a>
     </script>
     
-    <script type="text/html" id="businessTypeTpl">
-        {{# var types = ['其他', '新增', '修改', '删除', '查询', '登录']; }}
-        {{# = types[d.businessType] || '其他' }}
-    </script>
-    
     <script type="text/html" id="statusTpl">
-        {{# if(d.status === 0) { }}
+        {{# if(d.status === '1') { }}
             <span class="layui-badge layui-bg-green">成功</span>
         {{# } else { }}
             <span class="layui-badge layui-bg-red">失败</span>
@@ -81,14 +76,16 @@
                 elem: '#tableList',
                 url: Config.api.operLog.page,
                 cols: [[
-                    { field: 'title', title: '操作模块', width: 150 },
-                    { field: 'businessType', title: '操作类型', width: 100, templet: '#businessTypeTpl' },
-                    { field: 'operator', title: '操作人', width: 120 },
-                    { field: 'ip', title: 'IP地址', width: 140 },
-                    { field: 'location', title: '操作地点', width: 150 },
+                    { field: 'type', title: '操作类型', width: 150 },
+                    { field: 'title', title: '操作模块', width: 200 },
+                    { field: 'url', title: '请求地址', width: 120 },
+                    { field: 'userName', title: '操作人', width: 120 },
+                    { field: 'ip', title: 'IP地址', width: 150 },
+                    { field: 'region', title: '操作地点', width: 150 },
                     { field: 'status', title: '状态', width: 100, templet: '#statusTpl' },
-                    { field: 'createTime', title: '操作时间', width: 170, templet: function(d) { return Common.formatDate(d.createTime); } },
-                    { fixed: 'right', title: '操作', width: 80, align: 'center', toolbar: '#toolbar' }
+                    { field: 'duration', title: '耗时(ms)', width: 100 },
+                    { field: 'operTime', title: '操作时间', width: 150, templet: function(d) { return Common.formatDate(d.operTime); } },
+                    { fixed: 'right', title: '操作', width: 200, align: 'center', toolbar: '#toolbar' }
                 ]]
             });
             

+ 7 - 0
ema-admin/src/main/resources/web/pages/menu/menu_form.html

@@ -113,6 +113,7 @@
             var layer = layui.layer;
             
             var id = Common.getQueryString('id');
+            var parentId = Common.getQueryString('parentId');
             var isEdit = !!id;
             
             // 加载菜单树
@@ -143,6 +144,12 @@
                         });
                         $('#parentSelect').html(html);
                         form.render('select');
+                        
+                        // 设置上级菜单默认值(添加下级时)
+                        if (parentId) {
+                            $('#parentSelect').val(parentId);
+                            form.render('select');
+                        }
                     }
                 });
             }

+ 6 - 11
ema-admin/src/main/resources/web/pages/menu/menu_list.html

@@ -396,12 +396,7 @@
                     '<span class="node-icon ' + iconClass + '"><i class="layui-icon ' + (item.icon || 'layui-icon-file') + '"></i></span>' +
                     '<div class="node-info">' +
                     '<div class="node-name">' + item.menuName + '</div>' +
-                    '<div class="node-path">' + (item.menuUrl || '无 URL') + '</div>' +
-                    '</div>' +
-                    '<div class="node-actions">' +
-                    '<button class="btn-edit" onclick="event.stopPropagation(); editMenu(' + item.id + ')" title="编辑"><i class="layui-icon layui-icon-edit"></i></button>' +
-                    '<button class="btn-add" onclick="event.stopPropagation(); addMenu(' + item.id + ')" title="添加下级"><i class="layui-icon layui-icon-add-1"></i></button>' +
-                    '<button class="btn-del" onclick="event.stopPropagation(); delMenu(' + item.id + ')" title="删除"><i class="layui-icon layui-icon-delete"></i></button>' +
+                    '<div class="node-path">' + item.path  + '</div>' +
                     '</div>' +
                     '</div>');
                 
@@ -487,10 +482,6 @@
                 '<div class="info-value"><span class="menu-type-tag ' + typeClass + '">' + typeText + '</span></div>' +
                 '</div>' +
                 '<div class="info-item">' +
-                '<div class="info-label">菜单编码</div>' +
-                '<div class="info-value">' + (menu.menuCode || '无') + '</div>' +
-                '</div>' +
-                '<div class="info-item">' +
                 '<div class="info-label">菜单状态</div>' +
                 '<div class="info-value"><span class="menu-status ' + statusClass + '">' + statusText + '</span></div>' +
                 '</div>' +
@@ -499,12 +490,16 @@
                 '<div class="info-value"><i class="layui-icon ' + (menu.icon || 'layui-icon-file') + '"></i> ' + (menu.icon || '无') + '</div>' +
                 '</div>' +
                 '<div class="info-item">' +
+                '<div class="info-label">权限标识</div>' +
+                '<div class="info-value">' + menu.perms + '</div>' +
+                '</div>' +
+                '<div class="info-item">' +
                 '<div class="info-label">排序号</div>' +
                 '<div class="info-value">' + (menu.orderNum || 0) + '</div>' +
                 '</div>' +
                 '<div class="info-item full-width">' +
                 '<div class="info-label">菜单路径</div>' +
-                '<div class="info-value">' + (menu.menuUrl || '无') + '</div>' +
+                '<div class="info-value">' + (menu.path || '无') + '</div>' +
                 '</div>' +
                 '<div class="info-item full-width">' +
                 '<div class="info-label">组件路径</div>' +

+ 18 - 6
ema-admin/src/main/resources/web/pages/user/user_form.html

@@ -113,6 +113,8 @@
                 loadUserData(id);
             }
             
+            var userData = null;
+            
             function loadRoles() {
                 Common.get(Config.api.role.list, function(res) {
                     if (res.code === 200) {
@@ -123,14 +125,29 @@
                         });
                         $('#roleCheckboxes').html(html);
                         form.render('checkbox');
+                        
+                        // 角色加载完成后,如果有用户数据则回显角色
+                        if (userData) {
+                            echoRoles(userData.roleList);
+                        }
                     }
                 });
             }
             
+            function echoRoles(roleList) {
+                if (roleList && roleList.length > 0) {
+                    roleList.forEach(function(role) {
+                        $('input[name="roleIds"][value="' + role.id + '"]').prop('checked', true);
+                    });
+                    form.render('checkbox');
+                }
+            }
+            
             function loadUserData(userId) {
                 Common.get(Config.api.user.getInfo + '/' + userId, function(res) {
                     if (res.code === 200) {
                         var data = res.data;
+                        userData = data;
                         form.val('userForm', {
                             id: data.id,
                             account: data.account,
@@ -143,12 +160,7 @@
                         });
                         
                         // 回显角色
-                        if (data.roles) {
-                            data.roles.forEach(function(role) {
-                                $('input[name="roleIds"][value="' + role.id + '"]').prop('checked', true);
-                            });
-                            form.render('checkbox');
-                        }
+                        echoRoles(data.roleList);
                     }
                 });
             }

+ 22 - 3
ema-admin/src/main/resources/web/pages/user/user_info.html

@@ -15,13 +15,14 @@
 <body>
     <div class="user-info-card">
         <form class="layui-form" lay-filter="userInfoForm" id="userInfoForm">
-            <div class="avatar-upload">
+            <!--<div class="avatar-upload">
                 <img src="../../images/user.png" class="avatar-img" id="avatarImg">
-            </div>
+            </div>-->
             
             <div class="layui-form-item">
                 <label class="layui-form-label">账号</label>
                 <div class="layui-input-block">
+                    <input type="text" name="id" class="layui-input" style="display: none;">
                     <input type="text" name="account" class="layui-input" readonly style="width: 300px; background: #f5f5f5;">
                 </div>
             </div>
@@ -68,6 +69,7 @@
                 if (res.code === 200) {
                     var user = res.data || res;
                     form.val('userInfoForm', {
+                        id: user.id,
                         account: user.account,
                         name: user.name,
                         phone: user.phone,
@@ -81,7 +83,24 @@
             
             // 提交表单
             form.on('submit(submitForm)', function(data) {
-                Common.success('个人信息已更新');
+                var loadingIndex = layer.load(2, { shade: [0.3, '#000'] });
+                Common.put(Config.api.user.update, data.field, function(res) {
+                    layer.close(loadingIndex);
+                    if (res.code === 200) {
+                        Common.success('个人信息已更新');
+                        // 更新本地存储的用户信息
+                        var userInfo = Common.getUserInfo() || {};
+                        userInfo.name = data.field.name;
+                        userInfo.phone = data.field.phone;
+                        userInfo.email = data.field.email;
+                        localStorage.setItem('userInfo', JSON.stringify(userInfo));
+                    } else {
+                        Common.error(res.msg || '更新失败');
+                    }
+                }, function() {
+                    layer.close(loadingIndex);
+                    Common.error('请求失败');
+                });
                 return false;
             });
         });

+ 5 - 5
ema-admin/src/main/resources/web/pages/user/user_list.html

@@ -102,13 +102,13 @@
                 url: Config.api.user.page,
                 cols: [[
                     { type: 'checkbox', fixed: 'left' },
-                    { field: 'account', title: '账号', width: 80 },
-                    { field: 'name', title: '姓名', width: 80 },
-                    { field: 'phone', title: '手机号', width: 100 },
-                    { field: 'email', title: '邮箱', width: 100 },
+                    { field: 'account', title: '账号', width: 120 },
+                    { field: 'name', title: '姓名', width: 100 },
+                    { field: 'phone', title: '手机号', width: 120 },
+                    { field: 'email', title: '邮箱', width: 150 },
                     { field: 'status', title: '状态', width: 80, templet: '#statusTpl' },
                     { field: 'roles', title: '角色', width: 200, templet: '#roleNamesTpl' },
-                    { field: 'createTime', title: '创建时间', width: 100 },
+                    { field: 'createTime', title: '创建时间', width: 150 },
                     { field: 'remark', title: '备注', width: 150 },
                     { fixed: 'right', title: '操作',  align: 'center', toolbar: '#toolbar' }
                 ]]

+ 0 - 111
ema-web/README.md

@@ -1,111 +0,0 @@
-# EMA Web 前端项目
-
-基于 LayUI 框架的企业管理系统前端项目,与 ema-admin 后端项目配套使用。
-
-## 项目结构
-
-```
-ema-web/
-├── index.html          # 登录页面
-├── lib/                # 第三方库
-│   └── layui/          # LayUI 框架
-├── css/                # 样式文件
-│   ├── login.css       # 登录页样式
-│   ├── main.css        # 主框架样式
-│   └── theme-blue.css  # 蓝色主题
-├── js/                 # JavaScript 文件
-│   ├── config.js       # 配置文件
-│   ├── common.js       # 公共工具
-│   ├── login.js        # 登录脚本
-│   └── main.js         # 主框架脚本
-├── images/             # 图片资源
-└── pages/              # 业务页面
-    ├── main.html       # 主框架页面
-    ├── home.html       # 首页
-    ├── user/           # 用户管理
-    ├── role/           # 角色管理
-    ├── menu/           # 菜单管理
-    ├── department/     # 部门管理
-    ├── dict/           # 字典管理
-    ├── file/           # 文件管理
-    ├── log/            # 日志管理
-    └── job/            # 定时任务
-```
-
-## 功能模块
-
-### 1. 登录模块
-- 账号密码登录
-- 图片验证码
-- 登录状态保持
-
-### 2. 用户管理 (SysUserController)
-- 用户列表(分页、搜索)
-- 添加/编辑用户
-- 删除用户
-- 分配角色
-
-### 3. 角色管理 (SysRoleController)
-- 角色列表
-- 添加/编辑角色
-- 分配菜单权限
-
-### 4. 菜单管理 (SysMenuController)
-- 菜单树结构
-- 添加/编辑菜单
-- 菜单类型(目录/菜单/按钮)
-
-### 5. 部门管理 (SysDepartmentController)
-- 部门树形列表
-- 添加/编辑部门
-
-### 6. 字典管理
-- 字典类型管理 (SysDictTypeController)
-- 字典数据管理 (SysDictDataController)
-
-### 7. 文件管理 (SysFileController)
-- 文件上传
-- 文件列表展示
-- 文件删除
-
-### 8. 操作日志 (SysOperLogController)
-- 日志列表查询
-- 日志详情查看
-
-### 9. 定时任务 (SysTimersJobController)
-- 任务列表
-- 添加/编辑任务
-- 启动/暂停任务
-
-## 配置说明
-
-修改 `js/config.js` 中的 `baseUrl` 配置,指向后端服务地址:
-
-```javascript
-baseUrl: 'http://localhost:8080',  // 修改为实际的后端地址
-```
-
-## 使用说明
-
-### 1. 安装依赖
-项目无需额外安装依赖,直接在浏览器打开即可运行。
-
-### 2. 启动项目
-- 开发环境:直接用浏览器打开 `index.html`
-- 生产环境:部署到 Web 服务器(如 Nginx、Apache)
-
-### 3. 注意事项
-- 确保后端服务已启动
-- 确保浏览器允许跨域请求(或配置后端 CORS)
-
-## API 接口
-
-详细的 API 接口请参考后端 Swagger 文档:
-```
-http://localhost:8080/doc.html
-```
-
-## 技术栈
-
-- LayUI 2.9.x
-- jQuery 3.x