Browse Source

Merge branch 'cloud_teacher_active_2021_09' into music_score

Joburgess 4 years ago
parent
commit
c21c8b557c
97 changed files with 3796 additions and 202 deletions
  1. 45 5
      cms/src/main/java/com/ym/mec/cms/controller/NewsController.java
  2. 12 0
      cms/src/main/java/com/ym/mec/cms/controller/queryinfo/NewsInformationQueryInfo.java
  3. 19 0
      cms/src/main/java/com/ym/mec/cms/dal/dao/StudentRegistrationDao.java
  4. 24 0
      cms/src/main/java/com/ym/mec/cms/dal/dao/SysConfigDao.java
  5. 104 0
      cms/src/main/java/com/ym/mec/cms/dal/entity/SysConfig.java
  6. 267 0
      cms/src/main/java/com/ym/mec/cms/service/SysConfigService.java
  7. 27 0
      cms/src/main/java/com/ym/mec/cms/service/impl/SysConfigServiceImpl.java
  8. 19 0
      cms/src/main/resources/config/mybatis/StudentRegistrationMapper.xml
  9. 85 0
      cms/src/main/resources/config/mybatis/SysConfigMapper.xml
  10. 12 0
      cms/src/main/resources/config/mybatis/SysNewsInformationMapper.xml
  11. 3 3
      codegen/src/main/resources/generateConfigration.xml
  12. 2 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/ChargeTypeDao.java
  13. 30 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/CloudTeacherOrderDao.java
  14. 14 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/IndexBaseMonthDataDao.java
  15. 7 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/MusicGroupDao.java
  16. 17 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/StudentDao.java
  17. 13 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/StudentPaymentOrderDao.java
  18. 13 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/StudentRegistrationDao.java
  19. 11 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/StudentVisitDao.java
  20. 43 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/SysCouponCodeDao.java
  21. 13 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/SysCouponDao.java
  22. 0 7
      mec-biz/src/main/java/com/ym/mec/biz/dal/dao/SysMusicCompareRecordDao.java
  23. 116 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dto/CloudTeacherActiveTargetDetailDto.java
  24. 105 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dto/CloudTeacherActiveTargetDto.java
  25. 35 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dto/CloudTeacherActiveTargetJsonDto.java
  26. 10 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dto/CountStudentTrainDataDto.java
  27. 36 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dto/HorseRaceLampDto.java
  28. 212 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/dto/SysCouponCodeDto.java
  29. 14 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/entity/CloudTeacherOrder.java
  30. 237 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/entity/SysCoupon.java
  31. 136 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/entity/SysCouponCode.java
  32. 34 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/enums/CouponTypeEnum.java
  33. 34 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/enums/EffectiveTypeEnum.java
  34. 2 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/enums/MessageTypeEnum.java
  35. 56 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/page/CloudTeacherActiveQueryInfo.java
  36. 11 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/page/StudentPaymentOrderQueryInfo.java
  37. 60 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/page/SysCouponCodeQueryInfo.java
  38. 34 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/page/SysCouponQueryInfo.java
  39. 10 0
      mec-biz/src/main/java/com/ym/mec/biz/dal/page/SysMusicCompareRecordQueryInfo.java
  40. 9 0
      mec-biz/src/main/java/com/ym/mec/biz/service/CloudTeacherOrderService.java
  41. 3 2
      mec-biz/src/main/java/com/ym/mec/biz/service/ContractService.java
  42. 15 1
      mec-biz/src/main/java/com/ym/mec/biz/service/MemberRankSettingService.java
  43. 1 1
      mec-biz/src/main/java/com/ym/mec/biz/service/OrganizationService.java
  44. 4 2
      mec-biz/src/main/java/com/ym/mec/biz/service/StudentPaymentOrderService.java
  45. 23 0
      mec-biz/src/main/java/com/ym/mec/biz/service/StudentService.java
  46. 9 0
      mec-biz/src/main/java/com/ym/mec/biz/service/SysConfigService.java
  47. 41 0
      mec-biz/src/main/java/com/ym/mec/biz/service/SysCouponCodeService.java
  48. 23 0
      mec-biz/src/main/java/com/ym/mec/biz/service/SysCouponService.java
  49. 4 3
      mec-biz/src/main/java/com/ym/mec/biz/service/SysMusicCompareRecordService.java
  50. 1 1
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/ChildrenDayReserveServiceImpl.java
  51. 5 0
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/CloudTeacherOrderServiceImpl.java
  52. 13 6
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/ContractServiceImpl.java
  53. 142 49
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/MemberRankSettingServiceImpl.java
  54. 12 3
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/MusicGroupServiceImpl.java
  55. 4 0
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/MusicGroupTrainPlanServiceImpl.java
  56. 1 1
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/ReplacementInstrumentActivityServiceImpl.java
  57. 2 2
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/SporadicChargeInfoImpl.java
  58. 1 1
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/StudentInstrumentServiceImpl.java
  59. 5 0
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/StudentPaymentOrderServiceImpl.java
  60. 2 2
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/StudentRepairServiceImpl.java
  61. 171 33
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/StudentServiceImpl.java
  62. 1 1
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/SubjectChangeServiceImpl.java
  63. 153 0
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/SysCouponCodeServiceImpl.java
  64. 85 0
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/SysCouponServiceImpl.java
  65. 60 5
      mec-biz/src/main/java/com/ym/mec/biz/service/impl/SysMusicCompareRecordServiceImpl.java
  66. 11 0
      mec-biz/src/main/resources/config/mybatis/ChargeTypeMapper.xml
  67. 82 5
      mec-biz/src/main/resources/config/mybatis/CloudTeacherOrderMapper.xml
  68. 31 0
      mec-biz/src/main/resources/config/mybatis/IndexBaseMonthDataMapper.xml
  69. 10 0
      mec-biz/src/main/resources/config/mybatis/MusicGroupMapper.xml
  70. 45 0
      mec-biz/src/main/resources/config/mybatis/StudentMapper.xml
  71. 11 1
      mec-biz/src/main/resources/config/mybatis/StudentPaymentOrderMapper.xml
  72. 34 0
      mec-biz/src/main/resources/config/mybatis/StudentRegistrationMapper.xml
  73. 6 0
      mec-biz/src/main/resources/config/mybatis/StudentVisitMapper.xml
  74. 216 0
      mec-biz/src/main/resources/config/mybatis/SysCouponCodeMapper.xml
  75. 153 0
      mec-biz/src/main/resources/config/mybatis/SysCouponMapper.xml
  76. 27 27
      mec-biz/src/main/resources/config/mybatis/SysMusicCompareRecordMapper.xml
  77. 6 0
      mec-client-api/src/main/java/com/ym/mec/task/TaskRemoteService.java
  78. 5 0
      mec-client-api/src/main/java/com/ym/mec/task/fallback/TaskRemoteServiceFallback.java
  79. 2 2
      mec-common/common-core/src/main/java/com/ym/mec/common/page/QueryInfo.java
  80. 3 2
      mec-student/src/main/java/com/ym/mec/student/controller/ContractsController.java
  81. 58 15
      mec-student/src/main/java/com/ym/mec/student/controller/MemberRankController.java
  82. 1 3
      mec-student/src/main/java/com/ym/mec/student/controller/MusicGroupController.java
  83. 0 2
      mec-student/src/main/java/com/ym/mec/student/controller/MusicGroupPaymentCalenderController.java
  84. 9 4
      mec-student/src/main/java/com/ym/mec/student/controller/StudentOrderController.java
  85. 54 0
      mec-student/src/main/java/com/ym/mec/student/controller/SysCouponCodeController.java
  86. 19 0
      mec-task/src/main/java/com/ym/mec/task/jobs/RemarkCountFlagTask.java
  87. 1 1
      mec-web/src/main/java/com/ym/mec/web/config/ResourceServerConfig.java
  88. 1 1
      mec-web/src/main/java/com/ym/mec/web/controller/ContractsController.java
  89. 92 0
      mec-web/src/main/java/com/ym/mec/web/controller/ExportController.java
  90. 1 2
      mec-web/src/main/java/com/ym/mec/web/controller/OrganizationController.java
  91. 33 0
      mec-web/src/main/java/com/ym/mec/web/controller/StudentManageController.java
  92. 33 0
      mec-web/src/main/java/com/ym/mec/web/controller/SysCouponCodeController.java
  93. 105 0
      mec-web/src/main/java/com/ym/mec/web/controller/SysCouponController.java
  94. 6 0
      mec-web/src/main/java/com/ym/mec/web/controller/TaskController.java
  95. 24 5
      mec-web/src/main/java/com/ym/mec/web/controller/education/ActivityController.java
  96. 3 2
      mec-web/src/main/java/com/ym/mec/web/controller/education/EduContractsController.java
  97. 2 2
      mec-web/src/main/resources/logback-spring.xml

+ 45 - 5
cms/src/main/java/com/ym/mec/cms/controller/NewsController.java

@@ -1,12 +1,14 @@
 package com.ym.mec.cms.controller;
 
+import com.ym.mec.cms.dal.dao.StudentRegistrationDao;
+import com.ym.mec.cms.dal.entity.SysConfig;
+import com.ym.mec.cms.service.SysConfigService;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiImplicitParam;
 import io.swagger.annotations.ApiOperation;
 
-import java.util.Date;
-import java.util.HashMap;
-import java.util.Map;
+import java.util.*;
+import java.util.stream.Collectors;
 
 import org.apache.commons.lang3.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -30,6 +32,8 @@ import com.ym.mec.util.collection.MapUtil;
 import com.ym.mec.web.WebFeignService;
 import com.yonge.log.model.AuditLogAnnotation;
 
+import javax.servlet.http.HttpServletRequest;
+
 @RestController
 @RequestMapping("news")
 @Api(tags = "资讯服务")
