Compare commits

...

32 Commits

Author SHA1 Message Date
嘉多宝宝
7aad37af87 feat:查询APP端AI测试性格报告结果 2026-01-17 15:11:34 +08:00
嘉多宝宝
3580e833a0 Merge remote-tracking branch 'refs/remotes/origin/master' into dev-chenjiajian 2026-01-16 17:16:12 +08:00
dde3fbb571 修复代理商活动的问题 2026-01-16 16:56:09 +08:00
61e1e86e88 修复代理商活动的问题 2026-01-16 16:25:55 +08:00
37dab3fe7a 优化当前登录用户和代理商的关系 2026-01-16 11:56:47 +08:00
08e7ab4150 优化当前登录用户和代理商的关系 2026-01-16 11:55:21 +08:00
嘉多宝宝
e09e3a32e6 Merge remote-tracking branch 'origin/master' into dev-chenjiajian 2026-01-16 11:38:24 +08:00
624d20283e 修改大模型的配置 2026-01-16 10:40:11 +08:00
eeae2978de 修改大模型的配置 2026-01-15 18:46:47 +08:00
eac3d0c6de 增加活动表单设计的功能 2026-01-15 18:35:20 +08:00
7a3f604763 Merge remote-tracking branch 'origin/dev-chenjiajian'
# Conflicts:
#	seer-mp/seer-mp-service-app-bootstrap/src/main/resources/db/mysql/V1.0.2__add_agent_activity_tables.sql
2026-01-15 18:24:06 +08:00
0803646604 增加活动表单设计的功能 2026-01-15 16:53:35 +08:00
83d4b41893 增加活动表单设计的功能 2026-01-15 16:45:51 +08:00
9efb21ae0c 增加活动表单设计的功能 2026-01-15 15:59:20 +08:00
28e7fbd8bb 增加活动表单设计的功能 2026-01-15 15:54:54 +08:00
f6834b225c 增加活动表单设计的功能 2026-01-15 15:52:10 +08:00
f2b0984fb4 增加活动表单设计的功能 2026-01-15 15:49:05 +08:00
c0922f884c 增加活动表单设计的功能 2026-01-15 15:28:19 +08:00
e359f9ef6b 增加活动表单设计的功能 2026-01-15 15:27:55 +08:00
c1614d1745 增加活动表单设计的功能 2026-01-15 15:24:26 +08:00
a045e9cbb9 增加活动表单设计的功能 2026-01-15 15:23:18 +08:00
619e3ea504 增加活动表单设计的功能 2026-01-15 15:20:35 +08:00
daa084b633 增加活动表单设计的功能 2026-01-15 15:04:53 +08:00
636849a227 增加活动表单设计的功能 2026-01-15 15:04:15 +08:00
fcf8122e0c 增加活动表单设计的功能 2026-01-15 14:50:06 +08:00
02ab1046c6 增加活动表单设计的功能 2026-01-15 14:30:20 +08:00
5df238f330 增加活动表单设计的功能 2026-01-15 14:25:05 +08:00
2c8a92fe41 增加活动表单设计的功能 2026-01-15 13:42:17 +08:00
90f0798321 增加活动表单设计的功能 2026-01-15 10:23:57 +08:00
6ce00db8fc 增加活动表单设计的功能 2026-01-15 09:43:18 +08:00
e9616a69c5 增加活动表单设计的功能 2026-01-13 10:22:34 +08:00
0047275149 增加根据手机号查询用户的功能 2026-01-10 16:19:27 +08:00
115 changed files with 3812 additions and 233 deletions

View File