@@ -49,13 +53,18 @@ public class NewsController extends BaseController {
 	
 	@Autowired
 	private WebFeignService webFeignService;
+
+	@Autowired
+	private StudentRegistrationDao studentRegistrationDao;
+
+	@Autowired
+	private SysConfigService sysConfigService;
 	
 	@ApiOperation("资讯列表分页查询")
 	@GetMapping(value = "/list")
 	public Object getList(NewsInformationQueryInfo queryInfo) {
-
 		SysUser user = sysUserFeignService.queryUserInfo();
-		
+
 		String clientId = queryInfo.getClientId();
 		
 		if (!StringUtils.equalsIgnoreCase("student", clientId)) {
@@ -67,6 +76,22 @@ public class NewsController extends BaseController {
 				queryInfo.setOrganId(user.getOrganId());
 			}
 		}
+
+		SysConfig cloudTeacherActiveIds = sysConfigService.findByParamName(SysConfigService.CLOUD_TEACHER_ACTIVE_BANNER_IDS);
+		List<Integer> excludeIds = new ArrayList<>();
+		if(Objects.nonNull(cloudTeacherActiveIds)&&StringUtils.isNotBlank(cloudTeacherActiveIds.getParanValue())){
+			excludeIds = Arrays.stream(cloudTeacherActiveIds.getParanValue().split(",")).map(id->Integer.valueOf(id)).collect(Collectors.toList());
+		}
+		if (user == null || user.getId() == null) {
+			queryInfo.setOrganId(43);
+			queryInfo.setExcludeIds(excludeIds);
+		} else {
+			queryInfo.setOrganId(user.getOrganId());
+			int memberGroupNum = studentRegistrationDao.countStudentMemberGroupNum(user.getId());
+			if(memberGroupNum>0){
+				queryInfo.setExcludeIds(excludeIds);
+			}
+		}
 		
 		Map<String, Object> params = new HashMap<String, Object>();
 		MapUtil.populateMap(params, queryInfo);
@@ -101,6 +126,21 @@ public class NewsController extends BaseController {
 	public Object getHomeList(NewsInformationQueryInfo queryInfo) {
 		queryInfo.setRows(10);
 		SysUser user = sysUserFeignService.queryUserInfo();
+		SysConfig cloudTeacherActiveIds = sysConfigService.findByParamName(SysConfigService.CLOUD_TEACHER_ACTIVE_BANNER_IDS);
+		List<Integer> excludeIds = new ArrayList<>();
+		if(Objects.nonNull(cloudTeacherActiveIds)&&StringUtils.isNotBlank(cloudTeacherActiveIds.getParanValue())){
+			excludeIds = Arrays.stream(cloudTeacherActiveIds.getParanValue().split(",")).map(id->Integer.valueOf(id)).collect(Collectors.toList());
+		}
+		if (user == null || user.getId() == null) {
+			queryInfo.setOrganId(43);
+			queryInfo.setExcludeIds(excludeIds);
+		} else {
+			queryInfo.setOrganId(user.getOrganId());
+			int memberGroupNum = studentRegistrationDao.countStudentMemberGroupNum(user.getId());
+			if(memberGroupNum>0){
+				queryInfo.setExcludeIds(excludeIds);
+			}
+		}
 		return succeed(sysNewsInformationService.getHomeList(user, queryInfo));
 	}
 

+ 12 - 0
cms/src/main/java/com/ym/mec/cms/controller/queryinfo/NewsInformationQueryInfo.java

@@ -3,6 +3,7 @@ package com.ym.mec.cms.controller.queryinfo;
 import io.swagger.annotations.ApiModelProperty;
 
 import java.util.Date;
+import java.util.List;
 
 import com.ym.mec.cms.dal.entity.NewsStatusEnum;
 import com.ym.mec.common.page.QueryInfo;
@@ -32,6 +33,9 @@ public class NewsInformationQueryInfo extends QueryInfo {
 	
 	@ApiModelProperty(value = "分部编号", required = false)
 	private Integer organId;
+
+	@ApiModelProperty(value = "需排除编号")
+	private List<Integer> excludeIds;
 	
 	private String clientName;
 	
@@ -136,4 +140,12 @@ public class NewsInformationQueryInfo extends QueryInfo {
 	public void setClientId(String clientId) {
 		this.clientId = clientId;
 	}
+
+	public List<Integer> getExcludeIds() {
+		return excludeIds;
+	}
+
+	public void setExcludeIds(List<Integer> excludeIds) {
+		this.excludeIds = excludeIds;
+	}
 }

+ 19 - 0
cms/src/main/java/com/ym/mec/cms/dal/dao/StudentRegistrationDao.java

@@ -0,0 +1,19 @@
+package com.ym.mec.cms.dal.dao;
+
+import com.ym.mec.auth.api.entity.SysUser;
+import org.apache.ibatis.annotations.Param;
+
+import java.math.BigDecimal;
+import java.util.*;
+
+public interface StudentRegistrationDao {
+
+    /**
+     * @describe 统计学员所在会员团的数量
+     * @author Joburgess
+     * @date 2021/9/9 0009
+     * @param studentId:
+     * @return int
+     */
+    int countStudentMemberGroupNum(@Param("studentId") Integer studentId);
+}

+ 24 - 0
cms/src/main/java/com/ym/mec/cms/dal/dao/SysConfigDao.java

@@ -0,0 +1,24 @@
+package com.ym.mec.cms.dal.dao;
+
+import com.ym.mec.cms.dal.entity.SysConfig;
+import com.ym.mec.common.dal.BaseDAO;
+
+public interface SysConfigDao extends BaseDAO<Long, SysConfig> {
+
+    /**
+     * @Author: Joburgess
+     * @Date: 2019/10/9
+     * @params [paramName]
+     * @return com.ym.mec.biz.dal.entity.SysConfig
+     * @describe 根据配置名称获取配置信息
+     */
+    SysConfig findByParamName(String paramName);
+
+    /**
+     * 获取value
+     * @param paramName
+     * @return
+     */
+    String findConfigValue(String paramName);
+	
+}

+ 104 - 0
cms/src/main/java/com/ym/mec/cms/dal/entity/SysConfig.java

@@ -0,0 +1,104 @@
+package com.ym.mec.cms.dal.entity;
+
+import io.swagger.annotations.ApiModelProperty;
+import org.apache.commons.lang3.builder.ToStringBuilder;
+
+/**
+ * 对应数据库表(sys_config):
+ */
+public class SysConfig {
+
+	/**  */
+	private Long id;
+	
+	/** 参数名称 */
+	@ApiModelProperty(value = "参数名称", required = true)
+	private String paramName;
+	
+	/** 参数值 */
+	@ApiModelProperty(value = "参数值", required = true)
+	private String paranValue;
+	
+	/** 描述 */
+	@ApiModelProperty(value = "描述", required = true)
+	private String description;
+	
+	/** 创建时间 */
+	private java.util.Date createOn;
+	
+	/** 修改时间 */
+	private java.util.Date modifyOn;
+	
+	@ApiModelProperty(value = "消息组", required = true)
+	private String group;
+	
+	public void setId(Long id){
+		this.id = id;
+	}
+	
+	public Long getId(){
+		return this.id;
+	}
+			
+	public void setParamName(String paramName){
+		this.paramName = paramName;
+	}
+	
+	public String getParamName(){
+		return this.paramName;
+	}
+			
+	public void setParanValue(String paranValue){
+		this.paranValue = paranValue;
+	}
+	
+	public String getParanValue(){
+		return this.paranValue;
+	}
+
+	public <T> T getParanValue(Class<T> cla){
+		try {
+			return cla.cast(cla.getMethod("valueOf", String.class).invoke(cla.getInterfaces(),this.paranValue));
+		} catch (Exception e) {
+			return (T)this.paranValue.getClass();
+		}
+	}
+			
+	public void setDescription(String description){
+		this.description = description;
+	}
+	
+	public String getDescription(){
+		return this.description;
+	}
+			
+	public void setCreateOn(java.util.Date createOn){
+		this.createOn = createOn;
+	}
+	
+	public java.util.Date getCreateOn(){
+		return this.createOn;
+	}
+			
+	public void setModifyOn(java.util.Date modifyOn){
+		this.modifyOn = modifyOn;
+	}
+	
+	public java.util.Date getModifyOn(){
+		return this.modifyOn;
+	}
+			
+	public String getGroup() {
+		return group;
+	}
+
+	public void setGroup(String group) {
+		this.group = group;
+	}
+
+	@Override
+	public String toString() {
+		return ToStringBuilder.reflectionToString(this);
+	}
+
+}

+ 267 - 0
cms/src/main/java/com/ym/mec/cms/service/SysConfigService.java

@@ -0,0 +1,267 @@
+package com.ym.mec.cms.service;
+
+
+import com.ym.mec.cms.dal.entity.SysConfig;
+import com.ym.mec.common.service.BaseService;
+
+public interface SysConfigService extends BaseService<Long, SysConfig> {
+
+    public static final String BASE_API_URL = "base_api_url";
+
+    /**
+     * 缴费状态提前{}天刷新
+     */
+    public static final String REFRESH_PAYMENT_STATUS_EARLY_DAYS = "refresh_payment_status_early_days";
+
+    /**
+     * VIP课结束后,用户可申诉时间,为课程结束后的{}天
+     */
+    public static final String VIP_APPEAL_DAYS_RANGE = "vip_appeal_days_range";
+
+    /**
+     * 线下课最早打卡时间可提前分钟数
+     */
+    String OFFLINE_SIGN_IN_EARLY_FORWARD_TIME = "offline_sign_in_early_forward_time";
+
+    /**
+     * 老师正常打卡时间,为课程当天,距离开课时间前{}分钟
+     */
+    public static final String ADVANCE_SIGN_IN_MINUTES = "advance_sign_in_minutes";
+
+    String ADVANCE_SIGN_OUT_MINUTES = "advance_sign_out_minutes";
+
+    /**
+     * 老师可以打卡范围,为教学定位方圆{}米
+     */
+    public static final String ATTENDANCE_RANGE = "attendance_range";
+
+    String ATTENDANCE_RANGE_VIP = "attendance_range_vip";
+
+    /**
+     * 学生允许请假的时间,为开课前{}小时
+     */
+    public static final String ADVANCE_LEAVE_HOURS = "advance_leave_hours";
+
+    /**
+     * 最早请假提前时间
+     */
+    String EARLIEST_TIME_FOR_LEAVE="earliest_time_for_leave";
+
+    String ENABLE_TEACHER_COURSE_ADJUST_DEFAULT_HOURS = "enable_teacher_course_adjust_default_hours";
+
+    /**
+     * 单技课梯度结算规则设置
+     */
+    public static final String SIGLE_GRADIENT_SETTLEMENT_RULE = "sigle_gradient_settlement_rule";
+
+    /**
+     * 合奏课梯度结算规则设置
+     */
+    public static final String MAX_GRADIENT_SETTLEMENT_RULE = "max_gradient_settlement_rule";
+
+    /**
+     * 小班课梯度结算规则设置
+     */
+    public static final String HIGH_GRADIENT_SETTLEMENT_RULE = "high_gradient_settlement_rule";
+
+    /**
+     * 如果没有签退,{}分钟后自动发送推送信息
+     */
+    public static final String SIGN_OUT_MESSAGE_PUSH_MINUTE = "sign_out_message_push_minute";
+
+    /**
+     * 试听课默认单节课时长
+     */
+    String DEMO_GROUP_SINGLE_CLASS_MINUTES_ = "demo_group_single_class_minutes_";
+    String USER_DEFAULT_HEAD_URL = "user_default_head_url";
+    String STUDENT_APPLY_URL = "student_apply_url";
+    String SERVER_PHONE = "server_phone";
+
+    String MUSIC_GROUP_SETTLEMENT_CLASS_MINUTES = "music_group_settlement_class_minutes";
+
+    String MUSIC_GROUP_SETTLEMENT_DAY = "music_group_settlement_day";
+
+    String MUSIC_GROUP_SETTLEMENT_SINGLE_CLASS_MINUTES = "music_group_settlement_single_class_minutes";
+
+    String REFUND_PERIOD = "refund_period";
+
+    /**
+     * 可签退时间限制(自然天)
+     */
+    String ENABLE_SIGN_OUT_TIME_RANGE = "enable_sign_out_time_range";
+
+    /**
+     * 可更新学生签到状态时间限制,课程结束后{}分钟
+     */
+    String ENABLE_STUDENT_ATTENDANCE_TIME_RANGE = "enable_student_attendance_time_range";
+
+    /**
+     * vip课程可更新学生签到状态时间限制,课程结束后{}分钟
+     */
+    String ENABLE_STUDENT_ATTENDANCE_TIME_RANGE_VIP = "enable_student_attendance_time_range_vip";
+
+    String ENABLE_STUDENT_ATTENDANCE_BEFOR_COURSE_START_TIME_RANGE_VIP = "enable_student_attendance_befor_course_start_time_range_vip";
+
+    /**
+     * @describe 陪练课课酬
+     */
+    String PRACTICE_COURSE_SALARY = "practice_course_salary";
+
+    /**
+     * @describe 陪练课时长
+     */
+    String PRACTICE_COURSE_MINUTES = "practice_course_minutes";
+
+    /**
+     * @describe 陪练课预约开始时间
+     */
+    String PRACTICE_APPLY_START_TIME = "practice_apply_start_time";
+
+    /**
+     * @describe 陪练课预约结束时间
+     */
+    String PRACTICE_APPLY_END_TIME = "practice_apply_end_time";
+
+    /**
+     * @describe 陪练课预约时间间隔
+     */
+    String PRACTICE_APPLY_INTERVAL_TIME = "practice_apply_interval_time";
+
+    /**
+     * @describe 陪练课可预约声部列表
+     */
+    String PRACTICE_SUBJECT_ID_LIST = "practice_subject_id_list";
+
+    /**
+     * @describe 教师请假数据
+     */
+    String TEACHER_LEAVE_DATA = "teacher_leave_data";
+
+    /**
+     * 十分钟内最大可发送的短信次数
+     */
+    String SMS_MAX_TIMES = "sms_max_times";
+
+    /**
+     * 连堂课间隔时间
+     */
+    String ONLINE_CONTINUE_COURSE_TIME = "online_continue_course_time";
+
+    /**
+     * 连堂课间隔时间
+     */
+    String AUTO_CLOSE_NETWORK_ROOM = "auto_close_network_room";
+
+    /**
+     * @describe 付费陪练课可购买最大月数
+     */
+    String PRACTICE_PAY_MAX_MONTH = "practice_pay_max_month";
+
+    /**
+     * @describe 付费陪练课单月上课数量
+     */
+    String PRACTICE_PAY_DRILL_TIMES_ON_ONE_WEEK = "practice_pay_drill_times_on_one_week";
+
+    /**
+     * @describe 付费陪练课活动截至日期
+     */
+    String PRACTICE_BUY_ACTIVITY_EXPIRE_DATE = "practice_buy_activity_expire_date";
+
+    /**
+     * 陪练老师端入口地址
+     */
+    String TEACHER_STUDY_REPORT_URL = "teacher_study_report_url";
+
+    /**
+     * 陪练课报告地址
+     */
+    String STUDENT_STUDY_REPORT_URL = "student_study_report_url";
+
+    /**
+     * @describe 陪练课续费地址
+     */
+    String PRACTICE_RENEW_URL = "practice_renew_url";
+
+    /**
+     * @describe 老师端baseUrl
+     */
+    String TEACHER_BASE_URL = "teacher_base_url";
+
+    String COURSE_BEFORE_BUFFER_TIME = "course_before_buffer_time";
+
+    String COURSE_AFTER_BUFFER_TIME = "course_after_buffer_time";
+
+    String PRACTICE_PROMOTION_ACTIVITY_START_DATE = "practice_promotion_activity_start_date";
+
+    String NEW_MSG_PUSH = "您收到一条训练回复,请点击查看";
+
+    /**
+     * @describe 教务端baseUrl
+     */
+    String EDU_TEACHER_BASE_URL = "edu_teacher_base_url";
+
+    String HOLIDAY_SETTING = "holiday_setting";
+
+    String PRACTICE_FREE_APPLY_EXPIRE_DATE = "practice_free_apply_expire_date";
+    
+    String START_TIME_OF_1111 = "start_time_of_1111";
+    
+    String END_TIME_OF_1111 = "end_time_of_1111";
+
+    String VIP_SPECIAL_ACTIVITY_IDS = "vip_special_activity_ids";
+
+    String DAYA_BASE_SALARY_AMOUNT = "daya_base_salary_amount";
+
+    String WARNING_MIN_COURSE_SALARY = "warning_min_course_salary";
+
+    //提醒乐团主管排下学期的课程的时间节点(默认提前14天)
+    String REMIND_COURSE_TIME = "remind_course_time";
+
+    //会员结束前15天提醒学员续费(默认提前15天)
+    String PUSH_MEMBER_RENEW = "push_member_renew";
+
+    //试用会员结束前3天提醒学员续费(默认提前3天)
+    String EXPERIENCE_PUSH_MEMBER_RENEW = "experience_push_member_renew";
+
+    //会员结束前15天自动创建乐团续费(默认提前15天)
+    String AUTO_CREATE_MEMBER_RENEW = "auto_create_member_renew";
+
+    //会员结束前15天提醒学员续费(默认提前5天)
+    String PUSH_MEMBER_RENEW_AGAIN = "push_member_renew_again";
+
+    //会员结束前5天提醒学员续费(退团提醒)(默认提前5天)
+    String PUSH_MEMBER_RENEW_QUIT = "push_member_renew_quit";
+
+    String CHILDREN_DAY_VIP_ACTIVITY_IDS = "children_day_vip_activity_ids";
+
+    //云教练作业开关0关1开
+    String HOMEWORK_OPEN_FLAG = "homework_open_flag";
+
+    //云教练免费体验开关0关1开
+    String FREE_CLOUD_OPEN_FLAG = "free_cloud_open_flag";
+
+    //乐团问卷调查编号
+    String MUSIC_GROUP_TOPIC_ID = "music_group_topic_id";
+
+    //云教练试用时间最晚截止时间
+    String EXPERIENCE_MEMBERSHIP_END_TIME = "experience_membership_end_time";
+
+    //云教练训练时长小于80分钟需要回访
+    String STUDENT_CLOUD_TEACHER_TOTAL_PLAY_TIME = "student_cloud_teacher_total_play_time";
+
+    //云教练训练次数小于4次需要回访
+    String STUDENT_CLOUD_TEACHER_TRAIN_NUM = "student_cloud_teacher_train_num";
+
+    //云教练活动分部目标JSON
+    String CLOUD_TEACHER_ACTIVE_TARGET = "cloud_teacher_active_target";
+
+    //云教练活动开屏广告编号
+    String CLOUD_TEACHER_ACTIVE_BANNER_IDS = "cloud_teacher_active_banner_ids";
+
+    /**
+     * @return com.ym.mec.biz.dal.entity.SysConfig
+     * @params paramName
+     * @describe 根据配置名称获取配置信息
+     */
+    SysConfig findByParamName(String paramName);
+}

+ 27 - 0
cms/src/main/java/com/ym/mec/cms/service/impl/SysConfigServiceImpl.java

@@ -0,0 +1,27 @@
+package com.ym.mec.cms.service.impl;
+
+
+import com.ym.mec.cms.dal.dao.SysConfigDao;
+import com.ym.mec.cms.dal.entity.SysConfig;
+import com.ym.mec.cms.service.SysConfigService;
+import com.ym.mec.common.dal.BaseDAO;
+import com.ym.mec.common.service.impl.BaseServiceImpl;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+@Service
+public class SysConfigServiceImpl extends BaseServiceImpl<Long, SysConfig>  implements SysConfigService {
+	
+	@Autowired
+	private SysConfigDao sysConfigDao;
+
+	@Override
+	public BaseDAO<Long, SysConfig> getDAO() {
+		return sysConfigDao;
+	}
+
+	@Override
+	public SysConfig findByParamName(String paramName) {
+		return sysConfigDao.findByParamName(paramName);
+	}
+}

+ 19 - 0
cms/src/main/resources/config/mybatis/StudentRegistrationMapper.xml

@@ -0,0 +1,19 @@
+<?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.ym.mec.cms.dal.dao.StudentRegistrationDao">
+
+    <select id="countStudentMemberGroupNum" resultType="int">
+        SELECT COUNT(DISTINCT sr.music_group_id_)
+        FROM student_registration sr
+            LEFT JOIN music_group mg ON sr.music_group_id_=mg.id_
+        WHERE sr.music_group_status_ IN ('APPLY', 'NORMAL')
+          AND mg.course_view_type_=2
+          AND mg.status_ NOT IN ('CANCELED', 'CLOSE')
+          AND sr.user_id_ = #{studentId}
+    </select>
+
+</mapper>

+ 85 - 0
cms/src/main/resources/config/mybatis/SysConfigMapper.xml

@@ -0,0 +1,85 @@
+<?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.ym.mec.cms.dal.dao.SysConfigDao">
+
+	<resultMap type="com.ym.mec.cms.dal.entity.SysConfig" id="SysConfig">
+		<result column="id_" property="id" />
+		<result column="param_name_" property="paramName" />
+		<result column="paran_value_" property="paranValue" />
+		<result column="description_" property="description" />
+		<result column="create_on_" property="createOn" />
+		<result column="modify_on_" property="modifyOn" />
+		<result column="group_" property="group" />
+	</resultMap>
+
+	<!-- 根据主键查询一条记录 -->
+	<select id="get" resultMap="SysConfig">
+		SELECT * FROM sys_config WHERE id_ = #{id}
+	</select>
+
+	<!-- 全查询 -->
+	<select id="findAll" resultMap="SysConfig">
+		SELECT * FROM sys_config where 1=1
+		<if test="group != null">
+			and group_ = #{group}
+		</if>
+		ORDER BY id_
+	</select>
+
+	<!-- 向数据库增加一条记录 -->
+	<insert id="insert" parameterType="com.ym.mec.cms.dal.entity.SysConfig"
+		useGeneratedKeys="true" keyColumn="id" keyProperty="id">
+		<!-- <selectKey resultClass="int" keyProperty="id" > SELECT SEQ_WSDEFINITION_ID.nextval 
+			AS ID FROM DUAL </selectKey> -->
+		INSERT INTO sys_config
+		(id_,param_name_,paran_value_,description_,create_on_,modify_on_,group_)
+		VALUES(#{id},#{paramName},#{paranValue},#{description},#{createOn},#{modifyOn},#{group})
+	</insert>
+
+	<!-- 根据主键查询一条记录 -->
+	<update id="update" parameterType="com.ym.mec.cms.dal.entity.SysConfig">
+		UPDATE sys_config
+		<set>
+			<if test="modifyOn != null">
+				modify_on_ = #{modifyOn},
+			</if>
+			<if test="paranValue != null">
+				paran_value_ = #{paranValue},
+			</if>
+			<if test="description != null">
+				description_ = #{description},
+			</if>
+			<if test="paramName != null">
+				param_name_ = #{paramName},
+			</if>
+			<if test="group != null">
+				group_ = #{group},
+			</if>
+		</set>
+		WHERE id_ = #{id}
+	</update>
+
+	<!-- 根据主键删除一条记录 -->
+	<delete id="delete">
+		DELETE FROM sys_config WHERE id_ = #{id}
+	</delete>
+
+	<!-- 分页查询 -->
+	<select id="queryPage" resultMap="SysConfig" parameterType="map">
+		SELECT * FROM sys_config ORDER BY id_
+		<include refid="global.limit" />
+	</select>
+
+	<!-- 查询当前表的总记录数 -->
+	<select id="queryCount" resultType="int">
+		SELECT COUNT(*) FROM sys_config
+	</select>
+	
+	<select id="findByParamName" resultMap="SysConfig">
+		SELECT * FROM sys_config WHERE param_name_ = #{paramName}
+	</select>
+    <select id="findConfigValue" resultType="java.lang.String">
+		SELECT paran_value_ FROM sys_config WHERE param_name_ = #{paramName}
+	</select>
+</mapper>

+ 12 - 0
cms/src/main/resources/config/mybatis/SysNewsInformationMapper.xml

@@ -68,6 +68,12 @@
 			<if test="organIdList != null">
 				and INTE_ARRAY(#{organIdList},sni.organ_id_list_)
 			</if>
+			<if test="excludeIds!=null and excludeIds.size()>0">
+				AND sni.id_ NOT IN
+				<foreach collection="excludeIds" item="excludeId" open="(" close=")" separator=",">
+					#{excludeId}
+				</foreach>
+			</if>
 			<if test="clientName != 'manage'">
 				<choose>
 					<when test="memo != null and memo != ''">
@@ -219,6 +225,12 @@
 		<if test="tenantId != null">
 			and sni.tenant_id_ = #{tenantId}
 		</if>
+		<if test="excludeIds!=null and excludeIds.size()>0">
+			AND sni.id_ NOT IN
+			<foreach collection="excludeIds" item="excludeId" open="(" close=")" separator=",">
+				#{excludeId}
+			</foreach>
+		</if>
 			<if test="subjectId != null">
 				and find_in_set(#{subjectId},sni.subject_id_list_)
 			</if>

+ 3 - 3
codegen/src/main/resources/generateConfigration.xml

@@ -2,11 +2,11 @@
 <GenerateConfiguration>
 	<dbConfiguration>
 		<driverClass>com.mysql.jdbc.Driver</driverClass>
-		<url>jdbc:mysql://47.114.1.200:3306/mec_dev</url>
+		<url>jdbc:mysql://47.114.1.200:3306/mec_test</url>
 		<username>mec_dev</username>
 		<password>dayaDataOnline@2019</password>
-		<catalog>mec_dev</catalog>
-		<schema>mec_dev</schema>
+		<catalog>mec_test</catalog>
+		<schema>mec_test</schema>
 	</dbConfiguration>
 	<srcBase>e:/javabean</srcBase>
 	<pojoPackageName>com.ym.mec.biz.dal.entity</pojoPackageName>

+ 2 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/ChargeTypeDao.java

@@ -16,4 +16,6 @@ public interface ChargeTypeDao extends BaseDAO<Integer, ChargeType> {
      * @return
      */
     List<Map<Integer, String>> queryNameByIds(@Param("chargeTypeIds") String chargeTypeIds);
+
+    List<Map<Integer, String>> queryNormalChargeName(List<Integer> studentIds);
 }

+ 30 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/CloudTeacherOrderDao.java

@@ -1,9 +1,12 @@
 package com.ym.mec.biz.dal.dao;
 
+import java.util.Collection;
 import java.util.List;
 import java.util.Map;
 import java.util.Set;
 
+import com.ym.mec.biz.dal.dto.CloudTeacherActiveTargetDetailDto;
+import com.ym.mec.biz.dal.page.CloudTeacherActiveQueryInfo;
 import org.apache.ibatis.annotations.Param;
 
 import com.ym.mec.biz.dal.dto.CloudTeacherOrderDto;
@@ -50,4 +53,31 @@ public interface CloudTeacherOrderDao extends BaseDAO<Long, CloudTeacherOrder> {
     CloudTeacherOrderDto queryOrderInfoByOrderId(Long orderId);
 
     List<Map<Long, String>> queryNoStartByUserIds(@Param("userIds") Set<Integer> userIds, @Param("isMusicMember") Boolean isMusicMember);
+
+    /**
+     * 获取购买了云教练活动的学员列表
+     * @param param
+     * @return
+     */
+    int countCloudTeacherActiveDetail(Map<String, Object> param);
+
+    /**
+     * 获取购买了云教练活动的学员列表
+     * @param param
+     * @return
+     */
+    List<CloudTeacherActiveTargetDetailDto> queryCloudTeacherActiveDetail(Map<String, Object> param);
+
+    /**
+     * 获取学员购买的云教练活动订单
+     * @param userId
+     * @param activeRemark
+     * @param remark
+     * @return
+     */
+    String queryActiveOrderPage(@Param("userId") Integer userId,
+                                                 @Param("activeRemark") Integer activeRemark,
+                                                 @Param("remark") String remark);
+
+    List<Integer> getStudentIds();
 }

+ 14 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/IndexBaseMonthDataDao.java

@@ -1,5 +1,6 @@
 package com.ym.mec.biz.dal.dao;
 
+import com.ym.mec.biz.dal.dto.CloudTeacherActiveTargetDto;
 import com.ym.mec.biz.dal.dto.OrganVipGroupCategoryCourseNumDto;
 import com.ym.mec.biz.dal.dto.StudentErrorLeaveDto;
 import com.ym.mec.biz.dal.dto.StudentLeaveCourseDto;
@@ -339,4 +340,17 @@ public interface IndexBaseMonthDataDao extends BaseDAO<Long, IndexBaseMonthData>
     List<IndexBaseMonthData> getCloudStudyLivelyStudentNumData(@Param("dayStr") String dayStr);
 
     List<IndexBaseMonthData> getCloudStudyNewStudentNumData(@Param("dayStr") String dayStr);
+
+    /**
+     * 云教练活动分部统计
+     * @param params
+     * @return
+     */
+    List<CloudTeacherActiveTargetDto> countCloudTeacherActive(Map<String, Object> params);
+
+    /**
+     * 获取各分部学员总人数
+     * @return
+     */
+    List<Map<String, Long>> countTotalStudentNum();
 }

+ 7 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/MusicGroupDao.java

@@ -469,4 +469,11 @@ public interface MusicGroupDao extends BaseDAO<String, MusicGroup> {
 	 * @return java.util.List<java.lang.String>
 	 */
     List<TeacherMusicStudentOverViewDto> queryTeacherMusicStudentOverView(@Param("musicGroupIds") List<String> musicGroupIds);
+
+    /**
+     * 获取在读,进行中的乐团名称
+     * @param studentIds
+     * @return
+     */
+    List<Map<Integer, String>> queryNormalGroupName(@Param("studentIds") List<Integer> studentIds);
 }

+ 17 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/StudentDao.java

@@ -372,4 +372,21 @@ public interface StudentDao extends com.ym.mec.common.dal.BaseDAO<Integer, Stude
      * @return java.util.Set<java.lang.Integer>
      */
     Set<Integer> getValidVipStudentIds();
+
+    /**
+     * 获取老师关联的有课的学员列表
+     * @param teacherId
+     * @return
+     */
+    List<Integer> getStudentByHasCourse(Integer teacherId);
+
+    /**
+     * 清空学员统计标记
+     */
+    void cleanCountFlag();
+
+    /**
+     * 标记进行中乐团在读学员+VIP、网管有课的学员
+     */
+    void remarkCountFlag(@Param("studentIds") List<Integer> studentIds);
 }

+ 13 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/StudentPaymentOrderDao.java

@@ -5,6 +5,7 @@ import java.util.Date;
 import java.util.List;
 import java.util.Map;
 
+import com.ym.mec.biz.dal.entity.CloudTeacherOrder;
 import org.apache.ibatis.annotations.Param;
 
 import com.ym.mec.biz.dal.dto.BasicUserDto;
@@ -436,4 +437,16 @@ public interface StudentPaymentOrderDao extends BaseDAO<Long, StudentPaymentOrde
      * @return
      */
     List<Mapper> getMoneyInMusicApply(@Param("musicGroupIds") List<String> musicGroupIds);
+
+    /**
+     * 获取学员购买的云教练活动订单
+     * @param userId
+     * @param activeRemark
+     * @param remark
+     * @return
+     */
+    StudentPaymentOrder findByUserAndActive(@Param("userId") Integer userId,
+                                            @Param("activeRemark") Integer activeRemark,
+                                            @Param("remark") String remark, @Param("status") String status);
+
 }

+ 13 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/StudentRegistrationDao.java

@@ -681,4 +681,17 @@ public interface StudentRegistrationDao extends BaseDAO<Long, StudentRegistratio
      * @return
      */
     List<Integer> findStudentIds();
+
+    /**
+     * 获取有会员团的学员
+     * @return
+     */
+    List<Integer> queryHasMemberGroupStudent();
+
+    /**
+     * 获取云教练活动分部目标
+     * @return
+     */
+    List<CloudTeacherActiveTargetJsonDto> queryOrganTarget();
+
 }

+ 11 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/StudentVisitDao.java

@@ -64,4 +64,15 @@ public interface StudentVisitDao extends BaseDAO<Integer, StudentVisit> {
      * @return
      */
     List<TeacherVisitDto> getTeacherVisitCount(@Param("teacherIds") List<Integer> teacherIds, @Param("startTime") Date startTime, @Param("endTime") Date endTime);
+
+    /**
+     * 时间段内是否有训练统计的回访
+     * @param teacherId
+     * @param addDays1
+     * @param addDays3
+     * @return
+     */
+    List<Integer> queryRecordVisitStudentIds(@Param("teacherId") Integer teacherId,
+                                             @Param("addDays1") Date addDays1,
+                                             @Param("addDays3") Date addDays3);
 }

+ 43 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/SysCouponCodeDao.java

@@ -0,0 +1,43 @@
+package com.ym.mec.biz.dal.dao;
+
+import com.ym.mec.biz.dal.dto.HorseRaceLampDto;
+import com.ym.mec.biz.dal.dto.SysCouponCodeDto;
+import com.ym.mec.common.dal.BaseDAO;
+import com.ym.mec.biz.dal.entity.SysCouponCode;
+import org.apache.ibatis.annotations.Param;
+
+import java.util.List;
+import java.util.Map;
+
+public interface SysCouponCodeDao extends BaseDAO<Long, SysCouponCode> {
+
+    int batchInsert(@Param("couponCodes") List<SysCouponCode> couponCodes);
+
+    /**
+     * @describe 统计指定用户指定优惠券的数量
+     * @author Joburgess
+     * @date 2021/9/8 0008
+     * @param userId:
+     * @param couponId:
+     * @return int
+     */
+    int countWithUserAndCoupon(@Param("userId") Integer userId,
+                               @Param("couponId") Integer couponId);
+
+    List<SysCouponCodeDto> querySysCouponUseList(Map<String, Object> params);
+    int countSysCouponUseList(Map<String, Object> params);
+
+    /**
+     * 获取优惠券跑马灯
+     * @param params
+     * @return
+     */
+    int countHorseRaceLampDtoList(Map<String, Object> params);
+
+    /**
+     * 获取优惠券跑马灯
+     * @param params
+     * @return
+     */
+    List<HorseRaceLampDto> queryHorseRaceLampDtoList(Map<String, Object> params);
+}

+ 13 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/SysCouponDao.java

@@ -0,0 +1,13 @@
+package com.ym.mec.biz.dal.dao;
+
+import com.ym.mec.common.dal.BaseDAO;
+import com.ym.mec.biz.dal.entity.SysCoupon;
+import org.apache.ibatis.annotations.Param;
+
+public interface SysCouponDao extends BaseDAO<Integer, SysCoupon> {
+
+    SysCoupon getWithName(@Param("name") String name);
+
+    SysCoupon lockCoupon(@Param("id") Integer id);
+	
+}

+ 0 - 7
mec-biz/src/main/java/com/ym/mec/biz/dal/dao/SysMusicCompareRecordDao.java

@@ -66,13 +66,6 @@ public interface SysMusicCompareRecordDao extends BaseDAO<Long, SysMusicCompareR
      * @param params
      * @return
      */
-    int countStudentTrain(Map<String, Object> params);
-
-    /**
-     * 老师端首页学员训练统计
-     * @param params
-     * @return
-     */
     List<CountStudentTrainDataDto> queryStudentTrain(Map<String, Object> params);
 
     /**

+ 116 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dto/CloudTeacherActiveTargetDetailDto.java

@@ -0,0 +1,116 @@
+package com.ym.mec.biz.dal.dto;
+
+import java.math.BigDecimal;
+import java.util.Date;
+
+public class CloudTeacherActiveTargetDetailDto {
+	private Integer userId;
+
+	private String username;
+
+	private String cooperationName;
+
+	private String musicGroupName;
+
+	private String chargeType;
+
+	private String subjectName;
+
+	private String currentGradeNum;
+
+	private String teacherName;
+
+	private String remark;
+
+	private BigDecimal amount = BigDecimal.ZERO;
+
+	private Date createTime;
+
+	public Date getCreateTime() {
+		return createTime;
+	}
+
+	public void setCreateTime(Date createTime) {
+		this.createTime = createTime;
+	}
+
+	public Integer getUserId() {
+		return userId;
+	}
+
+	public void setUserId(Integer userId) {
+		this.userId = userId;
+	}
+
+	public String getUsername() {
+		return username;
+	}
+
+	public void setUsername(String username) {
+		this.username = username;
+	}
+
+	public String getCooperationName() {
+		return cooperationName;
+	}
+
+	public void setCooperationName(String cooperationName) {
+		this.cooperationName = cooperationName;
+	}
+
+	public String getMusicGroupName() {
+		return musicGroupName;
+	}
+
+	public void setMusicGroupName(String musicGroupName) {
+		this.musicGroupName = musicGroupName;
+	}
+
+	public String getChargeType() {
+		return chargeType;
+	}
+
+	public void setChargeType(String chargeType) {
+		this.chargeType = chargeType;
+	}
+
+	public String getSubjectName() {
+		return subjectName;
+	}
+
+	public void setSubjectName(String subjectName) {
+		this.subjectName = subjectName;
+	}
+
+	public String getCurrentGradeNum() {
+		return currentGradeNum;
+	}
+
+	public void setCurrentGradeNum(String currentGradeNum) {
+		this.currentGradeNum = currentGradeNum;
+	}
+
+	public String getTeacherName() {
+		return teacherName;
+	}
+
+	public void setTeacherName(String teacherName) {
+		this.teacherName = teacherName;
+	}
+
+	public String getRemark() {
+		return remark;
+	}
+
+	public void setRemark(String remark) {
+		this.remark = remark;
+	}
+
+	public BigDecimal getAmount() {
+		return amount;
+	}
+
+	public void setAmount(BigDecimal amount) {
+		this.amount = amount;
+	}
+}

+ 105 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dto/CloudTeacherActiveTargetDto.java

@@ -0,0 +1,105 @@
+package com.ym.mec.biz.dal.dto;
+
+import java.math.BigDecimal;
+
+public class CloudTeacherActiveTargetDto{
+	private Integer organId;
+
+	private String organName;
+
+	private Integer targetNum = 0;
+
+	private BigDecimal targetAmount = BigDecimal.ZERO;
+
+	private Integer buyNum = 0;
+
+	private Integer totalNum = 0;
+
+	private BigDecimal buyAmount = BigDecimal.ZERO;
+
+	private BigDecimal avgBuyAmount = BigDecimal.ZERO;
+
+	private BigDecimal buyScale = BigDecimal.ZERO;
+
+	private BigDecimal targetFinishScale = BigDecimal.ZERO;
+
+	public String getOrganName() {
+		return organName;
+	}
+
+	public void setOrganName(String organName) {
+		this.organName = organName;
+	}
+
+	public Integer getBuyNum() {
+		return buyNum;
+	}
+
+	public void setBuyNum(Integer buyNum) {
+		this.buyNum = buyNum;
+	}
+
+	public Integer getTotalNum() {
+		return totalNum;
+	}
+
+	public void setTotalNum(Integer totalNum) {
+		this.totalNum = totalNum;
+	}
+
+	public BigDecimal getBuyAmount() {
+		return buyAmount;
+	}
+
+	public void setBuyAmount(BigDecimal buyAmount) {
+		this.buyAmount = buyAmount;
+	}
+
+	public BigDecimal getAvgBuyAmount() {
+		return avgBuyAmount;
+	}
+
+	public void setAvgBuyAmount(BigDecimal avgBuyAmount) {
+		this.avgBuyAmount = avgBuyAmount;
+	}
+
+	public BigDecimal getBuyScale() {
+		return buyScale;
+	}
+
+	public void setBuyScale(BigDecimal buyScale) {
+		this.buyScale = buyScale;
+	}
+
+	public BigDecimal getTargetFinishScale() {
+		return targetFinishScale;
+	}
+
+	public void setTargetFinishScale(BigDecimal targetFinishScale) {
+		this.targetFinishScale = targetFinishScale;
+	}
+
+	public Integer getOrganId() {
+		return organId;
+	}
+
+	public void setOrganId(Integer organId) {
+		this.organId = organId;
+	}
+
+	public Integer getTargetNum() {
+		return targetNum;
+	}
+
+	public void setTargetNum(Integer targetNum) {
+		this.targetNum = targetNum;
+	}
+
+	public BigDecimal getTargetAmount() {
+		return targetAmount;
+	}
+
+	public void setTargetAmount(BigDecimal targetAmount) {
+		this.targetAmount = targetAmount;
+	}
+}

+ 35 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dto/CloudTeacherActiveTargetJsonDto.java

@@ -0,0 +1,35 @@
+package com.ym.mec.biz.dal.dto;
+
+import java.math.BigDecimal;
+
+public class CloudTeacherActiveTargetJsonDto {
+	private Integer organId;
+
+	private Integer targetNum = 0;
+
+	private BigDecimal targetAmount = BigDecimal.ZERO;
+
+	public Integer getOrganId() {
+		return organId;
+	}
+
+	public void setOrganId(Integer organId) {
+		this.organId = organId;
+	}
+
+	public Integer getTargetNum() {
+		return targetNum;
+	}
+
+	public void setTargetNum(Integer targetNum) {
+		this.targetNum = targetNum;
+	}
+
+	public BigDecimal getTargetAmount() {
+		return targetAmount;
+	}
+
+	public void setTargetAmount(BigDecimal targetAmount) {
+		this.targetAmount = targetAmount;
+	}
+}

+ 10 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dto/CountStudentTrainDataDto.java

@@ -23,6 +23,16 @@ public class CountStudentTrainDataDto {
 
     private String musicGroupName;
 
+    private Integer visitFlag;
+
+    public Integer getVisitFlag() {
+        return visitFlag;
+    }
+
+    public void setVisitFlag(Integer visitFlag) {
+        this.visitFlag = visitFlag;
+    }
+
     public String getMusicGroupName() {
         return musicGroupName;
     }

+ 36 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dto/HorseRaceLampDto.java

@@ -0,0 +1,36 @@
+package com.ym.mec.biz.dal.dto;
+
+import java.math.BigDecimal;
+
+public class HorseRaceLampDto {
+
+    private Integer num;
+
+    private BigDecimal faceValue;
+
+    private String username;
+
+    public Integer getNum() {
+        return num;
+    }
+
+    public void setNum(Integer num) {
+        this.num = num;
+    }
+
+    public BigDecimal getFaceValue() {
+        return faceValue;
+    }
+
+    public void setFaceValue(BigDecimal faceValue) {
+        this.faceValue = faceValue;
+    }
+
+    public String getUsername() {
+        return username;
+    }
+
+    public void setUsername(String username) {
+        this.username = username;
+    }
+}

+ 212 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/dto/SysCouponCodeDto.java

@@ -0,0 +1,212 @@
+package com.ym.mec.biz.dal.dto;
+
+import com.ym.mec.biz.dal.enums.CouponTypeEnum;
+import io.swagger.annotations.ApiModelProperty;
+
+import java.math.BigDecimal;
+import java.util.Date;
+
+/**
+ * @Author Joburgess
+ * @Date 2021/9/8 0008
+ */
+public class SysCouponCodeDto {
+
+    @ApiModelProperty("分部编号")
+    private Integer organId;
+
+    @ApiModelProperty("分部名称")
+    private String organName;
+
+    @ApiModelProperty("用户编号")
+    private Integer userId;
+
+    @ApiModelProperty("用户名称")
+    private String userName;
+
+    @ApiModelProperty("手机号")
+    private String phone;
+
+    @ApiModelProperty("优惠券编号")
+    private Integer couponId;
+
+    @ApiModelProperty("优惠券类型")
+    private CouponTypeEnum couponType;
+
+    @ApiModelProperty("优惠券名称")
+    private String couponName;
+
+    @ApiModelProperty("描述")
+    private String couponDescription;
+
+    @ApiModelProperty("优惠码")
+    private String code;
+
+    @ApiModelProperty("券类型:FULL_REDUCTION(满减券),DISCOUNT(折扣券)")
+    private CouponTypeEnum type;
+
+    @ApiModelProperty("面值")
+    private java.math.BigDecimal faceValue;
+
+    @ApiModelProperty("满多少")
+    private java.math.BigDecimal fullAmount;
+
+    @ApiModelProperty("订单编号")
+    private Long paymentOrderId;
+
+    @ApiModelProperty("使用状态:0未使用,1已使用")
+    private Integer usageStatus;
+
+    @ApiModelProperty("实际使用时间")
+    private java.util.Date usedTime;
+
+    @ApiModelProperty("使用开始日期")
+    private java.util.Date useStartDate;
+
+    @ApiModelProperty("使用截止日期")
+    private java.util.Date useDeadlineDate;
+
+    public Integer getOrganId() {
+        return organId;
+    }
+
+    public void setOrganId(Integer organId) {
+        this.organId = organId;
+    }
+
+    public String getOrganName() {
+        return organName;
+    }
+
+    public void setOrganName(String organName) {
+        this.organName = organName;
+    }
+
+    public Integer getUserId() {
+        return userId;
+    }
+
+    public void setUserId(Integer userId) {
+        this.userId = userId;
+    }
+
+    public String getUserName() {
+        return userName;
+    }
+
+    public void setUserName(String userName) {
+        this.userName = userName;
+    }
+
+    public String getPhone() {
+        return phone;
+    }
+
+    public void setPhone(String phone) {
+        this.phone = phone;
+    }
+
+    public CouponTypeEnum getType() {
+        return type;
+    }
+
+    public void setType(CouponTypeEnum type) {
+        this.type = type;
+    }
+
+    public BigDecimal getFaceValue() {
+        return faceValue;
+    }
+
+    public void setFaceValue(BigDecimal faceValue) {
+        this.faceValue = faceValue;
+    }
+
+    public BigDecimal getFullAmount() {
+        return fullAmount;
+    }
+
+    public void setFullAmount(BigDecimal fullAmount) {
+        this.fullAmount = fullAmount;
+    }
+
+    public Integer getCouponId() {
+        return couponId;
+    }
+
+    public void setCouponId(Integer couponId) {
+        this.couponId = couponId;
+    }
+
+    public CouponTypeEnum getCouponType() {
+        return couponType;
+    }
+
+    public void setCouponType(CouponTypeEnum couponType) {
+        this.couponType = couponType;
+    }
+
+    public String getCouponName() {
+        return couponName;
+    }
+
+    public void setCouponName(String couponName) {
+        this.couponName = couponName;
+    }
+
+    public String getCouponDescription() {
+        return couponDescription;
+    }
+
+    public void setCouponDescription(String couponDescription) {
+        this.couponDescription = couponDescription;
+    }
+
+    public String getCode() {
+        return code;
+    }
+
+    public void setCode(String code) {
+        this.code = code;
+    }
+
+    public Long getPaymentOrderId() {
+        return paymentOrderId;
+    }
+
+    public void setPaymentOrderId(Long paymentOrderId) {
+        this.paymentOrderId = paymentOrderId;
+    }
+
+    public Integer getUsageStatus() {
+        return usageStatus;
+    }
+
+    public void setUsageStatus(Integer usageStatus) {
+        this.usageStatus = usageStatus;
+    }
+
+    public Date getUsedTime() {
+        return usedTime;
+    }
+
+    public void setUsedTime(Date usedTime) {
+        this.usedTime = usedTime;
+    }
+
+    public Date getUseStartDate() {
+        return useStartDate;
+    }
+
+    public void setUseStartDate(Date useStartDate) {
+        this.useStartDate = useStartDate;
+    }
+
+    public Date getUseDeadlineDate() {
+        return useDeadlineDate;
+    }
+
+    public void setUseDeadlineDate(Date useDeadlineDate) {
+        this.useDeadlineDate = useDeadlineDate;
+    }
+}

+ 14 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/entity/CloudTeacherOrder.java

@@ -84,6 +84,12 @@ public class CloudTeacherOrder {
     private String remark = "";
 
     /**
+     * 活动备注
+     */
+    @ApiModelProperty(value = "活动备注")
+    private Integer activeRemark;
+
+    /**
      * 备注
      */
     @ApiModelProperty(value = "版本")
@@ -105,6 +111,14 @@ public class CloudTeacherOrder {
     
     private StudentPaymentOrder studentPaymentOrder = new StudentPaymentOrder();
 
+    public Integer getActiveRemark() {
+        return activeRemark;
+    }
+
+    public void setActiveRemark(Integer activeRemark) {
+        this.activeRemark = activeRemark;
+    }
+
     public Long getId() {
         return id;
     }

+ 237 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/entity/SysCoupon.java

@@ -0,0 +1,237 @@
+package com.ym.mec.biz.dal.entity;
+
+import com.ym.mec.biz.dal.enums.CouponTypeEnum;
+import com.ym.mec.biz.dal.enums.EffectiveTypeEnum;
+import io.swagger.annotations.ApiModelProperty;
+import org.apache.commons.lang3.builder.ToStringBuilder;
+
+import java.math.BigDecimal;
+import java.util.Date;
+
+/**
+ * 对应数据库表(sys_coupon):
+ */
+public class SysCoupon {
+
+	private Integer id;
+
+	@ApiModelProperty("优惠券名称")
+	private String name;
+
+	@ApiModelProperty("描述")
+	private String description;
+
+	@ApiModelProperty("状态:0停用,1启用")
+	private Integer status;
+
+	@ApiModelProperty("券类型:FULL_REDUCTION(满减券),DISCOUNT(折扣券)")
+	private CouponTypeEnum type;
+
+	@ApiModelProperty("面值")
+	private java.math.BigDecimal faceValue;
+
+	@ApiModelProperty("满多少")
+	private java.math.BigDecimal fullAmount;
+
+	@ApiModelProperty("限制兑换的最大次数")
+	private Integer limitExchangeNum;
+
+	@ApiModelProperty("期限(单位:天)")
+	private Integer deadline;
+
+	@ApiModelProperty("有效期类型")
+	private EffectiveTypeEnum effectiveType;
+
+	@ApiModelProperty("有效起始时间")
+	private java.util.Date effectiveStartTime;
+
+	@ApiModelProperty("有效截止时间")
+	private java.util.Date effectiveExpireTime;
+
+	@ApiModelProperty("领取结束时间")
+	private java.util.Date endDate;
+
+	@ApiModelProperty("领取开始时间")
+	private java.util.Date startDate;
+
+	@ApiModelProperty("库存量")
+	private Integer stockCount;
+
+	@ApiModelProperty("消耗数量")
+	private Integer consumeNum;
+
+	@ApiModelProperty("预警值")
+	private Integer warningStockNum;
+
+	private Integer warningStatus;
+
+	private java.util.Date createTime;
+
+	private java.util.Date updateTime;
+
+	public Integer getId() {
+		return id;
+	}
+
+	public void setId(Integer id) {
+		this.id = id;
+	}
+
+	public String getName() {
+		return name;
+	}
+
+	public void setName(String name) {
+		this.name = name;
+	}
+
+	public String getDescription() {
+		return description;
+	}
+
+	public void setDescription(String description) {
+		this.description = description;
+	}
+
+	public Integer getStatus() {
+		return status;
+	}
+
+	public void setStatus(Integer status) {
+		this.status = status;
+	}
+
+	public CouponTypeEnum getType() {
+		return type;
+	}
+
+	public void setType(CouponTypeEnum type) {
+		this.type = type;
+	}
+
+	public BigDecimal getFaceValue() {
+		return faceValue;
+	}
+
+	public void setFaceValue(BigDecimal faceValue) {
+		this.faceValue = faceValue;
+	}
+
+	public BigDecimal getFullAmount() {
+		return fullAmount;
+	}
+
+	public void setFullAmount(BigDecimal fullAmount) {
+		this.fullAmount = fullAmount;
+	}
+
+	public Integer getLimitExchangeNum() {
+		return limitExchangeNum;
+	}
+
+	public void setLimitExchangeNum(Integer limitExchangeNum) {
+		this.limitExchangeNum = limitExchangeNum;
+	}
+
+	public EffectiveTypeEnum getEffectiveType() {
+		return effectiveType;
+	}
+
+	public void setEffectiveType(EffectiveTypeEnum effectiveType) {
+		this.effectiveType = effectiveType;
+	}
+
+	public Integer getDeadline() {
+		return deadline;
+	}
+
+	public void setDeadline(Integer deadline) {
+		this.deadline = deadline;
+	}
+
+	public Date getEffectiveStartTime() {
+		return effectiveStartTime;
+	}
+
+	public void setEffectiveStartTime(Date effectiveStartTime) {
+		this.effectiveStartTime = effectiveStartTime;
+	}
+
+	public Date getEffectiveExpireTime() {
+		return effectiveExpireTime;
+	}
+
+	public void setEffectiveExpireTime(Date effectiveExpireTime) {
+		this.effectiveExpireTime = effectiveExpireTime;
+	}
+
+	public Date getEndDate() {
+		return endDate;
+	}
+
+	public void setEndDate(Date endDate) {
+		this.endDate = endDate;
+	}
+
+	public Date getStartDate() {
+		return startDate;
+	}
+
+	public void setStartDate(Date startDate) {
+		this.startDate = startDate;
+	}
+
+	public Integer getStockCount() {
+		return stockCount;
+	}
+
+	public void setStockCount(Integer stockCount) {
+		this.stockCount = stockCount;
+	}
+
+	public Integer getConsumeNum() {
+		return consumeNum;
+	}
+
+	public void setConsumeNum(Integer consumeNum) {
+		this.consumeNum = consumeNum;
+	}
+
+	public Integer getWarningStockNum() {
+		return warningStockNum;
+	}
+
+	public void setWarningStockNum(Integer warningStockNum) {
+		this.warningStockNum = warningStockNum;
+	}
+
+	public Integer getWarningStatus() {
+		return warningStatus;
+	}
+
+	public void setWarningStatus(Integer warningStatus) {
+		this.warningStatus = warningStatus;
+	}
+
+	public Date getCreateTime() {
+		return createTime;
+	}
+
+	public void setCreateTime(Date createTime) {
+		this.createTime = createTime;
+	}
+
+	public Date getUpdateTime() {
+		return updateTime;
+	}
+
+	public void setUpdateTime(Date updateTime) {
+		this.updateTime = updateTime;
+	}
+
+	@Override
+	public String toString() {
+		return ToStringBuilder.reflectionToString(this);
+	}
+
+}

+ 136 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/entity/SysCouponCode.java

@@ -0,0 +1,136 @@
+package com.ym.mec.biz.dal.entity;
+
+import org.apache.commons.lang3.builder.ToStringBuilder;
+
+/**
+ * 对应数据库表(sys_coupon_code):
+ */
+public class SysCouponCode {
+
+	/**  */
+	private Long id;
+	
+	/**  */
+	private Integer couponId;
+	
+	/** 优惠码 */
+	private String code;
+	
+	/** 使用状态:0未使用,1已使用 */
+	private Integer usageStatus;
+	
+	/** 用户编号 */
+	private Integer userId;
+	
+	/** 实际使用时间 */
+	private java.util.Date usedTime;
+	
+	/** 使用开始日期 */
+	private java.util.Date useStartDate;
+	
+	/** 使用截止日期 */
+	private java.util.Date useDeadlineDate;
+	
+	/** 关联的订单号 */
+	private Long paymentOrderId;
+	
+	/**  */
+	private java.util.Date createTime;
+	
+	/**  */
+	private java.util.Date updateTime;
+	
+	public void setId(Long id){
+		this.id = id;
+	}
+	
+	public Long getId(){
+		return this.id;
+	}
+			
+	public void setCouponId(Integer couponId){
+		this.couponId = couponId;
+	}
+	
+	public Integer getCouponId(){
+		return this.couponId;
+	}
+			
+	public void setCode(String code){
+		this.code = code;
+	}
+	
+	public String getCode(){
+		return this.code;
+	}
+			
+	public void setUsageStatus(Integer usageStatus){
+		this.usageStatus = usageStatus;
+	}
+	
+	public Integer getUsageStatus(){
+		return this.usageStatus;
+	}
+			
+	public void setUserId(Integer userId){
+		this.userId = userId;
+	}
+	
+	public Integer getUserId(){
+		return this.userId;
+	}
+			
+	public void setUsedTime(java.util.Date usedTime){
+		this.usedTime = usedTime;
+	}
+	
+	public java.util.Date getUsedTime(){
+		return this.usedTime;
+	}
+			
+	public void setUseStartDate(java.util.Date useStartDate){
+		this.useStartDate = useStartDate;
+	}
+	
+	public java.util.Date getUseStartDate(){
+		return this.useStartDate;
+	}
+			
+	public void setUseDeadlineDate(java.util.Date useDeadlineDate){
+		this.useDeadlineDate = useDeadlineDate;
+	}
+	
+	public java.util.Date getUseDeadlineDate(){
+		return this.useDeadlineDate;
+	}
+			
+	public void setPaymentOrderId(Long paymentOrderId){
+		this.paymentOrderId = paymentOrderId;
+	}
+	
+	public Long getPaymentOrderId(){
+		return this.paymentOrderId;
+	}
+			
+	public void setCreateTime(java.util.Date createTime){
+		this.createTime = createTime;
+	}
+	
+	public java.util.Date getCreateTime(){
+		return this.createTime;
+	}
+			
+	public void setUpdateTime(java.util.Date updateTime){
+		this.updateTime = updateTime;
+	}
+	
+	public java.util.Date getUpdateTime(){
+		return this.updateTime;
+	}
+			
+	@Override
+	public String toString() {
+		return ToStringBuilder.reflectionToString(this);
+	}
+
+}

+ 34 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/enums/CouponTypeEnum.java

@@ -0,0 +1,34 @@
+package com.ym.mec.biz.dal.enums;
+
+import com.ym.mec.common.enums.BaseEnum;
+
+public enum CouponTypeEnum implements BaseEnum<String, CouponTypeEnum> {
+
+    FULL_REDUCTION("FULL_REDUCTION","满减券"),
+    DISCOUNT("DISCOUNT","折扣券");
+
+    private String code;
+
+    private String msg;
+
+    CouponTypeEnum(String code, String msg) {
+        this.code = code;
+        this.msg = msg;
+    }
+
+    public void setCode(String code) {
+        this.code = code;
+    }
+
+    public String getMsg() {
+        return msg;
+    }
+
+    public void setMsg(String msg) {
+        this.msg = msg;
+    }
+
+    @Override
+    public String getCode() {
+        return this.code;
+    }}

+ 34 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/enums/EffectiveTypeEnum.java

@@ -0,0 +1,34 @@
+package com.ym.mec.biz.dal.enums;
+
+import com.ym.mec.common.enums.BaseEnum;
+
+public enum EffectiveTypeEnum implements BaseEnum<String, EffectiveTypeEnum> {
+
+    DAYS("DAYS","天数"),
+    TIME_BUCKET("TIME_BUCKET","时间段");
+
+    private String code;
+
+    private String msg;
+
+    EffectiveTypeEnum(String code, String msg) {
+        this.code = code;
+        this.msg = msg;
+    }
+
+    public void setCode(String code) {
+        this.code = code;
+    }
+
+    public String getMsg() {
+        return msg;
+    }
+
+    public void setMsg(String msg) {
+        this.msg = msg;
+    }
+
+    @Override
+    public String getCode() {
+        return this.code;
+    }}

+ 2 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/enums/MessageTypeEnum.java

@@ -192,6 +192,8 @@ public enum MessageTypeEnum implements BaseEnum<String, MessageTypeEnum> {
     TRAIN_NO_RANK_STUDENT_PUSH("TRAIN_NO_RANK_STUDENT_PUSH", "云教练训练提醒"),
     TRAIN_RANK_STUDENT_PUSH("TRAIN_RANK_STUDENT_PUSH", "云教练训练提醒"),
     NO_TRAIN_STUDENT_PUSH("NO_TRAIN_STUDENT_PUSH", "云教练训练提醒"),
+
+    COUPON_STOCK_WARNING("COUPON_STOCK_WARNING", "优惠券库存预警"),
     ;
 
     MessageTypeEnum(String code, String msg) {

+ 56 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/page/CloudTeacherActiveQueryInfo.java

@@ -0,0 +1,56 @@
+package com.ym.mec.biz.dal.page;
+
+import com.ym.mec.common.page.QueryInfo;
+
+public class CloudTeacherActiveQueryInfo extends QueryInfo {
+
+    private String organIds;
+
+    private Integer chargeType;
+
+    private Integer subjectId;
+
+    private Integer teacherId;
+
+    private String remarkType;
+
+    public String getOrganIds() {
+        return organIds;
+    }
+
+    public void setOrganIds(String organIds) {
+        this.organIds = organIds;
+    }
+
+    public Integer getChargeType() {
+        return chargeType;
+    }
+
+    public void setChargeType(Integer chargeType) {
+        this.chargeType = chargeType;
+    }
+
+    public Integer getSubjectId() {
+        return subjectId;
+    }
+
+    public void setSubjectId(Integer subjectId) {
+        this.subjectId = subjectId;
+    }
+
+    public Integer getTeacherId() {
+        return teacherId;
+    }
+
+    public void setTeacherId(Integer teacherId) {
+        this.teacherId = teacherId;
+    }
+
+    public String getRemarkType() {
+        return remarkType;
+    }
+
+    public void setRemarkType(String remarkType) {
+        this.remarkType = remarkType;
+    }
+}

+ 11 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/page/StudentPaymentOrderQueryInfo.java

@@ -8,6 +8,9 @@ import java.util.List;
 
 public class StudentPaymentOrderQueryInfo extends QueryInfo {
 
+    @ApiModelProperty("订单编号")
+    private Long paymentOrderId;
+
     @ApiModelProperty(value = "开始时间",required = false)
     private String orderStartDate;
 
@@ -69,6 +72,14 @@ public class StudentPaymentOrderQueryInfo extends QueryInfo {
 
     private String oldOrganId;
 
+    public Long getPaymentOrderId() {
+        return paymentOrderId;
+    }
+
+    public void setPaymentOrderId(Long paymentOrderId) {
+        this.paymentOrderId = paymentOrderId;
+    }
+
     public boolean getIsExport() {
         return isExport;
     }

+ 60 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/page/SysCouponCodeQueryInfo.java

@@ -0,0 +1,60 @@
+package com.ym.mec.biz.dal.page;
+
+import com.ym.mec.common.page.QueryInfo;
+
+/**
+ * @Author Joburgess
+ * @Date 2021/9/8 0008
+ */
+public class SysCouponCodeQueryInfo extends QueryInfo {
+
+    private Integer organId;
+
+    private Integer userId;
+
+    private String couponName;
+
+    private Long paymentOrderId;
+
+    private Integer usageStatus;
+
+    public Integer getOrganId() {
+        return organId;
+    }
+
+    public void setOrganId(Integer organId) {
+        this.organId = organId;
+    }
+
+    public Integer getUserId() {
+        return userId;
+    }
+
+    public void setUserId(Integer userId) {
+        this.userId = userId;
+    }
+
+    public String getCouponName() {
+        return couponName;
+    }
+
+    public void setCouponName(String couponName) {
+        this.couponName = couponName;
+    }
+
+    public Long getPaymentOrderId() {
+        return paymentOrderId;
+    }
+
+    public void setPaymentOrderId(Long paymentOrderId) {
+        this.paymentOrderId = paymentOrderId;
+    }
+
+    public Integer getUsageStatus() {
+        return usageStatus;
+    }
+
+    public void setUsageStatus(Integer usageStatus) {
+        this.usageStatus = usageStatus;
+    }
+}

+ 34 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/page/SysCouponQueryInfo.java

@@ -0,0 +1,34 @@
+package com.ym.mec.biz.dal.page;
+
+import com.ym.mec.biz.dal.enums.CouponTypeEnum;
+import com.ym.mec.common.page.QueryInfo;
+import io.swagger.annotations.ApiModelProperty;
+
+/**
+ * @Author Joburgess
+ * @Date 2021/9/8 0008
+ */
+public class SysCouponQueryInfo extends QueryInfo {
+
+    @ApiModelProperty("券类型:FULL_REDUCTION(满减券),DISCOUNT(折扣券)")
+    private CouponTypeEnum type;
+
+    @ApiModelProperty("状态:0停用,1启用")
+    private Integer status;
+
+    public CouponTypeEnum getType() {
+        return type;
+    }
+
+    public void setType(CouponTypeEnum type) {
+        this.type = type;
+    }
+
+    public Integer getStatus() {
+        return status;
+    }
+
+    public void setStatus(Integer status) {
+        this.status = status;
+    }
+}

+ 10 - 0
mec-biz/src/main/java/com/ym/mec/biz/dal/page/SysMusicCompareRecordQueryInfo.java

@@ -31,6 +31,16 @@ public class SysMusicCompareRecordQueryInfo extends QueryInfo {
 
     private HeardLevelEnum heardLevel;
 
+    private Boolean visitFlag;
+
+    public Boolean getVisitFlag() {
+        return visitFlag;
+    }
+
+    public void setVisitFlag(Boolean visitFlag) {
+        this.visitFlag = visitFlag;
+    }
+
     public FeatureType getFeatureType() {
         return featureType;
     }

+ 9 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/CloudTeacherOrderService.java

@@ -87,4 +87,13 @@ public interface CloudTeacherOrderService extends BaseService<Long, CloudTeacher
     CloudTeacherOrderDto queryOrderInfoByOrderId(Long orderId);
 
     List<Map<Long, String>> queryNoStartByUserIds(Set<Integer> userIds,Boolean isMusicMember);
+
+    /**
+     * 获取学员购买的云教练活动订单
+     * @param userId
+     * @param activeRemark
+     * @param remark
+     * @return
+     */
+    String queryActiveOrderPage(Integer userId, Integer activeRemark, String remark);
 }

+ 3 - 2
mec-biz/src/main/java/com/ym/mec/biz/service/ContractService.java

@@ -8,6 +8,7 @@ import java.util.Map;
 import com.ym.mec.biz.dal.dto.CirculationUser;
 import com.ym.mec.biz.dal.dto.OAFinancialDto;
 import com.ym.mec.biz.dal.entity.SysUserTsign;
+import com.ym.mec.biz.dal.enums.CourseViewTypeEnum;
 import com.ym.mec.biz.dal.enums.KitGroupPurchaseTypeEnum;
 import com.ym.mec.common.entity.HttpResponseResult;
 
@@ -116,7 +117,7 @@ public interface ContractService {
 	 * @param userId
 	 * @return
 	 */
-	boolean transferProduceContract(Integer userId,String musicGroupId);
+	boolean transferProduceContract(Integer userId, String musicGroupId, CourseViewTypeEnum courseViewType);
 
 	/**
 	 * 传递产品协议-仅生成课程协议
@@ -130,7 +131,7 @@ public interface ContractService {
 	 * @param userId
 	 * @return
 	 */
-	Map<String, Object> queryProductContract(Integer userId,String musicGroupId);
+	Map<String, Object> queryProductContract(Integer userId,String musicGroupId, CourseViewTypeEnum courseViewType);
 
 
 	/**

+ 15 - 1
mec-biz/src/main/java/com/ym/mec/biz/service/MemberRankSettingService.java

@@ -7,6 +7,7 @@ import java.util.Map;
 import com.ym.mec.biz.dal.entity.MemberRankSetting;
 import com.ym.mec.biz.dal.entity.StudentPaymentOrder;
 import com.ym.mec.biz.dal.enums.PeriodEnum;
+import com.ym.mec.common.entity.HttpResponseResult;
 import com.ym.mec.common.service.BaseService;
 
 public interface MemberRankSettingService extends BaseService<Integer, MemberRankSetting> {
@@ -26,9 +27,20 @@ public interface MemberRankSettingService extends BaseService<Integer, MemberRan
 	 * @param periodEnum 会员周期
 	 * @param amount 金额
 	 * @param isUseBalance 是否使用余额
+	 * @param buyNum 购买数量
+	 * @param giveNum 赠送数量
+	 * @param activeRemark 活动标记
+	 * @param remark 备注
 	 * @return
 	 */
-	Map buy(Integer userId, Integer memberRankId, PeriodEnum periodEnum, BigDecimal amount, boolean isUseBalance) throws Exception;
+	Map buy(Integer userId,
+			Integer memberRankId,
+			PeriodEnum periodEnum,
+			BigDecimal amount,
+			boolean isUseBalance,
+			Integer buyNum,
+			Integer giveNum,
+			Integer activeRemark,String remark) throws Exception;
 	
 	/**
 	 * 订单回调
@@ -36,4 +48,6 @@ public interface MemberRankSettingService extends BaseService<Integer, MemberRan
 	 * @return
 	 */
 	boolean orderCallback(StudentPaymentOrder studentPaymentOrder);
+
+	HttpResponseResult ActiveBuy(Integer id, Integer memberRankId, PeriodEnum month, BigDecimal amount, boolean isUseBalance, Integer buyNum, int giveNum, int activeRemark, String remark, boolean repay) throws Exception;
 }

+ 1 - 1
mec-biz/src/main/java/com/ym/mec/biz/service/OrganizationService.java

@@ -9,7 +9,7 @@ import java.util.*;
 
 public interface OrganizationService extends BaseService<Integer, Organization> {
 
-    Set<Integer>  EXCLUDE_ORGAN_IDS = new HashSet<>(Arrays.asList(36,39,41,42,43,44,45,46,47,48,49,50,52,54,55,56));
+    Set<Integer>  EXCLUDE_ORGAN_IDS = new HashSet<>(Arrays.asList(36,38,39,41,42,43,44,45,46,47,48,49,50,52,54,55,56));
 
     /**
      * 获取节点树状结构

+ 4 - 2
mec-biz/src/main/java/com/ym/mec/biz/service/StudentPaymentOrderService.java

@@ -22,8 +22,10 @@ import com.ym.mec.common.page.PageInfo;
 import com.ym.mec.common.service.BaseService;
 
 public interface StudentPaymentOrderService extends BaseService<Long, StudentPaymentOrder> {
-	
-	Map createOrder(StudentPaymentOrder studentPaymentOrder, List<StudentPaymentOrderDetail> details, String payReceiver) throws Exception;
+
+    StudentPaymentOrder findByUserAndActive(Integer userId, Integer activeRemark, String remark,String status);
+
+    Map createOrder(StudentPaymentOrder studentPaymentOrder, List<StudentPaymentOrderDetail> details, String payReceiver) throws Exception;
 
     /**
      * 查询商品列表

+ 23 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/StudentService.java

@@ -3,8 +3,10 @@ package com.ym.mec.biz.service;
 import java.text.ParseException;
 import java.util.Date;
 import java.util.List;
+import java.util.Map;
 
 import com.ym.mec.biz.dal.dto.CloudStudyStudentDataDto;
+import com.ym.mec.biz.dal.dto.CloudTeacherActiveTargetDetailDto;
 import com.ym.mec.biz.dal.dto.EduOrganStudentDataDto;
 import com.ym.mec.biz.dal.dto.StatDto;
 import com.ym.mec.biz.dal.entity.CloudTeacherOrder;
@@ -12,6 +14,7 @@ import com.ym.mec.biz.dal.entity.CooperationOrgan;
 import com.ym.mec.biz.dal.entity.Student;
 import com.ym.mec.biz.dal.enums.GradeTypeEnum;
 import com.ym.mec.biz.dal.enums.PeriodEnum;
+import com.ym.mec.biz.dal.page.CloudTeacherActiveQueryInfo;
 import com.ym.mec.biz.dal.page.OrganCloudStudyStudentDataQueryInfo;
 import com.ym.mec.biz.dal.page.StudentQueryInfo;
 import com.ym.mec.common.page.PageInfo;
@@ -123,4 +126,24 @@ public interface StudentService extends BaseService<Integer, Student> {
      * @return void
      */
     void cleanStudentCloudStudySequenceDays();
+
+    /**
+     * 标记进行中乐团在读学员+VIP、网管有课学员总数(除弦乐声部、去重)
+     */
+    void remarkCountFlag();
+
+    /**
+     * 云教练活动统计
+     * @param organIds
+     * @param queryInfo
+     * @return
+     */
+    Map<String,Object> countCloudTeacherActive(List<Integer> organIds, CloudTeacherActiveQueryInfo queryInfo);
+
+    /**
+     * 云教练活动统计详情
+     * @param queryInfo
+     * @return
+     */
+    PageInfo<CloudTeacherActiveTargetDetailDto> countCloudTeacherActiveDetail(CloudTeacherActiveQueryInfo queryInfo);
 }

+ 9 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/SysConfigService.java

@@ -245,6 +245,15 @@ public interface SysConfigService extends BaseService<Long, SysConfig> {
     //云教练试用时间最晚截止时间
     String EXPERIENCE_MEMBERSHIP_END_TIME = "experience_membership_end_time";
 
+    //云教练训练时长小于80分钟需要回访
+    String STUDENT_CLOUD_TEACHER_TOTAL_PLAY_TIME = "student_cloud_teacher_total_play_time";
+
+    //云教练训练次数小于4次需要回访
+    String STUDENT_CLOUD_TEACHER_TRAIN_NUM = "student_cloud_teacher_train_num";
+
+    //云教练活动分部目标JSON
+    String CLOUD_TEACHER_ACTIVE_TARGET = "cloud_teacher_active_target";
+
     /**
      * @return com.ym.mec.biz.dal.entity.SysConfig
      * @params paramName

+ 41 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/SysCouponCodeService.java

@@ -0,0 +1,41 @@
+package com.ym.mec.biz.service;
+
+import com.ym.mec.biz.dal.dto.HorseRaceLampDto;
+import com.ym.mec.biz.dal.dto.SysCouponCodeDto;
+import com.ym.mec.biz.dal.entity.SysCouponCode;
+import com.ym.mec.biz.dal.page.SysCouponCodeQueryInfo;
+import com.ym.mec.common.page.PageInfo;
+import com.ym.mec.common.page.QueryInfo;
+import com.ym.mec.common.service.BaseService;
+
+public interface SysCouponCodeService extends BaseService<Long, SysCouponCode> {
+
+    /**
+     * @describe 兑换优惠券
+     * @author Joburgess
+     * @date 2021/9/8 0008
+     * @param userId: 用户编号
+     * @param couponId: 优惠券编号
+     * @param paymentOrderId: 订单编号
+     * @param exchangeNum: 兑换数量
+     * @return boolean
+     */
+    boolean exchangeCoupon(Integer userId, Integer couponId, Long paymentOrderId, Integer exchangeNum);
+    boolean exchangeCouponTest(Integer userId, Integer couponId, Long paymentOrderId, Integer exchangeNum);
+
+    /**
+     * @describe 优惠券领取列表
+     * @author Joburgess
+     * @date 2021/9/8 0008
+     * @param queryInfo:
+     * @return com.ym.mec.common.page.PageInfo<com.ym.mec.biz.dal.dto.SysCouponCodeDto>
+     */
+    PageInfo<SysCouponCodeDto> querySysCouponUseList(SysCouponCodeQueryInfo queryInfo);
+
+    /**
+     * 获取优惠券跑马灯
+     * @param queryInfo
+     * @return
+     */
+    PageInfo<HorseRaceLampDto> queryHorseRaceLampDtoList(QueryInfo queryInfo);
+}

+ 23 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/SysCouponService.java

@@ -0,0 +1,23 @@
+package com.ym.mec.biz.service;
+
+import com.ym.mec.biz.dal.entity.SysCoupon;
+import com.ym.mec.biz.dal.page.SysCouponQueryInfo;
+import com.ym.mec.common.page.PageInfo;
+import com.ym.mec.common.service.BaseService;
+
+public interface SysCouponService extends BaseService<Integer, SysCoupon> {
+
+    PageInfo<SysCoupon> queryPage(SysCouponQueryInfo queryInfo);
+
+    void updateCoupon(SysCoupon sysCoupon);
+
+    /**
+     * @describe 优惠券低库存警告
+     * @author Joburgess
+     * @date 2021/9/8 0008
+     * @param couponId: 优惠券编号
+     * @return void
+     */
+    void stockWarning(Integer couponId, String couponName);
+
+}

+ 4 - 3
mec-biz/src/main/java/com/ym/mec/biz/service/SysMusicCompareRecordService.java

@@ -1,13 +1,14 @@
 package com.ym.mec.biz.service;
 
-import com.alibaba.fastjson.JSONObject;
-import com.ym.mec.biz.dal.dto.*;
+import com.ym.mec.biz.dal.dto.CountStudentTrainDataDto;
+import com.ym.mec.biz.dal.dto.MusicCompareRankingDto;
+import com.ym.mec.biz.dal.dto.SoundCompareHelper;
+import com.ym.mec.biz.dal.dto.StatDto;
 import com.ym.mec.biz.dal.entity.SysMusicCompareRecord;
 import com.ym.mec.biz.dal.page.SysMusicCompareRecordQueryInfo;
 import com.ym.mec.common.page.PageInfo;
 import com.ym.mec.common.service.BaseService;
 
-import java.util.List;
 import java.util.Map;
 
 public interface SysMusicCompareRecordService extends BaseService<Long, SysMusicCompareRecord> {

+ 1 - 1
mec-biz/src/main/java/com/ym/mec/biz/service/impl/ChildrenDayReserveServiceImpl.java

@@ -413,7 +413,7 @@ public class ChildrenDayReserveServiceImpl extends BaseServiceImpl<Integer, Chil
             }
 
             try {
-                contractService.transferProduceContract(userId, null);
+                contractService.transferProduceContract(userId, null, null);
             } catch (Exception e) {
                 logger.error("产品协议生成失败", e);
             }

+ 5 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/impl/CloudTeacherOrderServiceImpl.java

@@ -248,4 +248,9 @@ public class CloudTeacherOrderServiceImpl extends BaseServiceImpl<Long, CloudTea
     public List<Map<Long, String>> queryNoStartByUserIds(Set<Integer> userIds,Boolean isMusicMember) {
         return cloudTeacherOrderDao.queryNoStartByUserIds(userIds,isMusicMember);
     }
+
+    @Override
+    public String queryActiveOrderPage(Integer userId, Integer activeRemark, String remark) {
+        return cloudTeacherOrderDao.queryActiveOrderPage(userId,activeRemark,remark);
+    }
 }

+ 13 - 6
mec-biz/src/main/java/com/ym/mec/biz/service/impl/ContractServiceImpl.java

@@ -330,7 +330,7 @@ public class ContractServiceImpl implements ContractService, InitializingBean {
 	@Override
 	public boolean transferMusicGroupCoursesContract(Integer userId, String musicGroupId) {
 		if(true){
-			return transferProduceContract(userId, musicGroupId);
+			return transferProduceContract(userId, musicGroupId, null);
 		}
 		SysUserTsign sysUserTsign = sysUserTsignService.get(userId);
 
@@ -525,7 +525,7 @@ public class ContractServiceImpl implements ContractService, InitializingBean {
 	@Override
 	public boolean transferVipGroupCoursesContract(Integer userId, Long vipGroupId) {
 		if(true){
-			return transferProduceContract(userId, null);
+			return transferProduceContract(userId, null, null);
 		}
 
 		SysUserTsign sysUserTsign = sysUserTsignService.get(userId);
@@ -668,7 +668,7 @@ public class ContractServiceImpl implements ContractService, InitializingBean {
 	@Override
 	public boolean transferGoodsContract(Integer userId, String musicGroupId, String goodsIds, KitGroupPurchaseTypeEnum kitGroupPurchaseTypeEnum) {
 		if(true){
-			return transferProduceContract(userId, musicGroupId);
+			return transferProduceContract(userId, musicGroupId, null);
 		}
 
 		SysUserTsign sysUserTsign = sysUserTsignService.get(userId);
@@ -890,7 +890,7 @@ public class ContractServiceImpl implements ContractService, InitializingBean {
 	@Override
 	public boolean transferPracticeCoursesContract(Integer userId, int courseSectionNum, Date startDate, Date endDate, BigDecimal fee) {
 		if(true){
-			return transferProduceContract(userId, null);
+			return transferProduceContract(userId, null, null);
 		}
 
 		SysUserTsign sysUserTsign = sysUserTsignService.get(userId);
@@ -968,7 +968,7 @@ public class ContractServiceImpl implements ContractService, InitializingBean {
 
 	@Override
 	@Transactional(rollbackFor = Exception.class, isolation = Isolation.READ_COMMITTED, propagation = Propagation.REQUIRES_NEW)
-	public boolean transferProduceContract(Integer userId,String musicGroupId) {
+	public boolean transferProduceContract(Integer userId,String musicGroupId, CourseViewTypeEnum courseViewType) {
 		SysUser user = studentDao.lockUserReturnInfo(userId);
 
 		if (user == null) {
@@ -1031,6 +1031,10 @@ public class ContractServiceImpl implements ContractService, InitializingBean {
 			ownershipType = musicGroup.getCourseViewType();
 		}
 
+		if(Objects.nonNull(courseViewType)){
+			ownershipType = courseViewType;
+		}
+
 		List<SysUserContracts> userContracts = sysUserContractsService.getUserContractWithType(userId, ContractType.PRODUCT, ownershipType.getContractVersion());
 		if(!CollectionUtils.isEmpty(userContracts)){
 			return true;
@@ -1084,7 +1088,7 @@ public class ContractServiceImpl implements ContractService, InitializingBean {
 
 	@Override
 	@Transactional(isolation = Isolation.READ_COMMITTED)
-	public Map<String, Object> queryProductContract(Integer userId,String musicGroupId) {
+	public Map<String, Object> queryProductContract(Integer userId,String musicGroupId, CourseViewTypeEnum courseViewType) {
 		// 合成freemarker
 		String srcPdfPath = contractBaseDir + "/product/" + userId + ".pdf";
 
@@ -1131,6 +1135,9 @@ public class ContractServiceImpl implements ContractService, InitializingBean {
 			ownershipType = musicGroup.getCourseViewType();
 		}
 
+		if(Objects.nonNull(courseViewType)){
+			ownershipType = courseViewType;
+		}
 
 		templateEngine.render(params, "product"+ownershipType.getContractVersion()+".ftl", srcFile);
 

+ 142 - 49
mec-biz/src/main/java/com/ym/mec/biz/service/impl/MemberRankSettingServiceImpl.java

@@ -6,10 +6,16 @@ import java.util.List;
 import java.util.Map;
 import java.util.stream.Collectors;
 
+import com.ym.mec.biz.dal.enums.*;
+import com.ym.mec.biz.service.*;
+import com.ym.mec.common.entity.HttpResponseResult;
+import org.apache.commons.lang3.StringUtils;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.http.HttpStatus;
 import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Isolation;
 import org.springframework.transaction.annotation.Propagation;
 import org.springframework.transaction.annotation.Transactional;
 
@@ -25,19 +31,6 @@ import com.ym.mec.biz.dal.entity.Student;
 import com.ym.mec.biz.dal.entity.StudentPaymentOrder;
 import com.ym.mec.biz.dal.entity.SysUserCashAccount;
 import com.ym.mec.biz.dal.entity.SysUserCashAccountDetail;
-import com.ym.mec.biz.dal.enums.DealStatusEnum;
-import com.ym.mec.biz.dal.enums.GroupType;
-import com.ym.mec.biz.dal.enums.OrderTypeEnum;
-import com.ym.mec.biz.dal.enums.PeriodEnum;
-import com.ym.mec.biz.dal.enums.PlatformCashAccountDetailTypeEnum;
-import com.ym.mec.biz.service.CloudTeacherOrderService;
-import com.ym.mec.biz.service.ContractService;
-import com.ym.mec.biz.service.MemberFeeSettingService;
-import com.ym.mec.biz.service.MemberRankSettingService;
-import com.ym.mec.biz.service.StudentPaymentOrderService;
-import com.ym.mec.biz.service.StudentService;
-import com.ym.mec.biz.service.SysUserCashAccountDetailService;
-import com.ym.mec.biz.service.SysUserCashAccountService;
 import com.ym.mec.common.dal.BaseDAO;
 import com.ym.mec.common.exception.BizException;
 import com.ym.mec.common.service.IdGeneratorService;
@@ -79,6 +72,9 @@ public class MemberRankSettingServiceImpl extends BaseServiceImpl<Integer, Membe
 	@Autowired
 	private IdGeneratorService idGeneratorService;
 
+	@Autowired
+	private SysCouponCodeService sysCouponCodeService;
+
 	private final Logger logger = LoggerFactory.getLogger(this.getClass());
 
 	@Override
@@ -124,14 +120,46 @@ public class MemberRankSettingServiceImpl extends BaseServiceImpl<Integer, Membe
 		return memberRankSettingDao.queryListByIsDefault(isDefault);
 	}
 
+	//是否有购买资格
+	public void buyCloudTeacherActive(Integer userId,Integer activeRemark,String remark){
+		if(activeRemark == null || StringUtils.isEmpty(remark)){
+			return;
+		}
+		if(activeRemark.equals(202109)){
+			if(remark.equals("单月")){
+				return;
+			}
+			StudentPaymentOrder studentPaymentOrder = studentPaymentOrderService.findByUserAndActive(userId,activeRemark,remark,null);
+			if(studentPaymentOrder != null){
+				DealStatusEnum status = studentPaymentOrder.getStatus();
+				if(status == DealStatusEnum.SUCCESS){
+					throw new BizException("您已参与此云教练活动,快去练习吧!");
+				}
+				if(status == DealStatusEnum.ING){
+					throw new BizException("您有待处理的订单,请稍后重试");
+				}
+			}
+		}
+	}
+
 	@Override
-	@Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
-	public Map buy(Integer userId, Integer memberRankId, PeriodEnum periodEnum, BigDecimal amount, boolean isUseBalance) throws Exception {
-		Student student = studentService.get(userId);
+	@Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class,isolation = Isolation.READ_COMMITTED)
+	public Map buy(Integer userId,
+				   Integer memberRankId,
+				   PeriodEnum periodEnum,
+				   BigDecimal amount,
+				   boolean isUseBalance,
+				   Integer buyNum,
+				   Integer giveNum,
+				   Integer activeRemark,String remark) throws Exception {
+		logger.info("云教练活动购买:userId:{} memberRankId:{} periodEnum:{} amount:{} isUseBalance:{} buyNum:{} giveNum:{} activeRemark:{} remark:{}",
+				userId,memberRankId,periodEnum,amount,isUseBalance,buyNum,giveNum,activeRemark,remark);
+		Student student = studentService.getLocked(userId);
 		if (student == null) {
 			throw new BizException("非法访问");
 		}
-
+		//是否可以购买
+		buyCloudTeacherActive(userId,activeRemark,remark);
 		SysUser user = sysUserFeignService.queryUserById(userId);
 
 		Integer organId = user.getOrganId();
@@ -155,34 +183,35 @@ public class MemberRankSettingServiceImpl extends BaseServiceImpl<Integer, Membe
 		BigDecimal actualAmount = BigDecimal.ZERO;
 
 		switch (periodEnum) {
-		case DAY:
-			actualAmount = memberFeeSetting.getCurrentDayFee();
-			cloudTeacherOrder.setType(1);
-			cloudTeacherOrder.setTime(1);
-			break;
-		case MONTH:
-			actualAmount = memberFeeSetting.getCurrentMonthFee();
-			cloudTeacherOrder.setType(2);
-			cloudTeacherOrder.setTime(1);
-			break;
-		case QUARTERLY:
-			actualAmount = memberFeeSetting.getCurrentQuarterlyFee();
-			cloudTeacherOrder.setType(2);
-			cloudTeacherOrder.setTime(3);
-			break;
-		case YEAR_HALF:
-			actualAmount = memberFeeSetting.getCurrentHalfYearFee();
-			cloudTeacherOrder.setType(2);
-			cloudTeacherOrder.setTime(6);
-			break;
-		case YEAR:
-			actualAmount = memberFeeSetting.getCurrentYearFee();
-			cloudTeacherOrder.setType(3);
-			cloudTeacherOrder.setTime(1);
-			break;
-
-		default:
-			break;
+			case DAY:
+				actualAmount = memberFeeSetting.getCurrentDayFee();
+				cloudTeacherOrder.setType(1);
+				cloudTeacherOrder.setTime(1);
+				break;
+			case MONTH:
+				actualAmount = memberFeeSetting.getCurrentMonthFee().multiply(new BigDecimal(buyNum));
+				cloudTeacherOrder.setType(2);
+				//购买月份加上赠送月份,目前只有按月购买的活动,其他的暂不处理
+				cloudTeacherOrder.setTime(buyNum + giveNum);
+				break;
+			case QUARTERLY:
+				actualAmount = memberFeeSetting.getCurrentQuarterlyFee();
+				cloudTeacherOrder.setType(2);
+				cloudTeacherOrder.setTime(3);
+				break;
+			case YEAR_HALF:
+				actualAmount = memberFeeSetting.getCurrentHalfYearFee();
+				cloudTeacherOrder.setType(2);
+				cloudTeacherOrder.setTime(6);
+				break;
+			case YEAR:
+				actualAmount = memberFeeSetting.getCurrentYearFee();
+				cloudTeacherOrder.setType(3);
+				cloudTeacherOrder.setTime(1);
+				break;
+
+			default:
+				break;
 		}
 
 		// 判断金额是否正确
@@ -246,6 +275,8 @@ public class MemberRankSettingServiceImpl extends BaseServiceImpl<Integer, Membe
 		cloudTeacherOrder.setOrderId(studentPaymentOrder.getId());
 		cloudTeacherOrder.setCreateTime(date);
 		cloudTeacherOrder.setUpdateTime(date);
+		cloudTeacherOrder.setActiveRemark(activeRemark);
+		cloudTeacherOrder.setRemark(remark);
 		cloudTeacherOrderService.insert(cloudTeacherOrder);
 
 		Map result = studentPaymentOrderService.createOrder(studentPaymentOrder, null, "BUY_MEMBER");
@@ -259,7 +290,7 @@ public class MemberRankSettingServiceImpl extends BaseServiceImpl<Integer, Membe
 
 		Integer userId = studentPaymentOrder.getUserId();
 
-		Student student = studentService.getLocked(userId);
+		Student student = studentService.get(userId);
 		if (student == null) {
 			throw new BizException("学员信息不存在");
 		}
@@ -338,7 +369,8 @@ public class MemberRankSettingServiceImpl extends BaseServiceImpl<Integer, Membe
 			cloudTeacherOrderService.update(cloudTeacherOrder);
 			// 添加会员有效时长
 			studentService.updateMemberRank(cloudTeacherOrder, periodEnum);
-
+			//云教练活动赠送优惠券
+			cloudTeacherActiveGiveCoupon(cloudTeacherOrder);
 			// 插入交易明细
 			BigDecimal amount = studentPaymentOrder.getActualAmount();
 			if (amount.compareTo(BigDecimal.ZERO) > 0) {
@@ -375,11 +407,72 @@ public class MemberRankSettingServiceImpl extends BaseServiceImpl<Integer, Membe
 			}
 
 			try {
-				contractService.transferProduceContract(userId, null);
+				contractService.transferProduceContract(userId, null, CourseViewTypeEnum.MEMBER_FEE);
 			} catch (Exception e) {
 				logger.error("产品协议生成失败", e);
 			}
 		}
 		return true;
 	}
-}
+
+	@Override
+	@Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class,isolation = Isolation.READ_COMMITTED)
+	public HttpResponseResult ActiveBuy(Integer userId, Integer memberRankId, PeriodEnum month, BigDecimal amount, boolean isUseBalance, Integer buyNum, int giveNum, int activeRemark, String remark,boolean repay) throws Exception {
+		HttpResponseResult result = new HttpResponseResult();
+		//判断用户是否已存在订单
+		StudentPaymentOrder applyOrder = studentPaymentOrderService.findByUserAndActive(userId,202109,remark,"ING");
+		if (applyOrder != null) {
+			// 查询订单状态
+			PayStatus payStatus = studentPaymentOrderService.queryPayStatus(applyOrder.getPaymentChannel(), applyOrder.getOrderNo(), applyOrder.getTransNo());
+			if(payStatus == PayStatus.SUCCESSED){
+				throw new BizException("订单已支付成功,请勿重复支付");
+			}else if(payStatus == PayStatus.PAYING){
+				throw new BizException("订单还在交易中,请稍后重试");
+			}
+			if(repay){
+				//处理关闭订单
+				applyOrder.setStatus(DealStatusEnum.CLOSE);
+				applyOrder.setMemo("关闭云教练活动订单");
+				if (applyOrder.getBalancePaymentAmount() != null && applyOrder.getBalancePaymentAmount().compareTo(BigDecimal.ZERO) > 0) {
+					sysUserCashAccountService.updateBalance(applyOrder.getUserId(), applyOrder.getBalancePaymentAmount(),
+							PlatformCashAccountDetailTypeEnum.REFUNDS, "购买云教练活动支付失败");
+				}
+				studentPaymentOrderService.update(applyOrder);
+			}else {
+				result.setCode(HttpStatus.CONTINUE.value());
+				result.setMsg("您有待支付的订单");
+				return result;
+			}
+
+		}
+		result.setCode(HttpStatus.OK.value());
+		result.setData(this.buy(userId,
+				memberRankId,
+				month,
+				amount,
+				isUseBalance,
+				buyNum,
+				giveNum,
+				activeRemark,remark));
+		return result;
+	}
+
+	//云教练活动赠送优惠券
+	public void cloudTeacherActiveGiveCoupon(CloudTeacherOrder cloudTeacherOrder){
+		Integer activeRemark = cloudTeacherOrder.getActiveRemark();
+		String remark = cloudTeacherOrder.getRemark();
+		if(activeRemark == null || StringUtils.isEmpty(remark)){
+			return;
+		}
+		if(activeRemark.equals(202109)){
+			switch (remark){
+				case "2赠1":
+					sysCouponCodeService.exchangeCoupon(cloudTeacherOrder.getStudentId(),1,cloudTeacherOrder.getOrderId(),3);
+					break;
+				case "3赠2":
+					sysCouponCodeService.exchangeCoupon(cloudTeacherOrder.getStudentId(),1,cloudTeacherOrder.getOrderId(),6);
+					break;
+			}
+		}
+	}
+}

+ 12 - 3
mec-biz/src/main/java/com/ym/mec/biz/service/impl/MusicGroupServiceImpl.java

@@ -2627,6 +2627,7 @@ public class MusicGroupServiceImpl extends BaseServiceImpl<String, MusicGroup> i
         studentPaymentOrder.setUpdateTime(date);
         studentPaymentOrder.setVersion(0);
         studentPaymentOrderService.insert(studentPaymentOrder);
+        calenderDetail.setPaymentStatus(PaymentStatus.PROCESSING);
         calenderDetail.setPaymentOrderId(studentPaymentOrder.getId());
         musicGroupPaymentCalenderDetailDao.update(calenderDetail);
         
@@ -2746,9 +2747,11 @@ public class MusicGroupServiceImpl extends BaseServiceImpl<String, MusicGroup> i
         Map<Integer, String> push = new HashMap<>(1);
         push.put(userId, userId.toString());
         yimei.put(userId, studentRegistration.getParentsPhone());
+
+        MusicGroupPaymentCalenderDetail calenderDetail = musicGroupPaymentCalenderDetailDao.findByOrderId(studentPaymentOrder.getId());
+        
         if (studentPaymentOrder.getStatus() == SUCCESS) {
             //当前乐团报名是否赠送乐团网管课
-            MusicGroupPaymentCalenderDetail calenderDetail = musicGroupPaymentCalenderDetailDao.findByOrderId(studentPaymentOrder.getId());
             MusicGroupStudentFee musicGroupStudentFee = musicGroupPaymentCalenderService.updateCalender(calenderDetail.getId(), studentRegistration.getUserId());
             if (musicGroupStudentFee != null) {
                 musicGroupStudentFee.setUpdateTime(date);
@@ -2905,7 +2908,7 @@ public class MusicGroupServiceImpl extends BaseServiceImpl<String, MusicGroup> i
             studentRegistrationService.updateUserSurplusCourseFee(userId, musicGroupId, courseFee, "乐团续费", userId);
 
             try {
-                contractService.transferProduceContract(userId, musicGroupId);
+                contractService.transferProduceContract(userId, musicGroupId, null);
             } catch (Exception e) {
                 logger.error("产品协议生成失败", e);
             }
@@ -2918,6 +2921,12 @@ public class MusicGroupServiceImpl extends BaseServiceImpl<String, MusicGroup> i
             }
             return true;
         } else {
+
+    		//更新学生的缴费记录状态
+    		calenderDetail.setPaymentStatus(MusicGroupStudentFee.PaymentStatus.NON_PAYMENT);
+    		calenderDetail.setUpdateTime(date);
+    		musicGroupPaymentCalenderDetailDao.update(calenderDetail);
+    		
             if (studentPaymentOrder.getBalancePaymentAmount() != null && studentPaymentOrder.getBalancePaymentAmount().doubleValue() > 0) {
                 sysUserCashAccountService.updateBalance(userId, studentPaymentOrder.getBalancePaymentAmount(), PlatformCashAccountDetailTypeEnum.REFUNDS,
                         "乐团续费失败");
@@ -3249,7 +3258,7 @@ public class MusicGroupServiceImpl extends BaseServiceImpl<String, MusicGroup> i
         }
         //课程团和amr可以互相修改,但不可以改为会员团
         if(group.getCourseViewType() != musicGroup.getCourseViewType()){
-            if(group.getCourseViewType() == CourseViewTypeEnum.MEMBER_FEE){
+            if(group.getStatus() == MusicGroupStatusEnum.PROGRESS && group.getCourseViewType() == CourseViewTypeEnum.MEMBER_FEE){
                 throw new BizException("会员收费乐团不可更改收费模式");
             }
             if(musicGroup.getCourseViewType() == CourseViewTypeEnum.MEMBER_FEE){

+ 4 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/impl/MusicGroupTrainPlanServiceImpl.java

@@ -150,6 +150,10 @@ public class MusicGroupTrainPlanServiceImpl extends BaseServiceImpl<Integer, Mus
 		return musicGroupTrainPlanSaveDto;
 	}
 
+	public static void main(String[] args) {
+
+	}
+
 	@Override
 	public MusicGroupTrainPlanSaveDto getSchoolTerm(CourseSchedule courseSchedule){
 		MusicGroupTrainPlanSaveDto musicGroupTrainPlanSaveDto = new MusicGroupTrainPlanSaveDto();

+ 1 - 1
mec-biz/src/main/java/com/ym/mec/biz/service/impl/ReplacementInstrumentActivityServiceImpl.java

@@ -447,7 +447,7 @@ public class ReplacementInstrumentActivityServiceImpl extends BaseServiceImpl<In
             //添加sell_order
             this.addSellOrder(studentPaymentOrder, replacementInstrumentActivity);
             try {
-                contractService.transferProduceContract(userId, null);
+                contractService.transferProduceContract(userId, null, null);
             } catch (Exception e) {
                 logger.error("产品协议生成失败", e);
             }

+ 2 - 2
mec-biz/src/main/java/com/ym/mec/biz/service/impl/SporadicChargeInfoImpl.java

@@ -72,12 +72,12 @@ public class SporadicChargeInfoImpl extends BaseServiceImpl<Integer, SporadicCha
         SporadicChargeInfo info = sporadicChargeInfoDao.get(Integer.parseInt(studentPaymentOrder.getMusicGroupId()));
 
         Map<Integer, String> map = new HashMap<>();
-        map.put(userId, sysUser.getPhone());
         Map<Integer, String> yimei = new HashMap<>();
+        yimei.put(userId, sysUser.getPhone());
         map.put(userId, userId.toString());
         if (studentPaymentOrder.getStatus() == DealStatusEnum.SUCCESS) {
             try {
-                contractService.transferProduceContract(userId, null);
+                contractService.transferProduceContract(userId, null, null);
             } catch (Exception e) {
                 logger.error("产品协议生成失败", e);
             }

+ 1 - 1
mec-biz/src/main/java/com/ym/mec/biz/service/impl/StudentInstrumentServiceImpl.java

@@ -219,7 +219,7 @@ public class StudentInstrumentServiceImpl extends BaseServiceImpl<Long, StudentI
         //支付成功
         if (studentPaymentOrder.getStatus() == DealStatusEnum.SUCCESS) {
             try {
-                contractService.transferProduceContract(userId, null);
+                contractService.transferProduceContract(userId, null, null);
             } catch (Exception e) {
                 logger.error("产品协议生成失败", e);
             }

+ 5 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/impl/StudentPaymentOrderServiceImpl.java

@@ -113,6 +113,11 @@ public class StudentPaymentOrderServiceImpl extends BaseServiceImpl<Long, Studen
     }
 
     @Override
+    public StudentPaymentOrder findByUserAndActive(Integer userId, Integer activeRemark, String remark,String status) {
+        return studentPaymentOrderDao.findByUserAndActive(userId,activeRemark,remark,status);
+    }
+
+    @Override
     @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
 	public Map createOrder(StudentPaymentOrder studentPaymentOrder, List<StudentPaymentOrderDetail> details, String payReceiver)
 			throws Exception {

+ 2 - 2
mec-biz/src/main/java/com/ym/mec/biz/service/impl/StudentRepairServiceImpl.java

@@ -715,7 +715,7 @@ public class StudentRepairServiceImpl extends BaseServiceImpl<Integer, StudentRe
 
         if (studentPaymentOrder.getStatus() == DealStatusEnum.SUCCESS) {
             try {
-                contractService.transferProduceContract(userId, null);
+                contractService.transferProduceContract(userId, null, null);
             } catch (Exception e) {
                 logger.error("产品协议生成失败", e);
             }
@@ -1013,7 +1013,7 @@ public class StudentRepairServiceImpl extends BaseServiceImpl<Integer, StudentRe
 
         if (studentPaymentOrder.getStatus() == DealStatusEnum.SUCCESS) {
             try {
-                contractService.transferProduceContract(userId, null);
+                contractService.transferProduceContract(userId, null, null);
             } catch (Exception e) {
                 logger.error("产品协议生成失败", e);
             }

+ 171 - 33
mec-biz/src/main/java/com/ym/mec/biz/service/impl/StudentServiceImpl.java

@@ -1,9 +1,12 @@
 package com.ym.mec.biz.service.impl;
 
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
 import com.ym.mec.biz.dal.dao.*;
 import com.ym.mec.biz.dal.dto.*;
 import com.ym.mec.biz.dal.entity.*;
 import com.ym.mec.biz.dal.enums.*;
+import com.ym.mec.biz.dal.page.CloudTeacherActiveQueryInfo;
 import com.ym.mec.biz.dal.page.OrganCloudStudyStudentDataQueryInfo;
 import com.ym.mec.biz.dal.page.StudentQueryInfo;
 import com.ym.mec.biz.service.StudentService;
@@ -13,18 +16,15 @@ import com.ym.mec.common.constant.CommonConstants;
 import com.ym.mec.common.dal.BaseDAO;
 import com.ym.mec.common.exception.BizException;
 import com.ym.mec.common.page.PageInfo;
-import com.ym.mec.common.page.QueryInfo;
 import com.ym.mec.common.service.impl.BaseServiceImpl;
 import com.ym.mec.thirdparty.message.MessageSenderPluginContext;
 import com.ym.mec.util.collection.MapUtil;
 import com.ym.mec.util.date.DateUtil;
 import org.apache.commons.lang3.StringUtils;
-import org.apache.poi.ss.formula.functions.T;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 import org.springframework.util.CollectionUtils;
-import sun.nio.cs.ext.Big5;
 
 import java.math.BigDecimal;
 import java.time.LocalDate;
@@ -41,36 +41,28 @@ public class StudentServiceImpl extends BaseServiceImpl<Integer, Student> implem
     private StudentDao studentDao;
     @Autowired
     private TeacherDao teacherDao;
-
     @Autowired
     private CourseScheduleStudentPaymentDao courseScheduleStudentPaymentDao;
-
     @Autowired
     private StudentRegistrationDao studentRegistrationDao;
-
     @Autowired
     private MusicGroupDao musicGroupDao;
-
     @Autowired
     private PracticeGroupDao practiceGroupDao;
-
     @Autowired
     private MemberRankSettingDao memberRankSettingDao;
-
     @Autowired
     private SysConfigDao sysConfigDao;
     @Autowired
     private SysMessageService sysMessageService;
-
     @Autowired
     private SysMusicCompareRecordDao sysMusicCompareRecordDao;
-
     @Autowired
     private CloudTeacherDao cloudTeacherDao;
-
+    @Autowired
+    private CloudTeacherOrderDao cloudTeacherOrderDao;
     @Autowired
     private OrganizationDao organizationDao;
-
     @Autowired
     private IndexBaseMonthDataDao indexBaseMonthDataDao;
 
@@ -654,23 +646,6 @@ public class StudentServiceImpl extends BaseServiceImpl<Integer, Student> implem
             organsNewCloudStudyNumMap = MapUtil.convertIntegerMap(organsNewCloudStudyNumMapList);
         }
 
-        //获取新增人数占比(已上乐团课小于等于4)
-        //获取有在读学员的乐团编号
-        //获取有在读学员的学员编号
-//        List<String> musicGroupIds = studentRegistrationDao.findMusicGroupIds();
-//        List<Integer> studentIdList = studentRegistrationDao.findStudentIds();
-//        List<BaseMapDto<Integer, Long>> studentMusicCourseNum = studentDao.getOrganCloudNewStudentNum(musicGroupIds,studentIdList);
-//        //获取有乐团没排课的数据
-//        List<Integer> noCourseStudentIdList = studentRegistrationDao.findNoCourseStudentIds();
-//        List<Integer> userIdList = new ArrayList<>();
-//        if(!CollectionUtils.isEmpty(studentMusicCourseNum)){
-//            List<BaseMapDto<Integer, Long>> collect = studentMusicCourseNum.stream().filter(e -> e.getValue() < 5).collect(Collectors.toList());
-//            userIdList = collect.stream().map(e -> e.getKey()).collect(Collectors.toList());
-//        }
-//        userIdList.addAll(noCourseStudentIdList);
-//        List<Map<Long, Long>> organsNewCloudNewStudentNumMapList = studentDao.groupOrganId(organIds,userIdList);
-//        Map<String, Long> organsNewCloudNewStudentNumMap = MapUtil.convertIntegerMap(organsNewCloudNewStudentNumMapList);
-
         List<IndexBaseMonthData> withDayAndDataType = indexBaseMonthDataDao.getWithDayAndDataType(LocalDate.now().toString(), CLOUD_NEW_STUDENT_NUM);
         Map<Integer, Integer> organsNewCloudNewStudentNumMap = withDayAndDataType.stream().collect(Collectors.toMap(IndexBaseMonthData::getOrganId, e -> e.getActivateNum().intValue(), (e1, e2) -> e1));
 
@@ -686,9 +661,6 @@ public class StudentServiceImpl extends BaseServiceImpl<Integer, Student> implem
             if(organsVipStudentNumMap.containsKey(organ.getId().toString())){
                 organStudentVipData.setVipStudentNum(organsVipStudentNumMap.get(organ.getId().toString()).intValue());
             }
-//            if(organsEVipStudentNumMap.containsKey(organ.getId().toString())){
-//                organStudentVipData.seteVipStudentNum(organsEVipStudentNumMap.get(organ.getId().toString()).intValue());
-//            }
             if(organCloudStudyStudentNumMap.containsKey(organ.getId().toString())){
                 organStudentVipData.setCloudStudyUseStudentNum(organCloudStudyStudentNumMap.get(organ.getId().toString()).intValue());
             }
@@ -815,4 +787,170 @@ public class StudentServiceImpl extends BaseServiceImpl<Integer, Student> implem
     public void cleanStudentCloudStudySequenceDays() {
         studentDao.cleanStudentCloudStudySequenceDays();
     }
+
+    @Override
+    public void remarkCountFlag() {
+        //清除标记
+        studentDao.cleanCountFlag();
+        //打标记
+        List<Integer> studentIds = new ArrayList<>();
+        //获取在会员团的学员
+        studentIds.addAll(studentRegistrationDao.queryHasMemberGroupStudent());
+        //获取购买过云教练(非活动)的学员
+        studentIds.addAll(cloudTeacherOrderDao.getStudentIds());
+        studentDao.remarkCountFlag(studentIds);
+        //更新目标学员、目标金额
+        SysConfig config = sysConfigDao.findByParamName("cloud_teacher_active_target");
+        config.setParanValue(JSON.toJSONString(studentRegistrationDao.queryOrganTarget()));
+        sysConfigDao.update(config);
+    }
+
+    @Override
+    public Map<String,Object> countCloudTeacherActive(List<Integer> organIdList, CloudTeacherActiveQueryInfo queryInfo) {
+        Map<String, Object> params = new HashMap<String, Object>();
+        MapUtil.populateMap(params, queryInfo);
+        //获取分部目标
+        String cloudTeacherActiveTarget = sysConfigDao.findConfigValue(SysConfigService.CLOUD_TEACHER_ACTIVE_TARGET);
+        if(StringUtils.isEmpty(cloudTeacherActiveTarget)){
+            return null;
+        }
+        List<CloudTeacherActiveTargetDto> targetDtoList = JSONArray.parseArray(cloudTeacherActiveTarget, CloudTeacherActiveTargetDto.class);
+        Map<Integer, List<CloudTeacherActiveTargetDto>> targetMap = targetDtoList.stream().collect(Collectors.groupingBy(e -> e.getOrganId()));
+        //获取各分部总人数
+        List<Map<String, Long>> maps = indexBaseMonthDataDao.countTotalStudentNum();
+        Map<String, Long> organStudentNumMap = new HashMap<>(20);
+        if(maps != null && maps.size() > 0){
+            organStudentNumMap = MapUtil.convertIntegerMap(maps);
+        }
+        params.put("organIdList",organIdList);
+        List<CloudTeacherActiveTargetDto> resultList = indexBaseMonthDataDao.countCloudTeacherActive(params);
+        for (CloudTeacherActiveTargetDto dto : resultList) {
+            Long aLong = organStudentNumMap.get(dto.getOrganId().toString());
+            dto.setTotalNum(aLong==null?0:aLong.intValue());
+            List<CloudTeacherActiveTargetDto> targetDtos = targetMap.get(dto.getOrganId());
+            if(targetDtos != null && targetDtos.size() > 0){
+                CloudTeacherActiveTargetDto target = targetDtos.get(0);
+                dto.setTargetNum(target.getTargetNum());
+                dto.setTargetAmount(target.getTargetAmount());
+            }
+            if(dto.getBuyAmount().doubleValue() > 0d && dto.getBuyNum() > 0){
+                BigDecimal avgBuyAmount = dto.getBuyAmount().divide(new BigDecimal(dto.getBuyNum()), CommonConstants.DECIMAL_FINAL_PLACE, BigDecimal.ROUND_HALF_UP);
+                dto.setAvgBuyAmount(avgBuyAmount);
+            }
+            if(dto.getTotalNum() > 0 && dto.getBuyNum() > 0){
+                BigDecimal buyScale = new BigDecimal(dto.getBuyNum()).divide(new BigDecimal(dto.getTotalNum()), CommonConstants.DECIMAL_FINAL_PLACE, BigDecimal.ROUND_HALF_UP).multiply(new BigDecimal(100));
+                dto.setBuyScale(buyScale);
+            }
+            if(dto.getTargetNum() > 0 && dto.getBuyNum() > 0){
+                BigDecimal targetFinishScale = new BigDecimal(dto.getBuyNum()).divide(new BigDecimal(dto.getTargetNum()), CommonConstants.DECIMAL_FINAL_PLACE, BigDecimal.ROUND_HALF_UP).multiply(new BigDecimal(100));
+                dto.setTargetFinishScale(targetFinishScale);
+            }
+        }
+        Map<String,Object> resultMap = new HashMap<>(7);
+        BigDecimal targetAmount = resultList.stream().map(CloudTeacherActiveTargetDto::getTargetAmount).reduce(BigDecimal.ZERO, BigDecimal::add);
+        resultMap.put("targetAmount",targetAmount);
+        BigDecimal buyAmount = resultList.stream().map(CloudTeacherActiveTargetDto::getBuyAmount).reduce(BigDecimal.ZERO, BigDecimal::add);
+        resultMap.put("buyAmount",buyAmount);
+        Integer buyNum = resultList.stream().mapToInt(CloudTeacherActiveTargetDto::getBuyNum).sum();
+        resultMap.put("buyNum",buyNum);
+        Integer totalNum = resultList.stream().mapToInt(CloudTeacherActiveTargetDto::getTotalNum).sum();
+        resultMap.put("totalNum",totalNum);
+        Integer targetNum = resultList.stream().mapToInt(CloudTeacherActiveTargetDto::getTargetNum).sum();
+        resultMap.put("targetNum",targetNum);
+        resultMap.put("avgBuyAmount",0);
+        resultMap.put("buyScale",0);
+        resultMap.put("targetFinishScale",0);
+        if(buyAmount.doubleValue() > 0d && buyNum > 0){
+            BigDecimal avgBuyAmount = buyAmount.divide(new BigDecimal(buyNum), CommonConstants.DECIMAL_FINAL_PLACE, BigDecimal.ROUND_HALF_UP);
+            resultMap.put("avgBuyAmount",avgBuyAmount);
+        }
+        if(totalNum > 0 && buyNum > 0){
+            BigDecimal buyScale = new BigDecimal(buyNum).divide(new BigDecimal(totalNum), CommonConstants.DECIMAL_FINAL_PLACE, BigDecimal.ROUND_HALF_UP).multiply(new BigDecimal(100));
+            resultMap.put("buyScale",buyScale);
+        }
+        if(targetNum > 0 && buyNum > 0){
+            BigDecimal targetFinishScale = new BigDecimal(buyNum).divide(new BigDecimal(targetNum), CommonConstants.DECIMAL_FINAL_PLACE, BigDecimal.ROUND_HALF_UP).multiply(new BigDecimal(100));
+            resultMap.put("targetFinishScale",targetFinishScale);
+        }
+        Map<String,Object> result = new HashMap<>(2);
+        result.put("head",resultMap);
+        String sort = queryInfo.getSort();
+        if(StringUtils.isEmpty(sort)){
+            sort = "targetFinishScale";
+        }
+        String order = queryInfo.getOrder();
+        switch (sort){
+            case "buyAmount":
+                if("DESC".equalsIgnoreCase(order)){
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getBuyAmount,Comparator.reverseOrder())).collect(Collectors.toList());
+                }else {
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getBuyAmount)).collect(Collectors.toList());
+                }
+                break;
+            case "buyNum":
+                if("DESC".equalsIgnoreCase(order)){
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getBuyNum,Comparator.reverseOrder())).collect(Collectors.toList());
+                }else {
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getBuyNum)).collect(Collectors.toList());
+                }
+                break;
+            case "avgBuyAmount":
+                if("DESC".equalsIgnoreCase(order)){
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getAvgBuyAmount,Comparator.reverseOrder())).collect(Collectors.toList());
+                }else {
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getAvgBuyAmount)).collect(Collectors.toList());
+                }
+                break;
+            case "totalNum":
+                if("DESC".equalsIgnoreCase(order)){
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getTotalNum,Comparator.reverseOrder())).collect(Collectors.toList());
+                }else {
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getTotalNum)).collect(Collectors.toList());
+                }
+                break;
+            case "buyScale":
+                if("DESC".equalsIgnoreCase(order)){
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getBuyScale,Comparator.reverseOrder())).collect(Collectors.toList());
+                }else {
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getBuyScale)).collect(Collectors.toList());
+                }
+                break;
+            case "targetNum":
+                if("DESC".equalsIgnoreCase(order)){
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getTargetNum,Comparator.reverseOrder())).collect(Collectors.toList());
+                }else {
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getTargetNum)).collect(Collectors.toList());
+                }
+                break;
+            case "targetFinishScale":
+                if("DESC".equalsIgnoreCase(order)){
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getTargetFinishScale,Comparator.reverseOrder())).collect(Collectors.toList());
+                }else {
+                    resultList = resultList.stream().sorted(Comparator.comparing(CloudTeacherActiveTargetDto::getTargetFinishScale)).collect(Collectors.toList());
+                }
+                break;
+        }
+        result.put("resultList",resultList);
+        return result;
+    }
+
+    @Override
+    public PageInfo<CloudTeacherActiveTargetDetailDto> countCloudTeacherActiveDetail(CloudTeacherActiveQueryInfo queryInfo) {
+        PageInfo<CloudTeacherActiveTargetDetailDto> pageInfo = new PageInfo<>(queryInfo.getPage(), queryInfo.getRows());
+        Map<String, Object> params = new HashMap<String, Object>();
+        MapUtil.populateMap(params, queryInfo);
+
+        List<CloudTeacherActiveTargetDetailDto> dataList = null;
+        int count = cloudTeacherOrderDao.countCloudTeacherActiveDetail(params);
+        if (count > 0) {
+            pageInfo.setTotal(count);
+            params.put("offset", pageInfo.getOffset());
+            dataList = cloudTeacherOrderDao.queryCloudTeacherActiveDetail(params);
+        }
+        if (count == 0) {
+            dataList = new ArrayList<>();
+        }
+        pageInfo.setRows(dataList);
+        return pageInfo;
+    }
 }