@ -1,4 +1,4 @@
cdpipeline {
pipeline {
agent any
tools {
@ -7,15 +7,18 @@ cdpipeline {
parameters {
string(
name: 'DEPLOY_SERVERS',
defaultValue: '192.168.0.238',
description: '部署的目标服务器多个目标服务器以英文逗号分隔192.168.0.47,192.168.0.79'
name: 'DEPLOY_SERVERS'
)
choice(
name: 'spring.profiles.active',
choices: ['dev','test', 'prod'],
description: '选择要激活的 Spring Profile'
)
choice(
name: 'BRANCH_NAME',
choices: ['master', 'dev'],
description: '要构建的 Git 分支名称'
)
}
environment {
@ -57,13 +60,16 @@ cdpipeline {
stage('构建 Maven 项目') {
steps {
sh 'echo "初始工作目录: $(pwd)"'
sh 'ls -la '
sh 'mvn clean package -Dmaven.test.skip=true -pl :seer-admin -am'
script {
sh '''
JAVA_HOME=/opt/java/openjdk \
PATH=/opt/java/openjdk/bin:$PATH \
mvn clean package -Dmaven.test.skip=true -pl :seer-admin -am
'''
echo " Maven 构建完成"
}
}
}
stage('构建 Docker 镜像') {
steps {
dir('seer-admin') {

View File

@ -29,34 +29,34 @@ public class LlmConfig implements InitializingBean {
@Value("${largeModel.planCoverImage:}")
private String planCoverImage;
@Value("${largeModel.tts}")
@Value("${largeModel.tts:}")
private String tts;
@Value("${largeModel.stt}")
@Value("${largeModel.stt:}")
private String stt;
@Value("${largeModel.getComment}")
@Value("${largeModel.comment:}")
private String getComment;
@Value("${largeModel.sseAiChat}")
@Value("${largeModel.sseAiChat:}")
private String sseAiChat;
@Value("${largeModel.sseStudy}")
@Value("${largeModel.sseStudy:}")
private String sseStudy;
@Value("${largeModel.sseAiCorrect}")
@Value("${largeModel.sseAiCorrect:}")
private String sseAiCorrect;
@Value("${largeModel.ocr}")
@Value("${largeModel.ocr:}")
private String ocr;
@Value("${largeModel.processUpload}")
@Value("${largeModel.processUpload:}")
private String processUpload;
@Value("${largeModel.getContextAboutSingleQuestion}")
@Value("${largeModel.contextAboutSingleQuestion:}")
private String getContextAboutSingleQuestion;
@Value("${largeModel.getTextBase64}")
@Value("${largeModel.textBase64:}")
private String getTextBase64;
public static String IP;

File diff suppressed because one or more lines are too long

View File

@ -43,6 +43,20 @@ public class PageConverterUtils {
return result;
}
public static <T, R> PageListBean<R> convertPageListBean(
IPage<T> sourcePage,
List<R> records) {
PageListBean<R> result = new PageListBean<>();
if (null == sourcePage || sourcePage.getRecords() == null || sourcePage.getRecords().isEmpty()) {
return result;
}
result.setList(records);
result.setPageSize(sourcePage.getSize());
result.setTotalPage(sourcePage.getPages());
result.setTotal(sourcePage.getTotal());
return result;
}
/**
* 分页数据转换方法
* 将MyBatis-Plus的IPage分页结果转换为目标分页Bean

View File

@ -757,7 +757,10 @@
<encoding>UTF-8</encoding>
<debug>true</debug>
<debuglevel>lines,vars,source</debuglevel>
<compilerArgument>-parameters</compilerArgument>
<compilerArgument>
<arg>-parameters</arg>
<arg>-Xlint:-options</arg>
</compilerArgument>
</configuration>
</plugin>

View File

@ -7,7 +7,9 @@ pipeline {
parameters {
string(
name: 'DEPLOY_SERVERS'
name: 'DEPLOY_SERVERS',
defaultValue: '192.168.0.212',
description: '部署的目标服务器多个目标服务器以英文逗号分隔192.168.0.212,192.168.0.47,192.168.0.79'
)
choice(
name: 'spring.profiles.active',
@ -27,6 +29,7 @@ pipeline {
DEPLOY_USER = 'root'
LOGS_HOST_PATH = '/app/java/seer-mall/logs'
LOGS_CONTAINER_PATH = '/app/java/seer-mall/logs'
JAVA_HOME = "/usr/local/java21"
}
options {
@ -38,6 +41,8 @@ pipeline {
stage('初始化 & 分支校验') {
steps {
script {
sh 'echo "JAVA_HOME: $JAVA_HOME"'
sh 'java -version'
sh 'echo "初始Git工作目录: $(pwd)"'
sh 'ls -la '
checkout scm

View File

@ -0,0 +1,46 @@
package com.seer.teach.mp.api.dto;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.time.LocalDateTime;
/**
* <p>
* 活动表单执行实例DTO
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Schema(name = "ActivityFormExecutionDTO", description = "活动表单执行实例DTO")
@Data
public class ActivityFormExecutionDTO {
private Integer id;
@Schema(description = "执行编号")
private String executionNo;
@Schema(description = "活动ID")
private Integer activityId;
@Schema(description = "代理商ID")
private Integer agentId;
@Schema(description = "使用的表单模板ID")
private Integer templateId;
@Schema(description = "提交人ID家长ID")
private Integer submitterId;
@Schema(description = "提交人姓名")
private String submitterName;
@Schema(description = "提交时间")
private LocalDateTime submitTime;
@Schema(description = "状态draft-草稿submitted-已提交approved-已批准rejected-已拒绝")
private String status;
}

View File

@ -0,0 +1,50 @@
package com.seer.teach.mp.api.dto;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
/**
* <p>
* 活动表单字段DTO
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Schema(name = "ActivityFormFieldDTO", description = "活动表单字段DTO")
@Data
public class ActivityFormFieldDTO {
private Integer id;
@Schema(description = "所属模板ID")
private Integer templateId;
@Schema(description = "字段名称")
private String fieldName;
@Schema(description = "字段代码(英文标识)")
private String fieldCode;
@Schema(description = "字段类型text, textarea, select, radio, checkbox, date, number等")
private String fieldType;
@Schema(description = "字段选项JSON格式适用于select, radio, checkbox等")
private String fieldOptions;
@Schema(description = "占位符提示")
private String placeholder;
@Schema(description = "是否必填0-否1-是")
private Integer isRequired;
@Schema(description = "排序")
private Integer sortOrder;
@Schema(description = "验证规则JSON格式")
private String validationRules;
@Schema(description = "字段描述")
private String description;
}

View File

@ -0,0 +1,29 @@
package com.seer.teach.mp.api.dto;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
/**
* <p>
* 活动表单模板DTO
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Schema(name = "ActivityFormTemplateDTO", description = "活动表单模板DTO")
@Data
public class ActivityFormTemplateDTO {
private Integer id;
@Schema(description = "表单模板名称")
private String templateName;
@Schema(description = "表单模板描述")
private String templateDescription;
@Schema(description = "状态0-禁用1-启用")
private Integer status;
}

View File

@ -0,0 +1,35 @@
package com.seer.teach.mp.api.dto;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
/**
* <p>
* 活动表单变量DTO
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Schema(name = "ActivityFormVariableDTO", description = "活动表单变量DTO")
@Data
public class ActivityFormVariableDTO {
private Integer id;
@Schema(description = "表单执行实例ID")
private Integer executionId;
@Schema(description = "变量名称")
private String variableName;
@Schema(description = "变量代码")
private String variableCode;
@Schema(description = "变量值")
private String variableValue;
@Schema(description = "数据类型string, number, boolean, json等")
private String dataType;
}

View File

@ -0,0 +1,50 @@
package com.seer.teach.mp.entity;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import com.baomidou.mybatisplus.extension.handlers.JacksonTypeHandler;
import com.seer.teach.common.entity.BaseEntity;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Getter;
import lombok.Setter;
import java.util.List;
/**
* <p>
* 活动表单模板表
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Getter
@Setter
@TableName(value = "mp_activity_form",autoResultMap = true)
@Schema(name = "MpActivityFormEntity对象", description = "活动表单表")
public class MpActivityFormEntity extends BaseEntity {
/**
* 表单名称
*/
@TableField("form_name")
private String formName;
/**
* 表单描述
*/
@TableField("form_description")
private String formDescription;
/**
* 配置
*/
@TableField("config")
private String config;
/**
* 字段列表
*/
@TableField(value = "fields",typeHandler = JacksonTypeHandler.class)
private List<String> fields;
}

View File

@ -0,0 +1,74 @@
package com.seer.teach.mp.entity;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import com.seer.teach.common.entity.BaseEntity;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Getter;
import lombok.Setter;
import java.time.LocalDateTime;
/**
* <p>
* 活动表单执行实例表
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Getter
@Setter
@TableName("mp_activity_form_execution")
@Schema(name = "MpActivityFormExecutionEntity对象", description = "活动表单执行实例表")
public class MpActivityFormExecutionEntity extends BaseEntity {
/**
* 执行编号
*/
@TableField("execution_no")
private String executionNo;
/**
* 活动ID
*/
@TableField("activity_id")
private Integer activityId;
/**
* 代理商ID
*/
@TableField("agent_id")
private Integer agentId;
/**
* 使用的表单模板ID
*/
@TableField("form_id")
private Integer formId;
/**
* 提交人ID家长ID
*/
@TableField("submitter_id")
private Integer submitterId;
/**
* 提交人姓名
*/
@TableField("submitter_name")
private String submitterName;
/**
* 提交时间
*/
@TableField("submit_time")
private LocalDateTime submitTime;
/**
* 状态draft-草稿submitted-已提交approved-已批准rejected-已拒绝
*/
@TableField("status")
private String status;
}

View File

@ -0,0 +1,84 @@
package com.seer.teach.mp.entity;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import com.seer.teach.common.entity.BaseEntity;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Getter;
import lombok.Setter;
/**
* <p>
* 活动表单字段定义表
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Getter
@Setter
@TableName("mp_activity_form_field")
@Schema(name = "MpActivityFormFieldEntity对象", description = "活动表单字段定义表")
public class MpActivityFormFieldEntity extends BaseEntity {
/**
* 所属模板ID
*/
@TableField("form_id")
private Integer formId;
/**
* 字段名称
*/
@TableField("field_name")
private String fieldName;
/**
* 字段代码英文标识
*/
@TableField("field_code")
private String fieldCode;
/**
* 字段类型text, textarea, select, radio, checkbox, date, number等
*/
@TableField("field_type")
private String fieldType;
/**
* 字段选项JSON格式适用于select, radio, checkbox等
*/
@TableField("field_options")
private String fieldOptions;
/**
* 占位符提示
*/
@TableField("placeholder")
private String placeholder;
/**
* 是否必填0-1-
*/
@TableField("is_required")
private Integer isRequired;
/**
* 排序
*/
@TableField("sort_order")
private Integer sortOrder;
/**
* 验证规则JSON格式
*/
@TableField("validation_rules")
private String validationRules;
/**
* 字段描述
*/
@TableField("description")
private String description;
}

View File

@ -0,0 +1,47 @@
package com.seer.teach.mp.entity;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import com.seer.teach.common.entity.BaseEntity;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Getter;
import lombok.Setter;
/**
* <p>
* 活动与表单模板关联表
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Getter
@Setter
@TableName("mp_activity_form_relation")
@Schema(name = "MpActivityFormRelationEntity对象", description = "活动与表单模板关联表")
public class MpActivityFormRelationEntity extends BaseEntity {
/**
* 活动ID
*/
@TableField("activity_id")
private Integer activityId;
/**
* 表单模板ID
*/
@TableField("form_id")
private Integer formId;
/**
* 是否主要0-1-
*/
@TableField("is_primary")
private Integer isPrimary;
/**
* 版本,如1.0.0
*/
@TableField("version")
private String version;
}

View File

@ -0,0 +1,54 @@
package com.seer.teach.mp.entity;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import com.seer.teach.common.entity.BaseEntity;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Getter;
import lombok.Setter;
/**
* <p>
* 活动表单变量表
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Getter
@Setter
@TableName("mp_activity_form_variable")
@Schema(name = "MpActivityFormVariableEntity对象", description = "活动表单变量表")
public class MpActivityFormVariableEntity extends BaseEntity {
/**
* 表单执行实例ID
*/
@TableField("execution_id")
private Integer executionId;
/**
* 变量名称
*/
@TableField("variable_name")
private String variableName;
/**
* 变量代码
*/
@TableField("variable_code")
private String variableCode;
/**
* 变量值
*/
@TableField("variable_value")
private String variableValue;
/**
* 数据类型string, number, boolean, json等
*/
@TableField("data_type")
private String dataType;
}

View File

@ -19,7 +19,7 @@ import java.util.List;
* @since 2025-12-30
*/
@Data
@TableName("mp_activity_info_collection")
@TableName(value = "mp_activity_info_collection", autoResultMap = true)
@Schema(name = "MpActivityInfoCollectionEntity对象", description = "活动信息收集表")
public class MpActivityInfoCollectionEntity extends BaseEntity {

View File

@ -0,0 +1,63 @@
package com.seer.teach.mp.entity;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import com.seer.teach.common.entity.BaseEntity;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Getter;
import lombok.Setter;
import java.time.LocalDate;
/**
* <p>
*
* </p>
*
* @author 嘉多宝宝
* @since 2026-01-17
*/
@Getter
@Setter
@TableName("mp_test_child_character")
@Schema(name = "MpTestChildCharacterEntity对象", description = "测试孩子性格")
public class MpTestChildCharacterEntity extends BaseEntity {
@TableField("parent_id")
@Schema(description = "家长ID")
private Integer parentId;
@TableField("grade")
@Schema(description = "年级")
private String grade;
@TableField("constellation")
@Schema(description = "星座")
private String constellation;
@TableField("child_birth_date")
@Schema(description = "出生年月")
private LocalDate childBirthDate;
@TableField("child_gender")
@Schema(description = "孩子性别(男,女)")
private String childGender;
@TableField("character_analysis")
@Schema(description = "性格分析结果")
private String characterAnalysis;
@TableField("character_traits")
@Schema(description = "性格特征")
private String characterTraits;
@TableField("suggestions")
@Schema(description = "建议")
private String suggestions;
@TableField("character_type")
@Schema(description = "性格类型")
private String characterType;
}

View File

@ -0,0 +1,18 @@
package com.seer.teach.mp.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.seer.teach.mp.entity.MpActivityFormExecutionEntity;
import org.apache.ibatis.annotations.Mapper;
/**
* <p>
* 活动表单执行实例表 Mapper 接口
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Mapper
public interface MpActivityFormExecutionMapper extends BaseMapper<MpActivityFormExecutionEntity> {
}

View File

@ -0,0 +1,18 @@
package com.seer.teach.mp.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.seer.teach.mp.entity.MpActivityFormFieldEntity;
import org.apache.ibatis.annotations.Mapper;
/**
* <p>
* 活动表单字段定义表 Mapper 接口
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Mapper
public interface MpActivityFormFieldMapper extends BaseMapper<MpActivityFormFieldEntity> {
}

View File

@ -0,0 +1,18 @@
package com.seer.teach.mp.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.seer.teach.mp.entity.MpActivityFormEntity;
import org.apache.ibatis.annotations.Mapper;
/**
* <p>
* 活动表单模板表 Mapper 接口
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Mapper
public interface MpActivityFormMapper extends BaseMapper<MpActivityFormEntity> {
}

View File

@ -0,0 +1,18 @@
package com.seer.teach.mp.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.seer.teach.mp.entity.MpActivityFormRelationEntity;
import org.apache.ibatis.annotations.Mapper;
/**
* <p>
* 活动与表单模板关联表 Mapper 接口
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Mapper
public interface MpActivityFormRelationMapper extends BaseMapper<MpActivityFormRelationEntity> {
}

View File

@ -0,0 +1,18 @@
package com.seer.teach.mp.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.seer.teach.mp.entity.MpActivityFormVariableEntity;
import org.apache.ibatis.annotations.Mapper;
/**
* <p>
* 活动表单变量表 Mapper 接口
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Mapper
public interface MpActivityFormVariableMapper extends BaseMapper<MpActivityFormVariableEntity> {
}

View File

@ -0,0 +1,16 @@
package com.seer.teach.mp.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.seer.teach.mp.entity.MpTestChildCharacterEntity;
/**
* <p>
* Mapper 接口
* </p>
*
* @author 嘉多宝宝
* @since 2026-01-17
*/
public interface MpTestChildCharacterMapper extends BaseMapper<MpTestChildCharacterEntity> {
}

View File

@ -0,0 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.seer.teach.mp.mapper.MpTestChildCharacterMapper">
</mapper>

View File

@ -1,7 +1,6 @@
package com.seer.teach.mp.admin.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.dev33.satoken.stp.StpUtil;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.ResultBean;
import com.seer.teach.common.annotation.LogPrint;
@ -9,26 +8,30 @@ import com.seer.teach.mp.admin.controller.req.MpActivityQueryReq;
import com.seer.teach.mp.admin.controller.req.MpActivityReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityResp;
import com.seer.teach.mp.admin.service.IAdminActivityService;
import com.seer.teach.mp.entity.MpAgentEntity;
import com.seer.teach.mp.service.IMpAgentService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
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.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
@LogPrint
@RequiredArgsConstructor
@RestController
@Tag(name = "管理端 - 活动")
@RequestMapping("/mp/agent/activity")
@RequestMapping("/mp/activity")
public class AdminActivityController {
private final IAdminActivityService agentActivityService;
private final IMpAgentService mpAgentService;
@Operation(summary = "活动列表")
@PostMapping("/page-list")
@SaCheckPermission("mp:admin:agent:activity:list")
@ -46,25 +49,22 @@ public class AdminActivityController {
@Operation(summary = "删除活动")
@DeleteMapping("/{id}")
@SaCheckPermission("mp:admin:agent:activity:delete")
public ResultBean<Boolean> delete(@PathVariable Integer id) {
public ResultBean<Boolean> delete(@PathVariable("id") Integer id) {
return ResultBean.success(agentActivityService.deleteActivity(id));
}
@Operation(summary = "详情")
@GetMapping("/{id}")
@SaCheckPermission("mp:admin:agent:activity:get")
public ResultBean<AdminActivityResp> get(@PathVariable Integer id) {
public ResultBean<AdminActivityResp> get(@PathVariable("id") Integer id) {
AdminActivityResp result = agentActivityService.getById(id);
return ResultBean.success(result);
}
@Operation(summary = "获取活动二维码")
@GetMapping("/{activityId}/qrcode")
@SaCheckPermission("mp:admin:agent:activity:qrcode")
public ResultBean<String> getQrCode(@PathVariable("activityId") Integer activityId, @RequestParam("appId") String appId) {
Integer userId = StpUtil.getLoginIdAsInt();
MpAgentEntity one = mpAgentService.lambdaQuery().eq(MpAgentEntity::getContactUserId, userId).one();
Integer agentId = one.getId();
return ResultBean.success(agentActivityService.getQrCode(agentId, activityId, appId));
@Operation(summary = "查询代理商没有参与的活动列表")
@GetMapping("/agent/{agentId}")
@SaCheckPermission("mp:admin:agent:activity:list")
public ResultBean<List<AdminActivityResp>> getAgentActivities(@PathVariable("agentId") Integer agentId) {
return ResultBean.success(agentActivityService.getAgentActivities(agentId));
}
}

View File

@ -0,0 +1,82 @@
package com.seer.teach.mp.admin.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import com.seer.teach.common.ResultBean;
import com.seer.teach.common.annotation.DecryptionAnnotation;
import com.seer.teach.common.annotation.EncryptionAnnotation;
import com.seer.teach.common.annotation.LogPrint;
import com.seer.teach.mp.admin.controller.req.ActivityFormReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormResp;
import com.seer.teach.mp.admin.service.IAdminActivityFormService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
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.web.bind.annotation.RestController;
/**
* <p>
* 活动表单管理端控制器
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Tag(name = "ADMIN - 活动表单")
@RestController
@RequestMapping("/activity/form")
@LogPrint
@EncryptionAnnotation
@DecryptionAnnotation
@RequiredArgsConstructor
public class AdminActivityFormController {
private final IAdminActivityFormService adminActivityFormService;
@Operation(summary = "创建表单")
@PostMapping
@SaCheckPermission("mp:admin:activity:form:save")
public ResultBean<Boolean> save(@Valid @RequestBody ActivityFormReq request) {
Boolean result = adminActivityFormService.save(request);
return ResultBean.success(result);
}
@Operation(summary = "更新表单")
@PutMapping
@SaCheckPermission("mp:admin:activity:form:update")
public ResultBean<Boolean> update(@Valid @RequestBody ActivityFormReq request) {
Boolean result = adminActivityFormService.update(request);
return ResultBean.success(result);
}
@Operation(summary = "删除表单")
@DeleteMapping("/{id}")
@SaCheckPermission("mp:admin:activity:form:delete")
public ResultBean<Boolean> delete(@PathVariable Integer id) {
Boolean result = adminActivityFormService.deleteById(id);
return ResultBean.success(result);
}
@Operation(summary = "详情")
@GetMapping("/{id}")
@SaCheckPermission("mp:admin:activity:form:get")
public ResultBean<AdminActivityFormResp> get(@PathVariable Integer id) {
AdminActivityFormResp result = adminActivityFormService.getById(id);
return ResultBean.success(result);
}
@Operation(summary = "发布新版本")
@PostMapping("/publish-new-version")
@SaCheckPermission("mp:admin:activity:form:publish")
public ResultBean<Boolean> publishNewVersion(@RequestBody @Valid ActivityFormReq req) {
Boolean result = adminActivityFormService.publishNewVersion(req);
return ResultBean.success(result);
}
}

View File

@ -0,0 +1,77 @@
package com.seer.teach.mp.admin.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.ResultBean;
import com.seer.teach.common.annotation.DecryptionAnnotation;
import com.seer.teach.common.annotation.EncryptionAnnotation;
import com.seer.teach.common.annotation.LogPrint;
import com.seer.teach.mp.admin.controller.req.ActivityFormExecutionQueryReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormExecutionResp;
import com.seer.teach.mp.admin.service.IAdminActivityFormExecutionService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.RequiredArgsConstructor;
import org.springframework.web.bind.annotation.*;
import jakarta.validation.Valid;
/**
* <p>
* 活动表单执行实例管理端控制器
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Tag(name = "ADMIN - 活动表单执行实例")
@RestController
@RequestMapping("/activity/form/execution")
@LogPrint
@EncryptionAnnotation
@DecryptionAnnotation
@RequiredArgsConstructor
public class AdminActivityFormExecutionController {
private final IAdminActivityFormExecutionService adminActivityFormExecutionService;
@Operation(summary = "表单执行实例列表")
@PostMapping("/page-list")
@SaCheckPermission("mp:admin:activity:form:execution:list")
public ResultBean<PageListBean<AdminActivityFormExecutionResp>> pageList(@RequestBody @Valid ActivityFormExecutionQueryReq query) {
PageListBean<AdminActivityFormExecutionResp> result = adminActivityFormExecutionService.pageList(query);
return ResultBean.success(result);
}
@Operation(summary = "创建或更新表单执行实例")
@PostMapping("/save")
@SaCheckPermission("mp:admin:activity:form:execution:save")
public ResultBean<Boolean> save(@Valid @RequestBody ActivityFormExecutionQueryReq request) {
Boolean result = adminActivityFormExecutionService.saveOrUpdate(request);
return ResultBean.success(result);
}
@Operation(summary = "删除表单执行实例")
@DeleteMapping("/{id}")
@SaCheckPermission("mp:admin:activity:form:execution:delete")
public ResultBean<Boolean> delete(@PathVariable Integer id) {
Boolean result = adminActivityFormExecutionService.deleteById(id);
return ResultBean.success(result);
}
@Operation(summary = "详情")
@GetMapping("/{id}")
@SaCheckPermission("mp:admin:activity:form:execution:get")
public ResultBean<AdminActivityFormExecutionResp> get(@PathVariable Integer id) {
AdminActivityFormExecutionResp result = adminActivityFormExecutionService.getById(id);
return ResultBean.success(result);
}
@Operation(summary = "提交表单")
@PostMapping("/submit/{id}")
@SaCheckPermission("mp:admin:activity:form:execution:submit")
public ResultBean<Boolean> submit(@PathVariable Integer id) {
Boolean result = adminActivityFormExecutionService.submitById(id);
return ResultBean.success(result);
}
}

View File

@ -0,0 +1,78 @@
package com.seer.teach.mp.admin.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.ResultBean;
import com.seer.teach.common.annotation.DecryptionAnnotation;
import com.seer.teach.common.annotation.EncryptionAnnotation;
import com.seer.teach.common.annotation.LogPrint;
import com.seer.teach.mp.admin.controller.req.ActivityFormFieldQueryReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormFieldResp;
import com.seer.teach.mp.admin.service.IAdminActivityFormFieldService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.RequiredArgsConstructor;
import org.springframework.web.bind.annotation.*;
import jakarta.validation.Valid;
import java.util.List;
/**
* <p>
* 活动表单字段管理端控制器
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Tag(name = "ADMIN - 活动表单字段")
@RestController
@RequestMapping("/activity/form/field")
@LogPrint
@EncryptionAnnotation
@DecryptionAnnotation
@RequiredArgsConstructor
public class AdminActivityFormFieldController {
private final IAdminActivityFormFieldService adminActivityFormFieldService;
@Operation(summary = "表单字段列表")
@PostMapping("/page-list")
@SaCheckPermission("mp:admin:activity:form:field:list")
public ResultBean<PageListBean<AdminActivityFormFieldResp>> pageList(@RequestBody @Valid ActivityFormFieldQueryReq query) {
PageListBean<AdminActivityFormFieldResp> result = adminActivityFormFieldService.pageList(query);
return ResultBean.success(result);
}
@Operation(summary = "创建或更新表单字段")
@PostMapping("/save")
@SaCheckPermission("mp:admin:activity:form:field:save")
public ResultBean<Boolean> save(@Valid @RequestBody ActivityFormFieldQueryReq request) {
Boolean result = adminActivityFormFieldService.saveOrUpdate(request);
return ResultBean.success(result);
}
@Operation(summary = "删除表单字段")
@DeleteMapping("/{id}")
@SaCheckPermission("mp:admin:activity:form:field:delete")
public ResultBean<Boolean> delete(@PathVariable Integer id) {
Boolean result = adminActivityFormFieldService.deleteById(id);
return ResultBean.success(result);
}
@Operation(summary = "详情")
@GetMapping("/{id}")
@SaCheckPermission("mp:admin:activity:form:field:get")
public ResultBean<AdminActivityFormFieldResp> get(@PathVariable Integer id) {
AdminActivityFormFieldResp result = adminActivityFormFieldService.getById(id);
return ResultBean.success(result);
}
@Operation(summary = "根据模板ID获取字段列表")
@GetMapping("/list-by-template/{templateId}")
@SaCheckPermission("mp:admin:activity:form:field:list")
public ResultBean<List<AdminActivityFormFieldResp>> listByTemplate(@PathVariable Integer templateId) {
List<AdminActivityFormFieldResp> result = adminActivityFormFieldService.listByTemplateId(templateId);
return ResultBean.success(result);
}
}

View File

@ -0,0 +1,63 @@
package com.seer.teach.mp.admin.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import com.seer.teach.common.ResultBean;
import com.seer.teach.common.annotation.DecryptionAnnotation;
import com.seer.teach.common.annotation.EncryptionAnnotation;
import com.seer.teach.common.annotation.LogPrint;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormRelationResp;
import com.seer.teach.mp.admin.service.IAdminActivityFormRelationService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.RequiredArgsConstructor;
import org.springframework.web.bind.annotation.*;
import java.util.List;
/**
* <p>
* 活动与表单关联管理端控制器
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Tag(name = "ADMIN - 活动与表单关联")
@RestController
@RequestMapping("/activity/form/relation")
@LogPrint
@EncryptionAnnotation
@DecryptionAnnotation
@RequiredArgsConstructor
public class AdminActivityFormRelationController {
private final IAdminActivityFormRelationService adminActivityFormRelationService;
@Operation(summary = "为活动关联表单")
@PostMapping("/associate")
@SaCheckPermission("mp:admin:activity:form:relation:associate")
public ResultBean<Boolean> associateFormWithActivity(
@RequestParam Integer activityId,
@RequestParam Integer templateId) {
Boolean result = adminActivityFormRelationService.associateFormWithActivity(activityId, templateId);
return ResultBean.success(result);
}
@Operation(summary = "解除活动与表单的关联")
@DeleteMapping("/disassociate")
@SaCheckPermission("mp:admin:activity:form:relation:disassociate")
public ResultBean<Boolean> disassociateFormWithActivity(
@RequestParam Integer activityId,
@RequestParam Integer templateId) {
Boolean result = adminActivityFormRelationService.disassociateFormWithActivity(activityId, templateId);
return ResultBean.success(result);
}
@Operation(summary = "获取活动关联的表单列表")
@GetMapping("/{activityId}")
@SaCheckPermission("mp:admin:activity:form:relation:list")
public ResultBean<List<AdminActivityFormRelationResp>> getFormsByActivity(@PathVariable Integer activityId) {
List<AdminActivityFormRelationResp> result = adminActivityFormRelationService.getFormsByActivity(activityId);
return ResultBean.success(result);
}
}

View File

@ -0,0 +1,78 @@
package com.seer.teach.mp.admin.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.ResultBean;
import com.seer.teach.common.annotation.DecryptionAnnotation;
import com.seer.teach.common.annotation.EncryptionAnnotation;
import com.seer.teach.common.annotation.LogPrint;
import com.seer.teach.mp.admin.controller.req.ActivityFormVariableQueryReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormVariableResp;
import com.seer.teach.mp.admin.service.IAdminActivityFormVariableService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.RequiredArgsConstructor;
import org.springframework.web.bind.annotation.*;
import jakarta.validation.Valid;
import java.util.List;
/**
* <p>
* 活动表单变量管理端控制器
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Tag(name = "ADMIN - 活动表单变量")
@RestController
@RequestMapping("/activity/form/variable")
@LogPrint
@EncryptionAnnotation
@DecryptionAnnotation
@RequiredArgsConstructor
public class AdminActivityFormVariableController {
private final IAdminActivityFormVariableService adminActivityFormVariableService;
@Operation(summary = "表单变量列表")
@PostMapping("/page-list")
@SaCheckPermission("mp:admin:activity:form:variable:list")
public ResultBean<PageListBean<AdminActivityFormVariableResp>> pageList(@RequestBody @Valid ActivityFormVariableQueryReq query) {
PageListBean<AdminActivityFormVariableResp> result = adminActivityFormVariableService.pageList(query);
return ResultBean.success(result);
}
@Operation(summary = "创建或更新表单变量")
@PostMapping("/save")
@SaCheckPermission("mp:admin:activity:form:variable:save")
public ResultBean<Boolean> save(@Valid @RequestBody ActivityFormVariableQueryReq request) {
Boolean result = adminActivityFormVariableService.saveOrUpdate(request);
return ResultBean.success(result);
}
@Operation(summary = "删除表单变量")
@DeleteMapping("/{id}")
@SaCheckPermission("mp:admin:activity:form:variable:delete")
public ResultBean<Boolean> delete(@PathVariable Integer id) {
Boolean result = adminActivityFormVariableService.deleteById(id);
return ResultBean.success(result);
}
@Operation(summary = "详情")
@GetMapping("/{id}")
@SaCheckPermission("mp:admin:activity:form:variable:get")
public ResultBean<AdminActivityFormVariableResp> get(@PathVariable Integer id) {
AdminActivityFormVariableResp result = adminActivityFormVariableService.getById(id);
return ResultBean.success(result);
}
@Operation(summary = "根据执行实例ID获取变量列表")
@GetMapping("/list-by-execution/{executionId}")
@SaCheckPermission("mp:admin:activity:form:variable:list")
public ResultBean<List<AdminActivityFormVariableResp>> listByExecution(@PathVariable Integer executionId) {
List<AdminActivityFormVariableResp> result = adminActivityFormVariableService.listByExecutionId(executionId);
return ResultBean.success(result);
}
}

View File

@ -1,13 +1,14 @@
package com.seer.teach.mp.admin.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.dev33.satoken.stp.StpUtil;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.ResultBean;
import com.seer.teach.common.annotation.LogPrint;
import com.seer.teach.mp.admin.controller.req.AgentActivityParticipantQueryReq;
import com.seer.teach.mp.admin.controller.req.AgentActivityParticipantReq;
import com.seer.teach.mp.admin.controller.resp.AdminAgentActivityParticipantResp;
import com.seer.teach.mp.admin.service.IAdminAgentActivityParticipantService;
import com.seer.teach.mp.admin.service.IAdminAgentActivityRelationService;
import com.seer.teach.mp.entity.MpAgentActivityParticipantEntity;
import com.seer.teach.mp.service.IMpActivityService;
import com.seer.teach.mp.service.IMpAgentService;
@ -15,7 +16,15 @@ import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.RequiredArgsConstructor;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
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.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
@ -24,9 +33,9 @@ import java.util.List;
@RestController
@Tag(name = "管理端 - 代理商活动参与记录")
@RequestMapping("/mp/agent/activity/participant")
public class AdminAgentActivityParticipantController {
public class AdminAgentActivityRelationController {
private final IAdminAgentActivityParticipantService adminAgentActivityParticipantService;
private final IAdminAgentActivityRelationService adminAgentActivityParticipantService;
private final IMpAgentService mpAgentService;
@ -67,16 +76,12 @@ public class AdminAgentActivityParticipantController {
return ResultBean.success(adminAgentActivityParticipantService.deleteById(ids));
}
@Operation(summary = "查询代理商名称")
@GetMapping("/agent-name")
public ResultBean<List<String>> getAgentName() {
return ResultBean.success(mpAgentService.getAgentName());
@Operation(summary = "获取活动二维码")
@GetMapping("/{activityId}/{agentId}/qrcode")
@SaCheckPermission("mp:admin:agent:activity:qrcode")
public ResultBean<String> getQrCode(@PathVariable("activityId") Integer activityId,@PathVariable("agentId") Integer agentId, @RequestParam("appId") String appId) {
Integer userId = StpUtil.getLoginIdAsInt();
return ResultBean.success(adminAgentActivityParticipantService.getQrCode(agentId, activityId, appId,userId));
}
@Operation(summary = "查询活动名称")
@GetMapping("/activity-name")
public ResultBean<List<String>> getActivityName() {
return ResultBean.success(mpActivityService.getActivityName());
}
}

View File

@ -0,0 +1,50 @@
package com.seer.teach.mp.admin.controller.req;
import com.seer.teach.common.request.PageRequest;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import lombok.EqualsAndHashCode;
import jakarta.validation.constraints.NotNull;
import jakarta.validation.constraints.Size;
import java.time.LocalDateTime;
@Data
@EqualsAndHashCode(callSuper = true)
@Schema(description = "活动表单执行实例查询请求")
public class ActivityFormExecutionQueryReq extends PageRequest {
@Schema(description = "ID")
private Integer id;
@Schema(description = "执行编号")
@Size(max = 100, message = "执行编号长度不能超过100个字符")
private String executionNo;
@Schema(description = "活动ID")
@NotNull(message = "活动ID不能为空")
private Integer activityId;
@Schema(description = "代理商ID")
@NotNull(message = "代理商ID不能为空")
private Integer agentId;
@Schema(description = "使用的表单ID")
@NotNull(message = "表单ID不能为空")
private Integer formId;
@Schema(description = "提交人ID家长ID")
private Integer submitterId;
@Schema(description = "提交人姓名")
@Size(max = 255, message = "提交人姓名长度不能超过255个字符")
private String submitterName;
@Schema(description = "提交时间")
private LocalDateTime submitTime;
@Schema(description = "状态draft-草稿submitted-已提交approved-已批准rejected-已拒绝")
@Size(max = 50, message = "状态长度不能超过50个字符")
private String status;
}

View File

@ -0,0 +1,58 @@
package com.seer.teach.mp.admin.controller.req;
import com.seer.teach.common.request.PageRequest;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import lombok.EqualsAndHashCode;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import jakarta.validation.constraints.Size;
@Data
@EqualsAndHashCode(callSuper = true)
@Schema(description = "活动表单字段查询请求")
public class ActivityFormFieldQueryReq extends PageRequest {
@Schema(description = "ID")
private Integer id;
@Schema(description = "所属ID")
@NotNull(message = "所属ID不能为空")
private Integer formId;
@Schema(description = "字段名称")
@NotBlank(message = "字段名称不能为空")
@Size(max = 255, message = "字段名称长度不能超过255个字符")
private String fieldName;
@Schema(description = "字段代码(英文标识)")
@NotBlank(message = "字段代码不能为空")
@Size(max = 100, message = "字段代码长度不能超过100个字符")
private String fieldCode;
@Schema(description = "字段类型text, textarea, select, radio, checkbox, date, number等")
@NotBlank(message = "字段类型不能为空")
@Size(max = 50, message = "字段类型长度不能超过50个字符")
private String fieldType;
@Schema(description = "字段选项JSON格式适用于select, radio, checkbox等")
private String fieldOptions;
@Schema(description = "占位符提示")
@Size(max = 500, message = "占位符提示长度不能超过500个字符")
private String placeholder;
@Schema(description = "是否必填0-否1-是")
private Integer isRequired;
@Schema(description = "排序")
private Integer sortOrder;
@Schema(description = "验证规则JSON格式")
private String validationRules;
@Schema(description = "字段描述")
private String description;
}

View File

@ -0,0 +1,15 @@
package com.seer.teach.mp.admin.controller.req;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import jakarta.validation.constraints.NotNull;
@Data
@Schema(description = "活动表单发布新版本请求")
public class ActivityFormPublishVersionReq {
@NotNull(message = "活动ID不能为空")
@Schema(description = "活动ID")
private Integer activityId;
}

View File

@ -0,0 +1,30 @@
package com.seer.teach.mp.admin.controller.req;
import com.seer.teach.common.request.PageRequest;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import lombok.EqualsAndHashCode;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.Size;
@Data
@EqualsAndHashCode(callSuper = true)
@Schema(description = "活动表单模板查询请求")
public class ActivityFormQueryReq extends PageRequest {
@Schema(description = "ID")
private Integer id;
@Schema(description = "表单名称")
@NotBlank(message = "表单名称不能为空")
@Size(max = 255, message = "表单名称长度不能超过255个字符")
private String formName;
@Schema(description = "表单模板描述")
private String formDescription;
@Schema(description = "状态0-禁用1-启用")
private Integer status;
}

View File

@ -0,0 +1,40 @@
package com.seer.teach.mp.admin.controller.req;
import com.seer.teach.common.request.PageRequest;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.Size;
import lombok.Data;
import lombok.EqualsAndHashCode;
import java.util.List;
@Data
@EqualsAndHashCode(callSuper = true)
@Schema(description = "活动表单模板查询请求")
public class ActivityFormReq extends PageRequest {
@Schema(description = "ID")
private Integer id;
@Schema(description = "活动ID")
private Integer activityId;
@Schema(description = "表单名称")
@NotBlank(message = "表单名称不能为空")
@Size(max = 255, message = "表单名称长度不能超过255个字符")
private String formName;
@Schema(description = "表单模板描述")
private String formDescription;
@Schema(description = "状态0-禁用1-启用")
private Integer status;
@Schema(description = "表单配置")
private String config;
@Schema(description = "表单字段")
private List<String> fields;
}

View File

@ -0,0 +1,38 @@
package com.seer.teach.mp.admin.controller.req;
import com.seer.teach.common.request.PageRequest;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import lombok.EqualsAndHashCode;
import jakarta.validation.constraints.NotNull;
import jakarta.validation.constraints.Size;
@Data
@EqualsAndHashCode(callSuper = true)
@Schema(description = "活动表单变量查询请求")
public class ActivityFormVariableQueryReq extends PageRequest {
@Schema(description = "ID")
private Integer id;
@Schema(description = "表单执行实例ID")
@NotNull(message = "表单执行实例ID不能为空")
private Integer executionId;
@Schema(description = "变量名称")
@Size(max = 255, message = "变量名称长度不能超过255个字符")
private String variableName;
@Schema(description = "变量代码")
@Size(max = 100, message = "变量代码长度不能超过100个字符")
private String variableCode;
@Schema(description = "变量值")
private String variableValue;
@Schema(description = "数据类型string, number, boolean, json等")
@Size(max = 50, message = "数据类型长度不能超过50个字符")
private String dataType;
}

View File

@ -27,4 +27,7 @@ public class AgentActivityParticipantQueryReq {
@Schema(description = "代理商名称")
private String agentName;
@Schema(description = "代理商ID")
private Integer agentId;
}

View File

@ -2,6 +2,7 @@ package com.seer.teach.mp.admin.controller.req;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
@Data
@ -12,7 +13,15 @@ public class AgentActivityParticipantReq {
@NotBlank(message = "代理商名称不能为空")
private String agentName;
@Schema(description = "代理商ID")
@NotNull(message = "代理商ID不能为空")
private Integer agentId;
@Schema(description = "活动名称")
@NotBlank(message = "活动名称不能为空")
private String activityName;
@Schema(description = "活动ID")
@NotNull(message = "活动ID不能为空")
private Integer activityId;
}

View File

@ -0,0 +1,46 @@
package com.seer.teach.mp.admin.controller.resp;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.time.LocalDateTime;
@Schema(name = "AdminActivityFormExecutionResp", description = "活动表单执行实例响应参数")
@Data
public class AdminActivityFormExecutionResp {
private Integer id;
@Schema(description = "执行编号")
private String executionNo;
@Schema(description = "活动ID")
private Integer activityId;
@Schema(description = "代理商ID")
private Integer agentId;
@Schema(description = "使用的表单ID")
private Integer formId;
@Schema(description = "提交人ID家长ID")
private Integer submitterId;
@Schema(description = "提交人姓名")
private String submitterName;
@Schema(description = "提交时间")
private LocalDateTime submitTime;
@Schema(description = "状态draft-草稿submitted-已提交approved-已批准rejected-已拒绝")
private String status;
@Schema(description = "创建人ID")
private Integer creatorId;
@Schema(description = "创建时间")
private LocalDateTime createTime;
@Schema(description = "更新时间")
private LocalDateTime updateTime;
}

View File

@ -0,0 +1,52 @@
package com.seer.teach.mp.admin.controller.resp;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.time.LocalDateTime;
@Schema(name = "AdminActivityFormFieldResp", description = "活动表单字段响应参数")
@Data
public class AdminActivityFormFieldResp {
private Integer id;
@Schema(description = "所属表单ID")
private Integer formId;
@Schema(description = "字段名称")
private String fieldName;
@Schema(description = "字段代码(英文标识)")
private String fieldCode;
@Schema(description = "字段类型text, textarea, select, radio, checkbox, date, number等")
private String fieldType;
@Schema(description = "字段选项JSON格式适用于select, radio, checkbox等")
private String fieldOptions;
@Schema(description = "占位符提示")
private String placeholder;
@Schema(description = "是否必填0-否1-是")
private Integer isRequired;
@Schema(description = "排序")
private Integer sortOrder;
@Schema(description = "验证规则JSON格式")
private String validationRules;
@Schema(description = "字段描述")
private String description;
@Schema(description = "创建人ID")
private Integer creatorId;
@Schema(description = "创建时间")
private LocalDateTime createTime;
@Schema(description = "更新时间")
private LocalDateTime updateTime;
}

View File

@ -0,0 +1,55 @@
package com.seer.teach.mp.admin.controller.resp;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.util.List;
@Schema(name = "AdminActivityFormRelationResp", description = "活动表单模板响应参数")
@Data
public class AdminActivityFormRelationResp {
/**
* 活动ID
*/
@Schema(description = "活动ID")
private Integer activityId;
/**
* 表单模板ID
*/
@Schema(description = "表单ID")
private Integer formId;
/**
* 是否主要0-1-
*/
@Schema(description = "是否主要0-否1-是")
private Integer isPrimary;
/**
* 版本,如1.0.0
*/
@Schema(description = "版本,如1.0.0")
private String version;
/**
* 表单名称
*/
@Schema(description = "表单名称")
private String formName;
/**
* 表单描述
*/
@Schema(description = "表单描述")
private String fromDescription;
/**
* 状态0-禁用1-启用
*/
@Schema(description = "状态0-禁用1-启用")
private Integer status;
}

View File

@ -0,0 +1,42 @@
package com.seer.teach.mp.admin.controller.resp;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.util.List;
@Schema(name = "AdminActivityFormResp", description = "活动表单响应参数")
@Data
public class AdminActivityFormResp {
/**
* 表单ID
*/
@Schema(description = "表单ID")
private Integer id;
/**
* 表单名称
*/
@Schema(description = "表单名称")
private String formName;
/**
* 表单描述
*/
@Schema(description = "表单描述")
private String formDescription;
/**
* 表单配置
*/
@Schema(description = "表单配置")
private String config;
/**
* 表单字段
*/
@Schema(description = "表单字段")
private List<String> fields;
}

View File

@ -0,0 +1,37 @@
package com.seer.teach.mp.admin.controller.resp;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.time.LocalDateTime;
@Schema(name = "AdminActivityFormVariableResp", description = "活动表单变量响应参数")
@Data
public class AdminActivityFormVariableResp {
private Integer id;
@Schema(description = "表单执行实例ID")
private Integer executionId;
@Schema(description = "变量名称")
private String variableName;
@Schema(description = "变量代码")
private String variableCode;
@Schema(description = "变量值")
private String variableValue;
@Schema(description = "数据类型string, number, boolean, json等")
private String dataType;
@Schema(description = "创建人ID")
private Integer creatorId;
@Schema(description = "创建时间")
private LocalDateTime createTime;
@Schema(description = "更新时间")
private LocalDateTime updateTime;
}

View File

@ -0,0 +1,19 @@
package com.seer.teach.mp.admin.convert;
import com.seer.teach.mp.admin.controller.req.ActivityFormReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormRelationResp;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormResp;
import com.seer.teach.mp.entity.MpActivityFormEntity;
import org.mapstruct.Mapper;
import org.mapstruct.factory.Mappers;
@Mapper
public interface AdminActivityFormConvert {
AdminActivityFormConvert INSTANCE = Mappers.getMapper(AdminActivityFormConvert.class);
AdminActivityFormResp convertToResp(MpActivityFormEntity entity);
AdminActivityFormRelationResp convertToRelationResp(MpActivityFormEntity entity);
MpActivityFormEntity convertToEntity(ActivityFormReq request);
}

View File

@ -0,0 +1,15 @@
package com.seer.teach.mp.admin.convert;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormExecutionResp;
import com.seer.teach.mp.entity.MpActivityFormExecutionEntity;
import org.mapstruct.Mapper;
import org.mapstruct.Mapping;
import org.mapstruct.factory.Mappers;
@Mapper
public interface AdminActivityFormExecutionConvert {
AdminActivityFormExecutionConvert INSTANCE = Mappers.getMapper(AdminActivityFormExecutionConvert.class);
AdminActivityFormExecutionResp convertToResp(MpActivityFormExecutionEntity entity);
}

View File

@ -0,0 +1,14 @@
package com.seer.teach.mp.admin.convert;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormFieldResp;
import com.seer.teach.mp.entity.MpActivityFormFieldEntity;
import org.mapstruct.Mapper;
import org.mapstruct.Mapping;
import org.mapstruct.factory.Mappers;
@Mapper
public interface AdminActivityFormFieldConvert {
AdminActivityFormFieldConvert INSTANCE = Mappers.getMapper(AdminActivityFormFieldConvert.class);
AdminActivityFormFieldResp convertToResp(MpActivityFormFieldEntity entity);
}

View File

@ -0,0 +1,20 @@
package com.seer.teach.mp.admin.convert;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormVariableResp;
import com.seer.teach.mp.entity.MpActivityFormVariableEntity;
import org.mapstruct.Mapper;
import org.mapstruct.Mapping;
import org.mapstruct.factory.Mappers;
@Mapper
public interface AdminActivityFormVariableConvert {
AdminActivityFormVariableConvert INSTANCE = Mappers.getMapper(AdminActivityFormVariableConvert.class);
@Mapping(source = "id", target = "id")
@Mapping(source = "executionId", target = "executionId")
@Mapping(source = "variableName", target = "variableName")
@Mapping(source = "variableCode", target = "variableCode")
@Mapping(source = "variableValue", target = "variableValue")
@Mapping(source = "dataType", target = "dataType")
AdminActivityFormVariableResp convertToResp(MpActivityFormVariableEntity entity);
}

View File

@ -17,6 +17,11 @@ public interface AdminAgentActivityParticipantConvert {
List<AdminAgentActivityParticipantResp> convertToRespList(List<MpAgentActivityParticipantEntity> entity);
/**
* 转换为实体
*
* @param entity
* @return
*/
MpAgentActivityParticipantEntity convertToEntity(AgentActivityParticipantReq entity);
}

View File

@ -0,0 +1,25 @@
package com.seer.teach.mp.admin.convert;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormRelationResp;
import com.seer.teach.mp.entity.MpActivityFormRelationEntity;
import org.mapstruct.Mapper;
import org.mapstruct.factory.Mappers;
import java.util.List;
@Mapper
public interface AdminMpActivityFormRelationConvert {
AdminMpActivityFormRelationConvert INSTANCE = Mappers.getMapper(AdminMpActivityFormRelationConvert.class);
/**
* 转换
*
* @param entity
* @return
*/
AdminActivityFormRelationResp toAdminActivityFormRelationResp(MpActivityFormRelationEntity entity);
List<AdminActivityFormRelationResp> toAdminActivityFormRelationRespList(List<MpActivityFormRelationEntity> entityList);
}

View File

@ -12,7 +12,9 @@ import com.seer.teach.mp.admin.controller.req.MpAgentReq;
import com.seer.teach.mp.admin.controller.req.MpAgentSaveReq;
import com.seer.teach.mp.admin.controller.resp.AgentResp;
import com.seer.teach.mp.admin.convert.AgentConvert;
import com.seer.teach.mp.entity.MpAgentEmployeeRelationEntity;
import com.seer.teach.mp.entity.MpAgentEntity;
import com.seer.teach.mp.service.IMpAgentEmployeeRelationService;
import com.seer.teach.mp.service.IMpAgentService;
import com.seer.teach.user.api.UserInfoServiceApi;
import com.seer.teach.user.api.dto.UserInfoDTO;
@ -33,6 +35,8 @@ public class AdminAgentService {
private final UserInfoServiceApi userInfoServiceApi;
private final IMpAgentEmployeeRelationService mpAgentEmployeeRelationService;
/**
* 获取代理商列表
*
@ -72,7 +76,7 @@ public class AdminAgentService {
* @return 是否成功
*/
public Boolean saveAgent(MpAgentSaveReq req) {
boolean userIdByMobile = userInfoServiceApi.getUserIdByMobile(req.getContactPhone());
boolean userIdByMobile = mpAgentService.getCountByPhone(req.getContactPhone()) == 0;
AssertUtils.isTrue(userIdByMobile, ResultCodeEnum.AGENT_IS_EXISTS);
MpAgentEntity agentEntity = AgentConvert.INSTANCE.convertOneSave(req);
boolean result = mpAgentService.saveAgent(agentEntity, req.getPassword());
@ -89,29 +93,15 @@ public class AdminAgentService {
public Boolean updateAgent(MpAgentReq req) {
MpAgentEntity agent = mpAgentService.getById(req.getId());
AssertUtils.notNull(agent, ResultCodeEnum.AGENT_NOT_FOUND);
UserInfoDTO userInfoDTO = new UserInfoDTO();
userInfoDTO.setId(agent.getContactUserId());
userInfoDTO.setUserName(req.getContactName());
userInfoDTO.setMobile(req.getContactPhone());
if (StringUtils.isNotBlank(req.getPassword())) {
userInfoDTO.setPassword(req.getPassword());
}
boolean updateUserResult = userInfoServiceApi.updateUserInfo(userInfoDTO);
log.info("更新用户结果: {}", updateUserResult);
agent.setId(req.getId());
agent.setAgentName(req.getAgentName());
agent.setAgentCode(req.getAgentCode());
agent.setAgentLevel(req.getAgentLevel());
agent.setContactName(req.getContactName());
Integer contactUserId = userInfoServiceApi.getUserIdByUserName(agent.getContactName());
agent.setContactUserId(contactUserId);
agent.setContactPhone(req.getContactPhone());
agent.setAddress(req.getAddress());
agent.setStatus(req.getStatus());
boolean result = mpAgentService.updateAgent(agent);
log.info("更新代理商结果: {}", result);
return result && updateUserResult;
return mpAgentService.updateAgent(agent, req.getPassword());
}
/**
@ -125,17 +115,21 @@ public class AdminAgentService {
log.warn("删除代理商时ID列表为空");
return false;
}
List<MpAgentEntity> agentList = mpAgentService.lambdaQuery().in(MpAgentEntity::getId, ids)
.select(MpAgentEntity::getContactUserId).list();
List<Integer> contactUserIdList = agentList.stream().map(MpAgentEntity::getContactUserId)
.filter(Objects::nonNull).toList();
log.info("待删除代理商关联的用户ID列表: {}", contactUserIdList);
boolean result = mpAgentService.removeByIds(ids);
log.info("删除代理商结果: {}", result);
if (result) {
log.info("删除代理商成功ID列表: {}", ids);
// 删除关联的用户数据
List<MpAgentEntity> agentList = mpAgentService.lambdaQuery().in(MpAgentEntity::getId, ids)
.select(MpAgentEntity::getContactUserId).list();
List<Integer> contactUserIdList = agentList.stream().map(MpAgentEntity::getContactUserId)
.filter(Objects::nonNull).toList();
log.info("待删除代理商关联的用户ID列表: {}", contactUserIdList);
userInfoServiceApi.deleteUserRoleByUserId(contactUserIdList);
// 删除关联的代理商员工关系数据
boolean remove = mpAgentEmployeeRelationService.remove(new LambdaQueryWrapper<>(MpAgentEmployeeRelationEntity.class).in(MpAgentEmployeeRelationEntity::getAgentId, ids));
log.info("删除代理商员工关系结果: {}", remove);
}
return result;
}

View File

@ -0,0 +1,56 @@
package com.seer.teach.mp.admin.service;
import com.seer.teach.common.PageListBean;
import com.seer.teach.mp.admin.controller.req.ActivityFormExecutionQueryReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormExecutionResp;
/**
* <p>
* 管理端活动表单执行实例服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IAdminActivityFormExecutionService {
/**
* 分页查询活动表单执行实例
*
* @param query 查询参数
* @return 分页结果
*/
PageListBean<AdminActivityFormExecutionResp> pageList(ActivityFormExecutionQueryReq query);
/**
* 保存或更新活动表单执行实例
*
* @param request 请求参数
* @return 操作结果
*/
Boolean saveOrUpdate(ActivityFormExecutionQueryReq request);
/**
* 删除活动表单执行实例
*
* @param id 实例ID
* @return 操作结果
*/
Boolean deleteById(Integer id);
/**
* 根据ID获取活动表单执行实例
*
* @param id 实例ID
* @return 实例信息
*/
AdminActivityFormExecutionResp getById(Integer id);
/**
* 提交表单
*
* @param id 实例ID
* @return 操作结果
*/
Boolean submitById(Integer id);
}

View File

@ -0,0 +1,58 @@
package com.seer.teach.mp.admin.service;
import com.seer.teach.common.PageListBean;
import com.seer.teach.mp.admin.controller.req.ActivityFormFieldQueryReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormFieldResp;
import java.util.List;
/**
* <p>
* 管理端活动表单字段服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IAdminActivityFormFieldService {
/**
* 分页查询活动表单字段
*
* @param query 查询参数
* @return 分页结果
*/
PageListBean<AdminActivityFormFieldResp> pageList(ActivityFormFieldQueryReq query);
/**
* 保存或更新活动表单字段
*
* @param request 请求参数
* @return 操作结果
*/
Boolean saveOrUpdate(ActivityFormFieldQueryReq request);
/**
* 删除活动表单字段
*
* @param id 字段ID
* @return 操作结果
*/
Boolean deleteById(Integer id);
/**
* 根据ID获取活动表单字段
*
* @param id 字段ID
* @return 字段信息
*/
AdminActivityFormFieldResp getById(Integer id);
/**
* 根据模板ID获取字段列表
*
* @param templateId 模板ID
* @return 字段列表
*/
List<AdminActivityFormFieldResp> listByTemplateId(Integer templateId);
}

View File

@ -0,0 +1,43 @@
package com.seer.teach.mp.admin.service;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormRelationResp;
import java.util.List;
/**
* <p>
* 管理端活动与表单关联服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IAdminActivityFormRelationService {
/**
* 为活动关联表单
*
* @param activityId 活动ID
* @param formId 表单ID
* @return 操作结果
*/
Boolean associateFormWithActivity(Integer activityId, Integer formId);
/**
* 解除活动与表单的关联
*
* @param activityId 表单ID
* @param formId ID
* @return 操作结果
*/
Boolean disassociateFormWithActivity(Integer activityId, Integer formId);
/**
* 获取活动关联的表单列表
*
* @param activityId 活动ID
* @return 表单列表
*/
List<AdminActivityFormRelationResp> getFormsByActivity(Integer activityId);
}

View File

@ -0,0 +1,58 @@
package com.seer.teach.mp.admin.service;
import com.seer.teach.common.PageListBean;
import com.seer.teach.mp.admin.controller.req.ActivityFormQueryReq;
import com.seer.teach.mp.admin.controller.req.ActivityFormReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormRelationResp;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormResp;
/**
* <p>
* 管理端活动表单模板服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IAdminActivityFormService {
/**
* 保存活动表单模板
*
* @param request 请求参数
* @return 操作结果
*/
Boolean save(ActivityFormReq request);
/**
* 删除活动表单模板
*
* @param id 模板ID
* @return 操作结果
*/
Boolean deleteById(Integer id);
/**
* 根据ID获取活动表单模板
*
* @param id 模板ID
* @return 模板信息
*/
AdminActivityFormResp getById(Integer id);
/**
* 更新活动表单模板
*
* @param request 模板信息
* @return 操作结果
*/
Boolean update(ActivityFormReq request);
/**
* 发布新版本
*
* @param req 请求参数
* @return 操作结果
*/
Boolean publishNewVersion(ActivityFormReq req);
}

View File

@ -0,0 +1,58 @@
package com.seer.teach.mp.admin.service;
import com.seer.teach.common.PageListBean;
import com.seer.teach.mp.admin.controller.req.ActivityFormVariableQueryReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormVariableResp;
import java.util.List;
/**
* <p>
* 管理端活动表单变量服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IAdminActivityFormVariableService {
/**
* 分页查询活动表单变量
*
* @param query 查询参数
* @return 分页结果
*/
PageListBean<AdminActivityFormVariableResp> pageList(ActivityFormVariableQueryReq query);
/**
* 保存或更新活动表单变量
*
* @param request 请求参数
* @return 操作结果
*/
Boolean saveOrUpdate(ActivityFormVariableQueryReq request);
/**
* 删除活动表单变量
*
* @param id 变量ID
* @return 操作结果
*/
Boolean deleteById(Integer id);
/**
* 根据ID获取活动表单变量
*
* @param id 变量ID
* @return 变量信息
*/
AdminActivityFormVariableResp getById(Integer id);
/**
* 根据执行实例ID获取变量列表
*
* @param executionId 执行实例ID
* @return 变量列表
*/
List<AdminActivityFormVariableResp> listByExecutionId(Integer executionId);
}

View File

@ -5,6 +5,8 @@ import com.seer.teach.mp.admin.controller.req.MpActivityQueryReq;
import com.seer.teach.mp.admin.controller.req.MpActivityReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityResp;
import java.util.List;
/**
* <p>
* 管理端代理商活动服务类
@ -48,11 +50,10 @@ public interface IAdminActivityService {
AdminActivityResp getById(Integer id);
/**
* 获取活动二维码
* 根据代理商ID获取其参与的活动列表
*
* @param agentId 代理商ID
* @param activityId 活动ID
* @param appId 微信公众号ID
* @return 活动二维码
* @return 活动列表
*/
String getQrCode(Integer agentId, Integer activityId, String appId);
List<AdminActivityResp> getAgentActivities(Integer agentId);
}

View File

@ -16,7 +16,7 @@ import java.util.List;
* @author
* @since 2025-12-30
*/
public interface IAdminAgentActivityParticipantService {
public interface IAdminAgentActivityRelationService {
/**
* 分页查询代理商活动参与记录列表管理端
@ -57,4 +57,15 @@ public interface IAdminAgentActivityParticipantService {
* @return 操作是否成功
*/
Boolean deleteById(List<Integer> ids);
/**
* 获取活动二维码
*
* @param agentId 代理商ID
* @param activityId 活动ID
* @param appId 微信公众号appId
* @param userId 用户ID
* @return 二维码地址
*/
String getQrCode(Integer agentId, Integer activityId, String appId, Integer userId);
}

View File

@ -0,0 +1,90 @@
package com.seer.teach.mp.admin.service.impl;
import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.utils.PageConverterUtils;
import com.seer.teach.mp.admin.controller.req.ActivityFormExecutionQueryReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormExecutionResp;
import com.seer.teach.mp.admin.convert.AdminActivityFormExecutionConvert;
import com.seer.teach.mp.admin.service.IAdminActivityFormExecutionService;
import com.seer.teach.mp.entity.MpActivityFormExecutionEntity;
import com.seer.teach.mp.service.IMpActivityFormExecutionService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
/**
* <p>
* 管理端活动表单执行实例服务实现类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Slf4j
@Service
@RequiredArgsConstructor
public class AdminActivityFormExecutionServiceImpl implements IAdminActivityFormExecutionService {
private final IMpActivityFormExecutionService activityFormExecutionService;
@Override
public PageListBean<AdminActivityFormExecutionResp> pageList(ActivityFormExecutionQueryReq query) {
Page<MpActivityFormExecutionEntity> page = new Page<>(query.getPageNo(), query.getPageSize());
LambdaQueryWrapper<MpActivityFormExecutionEntity> wrapper = new LambdaQueryWrapper<>();
wrapper.eq(query.getActivityId() != null, MpActivityFormExecutionEntity::getActivityId, query.getActivityId())
.eq(query.getAgentId() != null, MpActivityFormExecutionEntity::getAgentId, query.getAgentId())
.eq(query.getFormId() != null, MpActivityFormExecutionEntity::getFormId, query.getFormId())
.eq(StringUtils.isNotBlank(query.getStatus()),
MpActivityFormExecutionEntity::getStatus, query.getStatus())
.like(StringUtils.isNotBlank(query.getSubmitterName()),
MpActivityFormExecutionEntity::getSubmitterName, query.getSubmitterName())
.orderByDesc(MpActivityFormExecutionEntity::getId);
Page<MpActivityFormExecutionEntity> pageResult = activityFormExecutionService.page(page, wrapper);
return PageConverterUtils.convertPageList(pageResult, AdminActivityFormExecutionConvert.INSTANCE::convertToResp);
}
@Override
public Boolean saveOrUpdate(ActivityFormExecutionQueryReq request) {
MpActivityFormExecutionEntity entity = new MpActivityFormExecutionEntity();
BeanUtil.copyProperties(request, entity);
if (request.getId() == null) {
// 新增时设置默认值
entity.setStatus(entity.getStatus() == null ? "draft" : entity.getStatus());
}
return activityFormExecutionService.saveOrUpdate(entity);
}
@Override
public Boolean deleteById(Integer id) {
return activityFormExecutionService.removeById(id);
}
@Override
public AdminActivityFormExecutionResp getById(Integer id) {
if (id == null) {
return null;
}
MpActivityFormExecutionEntity entity = activityFormExecutionService.getById(id);
return AdminActivityFormExecutionConvert.INSTANCE.convertToResp(entity);
}
@Override
public Boolean submitById(Integer id) {
MpActivityFormExecutionEntity entity = activityFormExecutionService.getById(id);
if (entity == null) {
return false;
}
entity.setStatus("submitted");
return activityFormExecutionService.updateById(entity);
}
}

View File

@ -0,0 +1,99 @@
package com.seer.teach.mp.admin.service.impl;
import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.utils.PageConverterUtils;
import com.seer.teach.mp.admin.controller.req.ActivityFormFieldQueryReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormFieldResp;
import com.seer.teach.mp.admin.convert.AdminActivityFormFieldConvert;
import com.seer.teach.mp.admin.service.IAdminActivityFormFieldService;
import com.seer.teach.mp.entity.MpActivityFormFieldEntity;
import com.seer.teach.mp.service.IMpActivityFormFieldService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import java.util.List;
import java.util.stream.Collectors;
/**
* <p>
* 管理端活动表单字段服务实现类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Slf4j
@Service
@RequiredArgsConstructor
public class AdminActivityFormFieldServiceImpl implements IAdminActivityFormFieldService {
private final IMpActivityFormFieldService activityFormFieldService;
@Override
public PageListBean<AdminActivityFormFieldResp> pageList(ActivityFormFieldQueryReq query) {
Page<MpActivityFormFieldEntity> page = new Page<>(query.getPageNo(), query.getPageSize());
LambdaQueryWrapper<MpActivityFormFieldEntity> wrapper = new LambdaQueryWrapper<>();
wrapper.eq(query.getFormId() != null, MpActivityFormFieldEntity::getFormId, query.getFormId())
.like(StringUtils.isNotBlank(query.getFieldName()),
MpActivityFormFieldEntity::getFieldName, query.getFieldName())
.eq(StringUtils.isNotBlank(query.getFieldType()),
MpActivityFormFieldEntity::getFieldType, query.getFieldType())
.orderByAsc(MpActivityFormFieldEntity::getSortOrder)
.orderByDesc(MpActivityFormFieldEntity::getId);
Page<MpActivityFormFieldEntity> pageResult = activityFormFieldService.page(page, wrapper);
return PageConverterUtils.convertPageList(pageResult, AdminActivityFormFieldConvert.INSTANCE::convertToResp);
}
@Override
public Boolean saveOrUpdate(ActivityFormFieldQueryReq request) {
MpActivityFormFieldEntity entity = new MpActivityFormFieldEntity();
BeanUtil.copyProperties(request, entity);
if (request.getId() == null) {
// 新增时设置默认值
entity.setIsRequired(entity.getIsRequired() == null ? 0 : entity.getIsRequired());
entity.setSortOrder(entity.getSortOrder() == null ? 0 : entity.getSortOrder());
}
return activityFormFieldService.saveOrUpdate(entity);
}
@Override
public Boolean deleteById(Integer id) {
return activityFormFieldService.removeById(id);
}
@Override
public AdminActivityFormFieldResp getById(Integer id) {
if (id == null) {
return null;
}
MpActivityFormFieldEntity entity = activityFormFieldService.getById(id);
return AdminActivityFormFieldConvert.INSTANCE.convertToResp(entity);
}
@Override
public List<AdminActivityFormFieldResp> listByTemplateId(Integer templateId) {
if (templateId == null) {
return java.util.Collections.emptyList();
}
List<MpActivityFormFieldEntity> entities = activityFormFieldService.list(
new LambdaQueryWrapper<MpActivityFormFieldEntity>()
.eq(MpActivityFormFieldEntity::getFormId, templateId)
.orderByAsc(MpActivityFormFieldEntity::getSortOrder)
.orderByDesc(MpActivityFormFieldEntity::getId)
);
return entities.stream()
.map(AdminActivityFormFieldConvert.INSTANCE::convertToResp)
.collect(Collectors.toList());
}
}

View File

@ -0,0 +1,90 @@
package com.seer.teach.mp.admin.service.impl;
import cn.hutool.core.collection.CollectionUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormRelationResp;
import com.seer.teach.mp.admin.convert.AdminMpActivityFormRelationConvert;
import com.seer.teach.mp.admin.service.IAdminActivityFormRelationService;
import com.seer.teach.mp.entity.MpActivityFormEntity;
import com.seer.teach.mp.entity.MpActivityFormRelationEntity;
import com.seer.teach.mp.service.IMpActivityFormRelationService;
import com.seer.teach.mp.service.IMpActivityFormService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.function.Function;
import java.util.stream.Collectors;
/**
* <p>
* 管理端活动与表单模板关联服务实现类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Slf4j
@Service
@RequiredArgsConstructor
public class AdminActivityFormRelationServiceImpl implements IAdminActivityFormRelationService {
private final IMpActivityFormRelationService activityFormTemplateRelationService;
private final IMpActivityFormService activityFormTemplateService;
@Override
public Boolean associateFormWithActivity(Integer activityId, Integer formId) {
return activityFormTemplateRelationService.createRelation(activityId, formId);
}
@Override
public Boolean disassociateFormWithActivity(Integer activityId, Integer formId) {
return activityFormTemplateRelationService.remove(
new LambdaQueryWrapper<MpActivityFormRelationEntity>()
.eq(MpActivityFormRelationEntity::getActivityId, activityId)
.eq(MpActivityFormRelationEntity::getFormId, formId)
);
}
@Override
public List<AdminActivityFormRelationResp> getFormsByActivity(Integer activityId) {
if (activityId == null) {
return java.util.Collections.emptyList();
}
List<MpActivityFormRelationEntity> relations = activityFormTemplateRelationService.list(
new LambdaQueryWrapper<MpActivityFormRelationEntity>()
.eq(MpActivityFormRelationEntity::getActivityId, activityId)
);
if(CollectionUtil.isEmpty(relations)){
return Collections.emptyList();
}
List<Integer> formIds = relations.stream()
.map(MpActivityFormRelationEntity::getFormId)
.collect(java.util.stream.Collectors.toList());
List<MpActivityFormEntity> forms = activityFormTemplateService.list(
new LambdaQueryWrapper<MpActivityFormEntity>()
.in(MpActivityFormEntity::getId, formIds)
);
log.info("getFormsByActivity: {}", forms);
if(CollectionUtil.isEmpty(forms)){
return Collections.emptyList();
}
Map<Integer, MpActivityFormEntity> mapping = forms.stream().collect(Collectors.toMap(MpActivityFormEntity::getId, Function.identity(), (old, newOne) -> newOne));
List<AdminActivityFormRelationResp> adminActivityFormRelationRespList = AdminMpActivityFormRelationConvert.INSTANCE.toAdminActivityFormRelationRespList(relations);
for (AdminActivityFormRelationResp adminActivityFormRelationResp : adminActivityFormRelationRespList) {
MpActivityFormEntity activityForm = mapping.get(adminActivityFormRelationResp.getFormId());
if(Objects.nonNull(activityForm)){
adminActivityFormRelationResp.setFormName(activityForm.getFormName());
adminActivityFormRelationResp.setFromDescription(activityForm.getFormDescription());
}
}
log.debug("getFormsByActivity: {}", adminActivityFormRelationRespList);
return adminActivityFormRelationRespList;
}
}

View File

@ -0,0 +1,109 @@
package com.seer.teach.mp.admin.service.impl;
import com.seer.teach.common.constants.CommonConstant;
import com.seer.teach.common.utils.CommonUtils;
import com.seer.teach.mp.admin.controller.req.ActivityFormReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormResp;
import com.seer.teach.mp.admin.convert.AdminActivityFormConvert;
import com.seer.teach.mp.admin.service.IAdminActivityFormService;
import com.seer.teach.mp.entity.MpActivityFormEntity;
import com.seer.teach.mp.entity.MpActivityFormRelationEntity;
import com.seer.teach.mp.service.IMpActivityFormRelationService;
import com.seer.teach.mp.service.IMpActivityFormService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import java.util.Optional;
/**
* <p>
* 管理端活动表单模板服务实现类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Slf4j
@Service
@RequiredArgsConstructor
public class AdminActivityFormServiceImpl implements IAdminActivityFormService {
private final IMpActivityFormService activityFormService;
private final IMpActivityFormRelationService activityFormRelationService;
@Override
public Boolean save(ActivityFormReq request) {
MpActivityFormEntity form = AdminActivityFormConvert.INSTANCE.convertToEntity(request);
boolean saveResult = activityFormService.save(form);
if (saveResult) {
MpActivityFormRelationEntity relation = new MpActivityFormRelationEntity();
relation.setActivityId(request.getActivityId());
relation.setFormId(form.getId());
Optional<MpActivityFormRelationEntity> optionalRelation = activityFormRelationService.getLatestVersionByActivityId(request.getActivityId());
if (optionalRelation.isPresent()) {
relation.setIsPrimary(CommonConstant.IS_NOT_DEFAULT);
relation.setVersion(CommonUtils.generateVersionNumber(optionalRelation.get().getVersion()));
} else {
relation.setIsPrimary(CommonConstant.IS_DEFAULT);
relation.setVersion("1.0.0");
}
boolean saved = activityFormRelationService.save(relation);
log.info("保存关联关系:{}", saved);
}
return saveResult;
}
@Override
public Boolean deleteById(Integer id) {
return activityFormService.removeById(id);
}
@Override
public AdminActivityFormResp getById(Integer id) {
if (id == null) {
return null;
}
MpActivityFormEntity entity = activityFormService.getById(id);
return AdminActivityFormConvert.INSTANCE.convertToResp(entity);
}
@Override
public Boolean update(ActivityFormReq request) {
if (request.getId() == null) {
return false;
}
MpActivityFormEntity form = AdminActivityFormConvert.INSTANCE.convertToEntity(request);
return activityFormService.updateById(form);
}
@Override
public Boolean publishNewVersion(ActivityFormReq req) {
Integer activityId = req.getActivityId();
if (activityId == null) {
return false;
}
Optional<MpActivityFormRelationEntity> optionalRelation = activityFormRelationService.getLatestVersionByActivityId(activityId);
if (optionalRelation.isEmpty()) {
return false;
}
MpActivityFormRelationEntity latestRelation = optionalRelation.get();
// 复制当前表单信息创建新版本
MpActivityFormEntity newForm = AdminActivityFormConvert.INSTANCE.convertToEntity(req);
// 保存新的表单记录
boolean saved = activityFormService.save(newForm);
if (!saved) {
log.error("publishNewVersion失败:{}", newForm);
return false;
}
MpActivityFormRelationEntity newRelation = new MpActivityFormRelationEntity();
newRelation.setActivityId(req.getActivityId());
newRelation.setFormId(req.getId());
newRelation.setIsPrimary(CommonConstant.IS_NOT_DEFAULT);
newRelation.setVersion(CommonUtils.generateVersionNumber(latestRelation.getVersion()));
return activityFormRelationService.save(newRelation);
}
}

View File

@ -0,0 +1,96 @@
package com.seer.teach.mp.admin.service.impl;
import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.utils.PageConverterUtils;
import com.seer.teach.mp.admin.controller.req.ActivityFormVariableQueryReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityFormVariableResp;
import com.seer.teach.mp.admin.convert.AdminActivityFormVariableConvert;
import com.seer.teach.mp.admin.service.IAdminActivityFormVariableService;
import com.seer.teach.mp.entity.MpActivityFormVariableEntity;
import com.seer.teach.mp.service.IMpActivityFormVariableService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import java.util.List;
import java.util.stream.Collectors;
/**
* <p>
* 管理端活动表单变量服务实现类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Slf4j
@Service
@RequiredArgsConstructor
public class AdminActivityFormVariableServiceImpl implements IAdminActivityFormVariableService {
private final IMpActivityFormVariableService activityFormVariableService;
@Override
public PageListBean<AdminActivityFormVariableResp> pageList(ActivityFormVariableQueryReq query) {
Page<MpActivityFormVariableEntity> page = new Page<>(query.getPageNo(), query.getPageSize());
LambdaQueryWrapper<MpActivityFormVariableEntity> wrapper = new LambdaQueryWrapper<>();
wrapper.eq(query.getExecutionId() != null, MpActivityFormVariableEntity::getExecutionId, query.getExecutionId())
.eq(StringUtils.isNotBlank(query.getVariableCode()),
MpActivityFormVariableEntity::getVariableCode, query.getVariableCode())
.like(StringUtils.isNotBlank(query.getVariableName()),
MpActivityFormVariableEntity::getVariableName, query.getVariableName())
.orderByDesc(MpActivityFormVariableEntity::getId);
Page<MpActivityFormVariableEntity> pageResult = activityFormVariableService.page(page, wrapper);
List<AdminActivityFormVariableResp> records = pageResult.getRecords().stream()
.map(AdminActivityFormVariableConvert.INSTANCE::convertToResp)
.collect(Collectors.toList());
return PageConverterUtils.convertPageListBean(pageResult, records);
}
@Override
public Boolean saveOrUpdate(ActivityFormVariableQueryReq request) {
MpActivityFormVariableEntity entity = new MpActivityFormVariableEntity();
BeanUtil.copyProperties(request, entity);
if (request.getId() == null) {
// 新增时设置默认值
entity.setDataType(entity.getDataType() == null ? "string" : entity.getDataType());
}
return activityFormVariableService.saveOrUpdate(entity);
}
@Override
public Boolean deleteById(Integer id) {
return activityFormVariableService.removeById(id);
}
@Override
public AdminActivityFormVariableResp getById(Integer id) {
MpActivityFormVariableEntity entity = activityFormVariableService.getById(id);
return AdminActivityFormVariableConvert.INSTANCE.convertToResp(entity);
}
@Override
public List<AdminActivityFormVariableResp> listByExecutionId(Integer executionId) {
if (executionId == null) {
return java.util.Collections.emptyList();
}
List<MpActivityFormVariableEntity> entities = activityFormVariableService.list(
new LambdaQueryWrapper<MpActivityFormVariableEntity>()
.eq(MpActivityFormVariableEntity::getExecutionId, executionId)
.orderByDesc(MpActivityFormVariableEntity::getId)
);
return entities.stream()
.map(AdminActivityFormVariableConvert.INSTANCE::convertToResp)
.collect(Collectors.toList());
}
}

View File

@ -3,26 +3,23 @@ package com.seer.teach.mp.admin.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.enums.ResultCodeEnum;
import com.seer.teach.common.exception.CommonException;
import com.seer.teach.common.utils.AssertUtils;
import com.seer.teach.common.utils.PageConverterUtils;
import com.seer.teach.mp.admin.controller.req.AgentGenerateQrCodeReq;
import com.seer.teach.mp.admin.controller.req.MpActivityQueryReq;
import com.seer.teach.mp.admin.controller.req.MpActivityReq;
import com.seer.teach.mp.admin.controller.resp.AdminActivityResp;
import com.seer.teach.mp.admin.controller.resp.AdminAgentQrCodeResp;
import com.seer.teach.mp.admin.convert.AdminActivityConvert;
import com.seer.teach.mp.admin.service.AdminOfficialQrCodeService;
import com.seer.teach.mp.admin.service.IAdminActivityService;
import com.seer.teach.mp.entity.MpActivityEntity;
import com.seer.teach.mp.entity.MpAgentActivityParticipantEntity;
import com.seer.teach.mp.service.IMpActivityService;
import com.seer.teach.mp.service.IMpAgentActivityParticipantService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
/**
@ -33,6 +30,7 @@ import java.util.Objects;
* @author Lingma
* @since 2025-12-30
*/
@Slf4j
@Service
@RequiredArgsConstructor
public class AdminActivityServiceImpl implements IAdminActivityService {
@ -41,8 +39,6 @@ public class AdminActivityServiceImpl implements IAdminActivityService {
private final IMpAgentActivityParticipantService agentActivityParticipantService;
private final AdminOfficialQrCodeService officialQrCodeService;
@Override
public PageListBean<AdminActivityResp> pageList(MpActivityQueryReq query) {
Page<MpActivityEntity> page = new Page<>(query.getPageNo(), query.getPageSize());
@ -70,25 +66,25 @@ public class AdminActivityServiceImpl implements IAdminActivityService {
}
@Override
public String getQrCode(Integer agentId, Integer activityId, String appId) {
MpActivityEntity activity = agentActivityService.getById(activityId);
AssertUtils.notNull(activity, ResultCodeEnum.INVALID_ACTIVITY);
if (activity.getStatus() != 1) {
throw new CommonException(ResultCodeEnum.INVALID_ACTIVITY);
public List<AdminActivityResp> getAgentActivities(Integer agentId) {
List<MpActivityEntity> result = new ArrayList<>();
// 先查询代理商参与的所有活动ID
var participants = agentActivityParticipantService.getListByAgentId(agentId);
if (participants.isEmpty()) {
log.info("没有代理商参与活动");
result.addAll(agentActivityService.list());
}else{
var activityIds = participants.stream()
.map(MpAgentActivityParticipantEntity::getActivityId)
.distinct()
.toList();
// 查询这些活动的详细信息
var wrapper = new LambdaQueryWrapper<MpActivityEntity>()
.notIn(MpActivityEntity::getId, activityIds)
.orderByDesc(MpActivityEntity::getCreateTime);
List<MpActivityEntity> activitys = agentActivityService.list(wrapper);
result.addAll(activitys);
}
MpAgentActivityParticipantEntity relation = agentActivityParticipantService.getParticipantsByActivityAndAgent(activityId, agentId);
AssertUtils.notNull(relation, ResultCodeEnum.INVALID_ACTIVITY);
if (StringUtils.isNotBlank(relation.getQrCodeUrl())) {
return relation.getQrCodeUrl();
}
AgentGenerateQrCodeReq req = new AgentGenerateQrCodeReq();
req.setSceneStr("agentId=" + agentId + "&activityId=" + activityId);
req.setAppId(appId);
req.setType(2);
AdminAgentQrCodeResp QrCodeResp = officialQrCodeService.generateQrCode(req);
relation.setQrCodeUrl(QrCodeResp.getQrCodeUrl());
agentActivityParticipantService.updateById(relation);
return QrCodeResp.getQrCodeUrl();
return AdminActivityConvert.INSTANCE.convertToRespList(result);
}
}

View File

@ -3,12 +3,18 @@ package com.seer.teach.mp.admin.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.enums.ResultCodeEnum;
import com.seer.teach.common.exception.CommonException;
import com.seer.teach.common.utils.AssertUtils;
import com.seer.teach.common.utils.PageConverterUtils;
import com.seer.teach.mp.admin.controller.req.AgentActivityParticipantQueryReq;
import com.seer.teach.mp.admin.controller.req.AgentActivityParticipantReq;
import com.seer.teach.mp.admin.controller.req.AgentGenerateQrCodeReq;
import com.seer.teach.mp.admin.controller.resp.AdminAgentActivityParticipantResp;
import com.seer.teach.mp.admin.controller.resp.AdminAgentQrCodeResp;
import com.seer.teach.mp.admin.convert.AdminAgentActivityParticipantConvert;
import com.seer.teach.mp.admin.service.IAdminAgentActivityParticipantService;
import com.seer.teach.mp.admin.service.AdminOfficialQrCodeService;
import com.seer.teach.mp.admin.service.IAdminAgentActivityRelationService;
import com.seer.teach.mp.entity.MpActivityEntity;
import com.seer.teach.mp.entity.MpAgentActivityParticipantEntity;
import com.seer.teach.mp.entity.MpAgentEntity;
@ -16,6 +22,7 @@ import com.seer.teach.mp.service.IMpActivityService;
import com.seer.teach.mp.service.IMpAgentActivityParticipantService;
import com.seer.teach.mp.service.IMpAgentService;
import lombok.RequiredArgsConstructor;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import java.util.List;
@ -30,7 +37,7 @@ import java.util.List;
*/
@Service
@RequiredArgsConstructor
public class AdminAgentActivityParticipantServiceImpl implements IAdminAgentActivityParticipantService {
public class AdminAgentActivityRelationServiceImpl implements IAdminAgentActivityRelationService {
private final IMpAgentActivityParticipantService mpAgentActivityParticipantService;
@ -38,6 +45,8 @@ public class AdminAgentActivityParticipantServiceImpl implements IAdminAgentActi
private final IMpActivityService mpActivityService;
private final AdminOfficialQrCodeService officialQrCodeService;
@Override
public PageListBean<AdminAgentActivityParticipantResp> pageList(AgentActivityParticipantQueryReq query) {
Page<MpAgentActivityParticipantEntity> page = new Page<>(query.getPageNum(), query.getPageSize());
@ -51,27 +60,26 @@ public class AdminAgentActivityParticipantServiceImpl implements IAdminAgentActi
if (query.getAgentName() != null) {
wrapper.like(MpAgentActivityParticipantEntity::getAgentName, query.getAgentName());
}
if (query.getAgentId() != null) {
wrapper.eq(MpAgentActivityParticipantEntity::getAgentId, query.getAgentId());
}
Page<MpAgentActivityParticipantEntity> result = mpAgentActivityParticipantService.page(page, wrapper);
return PageConverterUtils.convertPageListBean(result, AdminAgentActivityParticipantConvert.INSTANCE::convertToRespList);
}
@Override
public boolean saveParticipant(AgentActivityParticipantReq entity) {
public boolean saveParticipant(AgentActivityParticipantReq req) {
// 检查是否已存在相同的活动代理商和家长记录
LambdaQueryWrapper<MpAgentActivityParticipantEntity> wrapper = new LambdaQueryWrapper<>();
wrapper.eq(MpAgentActivityParticipantEntity::getActivityName, entity.getActivityName())
.eq(MpAgentActivityParticipantEntity::getAgentName, entity.getAgentName());
wrapper.eq(MpAgentActivityParticipantEntity::getActivityId, req.getActivityId())
.eq(MpAgentActivityParticipantEntity::getAgentId, req.getAgentId());
long count = mpAgentActivityParticipantService.count(wrapper);
if (count > 0) {
throw new RuntimeException("该代理商活动参与记录已存在");
}
Integer agentId = mpAgentService.lambdaQuery().eq(MpAgentEntity::getAgentName, entity.getAgentName()).one().getId();
Integer activityId = mpActivityService.lambdaQuery().eq(MpActivityEntity::getActivityName, entity.getActivityName()).one().getId();
MpAgentActivityParticipantEntity result = AdminAgentActivityParticipantConvert.INSTANCE.convertToEntity(entity);
result.setActivityId(activityId);
result.setAgentId(agentId);
MpAgentActivityParticipantEntity result = AdminAgentActivityParticipantConvert.INSTANCE.convertToEntity(req);
return mpAgentActivityParticipantService.save(result);
}
@ -108,4 +116,27 @@ public class AdminAgentActivityParticipantServiceImpl implements IAdminAgentActi
return mpAgentActivityParticipantService.removeByIds(ids);
}
@Override
public String getQrCode(Integer agentId, Integer activityId, String appId, Integer userId) {
MpActivityEntity activity = mpActivityService.getById(activityId);
AssertUtils.notNull(activity, ResultCodeEnum.INVALID_ACTIVITY);
if (activity.getStatus() != 1) {
throw new CommonException(ResultCodeEnum.INVALID_ACTIVITY);
}
MpAgentActivityParticipantEntity relation = mpAgentActivityParticipantService.getParticipantsByActivityAndAgent(activityId, agentId);
AssertUtils.notNull(relation, ResultCodeEnum.INVALID_ACTIVITY);
if (StringUtils.isNotBlank(relation.getQrCodeUrl())) {
return relation.getQrCodeUrl();
}
AgentGenerateQrCodeReq req = new AgentGenerateQrCodeReq();
req.setSceneStr("agentId=" + agentId + "&activityId=" + activityId);
req.setAppId(appId);
req.setType(2);
AdminAgentQrCodeResp QrCodeResp = officialQrCodeService.generateQrCode(req);
relation.setQrCodeUrl(QrCodeResp.getQrCodeUrl());
mpAgentActivityParticipantService.updateById(relation);
return QrCodeResp.getQrCodeUrl();
}
}

View File

@ -38,8 +38,7 @@ pipeline {
stage('初始化 & 分支校验') {
steps {
script {
sh 'echo "初始Git工作目录: $(pwd)"'
sh 'ls -la '
checkout scm
def branch = params.BRANCH_NAME
@ -56,11 +55,16 @@ pipeline {
stage('构建 Maven 项目') {
steps {
sh 'echo "初始工作目录: $(pwd)"'
sh 'ls -la '
sh 'mvn clean package -Dmaven.test.skip=true -pl :seer-mp-service-app-bootstrap -am'
script {
sh '''
JAVA_HOME=/opt/java/openjdk
PATH=/opt/java/openjdk/bin:$PATH
mvn clean package -Dmaven.test.skip=true -pl :seer-mp-service-app-bootstrap -am
'''
echo " Maven 构建完成"
}
}
}
stage('构建 Docker 镜像') {

View File

@ -139,6 +139,7 @@ CREATE TABLE `mp_activity_info_collection` (
`region` varchar(255) COMMENT '地区',
`parent_identity` varchar(20) COMMENT '家长身份(爸爸,妈妈)',
`learning_situation` varchar(20) COMMENT '学习情况(优、良、中、差)',
`contact_call_count` int NOT NULL DEFAULT 0 COMMENT '代理商拨打电话联系家长次数',
`weak_subject_ids` json COMMENT '薄弱科目',
`strong_subject_ids` json COMMENT '优势科目',
`weak_subject` varchar(50) COMMENT '偏科(数学、英语等)',

View File

@ -0,0 +1,105 @@
-- 创建表单表
DROP TABLE IF EXISTS `mp_activity_form`;
CREATE TABLE `mp_activity_form` (
`id` int NOT NULL AUTO_INCREMENT COMMENT '主键ID',
`form_name` varchar(255) NOT NULL COMMENT '表单名称',
`form_description` text COMMENT '表单描述',
`config` text COMMENT '表单的配置信息',
`fields` text COMMENT '表单项的数组',
`create_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`create_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '创建人',
`update_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '修改时间',
`update_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '修改人',
`deleted` bit(1) NULL DEFAULT b'0' COMMENT '是否删除',
`tenant_id` varchar(20) DEFAULT 'Default' COMMENT '租户id',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='活动表单表';
-- 创建表单字段定义表
DROP TABLE IF EXISTS `mp_activity_form_field`;
CREATE TABLE `mp_activity_form_field` (
`id` int NOT NULL AUTO_INCREMENT COMMENT '主键ID',
`form_id` int NOT NULL COMMENT '所属ID',
`field_name` varchar(255) NOT NULL COMMENT '字段名称',
`field_code` varchar(100) NOT NULL COMMENT '字段代码(英文标识)',
`field_type` varchar(50) NOT NULL COMMENT '字段类型text, textarea, select, radio, checkbox, date, number等',
`field_options` text COMMENT '字段选项JSON格式适用于select, radio, checkbox等',
`placeholder` varchar(500) DEFAULT NULL COMMENT '占位符提示',
`is_required` tinyint NOT NULL DEFAULT '0' COMMENT '是否必填0-否1-是',
`sort_order` int DEFAULT '0' COMMENT '排序',
`validation_rules` text COMMENT '验证规则JSON格式',
`description` text COMMENT '字段描述',
`create_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`create_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '创建人',
`update_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '修改时间',
`update_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '修改人',
`deleted` bit(1) NULL DEFAULT b'0' COMMENT '是否删除',
`tenant_id` varchar(20) DEFAULT 'Default' COMMENT '租户id',
PRIMARY KEY (`id`),
KEY `idx_form_id` (`form_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='活动表单字段定义表';
-- 创建表单执行实例表
DROP TABLE IF EXISTS `mp_activity_form_execution`;
CREATE TABLE `mp_activity_form_execution` (
`id` int NOT NULL AUTO_INCREMENT COMMENT '主键ID',
`execution_no` varchar(100) NOT NULL COMMENT '执行编号',
`activity_id` int NOT NULL COMMENT '活动ID',
`agent_id` int NOT NULL COMMENT '代理商ID',
`form_id` int NOT NULL COMMENT '使用的表单ID',
`submitter_id` int DEFAULT NULL COMMENT '提交人ID家长ID',
`submitter_name` varchar(255) DEFAULT NULL COMMENT '提交人姓名',
`submit_time` datetime DEFAULT NULL COMMENT '提交时间',
`status` varchar(50) NOT NULL DEFAULT 'draft' COMMENT '状态draft-草稿submitted-已提交approved-已批准rejected-已拒绝',
`create_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`create_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '创建人',
`update_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '修改时间',
`update_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '修改人',
`deleted` bit(1) NULL DEFAULT b'0' COMMENT '是否删除',
`tenant_id` varchar(20) DEFAULT 'Default' COMMENT '租户id',
PRIMARY KEY (`id`),
UNIQUE KEY `uk_execution_no` (`execution_no`),
KEY `idx_activity_id` (`activity_id`),
KEY `idx_agent_id` (`agent_id`),
KEY `idx_form_id` (`form_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='活动表单执行实例表';
-- 创建表单变量表
DROP TABLE IF EXISTS `mp_activity_form_variable`;
CREATE TABLE `mp_activity_form_variable` (
`id` int NOT NULL AUTO_INCREMENT COMMENT '主键ID',
`execution_id` int NOT NULL COMMENT '表单执行实例ID',
`variable_name` varchar(255) NOT NULL COMMENT '变量名称',
`variable_code` varchar(100) NOT NULL COMMENT '变量代码',
`variable_value` text NOT NULL COMMENT '变量值',
`data_type` varchar(50) DEFAULT 'string' COMMENT '数据类型string, number, boolean, json等',
`create_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`update_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '修改时间',
`create_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '创建人',
`update_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '修改人',
`deleted` bit(1) NULL DEFAULT b'0' COMMENT '是否删除',
`tenant_id` varchar(20) DEFAULT 'Default' COMMENT '租户id',
PRIMARY KEY (`id`),
KEY `idx_execution_id` (`execution_id`),
KEY `idx_variable_code` (`variable_code`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='活动表单变量表';
-- 创建活动与表单关联表
DROP TABLE IF EXISTS `mp_activity_form_relation`;
CREATE TABLE `mp_activity_form_relation` (
`id` int NOT NULL AUTO_INCREMENT COMMENT '主键ID',
`activity_id` int NOT NULL COMMENT '活动ID',
`form_id` int NOT NULL COMMENT '表单ID',
`is_primary` tinyint NOT NULL DEFAULT '0' COMMENT '是否主要0-否1-是',
`version` varchar(32) NOT NULL DEFAULT '1.0.0' COMMENT '版本号',
`create_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`update_time` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '修改时间',
`create_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '创建人',
`update_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '修改人',
`deleted` bit(1) NULL DEFAULT b'0' COMMENT '是否删除',
`tenant_id` varchar(20) DEFAULT 'Default' COMMENT '租户id',
PRIMARY KEY (`id`),
UNIQUE KEY `uk_activity_template` (`activity_id`, `form_id`),
KEY `idx_activity_id` (`activity_id`),
KEY `idx_form_id` (`form_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='活动与表单关联表';

View File

@ -0,0 +1,24 @@
--
DROP TABLE IF EXISTS `mp_test_child_character`;
CREATE TABLE `mp_test_child_character`(
`id` int NOT NULL AUTO_INCREMENT,
`parent_id` int NULL DEFAULT NULL COMMENT '家长Id',
`grade` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '年级',
`constellation` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '星座',
`child_birth_date` date NULL DEFAULT NULL COMMENT '出生年月',
`child_gender` varchar(10) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '孩子性别(男,女)',
`character_analysis` varchar(200) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '性格分析结果',
`character_traits` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '性格特征',
`suggestions` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '建议',
`character_type` varchar(100) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '性格类型',
`deleted` int NOT NULL COMMENT '逻辑删除(0-正常1-已删除)',
`create_time` datetime NOT NULL COMMENT '创建时间',
`create_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '创建人',
`update_time` datetime NULL DEFAULT NULL COMMENT '修改时间',
`update_by` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '修改人',
`tenant_id` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_german2_ci NULL DEFAULT NULL COMMENT '租户Id',
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_german2_ci ROW_FORMAT = Dynamic;
SET
FOREIGN_KEY_CHECKS = 1;

View File

@ -0,0 +1,90 @@
package com.seer.teach.mp.app.controller;
import cn.dev33.satoken.annotation.SaCheckLogin;
import cn.dev33.satoken.stp.StpUtil;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.ResultBean;
import com.seer.teach.common.annotation.DecryptionAnnotation;
import com.seer.teach.common.annotation.EncryptionAnnotation;
import com.seer.teach.common.annotation.LogPrint;
import com.seer.teach.mp.app.controller.req.ActivityFormSubmitReq;
import com.seer.teach.mp.app.controller.req.AppActivityFormExecutionQueryReq;
import com.seer.teach.mp.app.controller.resp.AppActivityFormExecutionResp;
import com.seer.teach.mp.app.controller.resp.AppActivityFormFieldResp;
import com.seer.teach.mp.app.controller.resp.AppActivityFormResp;
import com.seer.teach.mp.app.service.IAppActivityFormService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
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.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
/**
* <p>
* APP端活动表单控制器
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Tag(name = "APP - 活动表单")
@RestController
@RequestMapping("/app/activity/form")
@LogPrint
@EncryptionAnnotation
@DecryptionAnnotation
@RequiredArgsConstructor
@Slf4j
public class AppActivityFormController {
private final IAppActivityFormService appActivityFormService;
@Operation(summary = "获取活动可用的表单")
@GetMapping("/{activityId}")
@SaCheckLogin
public ResultBean<AppActivityFormResp> getFormByActivity(@PathVariable Integer activityId) {
AppActivityFormResp result = appActivityFormService.getFormByActivity(activityId);
return ResultBean.success(result);
}
@Operation(summary = "获取表单字段列表")
@GetMapping("/field/{templateId}")
@SaCheckLogin
public ResultBean<List<AppActivityFormFieldResp>> getFieldList(@PathVariable Integer templateId) {
List<AppActivityFormFieldResp> result = appActivityFormService.getFieldListByTemplate(templateId);
return ResultBean.success(result);
}
@Operation(summary = "获取用户提交的表单列表")
@PostMapping("/execution/page-list")
@SaCheckLogin
public ResultBean<PageListBean<AppActivityFormExecutionResp>> getExecutionList(@RequestBody @Valid AppActivityFormExecutionQueryReq query) {
Integer userId = StpUtil.getLoginIdAsInt();
PageListBean<AppActivityFormExecutionResp> result = appActivityFormService.getExecutionList(query, userId);
return ResultBean.success(result);
}
@Operation(summary = "提交表单")
@PostMapping("/submit")
@SaCheckLogin
public ResultBean<String> submitForm(@RequestBody @Valid ActivityFormSubmitReq req) {
Integer userId = StpUtil.getLoginIdAsInt();
String executionNo = appActivityFormService.submitForm(req, userId);
return ResultBean.success(executionNo);
}
@Operation(summary = "获取表单执行详情")
@GetMapping("/execution/{id}")
@SaCheckLogin
public ResultBean<AppActivityFormExecutionResp> getExecutionDetail(@PathVariable Integer id) {
return ResultBean.success(appActivityFormService.getExecutionWithFormData(id));
}
}

View File

@ -7,7 +7,7 @@ import com.seer.teach.common.ResultBean;
import com.seer.teach.common.annotation.DecryptionAnnotation;
import com.seer.teach.common.annotation.EncryptionAnnotation;
import com.seer.teach.common.annotation.LogPrint;
import com.seer.teach.mp.app.controller.req.AppAgentActivityQueryReq;
import com.seer.teach.mp.app.controller.req.AppActivityQueryReq;
import com.seer.teach.mp.app.controller.resp.AppActivityResp;
import com.seer.teach.mp.app.service.IAppActivityService;
import io.swagger.v3.oas.annotations.Operation;
@ -41,7 +41,7 @@ public class AppMpActivityController {
@Operation(summary = "活动列表")
@GetMapping("/page-list")
@SaCheckPermission("mp:app:agent:activity:list")
public ResultBean<PageListBean<AppActivityResp>> pageList(AppAgentActivityQueryReq query) {
public ResultBean<PageListBean<AppActivityResp>> pageList(AppActivityQueryReq query) {
Integer userId = StpUtil.getLoginIdAsInt();
return ResultBean.success(agentActivityService.pageList(query,userId));
}
@ -53,11 +53,4 @@ public class AppMpActivityController {
return ResultBean.success(agentActivityService.getById(id));
}
@Operation(summary = "活动二维码")
@GetMapping("/{agentId}/{activityId}/qrcode")
@SaCheckPermission("mp:app:agent:activity:qrcode")
public ResultBean<String> getQrCode(@PathVariable("agentId") Integer agentId, @PathVariable("activityId") Integer activityId, @RequestParam("appId") String appId) {
Integer userId = StpUtil.getLoginIdAsInt();
return ResultBean.success(agentActivityService.getQrCode(userId,agentId,activityId,appId));
}
}

View File

@ -5,6 +5,7 @@ import cn.dev33.satoken.stp.StpUtil;
import com.seer.teach.common.ResultBean;
import com.seer.teach.mp.app.controller.req.AppMpSignUpActivityReq;
import com.seer.teach.mp.app.controller.req.TestChildCharacterReq;
import com.seer.teach.mp.app.controller.resp.AppChildCharacterResp;
import com.seer.teach.mp.app.controller.resp.AppMpSignUpActivityResp;
import com.seer.teach.mp.app.controller.resp.TestChildCharacterResp;
import com.seer.teach.mp.app.service.AppParentAgentActivityService;
@ -13,13 +14,7 @@ import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.validation.Valid;
import lombok.AllArgsConstructor;
import org.springframework.validation.annotation.Validated;
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.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.bind.annotation.*;
/**
* 家长参与代理商活动控制器 - 应用端
@ -66,9 +61,17 @@ public class AppParentAgentActivityController {
@PostMapping("/test-child-character")
@SaCheckLogin
@Operation(summary = "测试孩子性格")
@Operation(summary = "AI测试孩子性格")
public ResultBean<TestChildCharacterResp> testChildCharacter(@RequestBody @Valid TestChildCharacterReq request) {
Integer parentId = StpUtil.getLoginIdAsInt();
return ResultBean.success(appParentAgentActivityService.testChildCharacter(request, parentId));
}
@GetMapping("/get-child-character")
@SaCheckLogin
@Operation(summary = "获取AI测试性格报告")
public ResultBean<AppChildCharacterResp> getChildCharacter() {
Integer parentId = StpUtil.getLoginIdAsInt();
return ResultBean.success(appParentAgentActivityService.getChildCharacter(parentId));
}
}

View File

@ -0,0 +1,28 @@
package com.seer.teach.mp.app.controller.req;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import jakarta.validation.constraints.NotNull;
import java.util.Map;
@Data
@Schema(description = "活动表单提交请求")
public class ActivityFormSubmitReq {
@Schema(description = "活动ID")
@NotNull(message = "活动ID不能为空")
private Integer activityId;
@Schema(description = "代理商ID")
@NotNull(message = "代理商ID不能为空")
private Integer agentId;
@Schema(description = "表单ID")
@NotNull(message = "表单ID不能为空")
private Integer formId;
@Schema(description = "表单数据")
private Map<String, Object> formData;
}

View File

@ -0,0 +1,19 @@
package com.seer.teach.mp.app.controller.req;
import com.seer.teach.common.request.PageRequest;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import lombok.EqualsAndHashCode;
@Data
@EqualsAndHashCode(callSuper = true)
@Schema(description = "APP端活动表单执行实例查询请求")
public class AppActivityFormExecutionQueryReq extends PageRequest {
@Schema(description = "活动ID")
private Integer activityId;
@Schema(description = "代理商ID")
private Integer agentId;
}

View File

@ -4,9 +4,9 @@ import com.seer.teach.common.request.PageRequest;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
@Schema(name = "AppAgentActivityQueryReq", description = "代理商活动查询请求参数")
@Schema(name = "AppActivityQueryReq", description = "代理商活动查询请求参数")
@Data
public class AppAgentActivityQueryReq extends PageRequest {
public class AppActivityQueryReq extends PageRequest {
@Schema(description = "活动名称")
private String activityName;

View File

@ -1,9 +1,9 @@
package com.seer.teach.mp.app.controller.req;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import jakarta.validation.constraints.NotNull;
import java.time.LocalDate;
@Schema(description = "测试孩子性格请求对象")

View File

@ -0,0 +1,47 @@
package com.seer.teach.mp.app.controller.resp;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.time.LocalDateTime;
import java.util.Map;
@Schema(name = "AppActivityFormExecutionResp", description = "APP端活动表单执行实例响应参数")
@Data
public class AppActivityFormExecutionResp {
private Integer id;
@Schema(description = "执行编号")
private String executionNo;
@Schema(description = "活动ID")
private Integer activityId;
@Schema(description = "代理商ID")
private Integer agentId;
@Schema(description = "使用的表单模板ID")
private Integer templateId;
@Schema(description = "提交人ID")
private Integer submitterId;
@Schema(description = "提交人姓名")
private String submitterName;
@Schema(description = "提交时间")
private LocalDateTime submitTime;
@Schema(description = "状态draft-草稿submitted-已提交approved-已批准rejected-已拒绝")
private String status;
@Schema(description = "表单数据")
private Map<String, Object> formData;
@Schema(description = "创建时间")
private LocalDateTime createTime;
@Schema(description = "更新时间")
private LocalDateTime updateTime;
}

View File

@ -0,0 +1,39 @@
package com.seer.teach.mp.app.controller.resp;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
@Schema(name = "AppActivityFormFieldResp", description = "APP端活动表单字段响应参数")
@Data
public class AppActivityFormFieldResp {
private Integer id;
@Schema(description = "字段名称")
private String fieldName;
@Schema(description = "字段代码(英文标识)")
private String fieldCode;
@Schema(description = "字段类型text, textarea, select, radio, checkbox, date, number等")
private String fieldType;
@Schema(description = "字段选项JSON格式适用于select, radio, checkbox等")
private String fieldOptions;
@Schema(description = "占位符提示")
private String placeholder;
@Schema(description = "是否必填0-否1-是")
private Integer isRequired;
@Schema(description = "排序")
private Integer sortOrder;
@Schema(description = "验证规则JSON格式")
private String validationRules;
@Schema(description = "字段描述")
private String description;
}

View File

@ -0,0 +1,23 @@
package com.seer.teach.mp.app.controller.resp;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.util.List;
@Schema(name = "AppActivityFormResp", description = "APP端活动表单模板响应参数")
@Data
public class AppActivityFormResp {
private Integer id;
@Schema(description = "表单模板名称")
private String templateName;
@Schema(description = "表单模板描述")
private String templateDescription;
@Schema(description = "表单字段列表")
private List<AppActivityFormFieldResp> fields;
}

View File

@ -0,0 +1,35 @@
package com.seer.teach.mp.app.controller.resp;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.time.LocalDate;
@Schema(description = "孩子性格响应对象")
@Data
public class AppChildCharacterResp {
@Schema(description = "性格分析结果")
private String characterAnalysis;
@Schema(description = "性格特征")
private String characterTraits;
@Schema(description = "建议")
private String suggestions;
@Schema(description = "性格类型")
private String characterType;
@Schema(description = "年级")
private String grade;
@Schema(description = "星座")
private String constellation;
@Schema(description = "出生年月")
private LocalDate childBirthDate;
@Schema(description = "孩子性别(男,女)")
private String childGender;
}

View File

@ -30,4 +30,8 @@ public class AppMpAgentResp {
@Schema(description = "是否是代理商联系人")
private Boolean isContactPerson;
@Schema(description = "是否有多个代理商")
private Boolean hasMultipleAgents;
}

View File

@ -4,6 +4,7 @@ import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.time.LocalDate;
import java.util.List;
@Schema(name = "AppMpSignUpActivityResp", description = "家长报名参加代理商活动信息Resp")
@Data
@ -54,6 +55,12 @@ public class AppMpSignUpActivityResp {
@Schema(description = "薄弱科目")
private String weakSubject;
@Schema(description = "薄弱科目")
private List<Integer> weakSubjectIds;
@Schema(description = "优势科目")
private List<Integer> strongSubjectIds;
@Schema(description = "代理商拨打电话联系家长的次数")
private Integer contactCallCount;
}

View File

@ -0,0 +1,23 @@
package com.seer.teach.mp.app.convert;
import com.seer.teach.mp.app.controller.resp.AppActivityFormExecutionResp;
import com.seer.teach.mp.app.controller.resp.AppActivityFormFieldResp;
import com.seer.teach.mp.app.controller.resp.AppActivityFormResp;
import com.seer.teach.mp.entity.MpActivityFormExecutionEntity;
import com.seer.teach.mp.entity.MpActivityFormFieldEntity;
import com.seer.teach.mp.entity.MpActivityFormEntity;
import org.mapstruct.Mapper;
import org.mapstruct.Mapping;
import org.mapstruct.factory.Mappers;
@Mapper
public interface AppActivityFormConvert {
AppActivityFormConvert INSTANCE = Mappers.getMapper(AppActivityFormConvert.class);
@Mapping(source = "fields", target = "fields", ignore = true)
AppActivityFormResp convertToAppTemplateResp(MpActivityFormEntity entity);
AppActivityFormFieldResp convertToAppFieldResp(MpActivityFormFieldEntity entity);
AppActivityFormExecutionResp convertToAppExecutionResp(MpActivityFormExecutionEntity entity);
}

View File

@ -1,6 +1,6 @@
package com.seer.teach.mp.app.convert;
import com.seer.teach.mp.app.controller.req.AppAgentActivityQueryReq;
import com.seer.teach.mp.app.controller.req.AppActivityQueryReq;
import com.seer.teach.mp.app.controller.resp.AppActivityResp;
import com.seer.teach.mp.entity.MpActivityEntity;
import org.mapstruct.Mapper;
@ -14,7 +14,7 @@ public interface AppAgentActivityConvert {
AppAgentActivityConvert INSTANCE = Mappers.getMapper(AppAgentActivityConvert.class);
MpActivityEntity convert(AppAgentActivityQueryReq req);
MpActivityEntity convert(AppActivityQueryReq req);
@Mapping(target = "createTime", dateFormat = "yyyy-MM-dd HH:mm:ss")
@Mapping(target = "updateTime", dateFormat = "yyyy-MM-dd HH:mm:ss")

View File

@ -1,8 +1,10 @@
package com.seer.teach.mp.app.convert;
import com.seer.teach.mp.app.controller.req.AppMpSignUpActivityReq;
import com.seer.teach.mp.app.controller.resp.AppChildCharacterResp;
import com.seer.teach.mp.app.controller.resp.AppMpSignUpActivityResp;
import com.seer.teach.mp.entity.MpActivityInfoCollectionEntity;
import com.seer.teach.mp.entity.MpTestChildCharacterEntity;
import org.mapstruct.Mapper;
import org.mapstruct.Mapping;
import org.mapstruct.factory.Mappers;
@ -19,6 +21,8 @@ public interface AppMpActivityInfoCollectionConvert {
*/
@Mapping(source = "mobile", target = "mobile")
@Mapping(source = "contactCallCount", target = "contactCallCount")
@Mapping(source = "weakSubjectIds", target = "weakSubjectIds")
@Mapping(source = "strongSubjectIds", target = "strongSubjectIds")
AppMpSignUpActivityResp convert2Resp(MpActivityInfoCollectionEntity entity);
@ -28,4 +32,7 @@ public interface AppMpActivityInfoCollectionConvert {
* @return 实体
*/
MpActivityInfoCollectionEntity convertOne2Entity(AppMpSignUpActivityReq request);
AppChildCharacterResp convert2ChildCharacterResp(MpTestChildCharacterEntity entity);
}

View File

@ -5,6 +5,7 @@ import com.seer.teach.common.enums.ResultCodeEnum;
import com.seer.teach.common.utils.AssertUtils;
import com.seer.teach.mp.app.controller.req.AppMpSignUpActivityReq;
import com.seer.teach.mp.app.controller.req.TestChildCharacterReq;
import com.seer.teach.mp.app.controller.resp.AppChildCharacterResp;
import com.seer.teach.mp.app.controller.resp.AppMpSignUpActivityResp;
import com.seer.teach.mp.app.controller.resp.TestChildCharacterResp;
import com.seer.teach.mp.app.convert.AppMpActivityInfoCollectionConvert;
@ -37,6 +38,8 @@ public class AppParentAgentActivityService implements IAppParentAgentActivitySer
private final AiModelCallService aiModelCallService;
private final IMpTestChildCharacterService mpTestChildCharacterService;
/**
* 报名活动
*
@ -181,6 +184,13 @@ public class AppParentAgentActivityService implements IAppParentAgentActivitySer
// 获取AI返回的内容
String content = response.getChoices().get(0).getMessage().getContent();
result = parseAiResponse(content);
// 如果AI调用成功则将测试结果保存到数据库中
MpTestChildCharacterEntity entity = getCharacterEntity(request, parentId, result);
boolean save = mpTestChildCharacterService.save(entity);
if (save) {
log.info("保存性格测试结果成功");
}
} else {
// 如果AI调用失败返回默认响应
result.setCharacterAnalysis("暂时无法分析孩子的性格,请稍后重试。");
@ -193,6 +203,20 @@ public class AppParentAgentActivityService implements IAppParentAgentActivitySer
return result;
}
private MpTestChildCharacterEntity getCharacterEntity(TestChildCharacterReq request, Integer parentId, TestChildCharacterResp result) {
MpTestChildCharacterEntity entity = new MpTestChildCharacterEntity();
entity.setParentId(parentId);
entity.setConstellation(request.getConstellation());
entity.setGrade(request.getGrade());
entity.setChildBirthDate(request.getChildBirthDate());
entity.setChildGender(request.getChildGender());
entity.setCharacterType(result.getCharacterType());
entity.setCharacterAnalysis(result.getCharacterAnalysis());
entity.setCharacterTraits(result.getCharacterTraits());
entity.setSuggestions(result.getSuggestions());
return entity;
}
/**
* 构建性格测试的提示词
*
@ -281,5 +305,20 @@ public class AppParentAgentActivityService implements IAppParentAgentActivitySer
}
/**
* 获取孩子性格返回结果
* @param parentId 家长ID
* @return 孩子性格返回结果
*/
public AppChildCharacterResp getChildCharacter(Integer parentId) {
MpTestChildCharacterEntity one = mpTestChildCharacterService.lambdaQuery()
.eq(MpTestChildCharacterEntity::getParentId, parentId)
.orderByDesc(MpTestChildCharacterEntity::getCreateTime)
.last("limit 1") // 获取最新的一条数据
.one();
if (one == null) {
return new AppChildCharacterResp();
}
return AppMpActivityInfoCollectionConvert.INSTANCE.convert2ChildCharacterResp(one);
}
}

View File

@ -0,0 +1,63 @@
package com.seer.teach.mp.app.service;
import com.seer.teach.common.PageListBean;
import com.seer.teach.mp.app.controller.req.ActivityFormSubmitReq;
import com.seer.teach.mp.app.controller.req.AppActivityFormExecutionQueryReq;
import com.seer.teach.mp.app.controller.resp.AppActivityFormExecutionResp;
import com.seer.teach.mp.app.controller.resp.AppActivityFormResp;
import com.seer.teach.mp.app.controller.resp.AppActivityFormFieldResp;
import java.util.List;
/**
* <p>
* APP端活动表单服务接口
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IAppActivityFormService {
/**
* 根据活动ID获取表单模板
*
* @param activityId 活动ID
* @return 表单模板响应对象
*/
AppActivityFormResp getFormByActivity(Integer activityId);
/**
* 根据模板ID获取字段列表
*
* @param templateId 模板ID
* @return 字段列表
*/
List<AppActivityFormFieldResp> getFieldListByTemplate(Integer templateId);
/**
* 提交表单
*
* @param req 表单提交请求
* @param userId 用户ID
* @return 执行编号
*/
String submitForm(ActivityFormSubmitReq req, Integer userId);
/**
* 根据执行ID获取完整表单数据
*
* @param executionId 执行ID
* @return 完整表单数据
*/
AppActivityFormExecutionResp getExecutionWithFormData(Integer executionId);
/**
* 根据查询条件获取执行列表
*
* @param query 查询条件
* @param userId 用户ID
* @return 执行记录分页列表
*/
PageListBean<AppActivityFormExecutionResp> getExecutionList(AppActivityFormExecutionQueryReq query, Integer userId);
}

View File

@ -1,8 +1,8 @@
package com.seer.teach.mp.app.service;
import com.seer.teach.common.PageListBean;
import com.seer.teach.mp.app.controller.req.AppActivityQueryReq;
import com.seer.teach.mp.app.controller.resp.AppActivityResp;
import com.seer.teach.mp.app.controller.req.AppAgentActivityQueryReq;
/**
* <p>
@ -21,7 +21,7 @@ public interface IAppActivityService {
* @param agentId 代理商ID
* @return 代理商活动分页列表
*/
PageListBean<AppActivityResp> pageList(AppAgentActivityQueryReq query, Integer agentId);
PageListBean<AppActivityResp> pageList(AppActivityQueryReq query, Integer agentId);
/**
* 根据ID获取活动详情
@ -31,13 +31,4 @@ public interface IAppActivityService {
*/
AppActivityResp getById(Integer id);
/**
* 获取活动二维码
*
* @param userId 用户ID
* @param agentId 代理商ID
* @param activityId 活动ID
* @return 活动二维码
*/
String getQrCode(Integer userId,Integer agentId,Integer activityId,String appId);
}

View File

@ -2,6 +2,8 @@ package com.seer.teach.mp.app.service;
import com.seer.teach.mp.app.controller.resp.AppMpAgentResp;
import java.util.List;
/**
* App端代理商服务接口
*/
@ -21,5 +23,5 @@ public interface IAppAgentService {
* @param userId 用户ID
* @return 代理商ID
*/
Integer getAgentIdByUserId(Integer userId);
List<Integer> getAgentIdListByUserId(Integer userId);
}

View File

@ -0,0 +1,245 @@
package com.seer.teach.mp.app.service.impl;
import cn.hutool.core.util.IdUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.seer.teach.common.PageListBean;
import com.seer.teach.common.utils.PageConverterUtils;
import com.seer.teach.mp.app.controller.req.ActivityFormSubmitReq;
import com.seer.teach.mp.app.controller.req.AppActivityFormExecutionQueryReq;
import com.seer.teach.mp.app.controller.resp.AppActivityFormExecutionResp;
import com.seer.teach.mp.app.controller.resp.AppActivityFormResp;
import com.seer.teach.mp.app.controller.resp.AppActivityFormFieldResp;
import com.seer.teach.mp.app.convert.AppActivityFormConvert;
import com.seer.teach.mp.app.service.IAppActivityFormService;
import com.seer.teach.mp.entity.*;
import com.seer.teach.mp.service.*;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.stream.Collectors;
/**
* <p>
* APP端活动表单服务实现类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
@Slf4j
@Service
@RequiredArgsConstructor
public class AppActivityFormServiceImpl implements IAppActivityFormService {
private final IMpActivityFormService activityFormTemplateService;
private final IMpActivityFormFieldService activityFormFieldService;
private final IMpActivityFormExecutionService activityFormExecutionService;
private final IMpActivityFormVariableService activityFormVariableService;
private final IMpActivityService mpActivityService;
private final IMpActivityFormRelationService activityFormTemplateRelationService;
@Override
public AppActivityFormResp getFormByActivity(Integer activityId) {
// 首先检查活动是否存在
MpActivityEntity activity = mpActivityService.getById(activityId);
if (activity == null) {
log.warn("活动不存在ID{}", activityId);
return null;
}
// 从关联表中获取与活动关联的表单ID
Integer formId = activityFormTemplateRelationService.getPrimaryFormIdByActivityId(activityId);
if (formId != null) {
MpActivityFormEntity template = activityFormTemplateService.getById(formId);
if (template != null) {
AppActivityFormResp resp = AppActivityFormConvert.INSTANCE.convertToAppTemplateResp(template);
// 获取该表单的所有字段
List<MpActivityFormFieldEntity> fields = activityFormFieldService.list(
new LambdaQueryWrapper<MpActivityFormFieldEntity>()
.eq(MpActivityFormFieldEntity::getFormId, formId)
);
List<AppActivityFormFieldResp> fieldResps = fields.stream()
.map(AppActivityFormConvert.INSTANCE::convertToAppFieldResp)
.collect(Collectors.toList());
resp.setFields(fieldResps);
return resp;
}
}
Optional<MpActivityFormRelationEntity> relation = activityFormTemplateRelationService.getLatestVersionByActivityId(activityId);
if (relation.isPresent()) {
formId = relation.get().getFormId();
MpActivityFormEntity template = activityFormTemplateService.getById(formId);
if (template != null) {
AppActivityFormResp resp = AppActivityFormConvert.INSTANCE.convertToAppTemplateResp(template);
// 获取该表单的所有字段
List<MpActivityFormFieldEntity> fields = activityFormFieldService.list(
new LambdaQueryWrapper<MpActivityFormFieldEntity>()
.eq(MpActivityFormFieldEntity::getFormId, formId)
);
List<AppActivityFormFieldResp> fieldResps = fields.stream()
.map(AppActivityFormConvert.INSTANCE::convertToAppFieldResp)
.collect(Collectors.toList());
resp.setFields(fieldResps);
return resp;
}
}
log.warn("未找到活动 {} 关联的表单表单", activityId);
return null;
}
@Override
public List<AppActivityFormFieldResp> getFieldListByTemplate(Integer templateId) {
List<MpActivityFormFieldEntity> fields = activityFormFieldService.list(
new LambdaQueryWrapper<MpActivityFormFieldEntity>()
.eq(MpActivityFormFieldEntity::getFormId, templateId)
.orderByAsc(MpActivityFormFieldEntity::getSortOrder)
.orderByDesc(MpActivityFormFieldEntity::getId)
);
return fields.stream()
.map(AppActivityFormConvert.INSTANCE::convertToAppFieldResp)
.collect(Collectors.toList());
}
@Override
@Transactional
public String submitForm(ActivityFormSubmitReq req, Integer userId) {
// 生成执行编号
String executionNo = "AFE-" + System.currentTimeMillis() + "-" + IdUtil.getSnowflakeNextId();
// 创建表单执行实例
MpActivityFormExecutionEntity execution = new MpActivityFormExecutionEntity();
execution.setExecutionNo(executionNo);
execution.setActivityId(req.getActivityId());
execution.setAgentId(req.getAgentId());
execution.setFormId(req.getFormId());
execution.setSubmitterId(userId); // 设置提交人ID为当前登录用户ID
execution.setSubmitTime(LocalDateTime.now());
execution.setStatus("submitted"); // 设置状态为已提交
// 保存表单执行实例
activityFormExecutionService.save(execution);
// 处理表单数据将其存储到变量表中
if (req.getFormData() != null && !req.getFormData().isEmpty()) {
for (Map.Entry<String, Object> entry : req.getFormData().entrySet()) {
MpActivityFormVariableEntity variable = new MpActivityFormVariableEntity();
variable.setExecutionId(execution.getId());
variable.setVariableName(entry.getKey()); // 使用字段代码作为变量名
variable.setVariableCode(entry.getKey()); // 使用字段代码作为变量代码
variable.setVariableValue(String.valueOf(entry.getValue())); // 将值转换为字符串存储
variable.setDataType(getDataType(entry.getValue())); // 根据值确定数据类型
activityFormVariableService.save(variable);
}
}
log.info("表单提交成功,执行编号:{}", executionNo);
return executionNo;
}
/**
* 根据执行ID获取完整表单数据
*/
public AppActivityFormExecutionResp getExecutionWithFormData(Integer executionId) {
MpActivityFormExecutionEntity execution = activityFormExecutionService.getById(executionId);
if (execution == null) {
return null;
}
AppActivityFormExecutionResp resp = AppActivityFormConvert.INSTANCE.convertToAppExecutionResp(execution);
// 获取表单变量数据
List<MpActivityFormVariableEntity> variables = activityFormVariableService.list(
new LambdaQueryWrapper<MpActivityFormVariableEntity>()
.eq(MpActivityFormVariableEntity::getExecutionId, executionId)
);
// 转换为Map形式的表单数据
Map<String, Object> formData = new HashMap<>();
for (MpActivityFormVariableEntity variable : variables) {
// 根据数据类型转换值
Object value = convertValueByType(variable.getVariableValue(), variable.getDataType());
formData.put(variable.getVariableCode(), value);
}
resp.setFormData(formData);
return resp;
}
/**
* 根据数据类型转换值
*/
private Object convertValueByType(String value, String dataType) {
if (value == null) {
return null;
}
switch (dataType) {
case "boolean":
return Boolean.parseBoolean(value);
case "number":
try {
// 尝试解析为整数或浮点数
if (value.contains(".")) {
return Double.parseDouble(value);
} else {
return Long.parseLong(value);
}
} catch (NumberFormatException e) {
return value; // 如果无法解析为数字则返回原始字符串
}
case "string":
default:
return value;
}
}
/**
* 根据值判断数据类型
*/
private String getDataType(Object value) {
if (value instanceof Boolean) {
return "boolean";
} else if (value instanceof Number) {
return "number";
} else if (value instanceof String) {
return "string";
} else {
return "string";
}
}
@Override
public PageListBean<AppActivityFormExecutionResp> getExecutionList(AppActivityFormExecutionQueryReq query, Integer userId) {
Page<MpActivityFormExecutionEntity> page = new Page<>(query.getPageNo(), query.getPageSize());
LambdaQueryWrapper<MpActivityFormExecutionEntity> wrapper = new LambdaQueryWrapper<>();
wrapper.eq(MpActivityFormExecutionEntity::getSubmitterId, userId)
.eq(query.getActivityId() != null, MpActivityFormExecutionEntity::getActivityId, query.getActivityId())
.eq(query.getAgentId() != null, MpActivityFormExecutionEntity::getAgentId, query.getAgentId())
.orderByDesc(MpActivityFormExecutionEntity::getId);
Page<MpActivityFormExecutionEntity> pageResult = activityFormExecutionService.page(page, wrapper);
List<AppActivityFormExecutionResp> records = pageResult.getRecords().stream()
.map(AppActivityFormConvert.INSTANCE::convertToAppExecutionResp)
.collect(Collectors.toList());
return PageConverterUtils.convertPageListBean(pageResult, records);
}
}

View File

@ -9,7 +9,7 @@ import com.seer.teach.common.enums.ResultCodeEnum;
import com.seer.teach.common.exception.CommonException;
import com.seer.teach.common.utils.AssertUtils;
import com.seer.teach.common.utils.PageConverterUtils;
import com.seer.teach.mp.app.controller.req.AppAgentActivityQueryReq;
import com.seer.teach.mp.app.controller.req.AppActivityQueryReq;
import com.seer.teach.mp.app.controller.req.MpGenerateQrCodeReq;
import com.seer.teach.mp.app.controller.resp.AppActivityResp;
import com.seer.teach.mp.app.controller.resp.MpQrCodeResp;
@ -20,7 +20,6 @@ import com.seer.teach.mp.entity.MpActivityEntity;
import com.seer.teach.mp.entity.MpAgentActivityParticipantEntity;
import com.seer.teach.mp.service.IMpActivityService;
import com.seer.teach.mp.service.IMpAgentActivityParticipantService;
import com.seer.teach.mp.service.IMpAgentService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
@ -48,7 +47,7 @@ public class AppActivityServiceImpl implements IAppActivityService {
private final IMpAgentActivityParticipantService agentActivityParticipantService;
@Override
public PageListBean<AppActivityResp> pageList(AppAgentActivityQueryReq query, Integer agentId) {
public PageListBean<AppActivityResp> pageList(AppActivityQueryReq query, Integer agentId) {
log.info("查询参数:{}", query);
IPage<MpActivityEntity> page = new Page<>(query.getPageNo(), query.getPageSize());
var pageResult = activityService.page(page, new LambdaQueryWrapper<>(MpActivityEntity.class)
@ -66,27 +65,4 @@ public class AppActivityServiceImpl implements IAppActivityService {
MpActivityEntity entity = activityService.getById(id);
return AppAgentActivityConvert.INSTANCE.convertToResp(entity);
}
@Override
public String getQrCode(Integer userId,Integer agentId,Integer activityId,String appId) {
MpActivityEntity activity = activityService.getById(activityId);
AssertUtils.notNull(activity, ResultCodeEnum.INVALID_ACTIVITY);
if(activity.getStatus() != 1){
throw new CommonException(ResultCodeEnum.INVALID_ACTIVITY);
}
MpAgentActivityParticipantEntity relation = agentActivityParticipantService.getParticipantsByActivityAndAgent(activityId, agentId);
AssertUtils.notNull(relation, ResultCodeEnum.INVALID_ACTIVITY);
if(StringUtils.isNotBlank(relation.getQrCodeUrl())){
return relation.getQrCodeUrl();
}
MpGenerateQrCodeReq req = new MpGenerateQrCodeReq();
req.setSceneStr("agentId=" + agentId + "&activityId=" + activityId);
req.setAppId(appId);
req.setType(2);
MpQrCodeResp mpQrCodeResp = officialQrCodeService.generateQrCode(req);
relation.setQrCodeUrl(mpQrCodeResp.getQrCodeUrl());
agentActivityParticipantService.updateById(relation);
return mpQrCodeResp.getQrCodeUrl();
}
}

View File

@ -1,5 +1,6 @@
package com.seer.teach.mp.app.service.impl;
import cn.hutool.core.collection.CollectionUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.seer.teach.common.PageListBean;
@ -17,7 +18,6 @@ import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;
/**
@ -38,12 +38,11 @@ public class AppAgentActivityParentInfoServiceImpl implements IAppAgentActivityP
@Override
public List<AgentActivityParentInfoResp> getParentsByActivityAndAgent(Integer activityId, Integer agentId,Integer userId) {
var userAgentId = appAgentService.getAgentIdByUserId(userId);
if (Objects.isNull(userAgentId)) {
var userAgentIds = appAgentService.getAgentIdListByUserId(userId);
if (CollectionUtil.isEmpty(userAgentIds)) {
return List.of();
}
log.info("getParentsByActivityAndAgent userAgentId:{}", userAgentId);
if(userAgentId.intValue() != agentId){
if(!userAgentIds.contains(agentId)){
throw new CommonException(ResultCodeEnum.RELATION_NOT_FOUND);
}
LambdaQueryWrapper<MpActivityInfoCollectionEntity> queryWrapper = new LambdaQueryWrapper<>();
@ -61,12 +60,11 @@ public class AppAgentActivityParentInfoServiceImpl implements IAppAgentActivityP
@Override
public PageListBean<AgentActivityParentInfoResp> getParentsByActivityAndAgent(Integer userId,AgentActivityParentQueryReq queryReq) {
var userAgentId = appAgentService.getAgentIdByUserId(userId);
if (Objects.isNull(userAgentId)) {
var userAgentIds = appAgentService.getAgentIdListByUserId(userId);
if (CollectionUtil.isEmpty(userAgentIds)) {
return new PageListBean<>();
}
log.info("userAgentId:{}", userAgentId);
if(userAgentId.intValue() != queryReq.getAgentId()){
if(!userAgentIds.contains(queryReq.getAgentId())){
throw new CommonException(ResultCodeEnum.RELATION_NOT_FOUND);
}
// 创建分页对象
@ -75,7 +73,7 @@ public class AppAgentActivityParentInfoServiceImpl implements IAppAgentActivityP
// 构建查询条件
LambdaQueryWrapper<MpActivityInfoCollectionEntity> queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.eq(MpActivityInfoCollectionEntity::getActivityId, queryReq.getActivityId())
.eq(MpActivityInfoCollectionEntity::getAgentId, userAgentId);
.eq(MpActivityInfoCollectionEntity::getAgentId, queryReq.getAgentId());
// 执行分页查询
Page<MpActivityInfoCollectionEntity> pageResult = activityInfoCollectionService.page(page, queryWrapper);

View File

@ -56,12 +56,11 @@ public class AppAgentActivityParticipantServiceImpl implements IAppAgentActivity
@Override
public List<AgentActivityParticipantResp> getParticipantsByActivityAndAgent(Integer agentId, Integer userId) {
var userAgentId = appAgentService.getAgentIdByUserId(userId);
if (Objects.isNull(userAgentId)) {
var userAgentIds = appAgentService.getAgentIdListByUserId(userId);
if (CollectionUtil.isEmpty(userAgentIds)) {
return List.of();
}
log.info("userAgentId:{}", userAgentId);
if(userAgentId.intValue() != agentId){
if(!userAgentIds.contains(agentId) ){
throw new CommonException(ResultCodeEnum.RELATION_NOT_FOUND);
}
var participants = agentActivityParticipantService.getListByAgentId(agentId);

View File

@ -55,7 +55,7 @@ public class AppAgentEmployeeRelationServiceImpl implements IAppAgentEmployeeRel
Integer employeeUserId = StpUtil.getLoginIdAsInt();
MpAgentEmployeeRelationEntity one = mpAgentEmployeeRelationService.lambdaQuery().eq(MpAgentEmployeeRelationEntity::getEmployeeUserId, employeeUserId).one();
if (one == null) {
return PageConverterUtils.convertPageListBean(page, null);
return new PageListBean<>();
}
// 获取代理商ID
Integer agentId = one.getAgentId();
@ -68,7 +68,7 @@ public class AppAgentEmployeeRelationServiceImpl implements IAppAgentEmployeeRel
List<Integer> matchUserIds = userInfoServiceApi.getUserIdsByUserNameLike(query.getEmployeeName());
if (CollectionUtil.isEmpty(matchUserIds)) {
log.info("无匹配员工");
return PageConverterUtils.convertPageListBean(page, null);
return new PageListBean<>();
}
wrapper.in(MpAgentEmployeeRelationEntity::getEmployeeUserId, matchUserIds);
}

View File

@ -1,5 +1,6 @@
package com.seer.teach.mp.app.service.impl;
import cn.hutool.core.collection.CollectionUtil;
import com.seer.teach.common.enums.ResultCodeEnum;
import com.seer.teach.common.utils.AssertUtils;
import com.seer.teach.mp.app.controller.resp.AppMpAgentResp;
@ -10,9 +11,14 @@ import com.seer.teach.mp.entity.MpAgentEntity;
import com.seer.teach.mp.service.IMpAgentEmployeeRelationService;
import com.seer.teach.mp.service.IMpAgentService;
import lombok.RequiredArgsConstructor;
import lombok.val;
import org.springframework.stereotype.Service;
import java.util.Collections;
import java.util.List;
import java.util.Objects;
import java.util.Optional;
import java.util.stream.Collectors;
/**
* App端代理商服务实现类
@ -26,25 +32,38 @@ public class AppAgentServiceImpl implements IAppAgentService {
@Override
public AppMpAgentResp getAgentRespByUserId(Integer userId) {
MpAgentEntity one = mpAgentService.lambdaQuery().eq(MpAgentEntity::getContactUserId, userId).one();
AssertUtils.notNull(one, ResultCodeEnum.AGENT_NOT_FOUND);
Integer agentId = one.getId();
MpAgentEntity agentEntity = mpAgentService.getAgentById(agentId);
if (Objects.isNull(agentEntity)) {
return null;
List<MpAgentEntity> agents = mpAgentService.getListByUserId(userId);
AssertUtils.notEmpty(agents, ResultCodeEnum.AGENT_NOT_FOUND);
MpAgentEntity agentEntity = null;
boolean hasContactPerson = false;
for (MpAgentEntity agent : agents) {
if (Objects.nonNull(agent.getContactUserId()) && agent.getContactUserId().equals(userId)) {
agentEntity = agent;
hasContactPerson = true;
break;
}
}
// 如果没找到对应的联系人则取第一个代理商
if (agentEntity == null) {
agentEntity = agents.get(0);
}
AppMpAgentResp appMpAgentResp = AppAgentConvert.INSTANCE.entityToResp(agentEntity);
Boolean isContactPerson = Objects.nonNull(agentEntity.getContactUserId()) && agentEntity.getContactUserId().equals(userId);
appMpAgentResp.setIsContactPerson(isContactPerson);
appMpAgentResp.setIsContactPerson(hasContactPerson);
appMpAgentResp.setHasMultipleAgents(agents.size() > 1);
return appMpAgentResp;
}
@Override
public Integer getAgentIdByUserId(Integer userId) {
MpAgentEmployeeRelationEntity mpAgentEmployeeRelationEntity = mpAgentEmployeeRelationService.getOneByUserId(userId);
if (mpAgentEmployeeRelationEntity == null) {
return null;
public List<Integer> getAgentIdListByUserId(Integer userId) {
List<MpAgentEmployeeRelationEntity> mpAgentEmployeeRelations = mpAgentEmployeeRelationService.getListByUserId(userId);
if (CollectionUtil.isEmpty(mpAgentEmployeeRelations)) {
List<MpAgentEntity> mpAgentEntities = mpAgentService.lambdaQuery().eq(MpAgentEntity::getContactUserId, userId).list();
if (CollectionUtil.isEmpty(mpAgentEntities)) {
return Collections.emptyList();
}
return mpAgentEmployeeRelationEntity.getAgentId();
return mpAgentEntities.stream().map(MpAgentEntity::getId).collect(Collectors.toList());
}
return mpAgentEmployeeRelations.stream().map(MpAgentEmployeeRelationEntity::getAgentId).collect(Collectors.toList());
}
}

View File

@ -0,0 +1,16 @@
package com.seer.teach.mp.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.seer.teach.mp.entity.MpActivityFormExecutionEntity;
/**
* <p>
* 活动表单执行实例表 服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IMpActivityFormExecutionService extends IService<MpActivityFormExecutionEntity> {
}

View File

@ -0,0 +1,16 @@
package com.seer.teach.mp.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.seer.teach.mp.entity.MpActivityFormFieldEntity;
/**
* <p>
* 活动表单字段定义表 服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IMpActivityFormFieldService extends IService<MpActivityFormFieldEntity> {
}

View File

@ -0,0 +1,50 @@
package com.seer.teach.mp.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.seer.teach.mp.entity.MpActivityFormRelationEntity;
import java.util.Optional;
/**
* <p>
* 活动与表单模板关联表 服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IMpActivityFormRelationService extends IService<MpActivityFormRelationEntity> {
/**
* 根据活动ID获取关联的主要表单ID
*
* @param activityId 活动ID
* @return 表单模板ID如果不存在则返回null
*/
Integer getPrimaryFormIdByActivityId(Integer activityId);
/**
* 根据活动ID获取关联的表单模板数量
*
* @param activityId 活动ID
* @return 表单模板数量
*/
long getCountByActivityId(Integer activityId);
/**
* 根据活动ID和模板ID建立关联
*
* @param activityId 活动ID
* @param formId 表单ID
* @return 操作是否成功
*/
boolean createRelation(Integer activityId, Integer formId);
/**
* 获取指定活动ID的最新版本
*
* @param activityId 活动ID
* @return 最新版本号
*/
Optional<MpActivityFormRelationEntity> getLatestVersionByActivityId(Integer activityId);
}

View File

@ -0,0 +1,16 @@
package com.seer.teach.mp.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.seer.teach.mp.entity.MpActivityFormEntity;
/**
* <p>
* 活动表单模板表 服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IMpActivityFormService extends IService<MpActivityFormEntity> {
}

View File

@ -0,0 +1,16 @@
package com.seer.teach.mp.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.seer.teach.mp.entity.MpActivityFormVariableEntity;
/**
* <p>
* 活动表单变量表 服务类
* </p>
*
* @author Lingma
* @since 2026-01-10
*/
public interface IMpActivityFormVariableService extends IService<MpActivityFormVariableEntity> {
}

Some files were not shown because too many files have changed in this diff Show More