+ 1 - 1
mec-biz/src/main/java/com/ym/mec/biz/service/impl/SubjectChangeServiceImpl.java

@@ -566,7 +566,7 @@ public class SubjectChangeServiceImpl extends BaseServiceImpl<Integer, SubjectCh
 
         if (studentPaymentOrder.getStatus() == DealStatusEnum.SUCCESS) {
             try {
-                contractService.transferProduceContract(userId, subjectChange.getMusicGroupId());
+                contractService.transferProduceContract(userId, subjectChange.getMusicGroupId(), null);
             } catch (Exception e) {
                 logger.error("产品协议生成失败", e);
             }

+ 153 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/impl/SysCouponCodeServiceImpl.java

@@ -0,0 +1,153 @@
+package com.ym.mec.biz.service.impl;
+
+import com.ym.mec.biz.dal.dao.StudentPaymentOrderDao;
+import com.ym.mec.biz.dal.dao.SysCouponCodeDao;
+import com.ym.mec.biz.dal.dao.SysCouponDao;
+import com.ym.mec.biz.dal.dto.HorseRaceLampDto;
+import com.ym.mec.biz.dal.dto.SysCouponCodeDto;
+import com.ym.mec.biz.dal.entity.StudentPaymentOrder;
+import com.ym.mec.biz.dal.entity.SysCoupon;
+import com.ym.mec.biz.dal.entity.SysCouponCode;
+import com.ym.mec.biz.dal.page.SysCouponCodeQueryInfo;
+import com.ym.mec.biz.service.SysCouponCodeService;
+import com.ym.mec.biz.service.SysCouponService;
+import com.ym.mec.common.dal.BaseDAO;
+import com.ym.mec.common.exception.BizException;
+import com.ym.mec.common.page.PageInfo;
+import com.ym.mec.common.page.QueryInfo;
+import com.ym.mec.common.service.IdGeneratorService;
+import com.ym.mec.common.service.impl.BaseServiceImpl;
+import com.ym.mec.util.collection.MapUtil;
+import com.ym.mec.util.date.DateUtil;
+import org.springframework.beans.BeanUtils;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Isolation;
+import org.springframework.transaction.annotation.Propagation;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.*;
+import java.util.concurrent.atomic.AtomicInteger;
+
+@Service
+public class SysCouponCodeServiceImpl extends BaseServiceImpl<Long, SysCouponCode>  implements SysCouponCodeService {
+	
+	@Autowired
+	private SysCouponCodeDao sysCouponCodeDao;
+	@Autowired
+	private SysCouponService sysCouponService;
+	@Autowired
+	private SysCouponDao sysCouponDao;
+	@Autowired
+	private IdGeneratorService idGeneratorService;
+	@Autowired
+	private StudentPaymentOrderDao studentPaymentOrderDao;
+
+	@Override
+	public BaseDAO<Long, SysCouponCode> getDAO() {
+		return sysCouponCodeDao;
+	}
+
+	@Override
+	@Transactional(rollbackFor = Exception.class, isolation = Isolation.READ_COMMITTED)
+	public boolean exchangeCouponTest(Integer userId, Integer couponId, Long paymentOrderId, Integer exchangeNum) {
+		return exchangeCoupon(userId, couponId, paymentOrderId, exchangeNum);
+	}
+
+	@Override
+	@Transactional(rollbackFor = Exception.class, propagation = Propagation.REQUIRES_NEW, isolation = Isolation.READ_COMMITTED)
+	public boolean exchangeCoupon(Integer userId, Integer couponId, Long paymentOrderId, Integer exchangeNum) {
+		if(Objects.isNull(userId)||Objects.isNull(couponId)||Objects.isNull(paymentOrderId)||Objects.isNull(exchangeNum)){
+			throw new BizException("领取失败");
+		}
+		if(exchangeNum<=0){
+			return true;
+		}
+		SysCoupon sysCoupon = sysCouponDao.lockCoupon(couponId);
+		Date now = new Date();
+		//如果优惠券不存在,或者已停用,或者不在领取有效期内,或者已消耗完,则此优惠券无效
+		boolean invalid = Objects.isNull(sysCoupon)||0==sysCoupon.getStatus()||now.compareTo(sysCoupon.getStartDate())<0||now.compareTo(sysCoupon.getEndDate())>0;
+		invalid = invalid || sysCoupon.getStockCount()!=-1&&sysCoupon.getConsumeNum()>=sysCoupon.getStockCount()&&(sysCoupon.getStockCount()-sysCoupon.getConsumeNum()<exchangeNum);
+		if(invalid){
+			throw new BizException("无效优惠券");
+		}
+		StudentPaymentOrder studentPaymentOrder = studentPaymentOrderDao.get(paymentOrderId);
+		if(Objects.isNull(studentPaymentOrder)){
+			throw new BizException("无效订单");
+		}
+		if(sysCoupon.getLimitExchangeNum()!=-1){
+			int userUserNum = sysCouponCodeDao.countWithUserAndCoupon(userId, couponId);
+			invalid = (userUserNum + exchangeNum)>sysCoupon.getLimitExchangeNum();
+		}
+		//如果用户使用数量超过优惠券限制则领取无效
+		if(invalid){
+			throw new BizException("当前优惠券最多可领取{}次", sysCoupon.getLimitExchangeNum());
+		}
+		SysCouponCode sysCouponCode = new SysCouponCode();
+		sysCouponCode.setUserId(userId);
+		sysCouponCode.setCouponId(couponId);
+		sysCouponCode.setPaymentOrderId(paymentOrderId);
+		sysCouponCode.setUsageStatus(0);
+		switch (sysCoupon.getEffectiveType()){
+			case DAYS:
+				sysCouponCode.setUseStartDate(now);
+				sysCouponCode.setUseDeadlineDate(DateUtil.addDays(now, sysCoupon.getDeadline()));
+				break;
+			case TIME_BUCKET:
+				sysCouponCode.setUseStartDate(sysCoupon.getStartDate());
+				sysCouponCode.setUseDeadlineDate(sysCoupon.getEndDate());
+				break;
+			default:
+				throw new BizException("无效优惠券", sysCoupon.getLimitExchangeNum());
+		}
+		List<SysCouponCode> couponCodes = new ArrayList<>();
+		for (int i = 0; i < exchangeNum; i++) {
+			SysCouponCode couponCode = new SysCouponCode();
+			BeanUtils.copyProperties(sysCouponCode, couponCode);
+			couponCode.setCode(String.valueOf(idGeneratorService.generatorId("coupon")));
+			couponCodes.add(couponCode);
+		}
+		sysCouponCodeDao.batchInsert(couponCodes);
+		sysCoupon.setConsumeNum(new AtomicInteger(sysCoupon.getConsumeNum()).addAndGet(exchangeNum));
+		if(sysCoupon.getWarningStatus()==0&&sysCoupon.getStockCount()!=-1&&sysCoupon.getStockCount()-sysCoupon.getConsumeNum()<sysCoupon.getWarningStockNum()){
+			sysCouponService.stockWarning(sysCoupon.getId(), sysCoupon.getName());
+			sysCoupon.setWarningStatus(1);
+		}
+		sysCouponDao.update(sysCoupon);
+		return true;
+	}
+
+	@Override
+	public PageInfo<SysCouponCodeDto> querySysCouponUseList(SysCouponCodeQueryInfo queryInfo) {
+		PageInfo<SysCouponCodeDto> pageInfo = new PageInfo<>(queryInfo.getPage(), queryInfo.getRows());
+		Map<String, Object> params = new HashMap<String, Object>();
+		MapUtil.populateMap(params, queryInfo);
+
+		List<SysCouponCodeDto> dataList = new ArrayList<>();
+		int count = sysCouponCodeDao.countSysCouponUseList(params);
+		if (count > 0) {
+			pageInfo.setTotal(count);
+			params.put("offset", pageInfo.getOffset());
+			dataList = sysCouponCodeDao.querySysCouponUseList(params);
+		}
+		pageInfo.setRows(dataList);
+		return pageInfo;
+	}
+
+    @Override
+    public PageInfo<HorseRaceLampDto> queryHorseRaceLampDtoList(QueryInfo queryInfo) {
+		PageInfo<HorseRaceLampDto> pageInfo = new PageInfo<>(queryInfo.getPage(), queryInfo.getRows());
+		Map<String, Object> params = new HashMap<String, Object>();
+		MapUtil.populateMap(params, queryInfo);
+
+		List<HorseRaceLampDto> dataList = new ArrayList<>();
+		int count = sysCouponCodeDao.countHorseRaceLampDtoList(params);
+		if (count > 0) {
+			pageInfo.setTotal(count);
+			params.put("offset", pageInfo.getOffset());
+			dataList = sysCouponCodeDao.queryHorseRaceLampDtoList(params);
+		}
+		pageInfo.setRows(dataList);
+		return pageInfo;
+    }
+}

+ 85 - 0
mec-biz/src/main/java/com/ym/mec/biz/service/impl/SysCouponServiceImpl.java

@@ -0,0 +1,85 @@
+package com.ym.mec.biz.service.impl;
+
+import com.ym.mec.biz.dal.dao.SysCouponDao;
+import com.ym.mec.biz.dal.entity.SysCoupon;
+import com.ym.mec.biz.dal.enums.MessageTypeEnum;
+import com.ym.mec.biz.dal.page.SysCouponQueryInfo;
+import com.ym.mec.biz.service.SysCouponService;
+import com.ym.mec.biz.service.SysMessageService;
+import com.ym.mec.common.dal.BaseDAO;
+import com.ym.mec.common.exception.BizException;
+import com.ym.mec.common.page.PageInfo;
+import com.ym.mec.common.service.impl.BaseServiceImpl;
+import com.ym.mec.thirdparty.message.MessageSenderPluginContext;
+import com.ym.mec.util.collection.MapUtil;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.scheduling.annotation.Async;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Isolation;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.*;
+
+@Service
+public class SysCouponServiceImpl extends BaseServiceImpl<Integer, SysCoupon>  implements SysCouponService {
+	
+	@Autowired
+	private SysCouponDao sysCouponDao;
+	@Autowired
+	private SysMessageService sysMessageService;
+
+	@Override
+	public BaseDAO<Integer, SysCoupon> getDAO() {
+		return sysCouponDao;
+	}
+
+	@Override
+	public PageInfo<SysCoupon> queryPage(SysCouponQueryInfo queryInfo) {
+		PageInfo<SysCoupon> pageInfo = new PageInfo<>(queryInfo.getPage(), queryInfo.getRows());
+		Map<String, Object> params = new HashMap<String, Object>();
+		MapUtil.populateMap(params, queryInfo);
+
+		List<SysCoupon> dataList = new ArrayList<>();
+		int count = this.findCount(params);
+		if (count > 0) {
+			pageInfo.setTotal(count);
+			params.put("offset", pageInfo.getOffset());
+			dataList = this.getDAO().queryPage(params);
+		}
+		pageInfo.setRows(dataList);
+		return pageInfo;
+	}
+
+	@Override
+	@Transactional(rollbackFor = Exception.class, isolation = Isolation.READ_COMMITTED)
+	public void updateCoupon(SysCoupon sysCoupon) {
+		SysCoupon oldCoupon = sysCouponDao.lockCoupon(sysCoupon.getId());
+		if(Objects.isNull(oldCoupon)){
+			throw new BizException("优惠券信息不存在");
+		}
+		//如果已经有人领取,则只能修改库存总量与预警值
+		if(oldCoupon.getConsumeNum()>0){
+			if(oldCoupon.getStatus()==0){
+				oldCoupon.setStockCount(sysCoupon.getStockCount());
+				oldCoupon.setWarningStockNum(sysCoupon.getWarningStockNum());
+			}
+			oldCoupon.setStatus(sysCoupon.getStatus());
+			if(oldCoupon.getStockCount()-oldCoupon.getConsumeNum()>oldCoupon.getWarningStockNum()){
+				oldCoupon.setWarningStatus(0);
+			}
+			sysCouponDao.update(oldCoupon);
+		}else{
+			sysCouponDao.update(sysCoupon);
+		}
+	}
+
+	@Async
+	@Override
+	public void stockWarning(Integer couponId, String couponName) {
+		Map<Integer, String> teacherPhoneMap = new HashMap<>();
+		teacherPhoneMap.put(2112251, "13618651329");
+		sysMessageService.batchSendMessage(MessageSenderPluginContext.MessageSender.YIMEI, MessageTypeEnum.COUPON_STOCK_WARNING,
+				teacherPhoneMap, null, 0, null, null,
+				couponName);
+	}
+}

+ 60 - 5
mec-biz/src/main/java/com/ym/mec/biz/service/impl/SysMusicCompareRecordServiceImpl.java

@@ -15,6 +15,7 @@ import com.ym.mec.biz.service.SysMessageService;
 import com.ym.mec.biz.service.SysMusicCompareRecordService;
 import com.ym.mec.biz.service.SysMusicCompareWeekDataService;
 import com.ym.mec.common.dal.BaseDAO;
+import com.ym.mec.common.exception.BizException;
 import com.ym.mec.common.page.PageInfo;
 import com.ym.mec.common.service.impl.BaseServiceImpl;
 import com.ym.mec.thirdparty.message.MessageSenderPluginContext;
@@ -48,11 +49,16 @@ public class SysMusicCompareRecordServiceImpl extends BaseServiceImpl<Long, SysM
 	@Autowired
 	private StudentDao studentDao;
 	@Autowired
+	private StudentVisitDao studentVisitDao;
+	@Autowired
 	private SysMessageService sysMessageService;
 
 	@Autowired
 	private SysConfigDao sysConfigDao;
 
+	@Autowired
+	private MusicGroupDao musicGroupDao;
+
 	@Override
 	public BaseDAO<Long, SysMusicCompareRecord> getDAO() {
 		return sysMusicCompareRecordDao;
@@ -333,16 +339,65 @@ public class SysMusicCompareRecordServiceImpl extends BaseServiceImpl<Long, SysM
 
     @Override
     public PageInfo<CountStudentTrainDataDto> countStudentTrain(SysMusicCompareRecordQueryInfo queryInfo) {
+		if(queryInfo.getStartTime() == null || queryInfo.getEndTime() == null){
+			throw new BizException("请选择训练时间");
+		}
 		PageInfo<CountStudentTrainDataDto> pageInfo = new PageInfo<>(queryInfo.getPage(), queryInfo.getRows());
 		Map<String, Object> params = new HashMap<String, Object>();
+		String sort = queryInfo.getSort();
+		if(StringUtils.isNotEmpty(sort)){
+			queryInfo.setSort(sort.equals("trainNum")?"train_num_":sort.equals("totalPlayTime")?"total_play_time_":sort.equals("recordNum")?"record_num_":"train_day_");
+		}
 		MapUtil.populateMap(params, queryInfo);
-
+		Integer visitFlag = 0;
+		if(queryInfo.getVisitFlag() != null && queryInfo.getVisitFlag()){
+			//获取乐团在读,有vip网管课的学员列表
+			List<Integer> hasCourseUserIds = studentDao.getStudentByHasCourse(queryInfo.getTeacherId());
+			if(hasCourseUserIds == null || hasCourseUserIds.size() == 0){
+				return pageInfo;
+			}
+			params.put("hasCourseUserIds",hasCourseUserIds);
+			//获取所选时间段下一周的日期
+			Date addDays1 = DateUtil.addDays(DateUtil.toDate(queryInfo.getEndTime()), 1);
+			Date addDays3 = DateUtil.addDays(DateUtil.toDate(queryInfo.getEndTime()), 3);
+			//有回访过的学员列表
+			List<Integer> studentIds = studentVisitDao.queryRecordVisitStudentIds(queryInfo.getTeacherId(),addDays1,addDays3);
+			if(studentIds != null && studentIds.size() > 0){
+				params.put("visitStudents",studentIds);
+			}
+			Date date = DateUtil.toDate(DateUtil.format(new Date(),DateUtil.ISO_EXPANDED_DATE_FORMAT));
+			int daysBetween = DateUtil.daysBetween(addDays1, date);
+			//每周只有前三天可以回访
+			if(daysBetween >= 0 && daysBetween <= 2){
+				visitFlag = 1;
+			}
+			params.put("having",1);
+		}
+		String totalTime = sysConfigDao.findConfigValue(SysConfigService.STUDENT_CLOUD_TEACHER_TOTAL_PLAY_TIME);
+		if(StringUtils.isEmpty(totalTime)){
+			totalTime = "80";
+		}
+		params.put("totalTime",Integer.parseInt(totalTime));
+		String trainNum = sysConfigDao.findConfigValue(SysConfigService.STUDENT_CLOUD_TEACHER_TRAIN_NUM);
+		if(StringUtils.isEmpty(trainNum)){
+			trainNum = "4";
+		}
+		params.put("trainNum",Integer.parseInt(trainNum));
+		int count = sysMusicCompareRecordDao.queryStudentTrain(params).size();
 		List<CountStudentTrainDataDto> dataList = new ArrayList<>();
-		int count = sysMusicCompareRecordDao.countStudentTrain(params);
-		if (count > 0) {
-			pageInfo.setTotal(count);
+		if(count > 0){
 			params.put("offset", pageInfo.getOffset());
-			dataList =sysMusicCompareRecordDao.queryStudentTrain(params);
+			dataList = sysMusicCompareRecordDao.queryStudentTrain(params);
+			List<Integer> studentIds = dataList.stream().map(e -> e.getUserId()).collect(Collectors.toList());
+			//获取学员在读,进行中的乐团名称
+			Map<Integer,String> groupNameMap = MapUtil.convertMybatisMap(musicGroupDao.queryNormalGroupName(studentIds));
+			pageInfo.setTotal(count);
+			for (CountStudentTrainDataDto e : dataList) {
+				e.setMusicGroupName(groupNameMap.get(e.getUserId()));
+				if(visitFlag == 1){
+					e.setVisitFlag(visitFlag);
+				}
+			}
 		}
 		pageInfo.setRows(dataList);
 		return pageInfo;

+ 11 - 0
mec-biz/src/main/resources/config/mybatis/ChargeTypeMapper.xml

@@ -81,4 +81,15 @@
     <select id="queryNameByIds" resultType="java.util.Map" parameterType="list">
         SELECT id_ `key`,name_ `value` FROM charge_type WHERE FIND_IN_SET(id_,#{chargeTypeIds})
     </select>
+    <select id="queryNormalChargeName" resultType="java.util.Map">
+        SELECT sr.user_id_ 'key',GROUP_CONCAT(DISTINCT ct.name_) 'value' FROM student_registration sr
+        LEFT JOIN music_group mg ON mg.id_ = sr.music_group_id_
+        LEFT JOIN charge_type ct ON ct.id_ = mg.charge_type_id_
+        WHERE mg.status_ = 'PROGRESS' AND sr.music_group_status_ = 'NORMAL'
+        AND sr.user_id_ IN
+        <foreach collection="studentIds" item="userId" open="(" close=")" separator=",">
+            #{userId}
+        </foreach>
+        GROUP BY sr.user_id_
+    </select>
 </mapper>

+ 82 - 5
mec-biz/src/main/resources/config/mybatis/CloudTeacherOrderMapper.xml

@@ -17,6 +17,7 @@
         <result column="end_time_" property="endTime"/>
         <result column="order_id_" property="orderId"/>
         <result column="remark_" property="remark"/>
+        <result column="active_remark_" property="activeRemark"/>
         <result column="version_" property="version"/>
         <result column="create_time_" property="createTime"/>
         <result column="update_time_" property="updateTime"/>
@@ -58,14 +59,17 @@
             useGeneratedKeys="true">
         <!--@mbg.generated-->
         insert into cloud_teacher_order (organ_id_,student_id_, type_, level_, time_, amount_, refund_amount_, status_,
-        order_id_,start_time_,end_time_,remark_, create_time_, update_time_,music_group_id_)
+        order_id_,start_time_,end_time_,remark_, create_time_, update_time_,music_group_id_,active_remark_)
         values (#{organId},#{studentId}, #{type},#{level}, #{time}, #{amount}, #{refundAmount},
-        #{status},#{orderId},#{startTime},#{endTime}, #{remark}, NOW(), NOW(),#{musicGroupId})
+        #{status},#{orderId},#{startTime},#{endTime}, #{remark}, NOW(), NOW(),#{musicGroupId},#{activeRemark})
     </insert>
     <update id="update" parameterType="com.ym.mec.biz.dal.entity.CloudTeacherOrder">
         <!--@mbg.generated-->
         update cloud_teacher_order
         <set>
+            <if test="activeRemark != null">
+                active_remark_ = #{activeRemark},
+            </if>
             <if test="musicGroupId != null">
                 music_group_id_ = #{musicGroupId},
             </if>
@@ -105,9 +109,6 @@
             <if test="remark != null">
                 remark_ = #{remark},
             </if>
-            <if test="createTime != null">
-                create_time_ = #{createTime},
-            </if>
             version_ = version_+1,
             update_time_ = NOW(),
         </set>
@@ -208,4 +209,80 @@
         </if>
         GROUP BY student_id_
     </select>
+    <resultMap id="CloudTeacherActiveTargetDetailDto" type="com.ym.mec.biz.dal.dto.CloudTeacherActiveTargetDetailDto">
+        <result property="userId" column="student_id_"/>
+        <result property="username" column="username_"/>
+        <result property="amount" column="amount_"/>
+        <result property="remark" column="remark_"/>
+        <result property="cooperationName" column="cooperation_name_"/>
+        <result property="musicGroupName" column="music_group_name_"/>
+        <result property="chargeType" column="charge_type_name_"/>
+        <result property="subjectName" column="subject_name_"/>
+        <result property="currentGradeNum" column="current_grade_num_"/>
+        <result property="teacherName" column="teacher_name_"/>
+        <result property="createTime" column="create_time_"/>
+    </resultMap>
+    <select id="queryCloudTeacherActiveDetail" resultMap="CloudTeacherActiveTargetDetailDto">
+        SELECT su.username_,cto.remark_,cto.amount_,cto.student_id_,GROUP_CONCAT(DISTINCT co.name_) cooperation_name_,
+        GROUP_CONCAT(DISTINCT mg.name_) music_group_name_,GROUP_CONCAT(DISTINCT ct.name_) charge_type_name_,
+        sj.name_ subject_name_,st.current_grade_num_,sus.real_name_ teacher_name_,cto.create_time_
+        FROM cloud_teacher_order cto
+        LEFT JOIN sys_user su ON su.id_ = cto.student_id_
+        LEFT JOIN student_registration sr ON sr.user_id_ = cto.student_id_ AND sr.music_group_status_ = 'NORMAL'
+        LEFT JOIN music_group mg ON mg.id_ = sr.music_group_id_ AND mg.status_ = 'PROGRESS'
+        LEFT JOIN cooperation_organ co ON co.id_ = mg.cooperation_organ_id_
+        LEFT JOIN charge_type ct ON ct.id_ = mg.charge_type_id_
+        LEFT JOIN student st ON st.user_id_ = cto.student_id_
+        LEFT JOIN sys_user sus ON sus.id_ = st.teacher_id_
+        LEFT JOIN `subject` sj ON sj.id_ = st.subject_id_list_
+        <include refid="queryCloudTeacherActiveDetailSql"/>
+        GROUP BY cto.id_
+        ORDER BY cto.id_ DESC
+        <include refid="global.limit"/>
+    </select>
+    <select id="countCloudTeacherActiveDetail" resultType="int">
+        SELECT COUNT(DISTINCT cto.id_)
+        FROM cloud_teacher_order cto
+        LEFT JOIN sys_user su ON su.id_ = cto.student_id_
+        LEFT JOIN student st ON st.user_id_ = cto.student_id_
+        LEFT JOIN student_registration sr ON sr.user_id_ = cto.student_id_ AND sr.music_group_status_ = 'NORMAL'
+        LEFT JOIN music_group mg ON mg.id_ = sr.music_group_id_ AND mg.status_ = 'PROGRESS'
+        <include refid="queryCloudTeacherActiveDetailSql"/>
+    </select>
+    <select id="queryActiveOrderPage" resultType="string">
+        SELECT GROUP_CONCAT(DISTINCT cto.remark_) FROM cloud_teacher_order cto
+        LEFT JOIN student_payment_order spo ON spo.id_ = cto.order_id_
+        WHERE spo.status_ = 'SUCCESS' AND cto.active_remark_ = #{activeRemark}
+        AND cto.student_id_ = #{userId} AND cto.remark_ != '单月'
+        <if test="remark != null and remark != ''">
+            AND cto.remark_ = #{remark}
+        </if>
+    </select>
+    <select id="getStudentIds" resultType="java.lang.Integer">
+        SELECT DISTINCT student_id_ FROM cloud_teacher_order WHERE active_remark_ IS NULL AND status_ != 0
+    </select>
+    <sql id="queryCloudTeacherActiveDetailSql">
+        <where>
+            cto.status_ != 0 AND cto.active_remark_ = '202109'
+            <if test="organIds != null and organIds != ''">
+                AND FIND_IN_SET(su.organ_id_,#{organIds})
+            </if>
+            <if test="search != null and search != ''">
+                AND (su.id_ = #{search} OR su.username_ LIKE CONCAT('%',#{search},'%') OR mg.id_ LIKE CONCAT('%',#{search},'%'))
+            </if>
+            <if test="chargeType != null">
+                AND mg.charge_type_id_ = #{chargeType}
+            </if>
+            <if test="subjectId != null">
+                AND st.subject_id_list_ = #{subjectId}
+            </if>
+            <if test="teacherId != null">
+                AND st.teacher_id_ = #{teacherId}
+            </if>
+            <if test="remarkType != null and remarkType != ''">
+                AND cto.remark_ = #{remarkType}
+            </if>
+        </where>
+    </sql>
+
 </mapper>

+ 31 - 0
mec-biz/src/main/resources/config/mybatis/IndexBaseMonthDataMapper.xml

@@ -1820,4 +1820,35 @@
 		HAVING MIN(DATE( smcr.create_time_ ))= #{dayStr}) t
 		GROUP BY t.organ_id_
 	</select>
+	<resultMap id="CloudTeacherActiveTargetDto" type="com.ym.mec.biz.dal.dto.CloudTeacherActiveTargetDto">
+		<result property="organId" column="organ_id_"/>
+		<result property="organName" column="organ_name_"/>
+		<result property="totalNum" column="total_num_"/>
+		<result property="buyAmount" column="buy_amount_"/>
+		<result property="buyNum" column="buy_num_"/>
+		<result property="targetAmount" column="target_amount_"/>
+		<result property="targetNum" column="target_num_"/>
+	</resultMap>
+    <select id="countCloudTeacherActive" resultMap="CloudTeacherActiveTargetDto">
+		SELECT o.name_ organ_name_,o.id_ organ_id_,CASE WHEN SUM(cto.amount_) IS NULL THEN 0 ELSE SUM(cto.amount_) END buy_amount_,
+		COUNT(DISTINCT cto.student_id_) buy_num_
+		FROM student s
+		LEFT JOIN cloud_teacher_order cto ON cto.student_id_ = s.user_id_ AND cto.status_ != 0 AND cto.active_remark_ = '202109'
+		LEFT JOIN sys_user su ON su.id_ = s.user_id_
+		LEFT JOIN organization o ON o.id_ = su.organ_id_
+		WHERE 1=1
+		<if test="organIdList != null and organIdList.size > 0">
+			AND su.organ_id_ IN
+			<foreach collection="organIdList" open="(" close=")" item="item" separator=",">
+				#{item}
+			</foreach>
+		</if>
+		GROUP BY su.organ_id_
+	</select>
+	<select id="countTotalStudentNum" resultType="java.util.Map">
+		SELECT su.organ_id_ 'key',COUNT(DISTINCT s.user_id_) 'value' FROM student s
+		LEFT JOIN sys_user su ON su.id_ = s.user_id_
+		WHERE s.count_flag_ = 1
+		GROUP BY su.organ_id_
+	</select>
 </mapper>

+ 10 - 0
mec-biz/src/main/resources/config/mybatis/MusicGroupMapper.xml

@@ -964,4 +964,14 @@
         GROUP BY sr.music_group_id_
         ORDER BY mg.create_time_ DESC, mg.id_
     </select>
+    <select id="queryNormalGroupName" resultType="java.util.Map">
+        SELECT sr.user_id_ 'key',GROUP_CONCAT(mg.name_) 'value' FROM student_registration sr
+        LEFT JOIN music_group mg ON mg.id_ = sr.music_group_id_
+        WHERE mg.status_ = 'PROGRESS' AND sr.music_group_status_ = 'NORMAL'
+        AND sr.user_id_ IN
+        <foreach collection="studentIds" item="userId" open="(" close=")" separator=",">
+            #{userId}
+        </foreach>
+        GROUP BY sr.user_id_
+    </select>
 </mapper>

+ 45 - 0
mec-biz/src/main/resources/config/mybatis/StudentMapper.xml

@@ -1220,6 +1220,21 @@
     <select id="getValidVipStudentIds" resultType="java.lang.Integer">
         SELECT user_id_ FROM student WHERE member_rank_setting_id_ IS NOT NULl OR experience_member_rank_setting_id_ IS NOT NULL
     </select>
+    <select id="getStudentByHasCourse" resultType="java.lang.Integer">
+        SELECT s.user_id_ FROM student s WHERE s.teacher_id_ = #{teacherId} AND s.user_id_ IN (SELECT t.user_id_ FROM (
+        (SELECT sr.user_id_
+        FROM student_registration sr
+        LEFT JOIN music_group mg ON sr.music_group_id_=mg.id_
+        WHERE mg.status_='PROGRESS'
+        AND sr.music_group_status_='NORMAL')
+        UNION ALL
+        (SELECT
+        cssp.user_id_
+        FROM course_schedule_student_payment cssp
+        LEFT JOIN course_schedule cs ON cssp.course_schedule_id_=cs.id_
+        WHERE cssp.group_type_ IN ('VIP', 'PRACTICE')
+        AND cs.status_='NOT_START'))t)
+    </select>
 
     <update id="updateGrade"><![CDATA[
         UPDATE student SET current_grade_num_=current_grade_num_+1
@@ -1264,4 +1279,34 @@
     <update id="cleanStudentCloudStudySequenceDays">
         UPDATE student SET cloud_study_sequence_days_=0,cloud_study_use_last_day_=date_sub(curdate(), interval 1 day) WHERE cloud_study_use_last_day_&lt;date_sub(curdate(), interval 1 day)
     </update>
+    <update id="cleanCountFlag">
+        UPDATE student SET count_flag_ = 0 WHERE count_flag_ = 1
+    </update>
+    <update id="remarkCountFlag">
+        UPDATE student SET count_flag_ = 1 WHERE user_id_ IN (
+        SELECT * FROM (
+        SELECT DISTINCT user_id_
+        FROM ((SELECT sr.user_id_
+        FROM student_registration sr
+        LEFT JOIN music_group mg ON sr.music_group_id_=mg.id_
+        WHERE mg.status_='PROGRESS'
+        AND sr.music_group_status_='NORMAL')
+        UNION ALL
+        (SELECT
+        cssp.user_id_
+        FROM
+        course_schedule_student_payment cssp
+        LEFT JOIN course_schedule cs ON cssp.course_schedule_id_=cs.id_
+        WHERE
+        cssp.group_type_ IN ('VIP', 'PRACTICE')
+        AND cs.status_='NOT_START')) t
+        LEFT JOIN sys_user su ON t.user_id_=su.id_
+        WHERE su.del_flag_=0 AND t.user_id_ NOT IN (SELECT user_id_ FROM student WHERE subject_id_list_ REGEXP '21|25|26|27|28|29'))c)
+        <if test="studentIds != null and studentIds.size > 0">
+            AND user_id_ NOT IN
+            <foreach collection="studentIds" separator="," item="userId" open="(" close=")">
+                #{userId}
+            </foreach>
+        </if>
+    </update>
 </mapper>

+ 11 - 1
mec-biz/src/main/resources/config/mybatis/StudentPaymentOrderMapper.xml

@@ -370,7 +370,7 @@
                 <![CDATA[AND spo.balance_payment_amount_ <= #{lessBalancePaymentAmount}]]>
             </if>
             <if test="orderNo != null">
-                AND spo.order_no_ = #{orderNo}
+                AND (spo.id_ = #{orderNo} OR spo.order_no_ = #{orderNo})
             </if>
             <if test="merNos != null">
                 AND FIND_IN_SET(#{merNos},spo.mer_nos_)
@@ -996,4 +996,14 @@
         AND spo.type_ = 'APPLY' and spo.status_ = 'SUCCESS'
 		GROUP BY spo.music_group_id_
     </select>
+    <select id="findByUserAndActive" resultMap="StudentPaymentOrder">
+        SELECT spo.* FROM cloud_teacher_order cto
+        LEFT JOIN student_payment_order spo ON spo.id_ = cto.order_id_
+        WHERE spo.status_ IN ('SUCCESS','ING') AND cto.active_remark_ = #{activeRemark}
+        AND cto.remark_ = #{remark} AND cto.student_id_ = #{userId}
+        <if test="status != null and status != ''">
+            AND spo.status_ = #{status}
+        </if>
+        LIMIT 1
+    </select>
 </mapper>

+ 34 - 0
mec-biz/src/main/resources/config/mybatis/StudentRegistrationMapper.xml

@@ -1697,4 +1697,38 @@
       WHERE cs.`group_type_` = 'MUSIC' AND cs.`status_` = 'OVER' AND mg.`status_` = 'PROGRESS'
       GROUP BY cssp.`user_id_` HAVING COUNT(cs.`id_`) > 4) AND sr.user_id_ NOT IN (SELECT user_id_ FROM student WHERE subject_id_list_ REGEXP '21|25|26|27|28|29')
     </select>
+    <select id="queryHasMemberGroupStudent" resultType="java.lang.Integer">
+        SELECT DISTINCT sr.user_id_ FROM student_registration sr
+        LEFT JOIN music_group mg ON mg.id_ = sr.music_group_id_
+        WHERE sr.music_group_status_ != 'QUIT' AND mg.status_ NOT IN ('CANCELED','CLOSE') AND mg.course_view_type_ = 2
+    </select>
+    <resultMap id="CloudTeacherActiveTargetJsonDto" type="com.ym.mec.biz.dal.dto.CloudTeacherActiveTargetJsonDto">
+        <result property="targetNum" column="target_num_"/>
+        <result property="targetAmount" column="target_amount_"/>
+        <result property="organId" column="organ_id_"/>
+    </resultMap>
+    <select id="queryOrganTarget" resultMap="CloudTeacherActiveTargetJsonDto">
+        SELECT su.organ_id_,COUNT(DISTINCT su.id_) target_num_,COUNT(DISTINCT su.id_) * 2040 target_amount_ FROM student_registration sr
+        LEFT JOIN sys_user su  ON sr.user_id_ = su.id_
+        LEFT JOIN music_group mg ON mg.id_ = sr.music_group_id_
+        -- 新用户
+        WHERE su.id_ NOT IN (SELECT DISTINCT(cssp.`user_id_`)  FROM `course_schedule_student_payment` cssp
+        LEFT JOIN course_schedule cs on cssp.`course_schedule_id_` = cs.`id_`
+        LEFT JOIN `music_group` mg on mg.`id_` = cssp.`music_group_id_`
+        WHERE cs.`group_type_` = 'MUSIC' AND cs.`status_` = 'OVER' AND mg.`status_` = 'PROGRESS'
+        GROUP BY cssp.`user_id_` HAVING COUNT(cs.`id_`) &lt;= 4)
+        -- 			非管乐
+        AND su.id_ NOT IN (SELECT user_id_ FROM student WHERE subject_id_list_ REGEXP '21|25|26|27|28|29')
+        -- 			声部排除
+        AND su.organ_id_ NOT IN (36,38,39,41,42,43,44,45,46,47,48,49,50,52,54,55,56,63)
+        -- 			购买了云教练
+        AND su.id_ NOT IN (SELECT DISTINCT student_id_ FROM cloud_teacher_order WHERE active_remark_ IS NULL AND status_ != 0)
+        -- 			未退团,不是会员团
+        AND su.id_ NOT IN (SELECT DISTINCT sr.user_id_ FROM student_registration sr
+        LEFT JOIN music_group mg ON mg.id_ = sr.music_group_id_
+        WHERE sr.music_group_status_ != 'QUIT' AND mg.course_view_type_ = 2)
+
+        AND sr.music_group_status_ = 'NORMAL' AND mg.course_view_type_ != 2 AND mg.`status_` = 'PROGRESS'
+        GROUP BY su.organ_id_
+    </select>
 </mapper>

+ 6 - 0
mec-biz/src/main/resources/config/mybatis/StudentVisitMapper.xml

@@ -195,4 +195,10 @@
         <![CDATA[ AND visit_time_ <= #{endTime} ]]>
         GROUP BY teacher_id_,date_format(visit_time_, '%Y-%m')
     </select>
+    <select id="queryRecordVisitStudentIds" resultType="java.lang.Integer">
+        SELECT DISTINCT st.user_id_ FROM student st
+        LEFT JOIN student_visit sv ON st.user_id_ = sv.student_id_
+        WHERE sv.type_ = '云教练' AND st.teacher_id_ = #{teacherId}
+        AND sv.visit_time_ BETWEEN DATE_FORMAT(#{addDays1}, '%Y%m%d') AND DATE_FORMAT(#{addDays3}, '%Y%m%d')
+    </select>
 </mapper>

+ 216 - 0
mec-biz/src/main/resources/config/mybatis/SysCouponCodeMapper.xml

@@ -0,0 +1,216 @@
+<?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.ym.mec.biz.dal.dao.SysCouponCodeDao">
+
+	<resultMap type="com.ym.mec.biz.dal.entity.SysCouponCode" id="SysCouponCode">
+		<result column="id_" property="id" />
+		<result column="coupon_id_" property="couponId" />
+		<result column="code_" property="code" />
+		<result column="usage_status_" property="usageStatus" />
+		<result column="user_id_" property="userId" />
+		<result column="used_time_" property="usedTime" />
+		<result column="use_start_date_" property="useStartDate" />
+		<result column="use_deadline_date_" property="useDeadlineDate" />
+		<result column="payment_order_id_" property="paymentOrderId" />
+		<result column="create_time_" property="createTime" />
+		<result column="update_time_" property="updateTime" />
+	</resultMap>
+
+	<resultMap id="SysCouponCodeDto" type="com.ym.mec.biz.dal.dto.SysCouponCodeDto">
+		<result column="organ_id_" property="organId"/>
+		<result column="organ_name_" property="organName"/>
+		<result column="user_id_" property="userId"/>
+		<result column="username_" property="userName"/>
+		<result column="phone_" property="phone"/>
+		<result column="coupon_id_" property="couponId"/>
+		<result column="coupon_type_" property="couponType" typeHandler="com.ym.mec.common.dal.CustomEnumTypeHandler"/>
+		<result column="coupon_name_" property="couponName"/>
+		<result column="coupon_description_" property="couponDescription"/>
+		<result column="code_" property="code"/>
+		<result column="face_value_" property="faceValue" />
+		<result column="full_amount_" property="fullAmount" />
+		<result column="payment_order_id_" property="paymentOrderId"/>
+		<result column="usage_status_" property="usageStatus"/>
+		<result column="used_time_" property="usedTime"/>
+		<result column="use_start_date_" property="useStartDate"/>
+		<result column="use_deadline_date_" property="useDeadlineDate"/>
+	</resultMap>
+
+	<!-- 根据主键查询一条记录 -->
+	<select id="get" resultMap="SysCouponCode" >
+		SELECT * FROM sys_coupon_code WHERE id_ = #{id}
+	</select>
+
+	<!-- 全查询 -->
+	<select id="findAll" resultMap="SysCouponCode">
+		SELECT * FROM sys_coupon_code ORDER BY id_
+	</select>
+
+	<!-- 向数据库增加一条记录 -->
+	<insert id="insert" parameterType="com.ym.mec.biz.dal.entity.SysCouponCode" useGeneratedKeys="true" keyColumn="id" keyProperty="id">
+		<!--
+		<selectKey resultClass="int" keyProperty="id" > 
+		SELECT SEQ_WSDEFINITION_ID.nextval AS ID FROM DUAL 
+		</selectKey>
+		-->
+		INSERT INTO sys_coupon_code (coupon_id_,code_,usage_status_,user_id_,used_time_,use_start_date_,use_deadline_date_,
+		                             payment_order_id_,create_time_,update_time_)
+							 VALUES(#{couponId},#{code},#{usageStatus},#{userId},#{usedTime},#{useStartDate},#{useDeadlineDate},
+									#{paymentOrderId},NOW(),NOW())
+	</insert>
+
+	<insert id="batchInsert" parameterType="com.ym.mec.biz.dal.entity.SysCouponCode" useGeneratedKeys="true" keyColumn="id" keyProperty="id">
+		INSERT INTO sys_coupon_code (coupon_id_,code_,usage_status_,user_id_,used_time_,use_start_date_,use_deadline_date_,
+		payment_order_id_,create_time_,update_time_)
+		VALUE
+		<foreach collection="couponCodes" item="couponCode" separator=",">
+			(#{couponCode.couponId},#{couponCode.code},#{couponCode.usageStatus},#{couponCode.userId},#{couponCode.usedTime},#{couponCode.useStartDate},#{couponCode.useDeadlineDate},
+			#{couponCode.paymentOrderId},NOW(),NOW())
+		</foreach>
+	</insert>
+
+	<!-- 根据主键查询一条记录 -->
+	<update id="update" parameterType="com.ym.mec.biz.dal.entity.SysCouponCode">
+		UPDATE sys_coupon_code
+		<set>
+			<if test="couponId != null">
+				coupon_id_ = #{couponId},
+			</if>
+			<if test="usageStatus != null">
+				usage_status_ = #{usageStatus},
+			</if>
+			<if test="useStartDate != null">
+				use_start_date_ = #{useStartDate},
+			</if>
+			<if test="userId != null">
+				user_id_ = #{userId},
+			</if>
+			<if test="code != null">
+				code_ = #{code},
+			</if>
+			<if test="updateTime != null">
+				update_time_ = #{updateTime},
+			</if>
+			<if test="paymentOrderId != null">
+				payment_order_id_ = #{paymentOrderId},
+			</if>
+			<if test="useDeadlineDate != null">
+				use_deadline_date_ = #{useDeadlineDate},
+			</if>
+				used_time_ = NOW()
+		</set>
+		WHERE id_ = #{id}
+	</update>
+
+	<!-- 根据主键删除一条记录 -->
+	<delete id="delete" >
+		DELETE FROM sys_coupon_code WHERE id_ = #{id}
+	</delete>
+
+	<!-- 分页查询 -->
+	<select id="queryPage" resultMap="SysCouponCode" parameterType="map">
+		SELECT * FROM sys_coupon_code ORDER BY id_ <include refid="global.limit"/>
+	</select>
+
+	<!-- 查询当前表的总记录数 -->
+	<select id="queryCount" resultType="int">
+		SELECT COUNT(*) FROM sys_coupon_code
+	</select>
+
+	<select id="countWithUserAndCoupon" resultType="int">
+		SELECT COUNT(id_) FROM sys_coupon_code WHERE user_id_=#{userId} AND coupon_id_=#{couponId}
+	</select>
+
+	<sql id="querySysCouponUseListCondition">
+		<where>
+			<if test="userId!=null">
+				AND scc.user_id_=#{userId}
+			</if>
+			<if test="couponName!=null and couponName!=''">
+				AND sc.name_ LIKE CONCAT('%', #{couponName}, '%')
+			</if>
+			<if test="paymentOrderId!=null">
+				AND scc.payment_order_id_=#{paymentOrderId}
+			</if>
+			<if test="usageStatus!=null">
+				<if test="usageStatus == 0">
+					AND scc.usage_status_=0
+					AND scc.use_deadline_date_ &gt;= NOW()
+				</if>
+				<if test="usageStatus == 1">
+					AND scc.usage_status_=1
+				</if>
+				<if test="usageStatus == 2">
+					AND scc.usage_status_=0
+					AND scc.use_deadline_date_ &lt; NOW()
+				</if>
+			</if>
+			<if test="organId!=null">
+				AND su.organ_id_=#{organId}
+			</if>
+			<if test="search!=null and search!=''">
+				AND (scc.user_id_=#{search} OR su.phone_=#{search} OR su.username_ LIKE CONCAT('%', #{search}, '%'))
+			</if>
+		</where>
+	</sql>
+
+	<select id="querySysCouponUseList" resultMap="SysCouponCodeDto">
+		SELECT
+			organ.name_ organ_name_,
+		    scc.user_id_,
+			su.username_,
+			su.phone_,
+			scc.coupon_id_,
+			sc.type_ coupon_type_,
+			sc.name_ coupon_name_,
+		    sc.face_value_,
+		    sc.full_amount_,
+			sc.description_ coupon_description_,
+			scc.code_,
+			scc.payment_order_id_,
+			scc.use_start_date_,
+			scc.use_deadline_date_,
+			scc.used_time_,
+		    IF(scc.usage_status_ = 0 AND scc.use_deadline_date_ &lt; NOW(),2,scc.usage_status_) usage_status_
+		FROM sys_coupon_code scc
+			 LEFT JOIN sys_coupon sc ON scc.coupon_id_=sc.id_
+			 LEFT JOIN sys_user su ON scc.user_id_=su.id_
+			 LEFT JOIN organization organ ON su.organ_id_=organ.id_
+		<include refid="querySysCouponUseListCondition"></include>
+		ORDER BY scc.id_ DESC
+		<include refid="global.limit"></include>
+	</select>
+
+	<select id="countSysCouponUseList" resultType="java.lang.Integer">
+		SELECT
+			COUNT(scc.id_)
+		FROM sys_coupon_code scc
+			LEFT JOIN sys_coupon sc ON scc.coupon_id_=sc.id_
+			LEFT JOIN sys_user su ON scc.user_id_=su.id_
+			LEFT JOIN organization organ ON su.organ_id_=organ.id_
+		<include refid="querySysCouponUseListCondition"></include>
+	</select>
+	<resultMap id="HorseRaceLampDto" type="com.ym.mec.biz.dal.dto.HorseRaceLampDto">
+		<result property="username" column="username_"/>
+		<result property="num" column="num_"/>
+		<result property="faceValue" column="face_value_"/>
+	</resultMap>
+	<select id="queryHorseRaceLampDtoList" resultMap="HorseRaceLampDto">
+		SELECT COUNT(suc.coupon_id_) num_,sc.face_value_,su.username_ FROM sys_coupon_code suc
+		LEFT JOIN sys_user su ON su.id_ = suc.user_id_
+		LEFT JOIN sys_coupon sc ON sc.id_ = suc.coupon_id_
+		GROUP BY suc.user_id_,suc.payment_order_id_,suc.coupon_id_
+		<include refid="global.limit"/>
+	</select>
+	<select id="countHorseRaceLampDtoList" resultType="java.lang.Integer">
+		SELECT COUNT(t.num_) FROM (
+		SELECT COUNT(suc.coupon_id_) num_,sc.face_value_,su.username_ FROM sys_coupon_code suc
+		LEFT JOIN sys_user su ON su.id_ = suc.user_id_
+		LEFT JOIN sys_coupon sc ON sc.id_ = suc.coupon_id_
+		GROUP BY suc.user_id_,suc.payment_order_id_,suc.coupon_id_)t
+	</select>
+</mapper>

+ 153 - 0
mec-biz/src/main/resources/config/mybatis/SysCouponMapper.xml

@@ -0,0 +1,153 @@
+<?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.ym.mec.biz.dal.dao.SysCouponDao">
+
+	<resultMap type="com.ym.mec.biz.dal.entity.SysCoupon" id="SysCoupon">
+		<result column="id_" property="id" />
+		<result column="name_" property="name" />
+		<result column="description_" property="description" />
+		<result column="status_" property="status" />
+		<result column="type_" property="type" typeHandler="com.ym.mec.common.dal.CustomEnumTypeHandler"/>
+		<result column="face_value_" property="faceValue" />
+		<result column="full_amount_" property="fullAmount" />
+		<result column="limit_exchange_num_" property="limitExchangeNum" />
+		<result column="effective_type_" property="effectiveType" typeHandler="com.ym.mec.common.dal.CustomEnumTypeHandler"/>
+		<result column="deadline_" property="deadline" />
+		<result column="effective_start_time_" property="effectiveStartTime" />
+		<result column="effective_expire_time_" property="effectiveExpireTime" />
+		<result column="end_date_" property="endDate" />
+		<result column="start_date_" property="startDate" />
+		<result column="stock_count_" property="stockCount" />
+		<result column="consume_num_" property="consumeNum" />
+		<result column="warning_stock_num_" property="warningStockNum" />
+		<result column="warning_status_" property="warningStatus" />
+		<result column="create_time_" property="createTime" />
+		<result column="update_time_" property="updateTime" />
+	</resultMap>
+
+	<!-- 根据主键查询一条记录 -->
+	<select id="get" resultMap="SysCoupon" >
+		SELECT * FROM sys_coupon WHERE id_ = #{id}
+	</select>
+
+	<!-- 全查询 -->
+	<select id="findAll" resultMap="SysCoupon">
+		SELECT * FROM sys_coupon ORDER BY id_
+	</select>
+
+	<!-- 向数据库增加一条记录 -->
+	<insert id="insert" parameterType="com.ym.mec.biz.dal.entity.SysCoupon" useGeneratedKeys="true" keyColumn="id" keyProperty="id">
+		INSERT INTO sys_coupon (id_,name_,description_,status_,type_,face_value_,full_amount_,limit_exchange_num_,effective_type_,deadline_,
+		                        effective_start_time_, effective_expire_time_,end_date_,start_date_,stock_count_,consume_num_,warning_stock_num_,
+		                        create_time_,update_time_)
+		                        VALUES(#{id},#{name},#{description},#{status},#{type, typeHandler=com.ym.mec.common.dal.CustomEnumTypeHandler},#{faceValue},#{fullAmount},#{limitExchangeNum},
+		                               #{effectiveType, typeHandler=com.ym.mec.common.dal.CustomEnumTypeHandler},#{deadline},
+		                               #{effectiveStartTime},#{effectiveExpireTime},#{endDate},#{startDate},#{stockCount},#{consumeNum},#{warningStockNum},
+		                               NOW(), NOW())
+	</insert>
+
+	<!-- 根据主键查询一条记录 -->
+	<update id="update" parameterType="com.ym.mec.biz.dal.entity.SysCoupon">
+		UPDATE sys_coupon
+		<set>
+			<if test="status != null">
+				status_ = #{status},
+			</if>
+			<if test="effectiveExpireTime != null">
+				effective_expire_time_ = #{effectiveExpireTime},
+			</if>
+			<if test="startDate != null">
+				start_date_ = #{startDate},
+			</if>
+			<if test="faceValue != null">
+				face_value_ = #{faceValue},
+			</if>
+			<if test="name != null">
+				name_ = #{name},
+			</if>
+			<if test="fullAmount != null">
+				full_amount_ = #{fullAmount},
+			</if>
+			<if test="effectiveType != null">
+				effective_type_ = #{effectiveType, typeHandler=com.ym.mec.common.dal.CustomEnumTypeHandler},
+			</if>
+			<if test="deadline != null">
+				deadline_ = #{deadline},
+			</if>
+			<if test="stockCount != null">
+				stock_count_ = #{stockCount},
+			</if>
+			<if test="endDate != null">
+				end_date_ = #{endDate},
+			</if>
+			<if test="description != null">
+				description_ = #{description},
+			</if>
+			<if test="effectiveStartTime != null">
+				effective_start_time_ = #{effectiveStartTime},
+			</if>
+			<if test="consumeNum != null">
+				consume_num_ = #{consumeNum},
+			</if>
+			<if test="type != null">
+				type_ = #{type, typeHandler=com.ym.mec.common.dal.CustomEnumTypeHandler},
+			</if>
+			<if test="limitExchangeNum != null">
+				limit_exchange_num_ = #{limitExchangeNum},
+			</if>
+			<if test="warningStockNum != null">
+				warning_stock_num_ = #{warningStockNum},
+			</if>
+			<if test="warningStatus != null">
+				warning_status_ = #{warningStatus},
+			</if>
+				update_time_ = NOW()
+		</set>
+		WHERE id_ = #{id}
+	</update>
+
+	<!-- 根据主键删除一条记录 -->
+	<delete id="delete" >
+		DELETE FROM sys_coupon WHERE id_ = #{id}
+	</delete>
+
+	<sql id="queryCondition">
+		<where>
+			<if test="status != null">
+				AND status_ = #{status}
+			</if>
+			<if test="type != null">
+				AND type_ = #{type, typeHandler=com.ym.mec.common.dal.CustomEnumTypeHandler}
+			</if>
+			<if test="search != null and search != ''">
+				AND (id_=#{search} OR name_ LIKE CONCAT('%', #{search}, '%'))
+			</if>
+		</where>
+	</sql>
+
+	<!-- 分页查询 -->
+	<select id="queryPage" resultMap="SysCoupon" parameterType="map">
+		SELECT * FROM sys_coupon
+		<include refid="queryCondition"></include>
+		ORDER BY id_ DESC
+		<include refid="global.limit"/>
+	</select>
+
+	<!-- 查询当前表的总记录数 -->
+	<select id="queryCount" resultType="int">
+		SELECT COUNT(*) FROM sys_coupon
+		<include refid="queryCondition"></include>
+	</select>
+
+	<select id="lockCoupon" resultMap="SysCoupon">
+		SELECT * FROM sys_coupon WHERE id_ = #{id} FOR UPDATE
+	</select>
+
+	<select id="getWithName" resultMap="SysCoupon">
+		SELECT * FROM sys_coupon WHERE name_ = #{name}
+	</select>
+</mapper>

+ 27 - 27
mec-biz/src/main/resources/config/mybatis/SysMusicCompareRecordMapper.xml

@@ -41,11 +41,6 @@
 
 	<!-- 向数据库增加一条记录 -->
 	<insert id="insert" parameterType="com.ym.mec.biz.dal.entity.SysMusicCompareRecord" useGeneratedKeys="true" keyColumn="id" keyProperty="id">
-		<!--
-		<selectKey resultClass="int" keyProperty="id" > 
-		SELECT SEQ_WSDEFINITION_ID.nextval AS ID FROM DUAL 
-		</selectKey>
-		-->
 		INSERT INTO sys_music_compare_record (id_,user_id_,sys_music_score_id_,heard_level_,behavior_id_,score_data_,score_,intonation_,cadence_,integrity_,
 		                                      record_file_path_,video_file_path_,device_type_,client_id_,play_time_,monday_,
 											feature_,create_time_,update_time_)
@@ -264,23 +259,6 @@
 		GROUP BY
 			user_id_
 	</select>
-    <select id="countStudentTrain" resultType="java.lang.Integer">
-		SELECT COUNT(DISTINCT s.user_id_)
-		FROM teacher t
-				 LEFT JOIN student s ON t.id_ = s.teacher_id_
-				 LEFT JOIN sys_user su ON su.id_ = s.user_id_
-				 LEFT JOIN sys_music_compare_record mcr ON mcr.user_id_ = s.user_id_
-		<if test="startTime != null and startTime != ''">
-			AND (DATE_FORMAT(mcr.create_time_, '%Y-%m-%d') >= #{startTime} OR mcr.id_ IS NULL)
-		</if>
-		<if test="endTime != null and endTime != ''">
-			AND (DATE_FORMAT(mcr.create_time_, '%Y-%m-%d') &lt;= #{endTime} OR mcr.id_ IS NULL)
-		</if>
-		WHERE s.teacher_id_ = #{teacherId}
-		<if test="search != null and search != ''">
-			AND (su.phone_ LIKE CONCAT('%',#{search},'%') OR su.username_ LIKE CONCAT('%',#{search},'%'))
-		</if>
-	</select>
 	<resultMap id="CountStudentTrainDataDto" type="com.ym.mec.biz.dal.dto.CountStudentTrainDataDto">
 		<result property="trainNum" column="train_num_"/>
 		<result property="recordNum" column="record_num_"/>
@@ -290,17 +268,14 @@
 		<result property="phone" column="phone_"/>
 		<result property="totalPlayTime" column="total_play_time_"/>
 		<result property="trainDay" column="train_day_"/>
-		<result property="musicGroupName" column="music_group_name_"/>
 	</resultMap>
 	<select id="queryStudentTrain" resultMap="CountStudentTrainDataDto">
 		SELECT s.user_id_,su.avatar_,su.phone_,su.username_,ROUND(SUM(mcr.play_time_) / 60) total_play_time_,
 			   COUNT(DISTINCT DATE_FORMAT(mcr.create_time_,"%Y-%m-%d")) train_day_,
 			   COUNT(DISTINCT mcr.behavior_id_) train_num_,
-		COUNT(CASE WHEN mcr.feature_ = 'CLOUD_STUDY_EVALUATION' THEN mcr.behavior_id_ ELSE NULL END) record_num_,GROUP_CONCAT(DISTINCT mg.name_) music_group_name_
+		COUNT(CASE WHEN mcr.feature_ = 'CLOUD_STUDY_EVALUATION' THEN mcr.behavior_id_ ELSE NULL END) record_num_
 		FROM teacher t
 				 LEFT JOIN student s ON t.id_ = s.teacher_id_
-				 LEFT JOIN student_registration sr ON sr.user_id_ = s.user_id_ AND sr.music_group_status_ = 'NORMAL'
-				 LEFT JOIN music_group mg ON mg.id_ = sr.music_group_id_ AND mg.status_ = 'PROGRESS'
 				 LEFT JOIN sys_user su ON su.id_ = s.user_id_
 				 LEFT JOIN sys_music_compare_record mcr ON mcr.user_id_ = s.user_id_
 		<if test="startTime != null and startTime != ''">
@@ -313,8 +288,33 @@
 		<if test="search != null and search != ''">
 			AND (su.phone_ LIKE CONCAT('%',#{search},'%') OR su.username_ LIKE CONCAT('%',#{search},'%'))
 		</if>
+		<if test="visitStudents != null and visitStudents.size > 0">
+			AND s.user_id_ NOT IN
+			<foreach collection="visitStudents" open="(" close=")" item="userId" separator=",">
+				#{userId}
+			</foreach>
+		</if>
+		<if test="hasCourseUserIds != null and hasCourseUserIds.size > 0">
+			AND s.user_id_ IN
+			<foreach collection="hasCourseUserIds" open="(" close=")" item="userId" separator=",">
+				#{userId}
+			</foreach>
+		</if>
 		GROUP BY s.user_id_
-		ORDER BY total_play_time_ DESC
+		<if test="having == 1">
+			HAVING total_play_time_ &lt; ${totalTime} OR train_num_ &lt; ${trainNum}
+		</if>
+		ORDER BY
+		<if test="sort != null and sort != ''">
+			${sort}
+			<if test="order != null and order != ''">
+				${order}
+			</if>
+		</if>
+		<if test="sort == null or sort == ''">
+			total_play_time_ DESC
+		</if>
+		,s.user_id_
 		<include refid="global.limit"/>
 	</select>
 

+ 6 - 0
mec-client-api/src/main/java/com/ym/mec/task/TaskRemoteService.java

@@ -223,4 +223,10 @@ public interface TaskRemoteService {
 	/** 本周学员训练提醒 */
 	@GetMapping("task/curWeekStudentTrainRemind")
 	void curWeekStudentTrainRemind();
+
+	/**
+	 * 标记进行中乐团在读学员+VIP、网管有课学员(除弦乐声部、去重)
+	 */
+	@GetMapping("task/remarkCountFlag")
+    void remarkCountFlag();
 }

+ 5 - 0
mec-client-api/src/main/java/com/ym/mec/task/fallback/TaskRemoteServiceFallback.java

@@ -277,4 +277,9 @@ public class TaskRemoteServiceFallback implements TaskRemoteService {
 	public void curWeekStudentTrainRemind() {
 		logger.error("本周学员训练提醒失败");
 	}
+
+    @Override
+    public void remarkCountFlag() {
+        logger.error("标记进行中乐团在读学员+VIP、网管有课学员总数 失败");
+    }
 }

+ 2 - 2
mec-common/common-core/src/main/java/com/ym/mec/common/page/QueryInfo.java

@@ -22,11 +22,11 @@ public class QueryInfo {
 	/**
 	 * 默认排序列
 	 */
-	private String sort = "create_time_";
+	private String sort;
 	/**
 	 * 默认排序方向
 	 */
-	private String order = "desc";
+	private String order = "DESC";
 	
 	private String search;
 	

+ 3 - 2
mec-student/src/main/java/com/ym/mec/student/controller/ContractsController.java

@@ -5,6 +5,7 @@ import java.util.*;
 import java.util.stream.Collectors;
 
 import com.ym.mec.biz.dal.entity.SysUserContracts;
+import com.ym.mec.biz.dal.enums.CourseViewTypeEnum;
 import com.ym.mec.biz.service.SysUserContractsService;
 import com.ym.mec.common.entity.HttpResponseResult;
 import io.swagger.annotations.Api;
@@ -89,7 +90,7 @@ public class ContractsController extends BaseController {
 
 	@ApiOperation("查询产品协议")
 	@GetMapping(value = "queryProduceContract")
-	public Object queryProduceContract(Integer userId, String musicGroupId) {
+	public Object queryProduceContract(Integer userId, String musicGroupId, CourseViewTypeEnum courseViewType) {
 		if(Objects.isNull(userId)){
 			SysUser sysUser = sysUserFeignService.queryUserInfo();
 			if (sysUser == null) {
@@ -97,7 +98,7 @@ public class ContractsController extends BaseController {
 			}
 			userId = sysUser.getId();
 		}
-		return succeed(contractService.queryProductContract(userId,musicGroupId));
+		return succeed(contractService.queryProductContract(userId,musicGroupId, courseViewType));
 	}
 
 	@ApiOperation(value = "生成学生课程协议")

+ 58 - 15
mec-student/src/main/java/com/ym/mec/student/controller/MemberRankController.java

@@ -1,11 +1,18 @@
 package com.ym.mec.student.controller;
 
+import com.ym.mec.auth.api.client.SysUserFeignService;
+import com.ym.mec.auth.api.entity.SysUser;
+import com.ym.mec.biz.dal.dao.SysConfigDao;
+import com.ym.mec.biz.dal.entity.MemberRankSetting;
+import com.ym.mec.biz.dal.enums.PeriodEnum;
+import com.ym.mec.biz.dal.page.CloudTeacherOrderQueryInfo;
+import com.ym.mec.biz.service.*;
+import com.ym.mec.common.controller.BaseController;
+import com.ym.mec.common.entity.HttpResponseResult;
+import com.ym.mec.common.exception.BizException;
+import com.ym.mec.util.date.DateUtil;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
-
-import java.math.BigDecimal;
-import java.util.List;
-
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.http.HttpStatus;
 import org.springframework.web.bind.annotation.GetMapping;
@@ -13,16 +20,9 @@ import org.springframework.web.bind.annotation.PostMapping;
 import org.springframework.web.bind.annotation.RequestMapping;
 import org.springframework.web.bind.annotation.RestController;
 
-import com.ym.mec.auth.api.client.SysUserFeignService;
-import com.ym.mec.auth.api.entity.SysUser;
-import com.ym.mec.biz.dal.entity.MemberRankSetting;
-import com.ym.mec.biz.dal.enums.PeriodEnum;
-import com.ym.mec.biz.dal.page.CloudTeacherOrderQueryInfo;
-import com.ym.mec.biz.service.CloudTeacherOrderService;
-import com.ym.mec.biz.service.MemberFeeSettingService;
-import com.ym.mec.biz.service.MemberRankPrivilegesService;
-import com.ym.mec.biz.service.MemberRankSettingService;
-import com.ym.mec.common.controller.BaseController;
+import java.math.BigDecimal;
+import java.util.Date;
+import java.util.List;
 
 @RequestMapping("memberRank")
 @Api(tags = "会员收费设置服务")
@@ -44,6 +44,9 @@ public class MemberRankController extends BaseController {
 	@Autowired
 	private SysUserFeignService sysUserFeignService;
 
+	@Autowired
+	private SysConfigDao sysConfigDao;
+
 	@ApiOperation(value = "获取所有的收费标准")
 	@GetMapping("/queryList")
 	public Object getMemberDefaultFee() {
@@ -68,8 +71,38 @@ public class MemberRankController extends BaseController {
 		if (sysUser == null) {
 			return failed(HttpStatus.FORBIDDEN, "请登录");
 		}
+		return succeed(memberRankSettingService.buy(sysUser.getId(), memberRankId, periodEnum, amount, isUseBalance,1,0,null,null));
+	}
 
-		return succeed(memberRankSettingService.buy(sysUser.getId(), memberRankId, periodEnum, amount, isUseBalance));
+	@ApiOperation(value = "2021-09活动购买会员")
+	@PostMapping("/activeBuy")
+	public HttpResponseResult ActiveBuy(Integer memberRankId, Integer buyNum, BigDecimal amount, boolean isUseBalance, boolean repay) throws Exception {
+		Date nowTime = new Date();
+		String startTimeStr = sysConfigDao.findConfigValue("cloud_teacher_active_start_time");
+		Date startTime = DateUtil.stringToDate(startTimeStr);
+		if (startTime.compareTo(nowTime) > 0) {
+			throw new BizException("活动还未开始,谢谢关注");
+		}
+		String endTimeStr = sysConfigDao.findConfigValue("cloud_teacher_active_end_time");
+		Date endTime = DateUtil.stringToDate(endTimeStr);
+		if (endTime.compareTo(nowTime) <= 0) {
+			throw new BizException("活动已结束,谢谢关注");
+		}
+		SysUser sysUser = sysUserFeignService.queryUserInfo();
+		if (sysUser == null) {
+			return failed(HttpStatus.FORBIDDEN, "请登录");
+		}
+		//买2赠1、买3赠2
+		int giveNum = buyNum == 2?1:buyNum == 3?2:0;
+		String remark = buyNum == 2?"2赠1":buyNum == 3?"3赠2":buyNum == 1?"单月":"其他";
+		return memberRankSettingService.ActiveBuy(sysUser.getId(),
+				memberRankId,
+				PeriodEnum.MONTH,
+				amount,
+				isUseBalance,
+				buyNum,
+				giveNum,
+				202109,remark,repay);
 	}
 	
     @ApiOperation(value = "查询订单列表")
@@ -83,4 +116,14 @@ public class MemberRankController extends BaseController {
         return succeed(cloudTeacherOrderService.queryPage(queryInfo));
     }
 
+    @ApiOperation(value = "获取学员购买的云教练活动订单")
+    @GetMapping("/queryActiveOrderPage")
+    public Object queryActiveOrderPage() {
+    	SysUser user = sysUserFeignService.queryUserInfo();
+		if (user == null) {
+			return failed(HttpStatus.FORBIDDEN, "请登录");
+		}
+        return succeed(cloudTeacherOrderService.queryActiveOrderPage(user.getId(),202109,null));
+    }
+
 }

+ 1 - 3
mec-student/src/main/java/com/ym/mec/student/controller/MusicGroupController.java

@@ -270,8 +270,6 @@ public class MusicGroupController extends BaseController {
         }
         if (calenderDetail.getPaymentStatus() == PaymentStatus.PAID_COMPLETED) {
             throw new BizException("您已缴费,请勿重复提交");
-        } else if (calenderDetail.getPaymentStatus() == PaymentStatus.PROCESSING) {
-            throw new BizException("存在待处理的订单,请稍候尝试");
         }
         //缴费项目已开启或者单独开启
         Map renew;
@@ -380,7 +378,7 @@ public class MusicGroupController extends BaseController {
         if (err != null) {
             return failed(err + "不可缴费,请联系教务老师");
         }
-        Integer userId = studentRegistration.getUserId();
+//        Integer userId = studentRegistration.getUserId();
         /*StudentPaymentOrder ApplyOrder = studentPaymentOrderService.findMusicGroupApplyOrderByStatus(userId, studentRegistration.getMusicGroupId(), DealStatusEnum.SUCCESS);
         if (ApplyOrder != null) {
             return failed("您已支付成功,请勿重复支付");

+ 0 - 2
mec-student/src/main/java/com/ym/mec/student/controller/MusicGroupPaymentCalenderController.java

@@ -69,8 +69,6 @@ public class MusicGroupPaymentCalenderController extends BaseController {
         }
         if(calenderDetail.getPaymentStatus() == PaymentStatus.PAID_COMPLETED){
             throw new BizException("您已缴费,请勿重复提交");
-        }else if(calenderDetail.getPaymentStatus() == PaymentStatus.PROCESSING){
-            throw new BizException("存在待处理的订单,请稍候尝试");
         }
         if(calender.getStatus() == PaymentCalenderStatusEnum.OPEN || calenderDetail.getOpen() == 1){
             StudentRegistration studentRegistration = studentRegistrationService.queryByUserIdAndMusicGroupId(userId,musicGroupId);

+ 9 - 4
mec-student/src/main/java/com/ym/mec/student/controller/StudentOrderController.java

@@ -132,10 +132,9 @@ public class StudentOrderController extends BaseController {
     @Autowired
     private CloudTeacherOrderService cloudTeacherOrderService;
     @Autowired
-    private StudentRegistrationDao studentRegistrationDao;
-
+    private SysCouponCodeDao sysCouponCodeDao;
     @Autowired
-    private MemberRankPrivilegesService memberRankPrivilegesService;
+    private StudentRegistrationDao studentRegistrationDao;
 
     @Autowired
     private SellOrderService sellOrderService;
@@ -259,7 +258,13 @@ public class StudentOrderController extends BaseController {
         } else if (orderByOrderNo.getGroupType().equals(GroupType.DEGREE)) {
             orderDetail.put("detail", childrenDayDegreeDetailDao.getByOrderId(orderByOrderNo.getId()));
         } else if (orderByOrderNo.getGroupType().equals(GroupType.MEMBER)) {
-            orderDetail.put("detail", cloudTeacherOrderService.queryOrderInfoByOrderId(orderByOrderNo.getId()));
+            CloudTeacherOrderDto orderDto = cloudTeacherOrderService.queryOrderInfoByOrderId(orderByOrderNo.getId());
+            orderDetail.put("detail",orderDto);
+            if(orderDto != null){
+                Map<String,Object> map = new HashMap<>(1);
+                map.put("paymentOrderId",orderDto.getCloudTeacherOrder().getOrderId());
+                orderDetail.put("couponList",sysCouponCodeDao.querySysCouponUseList(map));
+            }
         }
         return succeed(orderDetail);
     }

+ 54 - 0
mec-student/src/main/java/com/ym/mec/student/controller/SysCouponCodeController.java

@@ -0,0 +1,54 @@
+package com.ym.mec.student.controller;
+
+import com.ym.mec.auth.api.client.SysUserFeignService;
+import com.ym.mec.auth.api.entity.SysUser;
+import com.ym.mec.biz.dal.page.SysCouponCodeQueryInfo;
+import com.ym.mec.biz.service.SysCouponCodeService;
+import com.ym.mec.common.controller.BaseController;
+import com.ym.mec.common.entity.HttpResponseResult;
+import com.ym.mec.common.page.QueryInfo;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+@RequestMapping("sysCouponCode")
+@Api(tags = "优惠券明细")
+@RestController
+public class SysCouponCodeController extends BaseController {
+
+	@Autowired
+	private SysCouponCodeService sysCouponCodeService;
+	@Autowired
+	private SysUserFeignService sysUserFeignService;
+
+	@ApiOperation("分页查询")
+	@RequestMapping(value = "queryPage")
+	public HttpResponseResult queryPage(SysCouponCodeQueryInfo queryInfo) {
+		SysUser sysUser = sysUserFeignService.queryUserInfo();
+		if (sysUser == null) {
+			return failed("请登录");
+		}
+		queryInfo.setUserId(sysUser.getId());
+		return succeed(sysCouponCodeService.querySysCouponUseList(queryInfo));
+	}
+
+	@ApiOperation("获取云教练活动跑马灯")
+	@RequestMapping(value = "queryPageAll")
+	public HttpResponseResult queryPageAll(QueryInfo queryInfo) {
+		return succeed(sysCouponCodeService.queryHorseRaceLampDtoList(queryInfo));
+	}
+
+	@ApiOperation("兑换优惠券")
+	@PostMapping(value = "exchangeCoupon")
+	public HttpResponseResult exchangeCoupon(Integer couponId, Long paymentOrderId, Integer exchangeNum){
+		SysUser sysUser = sysUserFeignService.queryUserInfo();
+		if (sysUser == null) {
+			return failed("用户信息获取失败");
+		}
+		return succeed(sysCouponCodeService.exchangeCouponTest(sysUser.getId(), couponId, paymentOrderId, exchangeNum));
+	}
+}

+ 19 - 0
mec-task/src/main/java/com/ym/mec/task/jobs/RemarkCountFlagTask.java

@@ -0,0 +1,19 @@
+package com.ym.mec.task.jobs;
+
+import com.ym.mec.task.TaskRemoteService;
+import com.ym.mec.task.core.BaseTask;
+import com.ym.mec.task.core.TaskException;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+@Service
+public class RemarkCountFlagTask extends BaseTask {
+
+	@Autowired
+	private TaskRemoteService taskRemoteService;
+
+	@Override
+	public void execute() throws TaskException {
+		taskRemoteService.remarkCountFlag();
+	}
+}

+ 1 - 1
mec-web/src/main/java/com/ym/mec/web/config/ResourceServerConfig.java

@@ -37,7 +37,7 @@ public class ResourceServerConfig extends ResourceServerConfigurerAdapter {
                         "/uploadFile", "/eduContracts/queryProduceContract", "/activity/doubleEleven2020Statis", "/replacementInstrument/queryPage",
                         "/replacementInstrumentActivity/queryReplacementsStat", "/eduStudentRegistration/queryPreApplyList",
                         "/eduSubject/findSubSubjects", "/eduFinancialExpenditure/batchAdd", "/eduSendNotice/*",
-                        "/oaContracts/*", "/eduStudent/organStudentOverView").permitAll().anyRequest().authenticated().and().httpBasic();
+                        "/oaContracts/*", "/eduStudent/organStudentOverView", "/activity/countCloudTeacherActive").permitAll().anyRequest().authenticated().and().httpBasic();
     }
 
     @Override

+ 1 - 1
mec-web/src/main/java/com/ym/mec/web/controller/ContractsController.java

@@ -81,7 +81,7 @@ public class ContractsController extends BaseController {
 	@PostMapping("transferProduceContract")
 	public HttpResponseResult transferProduceContract(@RequestBody List<Integer> userIds){
 		for (Integer userId : userIds) {
-			contractService.transferProduceContract(userId,null);
+			contractService.transferProduceContract(userId,null, null);
 		}
 		return succeed();
 	}

+ 92 - 0
mec-web/src/main/java/com/ym/mec/web/controller/ExportController.java

@@ -3301,4 +3301,96 @@ public class ExportController extends BaseController {
             }
         }
     }
+
+    @ApiOperation(value = "分部云教练活动统计数据导出")
+    @RequestMapping("export/countCloudTeacherActive")
+    @PreAuthorize("@pcs.hasPermissions('export/countCloudTeacherActive')")
+    public void countCloudTeacherActive(CloudTeacherActiveQueryInfo queryInfo,HttpServletResponse response) throws IOException {
+        SysUser sysUser = sysUserFeignService.queryUserInfo();
+        if (sysUser == null) {
+            throw new BizException("用户信息获取失败");
+        }
+        Employee employee = employeeDao.get(sysUser.getId());
+        queryInfo.setPage(1);
+        queryInfo.setRows(49999);
+        List<Integer> organIds = new ArrayList<>();
+        if(StringUtils.isNotBlank(queryInfo.getOrganIds())){
+            organIds = Arrays.stream(queryInfo.getOrganIds().split(",")).map(id->Integer.valueOf(id)).collect(Collectors.toList());
+        }else if(StringUtils.isNotBlank(employee.getOrganIdList())){
+            organIds = Arrays.stream(employee.getOrganIdList().split(",")).map(id->Integer.valueOf(id)).collect(Collectors.toList());
+        }
+        List<Integer> ids = organIds.stream().filter(id -> !OrganizationService.EXCLUDE_ORGAN_IDS.contains(id)).collect(Collectors.toList());
+        Object object = studentService.countCloudTeacherActive(ids, queryInfo).get("resultList");
+        if(object == null){
+            throw new BizException("没有可导出的记录");
+        }
+        List<CloudTeacherActiveTargetDto> rows = (List<CloudTeacherActiveTargetDto>) object;
+
+        OutputStream outputStream = response.getOutputStream();
+        try {
+            String[] header = {"分部", "购买人数", "购买金额", "目标金额", "人均购买金额", "总人数", "购买率", "目标人数", "目标达成率"};
+            String[] body = {"organName", "buyNum", "buyAmount", "targetAmount", "avgBuyAmount", "totalNum", "buyScale",
+                            "targetNum", "targetFinishScale"};
+            HSSFWorkbook workbook = POIUtil.exportExcel(header, body, rows);
+            response.setContentType("application/octet-stream");
+            response.setHeader("Content-Disposition", "attachment;filename=employeeInfo-" + DateUtil.getDate(new Date()) + ".xls");
+            response.flushBuffer();
+            outputStream = response.getOutputStream();
+            workbook.write(outputStream);
+            outputStream.flush();
+        } catch (Exception e) {
+            e.printStackTrace();
+        } finally {
+            if (outputStream != null) {
+                try {
+                    outputStream.close();
+                } catch (IOException e) {
+                    e.printStackTrace();
+                }
+            }
+        }
+    }
+
+    @ApiOperation(value = "分部云教练学员训练数据导出")
+    @RequestMapping("export/countCloudTeacherActiveDetail")
+    @PreAuthorize("@pcs.hasPermissions('export/countCloudTeacherActiveDetail')")
+    public void countCloudTeacherActiveDetail(CloudTeacherActiveQueryInfo queryInfo,HttpServletResponse response) throws IOException {
+        SysUser sysUser = sysUserFeignService.queryUserInfo();
+        if (sysUser == null) {
+            throw new BizException("用户信息获取失败");
+        }
+        queryInfo.setPage(1);
+        queryInfo.setRows(49999);
+        List<CloudTeacherActiveTargetDetailDto> rows = studentService.countCloudTeacherActiveDetail(queryInfo).getRows();
+        if (CollectionUtils.isEmpty(rows)) {
+            response.setStatus(200);
+            response.setContentType("Content-Type: application/json;charset=UTF-8");
+            response.getOutputStream().write("{\"data\": null, \"code\": 500, \"status\": false, \"msg\": \"没有可导出的记录\"}".getBytes());
+            response.flushBuffer();
+            return;
+        }
+        OutputStream outputStream = response.getOutputStream();
+        try {
+            String[] header = {"学员编号", "学员", "合作单位", "乐团", "乐团模式", "声部", "年级", "指导老师", "购买套餐", "购买金额"};
+            String[] body = {"userId", "username", "cooperationName", "musicGroupName", "chargeType",
+                            "subjectName", "currentGradeNum", "teacherName", "remark", "amount"};
+            HSSFWorkbook workbook = POIUtil.exportExcel(header, body, rows);
+            response.setContentType("application/octet-stream");
+            response.setHeader("Content-Disposition", "attachment;filename=employeeInfo-" + DateUtil.getDate(new Date()) + ".xls");
+            response.flushBuffer();
+            outputStream = response.getOutputStream();
+            workbook.write(outputStream);
+            outputStream.flush();
+        } catch (Exception e) {
+            e.printStackTrace();
+        } finally {
+            if (outputStream != null) {
+                try {
+                    outputStream.close();
+                } catch (IOException e) {
+                    e.printStackTrace();
+                }
+            }
+        }
+    }
 }

+ 1 - 2
mec-web/src/main/java/com/ym/mec/web/controller/OrganizationController.java

@@ -90,9 +90,8 @@ public class OrganizationController extends BaseController {
         return succeed(organizationService.get(id));
     }
 
-
     @ApiOperation(value = "获取用户所在分部的年级列表)")
-    @GetMapping("organization/getGradeList")
+    @GetMapping("/getGradeList")
     @PreAuthorize("@pcs.hasPermissions('organization/getGradeList')")
     @ApiParam(value = "分部编号", required = true)
     public HttpResponseResult<Map<Integer,String>> getGradeList(Integer id) {

+ 33 - 0
mec-web/src/main/java/com/ym/mec/web/controller/StudentManageController.java

@@ -471,4 +471,37 @@ public class StudentManageController extends BaseController {
     public HttpResponseResult<StatDto> organStudentData(StudentQueryInfo queryInfo){
         return succeed(studentService.organStudentData(queryInfo));
     }
+
+    @ApiOperation(value = "云教练活动统计")
+    @GetMapping("/countCloudTeacherActive")
+    @PreAuthorize("@pcs.hasPermissions('studentManage/countCloudTeacherActive')")
+    public Object countCloudTeacherActive(CloudTeacherActiveQueryInfo queryInfo) throws Exception {
+        SysUser sysUser = sysUserFeignService.queryUserInfo();
+        if (sysUser == null) {
+            return failed("用户信息获取失败");
+        }
+        Employee employee = employeeDao.get(sysUser.getId());
+        queryInfo.setPage(1);
+        queryInfo.setRows(49999);
+
+        List<Integer> organIds = new ArrayList<>();
+        if(StringUtils.isNotBlank(queryInfo.getOrganIds())){
+            organIds = Arrays.stream(queryInfo.getOrganIds().split(",")).map(id->Integer.valueOf(id)).collect(Collectors.toList());
+        }else if(StringUtils.isNotBlank(employee.getOrganIdList())){
+            organIds = Arrays.stream(employee.getOrganIdList().split(",")).map(id->Integer.valueOf(id)).collect(Collectors.toList());
+        }
+        List<Integer> ids = organIds.stream().filter(id -> !OrganizationService.EXCLUDE_ORGAN_IDS.contains(id)).collect(Collectors.toList());
+        return succeed(studentService.countCloudTeacherActive(ids, queryInfo));
+    }
+
+    @ApiOperation(value = "云教练活动统计详情")
+    @GetMapping("/countCloudTeacherActiveDetail")
+    @PreAuthorize("@pcs.hasPermissions('studentManage/countCloudTeacherActiveDetail')")
+    public Object countCloudTeacherActiveDetail(CloudTeacherActiveQueryInfo queryInfo) throws Exception {
+        SysUser sysUser = sysUserFeignService.queryUserInfo();
+        if (sysUser == null) {
+            return failed("用户信息获取失败");
+        }
+        return succeed(studentService.countCloudTeacherActiveDetail(queryInfo));
+    }
 }

+ 33 - 0
mec-web/src/main/java/com/ym/mec/web/controller/SysCouponCodeController.java

@@ -0,0 +1,33 @@
+package com.ym.mec.web.controller;
+
+import com.ym.mec.auth.api.client.SysUserFeignService;
+import com.ym.mec.auth.api.entity.SysUser;
+import com.ym.mec.biz.dal.page.SysCouponCodeQueryInfo;
+import com.ym.mec.biz.service.SysCouponCodeService;
+import com.ym.mec.common.controller.BaseController;
+import com.ym.mec.common.entity.HttpResponseResult;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+@RequestMapping("sysCouponCode")
+@Api(tags = "优惠券明细")
+@RestController
+public class SysCouponCodeController extends BaseController {
+
+	@Autowired
+	private SysCouponCodeService sysCouponCodeService;
+	@Autowired
+	private SysUserFeignService sysUserFeignService;
+
+	@ApiOperation("分页查询")
+	@RequestMapping(value = "queryPage")
+	@PreAuthorize("@pcs.hasPermissions('sysCouponCode/queryPage')")
+	public HttpResponseResult queryPage(SysCouponCodeQueryInfo queryInfo) {
+		return succeed(sysCouponCodeService.querySysCouponUseList(queryInfo));
+	}
+}

+ 105 - 0
mec-web/src/main/java/com/ym/mec/web/controller/SysCouponController.java

@@ -0,0 +1,105 @@
+package com.ym.mec.web.controller;
+
+import com.ym.mec.biz.dal.dao.SysCouponDao;
+import com.ym.mec.biz.dal.entity.SysCoupon;
+import com.ym.mec.biz.dal.page.SysCouponQueryInfo;
+import com.ym.mec.biz.service.SysCouponService;
+import com.ym.mec.common.controller.BaseController;
+import com.ym.mec.common.entity.HttpResponseResult;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import java.util.Objects;
+
+@RequestMapping("sysCoupon")
+@Api(tags = "优惠券")
+@RestController
+public class SysCouponController extends BaseController {
+
+	@Autowired
+	private SysCouponService sysCouponService;
+	@Autowired
+	private SysCouponDao sysCouponDao;
+
+	@ApiOperation("新增")
+	@PostMapping(value = "add")
+	@PreAuthorize("@pcs.hasPermissions('sysCoupon/add')")
+	public HttpResponseResult add(SysCoupon sysCoupon) {
+		sysCoupon.setStatus(0);
+		sysCoupon.setConsumeNum(0);
+		sysCoupon.setWarningStatus(0);
+		if(Objects.isNull(sysCoupon.getType())){
+			return failed("请指定优惠券类型");
+		}
+		switch (sysCoupon.getType()){
+			case DISCOUNT:
+				if(Objects.isNull(sysCoupon.getFaceValue())){
+					return failed("请指定折扣比例");
+				}
+				break;
+			case FULL_REDUCTION:
+				if(Objects.isNull(sysCoupon.getFaceValue())){
+					return failed("请指定优惠金额");
+				}
+				if(Objects.isNull(sysCoupon.getFullAmount())){
+					return failed("请指定达标金额");
+				}
+				break;
+			default:
+				return failed("请指定优惠券类型");
+		}
+		switch (sysCoupon.getEffectiveType()){
+			case DAYS:
+				if(Objects.isNull(sysCoupon.getDeadline())){
+					return failed("请指定有效天数");
+				}
+				break;
+			case TIME_BUCKET:
+				if(Objects.isNull(sysCoupon.getEffectiveStartTime())||Objects.isNull(sysCoupon.getEffectiveExpireTime())){
+					return failed("请指定有效时间段");
+				}
+				break;
+			default:
+				return failed("请指定有效期类型");
+		}
+		SysCoupon sysCouponDaoWithName = sysCouponDao.getWithName(sysCoupon.getName());
+		if(Objects.nonNull(sysCouponDaoWithName)){
+			return failed("优惠券名称重复");
+		}
+		return succeed(sysCouponService.insert(sysCoupon));
+	}
+
+	@ApiOperation("修改")
+	@PostMapping(value = "updateCoupon")
+	@PreAuthorize("@pcs.hasPermissions('sysCoupon/updateCoupon')")
+	public HttpResponseResult updateCoupon(SysCoupon sysCoupon) {
+		sysCouponService.updateCoupon(sysCoupon);
+		return succeed();
+	}
+
+	@ApiOperation("删除")
+	@PostMapping(value = "delete")
+	@PreAuthorize("@pcs.hasPermissions('sysCoupon/delete')")
+	public HttpResponseResult del(Integer id) {
+		SysCoupon sysCoupon = sysCouponService.get(id);
+		if(Objects.isNull(sysCoupon)){
+			return failed("优惠券信息不存在");
+		}
+		if(sysCoupon.getConsumeNum()>0){
+			return failed("此优惠券已消耗,暂不可删除");
+		}
+		return succeed(sysCouponService.delete(id));
+	}
+
+	@ApiOperation("分页查询")
+	@RequestMapping(value = "queryPage")
+	@PreAuthorize("@pcs.hasPermissions('sysCoupon/queryPage')")
+	public HttpResponseResult queryPage(SysCouponQueryInfo queryInfo) {
+		return succeed(sysCouponService.queryPage(queryInfo));
+	}
+}

+ 6 - 0
mec-web/src/main/java/com/ym/mec/web/controller/TaskController.java

@@ -500,4 +500,10 @@ public class TaskController extends BaseController {
 	public void curWeekStudentTrainRemind(){
 		sysMusicCompareRecordService.curWeekStudentTrainRemind();
 	}
+
+	@ApiOperation("标记进行中乐团在读学员+VIP、网管有课学员总数(除弦乐声部、去重,去除在云教练的乐团的学员")
+	@GetMapping(value = "/remarkCountFlag")
+	public void remarkCountFlag(){
+		studentService.remarkCountFlag();
+	}
 }

+ 24 - 5
mec-web/src/main/java/com/ym/mec/web/controller/education/ActivityController.java

@@ -8,22 +8,23 @@ import com.ym.mec.biz.dal.dto.LuckStatisDto;
 import com.ym.mec.biz.dal.dto.OrderStatisDto;
 import com.ym.mec.biz.dal.dto.OrganMaxAmountDto;
 import com.ym.mec.biz.dal.entity.Organization;
+import com.ym.mec.biz.dal.page.CloudTeacherActiveQueryInfo;
+import com.ym.mec.biz.service.OrganizationService;
+import com.ym.mec.biz.service.StudentService;
 import com.ym.mec.common.controller.BaseController;
 import com.ym.mec.common.entity.HttpResponseResult;
-
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
-
+import org.apache.commons.lang3.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.util.CollectionUtils;
 import org.springframework.web.bind.annotation.GetMapping;
 import org.springframework.web.bind.annotation.RequestMapping;
 import org.springframework.web.bind.annotation.RestController;
 
 import java.math.BigDecimal;
 import java.math.RoundingMode;
-import java.util.Comparator;
-import java.util.List;
-import java.util.Set;
+import java.util.*;
 import java.util.stream.Collectors;
 
 @RequestMapping("activity")
@@ -36,6 +37,10 @@ public class ActivityController extends BaseController {
     private SporadicChargeInfoDao sporadicChargeInfoDao;
     @Autowired
     private StudentRegistrationDao studentRegistrationDao;
+    @Autowired
+    private OrganizationService organizationService;
+    @Autowired
+    private StudentService studentService;
 
     @ApiOperation(value = "分部双11活动统计")
     @GetMapping("/doubleEleven2020Statis")
@@ -103,4 +108,18 @@ public class ActivityController extends BaseController {
         luckStatisDto.setScale(totalMoney.multiply(new BigDecimal(100)).divide(totalMaxAmount, 2, BigDecimal.ROUND_HALF_UP));
         return succeed(luckStatisDto);
     }
+
+    @ApiOperation(value = "云教练活动统计")
+    @GetMapping("/countCloudTeacherActive")
+    public Object countCloudTeacherActive(CloudTeacherActiveQueryInfo queryInfo) throws Exception {
+        List<Organization> organizations = organizationService.queryEmployeeOrgan(null);
+        List<Integer> organIds = new ArrayList<>();
+        if(StringUtils.isNotBlank(queryInfo.getOrganIds())){
+            organIds = Arrays.stream(queryInfo.getOrganIds().split(",")).map(id->Integer.valueOf(id)).collect(Collectors.toList());
+        }else if(!CollectionUtils.isEmpty(organizations)){
+            organIds = organizations.stream().map(Organization::getId).collect(Collectors.toList());
+        }
+        List<Integer> ids = organIds.stream().filter(id -> !OrganizationService.EXCLUDE_ORGAN_IDS.contains(id)).collect(Collectors.toList());
+        return succeed(studentService.countCloudTeacherActive(ids, queryInfo));
+    }
 }

+ 3 - 2
mec-web/src/main/java/com/ym/mec/web/controller/education/EduContractsController.java

@@ -2,6 +2,7 @@ package com.ym.mec.web.controller.education;
 
 import com.ym.mec.auth.api.client.SysUserFeignService;
 import com.ym.mec.auth.api.entity.SysUser;
+import com.ym.mec.biz.dal.enums.CourseViewTypeEnum;
 import com.ym.mec.biz.service.ContractService;
 import com.ym.mec.common.controller.BaseController;
 import io.swagger.annotations.Api;
@@ -29,7 +30,7 @@ public class EduContractsController extends BaseController {
 
     @ApiOperation("查询产品协议")
     @GetMapping(value = "queryProduceContract")
-    public Object queryProduceContract(Integer userId, String musicGroupId) {
+    public Object queryProduceContract(Integer userId, String musicGroupId, CourseViewTypeEnum courseViewType) {
         if(Objects.isNull(userId)){
             SysUser sysUser = sysUserFeignService.queryUserInfo();
             if (sysUser == null) {
@@ -37,6 +38,6 @@ public class EduContractsController extends BaseController {
             }
             userId = sysUser.getId();
         }
-        return succeed(contractService.queryProductContract(userId,musicGroupId));
+        return succeed(contractService.queryProductContract(userId,musicGroupId, courseViewType));
     }
 }

+ 2 - 2
mec-web/src/main/resources/logback-spring.xml

@@ -1,7 +1,7 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <configuration scan="true" scanPeriod="10 seconds">
 
-	<property name="LOG_HOME" value="/mdata/logs/web-%d{yyyy-MM-dd_HH}-%i.log" />
+	<property name="LOG_HOME" value="/Users/chenxiaoyu/Documents/logs/web-%d{yyyy-MM-dd_HH}-%i.log" />
 	<property name="CONSOLE_LOG_PATTERN"
 			  value="[%X{username} %X{ip} %d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{36}] : %msg%n" />
 
@@ -30,7 +30,7 @@
 	<appender name="messagefile"
 			  class="ch.qos.logback.core.rolling.RollingFileAppender">
 		<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
-			<FileNamePattern>/mdata/logs/web-message-%d{yyyy-MM-dd_HH}-%i.log</FileNamePattern>
+			<FileNamePattern>/Users/chenxiaoyu/Documents/logs/web-message-%d{yyyy-MM-dd_HH}-%i.log</FileNamePattern>
 			<MaxHistory>90</MaxHistory>
 			<TimeBasedFileNamingAndTriggeringPolicy
 					class="ch.qos.logback.core.rolling.SizeAndTimeBasedFNATP">