From 75b60332f174363cfe67f61dea87832be708ac15 Mon Sep 17 00:00:00 2001
From: puzhibing <393733352@qq.com>
Date: 星期二, 04 七月 2023 08:37:46 +0800
Subject: [PATCH] 更新部分接口

---
 cloud-server-account/src/main/java/com/dsh/account/entity/TAppUser.java                                  |    4 
 cloud-server-activity/src/main/java/com/dsh/activity/util/ResultUtil.java                                |   10 
 cloud-server-course/src/main/java/com/dsh/course/model/CoursePackageList.java                            |   28 
 cloud-server-course/src/main/resources/mapper/TCoursePackagePaymentMapper.xml                            |    8 
 cloud-server-course/src/main/java/com/dsh/course/util/GDMapGeocodingUtil.java                            |  148 +
 cloud-server-account/src/main/java/com/dsh/account/util/GeodesyUtil.java                                 |   63 
 cloud-server-account/src/main/java/com/dsh/account/util/TaskUtil.java                                    |   43 
 cloud-server-account/src/main/java/com/dsh/account/util/weChat/WeChatUtil.java                           |   19 
 cloud-server-course/src/main/java/com/dsh/course/feignclient/account/model/AppUser.java                  |  114 +
 cloud-server-other/src/main/java/com/dsh/other/util/TokenUtil.java                                       |    6 
 cloud-server-other/pom.xml                                                                               |   14 
 cloud-server-competition/src/main/java/com/dsh/competition/util/TokenUtil.java                           |    6 
 cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackageService.java                      |   11 
 cloud-server-competition/src/main/java/com/dsh/competition/util/ResultUtil.java                          |   10 
 cloud-server-activity/src/main/java/com/dsh/activity/mapper/CouponMapper.java                            |   11 
 cloud-server-account/src/main/java/com/dsh/account/feignclient/other/model/Store.java                    |   94 +
 cloud-server-activity/src/main/java/com/dsh/activity/model/CouponListVo.java                             |   26 
 cloud-server-course/src/main/java/com/dsh/course/service/impl/CoursePackagePaymentConfigServiceImpl.java |   15 
 cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackageMapper.java                        |    2 
 cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackageServiceImpl.java             |  195 ++
 cloud-server-account/src/main/java/com/dsh/account/model/JoinPlayPaiVo.java                              |   22 
 cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/StudentClient.java              |   24 
 cloud-server-activity/src/main/java/com/dsh/activity/controller/CouponController.java                    |   55 
 cloud-server-activity/src/main/java/com/dsh/activity/util/TokenUtil.java                                 |    6 
 cloud-server-other/src/main/java/com/dsh/other/util/httpClinet/HttpClientUtil.java                       |  267 +++
 cloud-server-activity/src/main/resources/mapper/CouponMapper.tld                                         |   34 
 cloud-server-other/src/main/java/com/dsh/other/model/BaseVo.java                                         |   18 
 cloud-server-activity/src/main/java/com/dsh/activity/service/impl/CouponServiceImpl.java                 |   92 +
 cloud-server-course/src/main/java/com/dsh/course/util/ResultUtil.java                                    |   10 
 cloud-server-account/src/main/java/com/dsh/account/util/ResultUtil.java                                  |    9 
 cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/AppUserClient.java              |   22 
 cloud-server-account/src/main/java/com/dsh/account/util/PayMoneyUtil.java                                |  803 ++++++++++
 cloud-server-account/src/main/resources/mapper/VipPaymentMapper.tld                                      |   20 
 cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackagePaymentServiceImpl.java      |   10 
 cloud-server-other/src/main/java/com/dsh/other/util/ResultUtil.java                                      |   10 
 cloud-server-account/src/main/java/com/dsh/account/service/IVipPaymentService.java                       |   29 
 cloud-server-course/src/main/java/com/dsh/course/controller/CourseController.java                        |   80 
 cloud-server-account/src/main/java/com/dsh/account/feignclient/other/StoreClient.java                    |   24 
 cloud-server-course/src/main/java/com/dsh/course/entity/CoursePackagePaymentConfig.java                  |   46 
 cloud-server-course/src/main/java/com/dsh/course/feignclient/other/model/Store.java                      |   94 +
 cloud-server-activity/src/main/java/com/dsh/activity/entity/Coupon.java                                  |  144 +
 cloud-server-course/src/main/resources/mapper/CoursePackagePaymentConfigMapper.xml                       |   14 
 cloud-server-account/src/main/java/com/dsh/account/entity/VipPayment.java                                |   76 
 cloud-server-course/pom.xml                                                                              |   19 
 cloud-server-course/src/main/java/com/dsh/course/feignclient/account/AppUserClient.java                  |   21 
 cloud-server-course/src/main/java/com/dsh/course/util/GeodesyUtil.java                                   |   63 
 cloud-server-course/src/main/java/com/dsh/course/model/BaseVo.java                                       |   18 
 cloud-server-course/src/main/java/com/dsh/course/util/TokenUtil.java                                     |    6 
 cloud-server-course/src/main/java/com/dsh/course/util/httpClinet/HttpResult.java                         |   31 
 cloud-server-other/src/main/java/com/dsh/other/service/impl/StoreServiceImpl.java                        |   58 
 cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/model/Student.java              |   70 
 cloud-server-account/src/main/java/com/dsh/AccountApplication.java                                       |    2 
 cloud-server-account/src/main/java/com/dsh/account/controller/StudentController.java                     |   40 
 cloud-server-other/src/main/java/com/dsh/other/controller/StoreController.java                           |  108 +
 cloud-server-other/src/main/java/com/dsh/other/model/StoreConfigVo.java                                  |   22 
 cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackagePaymentService.java               |    7 
 cloud-server-course/src/main/java/com/dsh/course/util/httpClinet/HttpClientUtil.java                     |  267 +++
 cloud-server-account/src/main/java/com/dsh/account/mapper/VipPaymentMapper.java                          |   11 
 cloud-server-account/src/main/java/com/dsh/account/controller/AppUserController.java                     |  180 ++
 cloud-server-account/src/main/java/com/dsh/account/service/impl/VipPaymentServiceImpl.java               |  260 +++
 cloud-server-account/src/main/java/com/dsh/account/util/MD5AndKL.java                                    |  112 +
 cloud-server-account/src/main/java/com/dsh/account/util/TokenUtil.java                                   |    6 
 cloud-server-course/src/main/resources/mapper/TCourseMapper.xml                                          |    1 
 cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/model/AppUser.java              |  114 +
 cloud-server-account/src/main/java/com/dsh/account/util/httpClinet/HttpClientUtil.java                   |   29 
 cloud-server-course/src/main/java/com/dsh/course/service/impl/TCourseServiceImpl.java                    |    3 
 cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackagePaymentMapper.java                 |    8 
 cloud-server-account/src/main/java/com/dsh/account/util/GDMapGeocodingUtil.java                          |   17 
 cloud-server-account/src/main/java/com/dsh/account/controller/ClassDetailsController.java                |   12 
 cloud-server-course/src/main/java/com/dsh/course/feignclient/other/StoreClient.java                      |   33 
 cloud-server-activity/src/main/java/com/dsh/activity/service/ICouponService.java                         |   23 
 cloud-server-account/pom.xml                                                                             |   10 
 cloud-server-account/src/main/java/com/dsh/account/mapper/TAppUserMapper.java                            |    6 
 cloud-server-course/src/main/java/com/dsh/course/model/CoursePackageListVo.java                          |   34 
 cloud-server-other/src/main/java/com/dsh/other/util/httpClinet/HttpResult.java                           |   31 
 cloud-server-account/src/main/resources/mapper/TAppUserMapper.xml                                        |    5 
 cloud-server-course/src/main/java/com/dsh/course/service/ICoursePackagePaymentConfigService.java         |   11 
 cloud-server-other/src/main/java/com/dsh/other/util/GDMapGeocodingUtil.java                              |  148 +
 cloud-server-account/src/main/java/com/dsh/account/service/impl/TAppUserServiceImpl.java                 |   60 
 cloud-server-other/src/main/java/com/dsh/other/service/StoreService.java                                 |   23 
 cloud-server-course/src/main/java/com/dsh/course/mapper/CoursePackagePaymentConfigMapper.java            |   11 
 cloud-server-other/src/main/java/com/dsh/other/controller/StoreConfigController.java                     |   57 
 cloud-server-account/src/main/java/com/dsh/account/feignclient/course/model/QueryStoreList.java          |   22 
 cloud-server-account/src/main/java/com/dsh/account/service/TAppUserService.java                          |   17 
 84 files changed, 4,626 insertions(+), 86 deletions(-)

diff --git a/cloud-server-account/pom.xml b/cloud-server-account/pom.xml
index 5d6ea38..5759cbd 100644
--- a/cloud-server-account/pom.xml
+++ b/cloud-server-account/pom.xml
@@ -91,6 +91,11 @@
         </dependency>
 
         <dependency>
+            <groupId>dom4j</groupId>
+            <artifactId>dom4j</artifactId>
+            <version>1.6.1</version>
+        </dependency>
+        <dependency>
             <groupId>com.alipay.sdk</groupId>
             <artifactId>alipay-sdk-java</artifactId>
             <version>4.8.10.ALL</version>
@@ -112,6 +117,11 @@
             <artifactId>jjwt</artifactId>
             <version>0.9.0</version>
         </dependency>
+        <dependency>
+            <groupId>org.gavaghan</groupId>
+            <artifactId>geodesy</artifactId>
+            <version>1.1.3</version>
+        </dependency>
     </dependencies>
 
     <build>
diff --git a/cloud-server-account/src/main/java/com/dsh/AccountApplication.java b/cloud-server-account/src/main/java/com/dsh/AccountApplication.java
index 10a2f78..de0ceac 100644
--- a/cloud-server-account/src/main/java/com/dsh/AccountApplication.java
+++ b/cloud-server-account/src/main/java/com/dsh/AccountApplication.java
@@ -11,6 +11,7 @@
 import org.springframework.context.annotation.Bean;
 import org.springframework.context.annotation.Import;
 import org.springframework.context.support.PropertySourcesPlaceholderConfigurer;
+import org.springframework.scheduling.annotation.EnableScheduling;
 import springfox.documentation.swagger2.annotations.EnableSwagger2;
 
 import javax.annotation.PostConstruct;
@@ -22,6 +23,7 @@
 @EnableSwagger2
 @EnableFeignClients
 @MBCloudApplication
+@EnableScheduling//开启定时任务
 @Import({WebConfig.class})
 @MapperScan("com.dsh.account.mapper")
 public class AccountApplication {
diff --git a/cloud-server-account/src/main/java/com/dsh/account/controller/AppUserController.java b/cloud-server-account/src/main/java/com/dsh/account/controller/AppUserController.java
index a7abfa4..7f75133 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/controller/AppUserController.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/controller/AppUserController.java
@@ -1,15 +1,26 @@
 package com.dsh.account.controller;
 
+import com.dsh.account.entity.TAppUser;
 import com.dsh.account.model.AddAppUserVo;
+import com.dsh.account.model.JoinPlayPaiVo;
 import com.dsh.account.model.LoginSMSCodeVo;
 import com.dsh.account.model.LoginWeChatVo;
+import com.dsh.account.service.IVipPaymentService;
 import com.dsh.account.service.TAppUserService;
+import com.dsh.account.util.PayMoneyUtil;
 import com.dsh.account.util.ResultUtil;
+import com.dsh.account.util.TokenUtil;
+import com.dsh.account.util.ToolUtil;
 import io.swagger.annotations.ApiImplicitParam;
 import io.swagger.annotations.ApiImplicitParams;
 import io.swagger.annotations.ApiOperation;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.web.bind.annotation.*;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import java.io.PrintWriter;
+import java.util.Map;
 
 /**
  * @author zhibing.pu
@@ -22,6 +33,15 @@
     @Autowired
     private TAppUserService appUserService;
 
+    @Autowired
+    private PayMoneyUtil payMoneyUtil;
+
+    @Autowired
+    private IVipPaymentService vipPaymentService;
+
+    @Autowired
+    private TokenUtil tokenUtil;
+
 
 
 
@@ -33,6 +53,12 @@
             @ApiImplicitParam(value = "电话号码", name = "phone", dataType = "string", required = true)
     })
     public ResultUtil getSMSCode(@RequestBody Integer type, @RequestBody String phone){
+        if(ToolUtil.isEmpty(phone)){
+            return ResultUtil.paranErr("phone");
+        }
+        if(ToolUtil.isEmpty(type)){
+            return ResultUtil.paranErr("type");
+        }
         try {
             ResultUtil smsCode = appUserService.getSMSCode(type, phone);
             return smsCode;
@@ -66,6 +92,12 @@
             @ApiImplicitParam(value = "登录密码", name = "password", dataType = "string", required = true)
     })
     public ResultUtil<String> loginPassword(@RequestBody String phone, @RequestBody String password){
+        if(ToolUtil.isEmpty(phone)){
+            return ResultUtil.paranErr("phone");
+        }
+        if(ToolUtil.isEmpty(password)){
+            return ResultUtil.paranErr("password");
+        }
         try {
             return appUserService.loginPassword(phone, password);
         }catch (Exception e){
@@ -116,6 +148,15 @@
             @ApiImplicitParam(value = "新密码", name = "password", dataType = "string", required = true)
     })
     public ResultUtil updatePassword(@RequestBody String phone, @RequestBody String code, @RequestBody String password){
+        if(ToolUtil.isEmpty(phone)){
+            return ResultUtil.paranErr("phone");
+        }
+        if(ToolUtil.isEmpty(code)){
+            return ResultUtil.paranErr("code");
+        }
+        if(ToolUtil.isEmpty(password)){
+            return ResultUtil.paranErr("password");
+        }
         try {
             return appUserService.updatePassword(phone, code, password);
         }catch (Exception e){
@@ -134,6 +175,15 @@
             @ApiImplicitParam(value = "新密码", name = "password", dataType = "string", required = true)
     })
     public ResultUtil forgetPassword(@RequestBody String phone, @RequestBody String code, @RequestBody String password){
+        if(ToolUtil.isEmpty(phone)){
+            return ResultUtil.paranErr("phone");
+        }
+        if(ToolUtil.isEmpty(code)){
+            return ResultUtil.paranErr("code");
+        }
+        if(ToolUtil.isEmpty(password)){
+            return ResultUtil.paranErr("password");
+        }
         try {
             return appUserService.updatePassword(phone, code, password);
         }catch (Exception e){
@@ -144,5 +194,135 @@
 
 
 
+    @ResponseBody
+    @PostMapping("/api/appUser/queryJoinPlayPai")
+    @ApiOperation(value = "获取加入玩湃首页数据", tags = {"APP-加入玩湃"})
+    @ApiImplicitParams({
+            @ApiImplicitParam(value = "经度", name = "lon", dataType = "string", required = true),
+            @ApiImplicitParam(value = "纬度", name = "lat", dataType = "string", required = true),
+            @ApiImplicitParam(name = "Authorization", value = "用户token(Bearer +token)", required = true, dataType = "String", paramType = "header", defaultValue = "Bearer eyJhbGciOiJIUzUxMiJ9.....")
+    })
+    public ResultUtil<JoinPlayPaiVo> queryJoinPlayPai(@RequestBody String lon, @RequestBody String lat){
+        if(ToolUtil.isEmpty(lon)){
+            return ResultUtil.paranErr("lon");
+        }
+        if(ToolUtil.isEmpty(lat)){
+            return ResultUtil.paranErr("lat");
+        }
+        try {
+            Integer uid = tokenUtil.getUserIdFormRedis();
+            if(null == uid){
+                return ResultUtil.tokenErr();
+            }
+            JoinPlayPaiVo joinPlayPaiVo = appUserService.queryJoinPlayPai(uid, lon, lat);
+            return ResultUtil.success(joinPlayPaiVo);
+        }catch (Exception e){
+            e.printStackTrace();
+            return ResultUtil.runErr();
+        }
+    }
 
+
+
+
+
+    @ResponseBody
+    @PostMapping("/api/appUser/addVipPayment")
+    @ApiOperation(value = "购买年度会员", tags = {"APP-成为会员"})
+    @ApiImplicitParams({
+            @ApiImplicitParam(value = "支付方式(1=微信,2=支付宝)", name = "payType", dataType = "int", required = true),
+            @ApiImplicitParam(name = "Authorization", value = "用户token(Bearer +token)", required = true, dataType = "String", paramType = "header", defaultValue = "Bearer eyJhbGciOiJIUzUxMiJ9.....")
+    })
+    public ResultUtil addVipPayment(@RequestBody Integer payType){
+        if(ToolUtil.isEmpty(payType)){
+            return ResultUtil.paranErr("payType");
+        }
+        try {
+            Integer uid = tokenUtil.getUserIdFormRedis();
+            if(null == uid){
+                return ResultUtil.tokenErr();
+            }
+            return vipPaymentService.addVipPayment(uid, payType);
+        }catch (Exception e){
+            e.printStackTrace();
+            return ResultUtil.runErr();
+        }
+    }
+
+
+
+
+
+
+    /**
+     * 购买年度会员支付微信回调
+     * @param request
+     * @param response
+     */
+    @ResponseBody
+    @PostMapping("/base/appUser/addVipPaymentWeChatCallback")
+    public void addVipPaymentWeChatCallback(HttpServletRequest request, HttpServletResponse response){
+        try {
+            Map<String, String> map = payMoneyUtil.weixinpayCallback(request);
+            if(null != map){
+                String out_trade_no = map.get("out_trade_no");
+                String transaction_id = map.get("transaction_id");
+                String result = map.get("result");
+                ResultUtil resultUtil = vipPaymentService.addVipPaymentCallback(out_trade_no, transaction_id);
+                if(resultUtil.getCode() == 200){
+                    PrintWriter out = response.getWriter();
+                    out.write(result);
+                    out.flush();
+                    out.close();
+                }
+            }
+        }catch (Exception e){
+            e.printStackTrace();
+        }
+    }
+
+
+    /**
+     * 购买年度会员支付支付宝回调
+     * @param request
+     * @param response
+     */
+    @ResponseBody
+    @PostMapping("/base/appUser/addVipPaymentAliCallback")
+    public void addVipPaymentAliCallback(HttpServletRequest request, HttpServletResponse response){
+        try {
+            Map<String, String> map = payMoneyUtil.alipayCallback(request);
+            if(null != map){
+                String out_trade_no = map.get("out_trade_no");
+                String trade_no = map.get("trade_no");
+                ResultUtil resultUtil = vipPaymentService.addVipPaymentCallback(out_trade_no, trade_no);
+                if(resultUtil.getCode() == 200){
+                    PrintWriter out = response.getWriter();
+                    out.write("success");
+                    out.flush();
+                    out.close();
+                }
+            }
+        }catch (Exception e){
+            e.printStackTrace();
+        }
+    }
+
+
+    /**
+     * 根据用户id获取用户信息
+     * @param appUserId
+     * @return
+     */
+    @ResponseBody
+    @PostMapping("/base/appUser/queryAppUser")
+    public TAppUser queryAppUser(@RequestBody Integer appUserId){
+        try {
+            TAppUser appUser = appUserService.getById(appUserId);
+            return appUser;
+        }catch (Exception e){
+            e.printStackTrace();
+            return null;
+        }
+    }
 }
diff --git a/cloud-server-account/src/main/java/com/dsh/account/controller/ClassDetailsController.java b/cloud-server-account/src/main/java/com/dsh/account/controller/ClassDetailsController.java
index 7980814..87eb972 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/controller/ClassDetailsController.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/controller/ClassDetailsController.java
@@ -58,9 +58,9 @@
             @ApiImplicitParam(value = "纬度值", name = "latitude", required = true, dataType = "String"),
             @ApiImplicitParam(name = "Authorization", value = "Bearer +token", required = true, dataType = "String", paramType = "header", defaultValue = "Bearer eyJhbGciOiJIUzUxMiJ9.....")
     })
-    public ResultUtil queryCouponRecord(String longitude,String latitude,HttpServletRequest request){
+    public ResultUtil queryCouponRecord(String longitude,String latitude){
         try {
-            Integer userIdFormRedis = tokenUtil.getUserIdFormRedis(request);
+            Integer userIdFormRedis = tokenUtil.getUserIdFormRedis();
             if(null == userIdFormRedis){
                 return ResultUtil.tokenErr();
             }
@@ -102,9 +102,9 @@
             @ApiImplicitParam(name = "Authorization", value = "Bearer +token", required = true, dataType = "String", paramType = "header", defaultValue = "Bearer eyJhbGciOiJIUzUxMiJ9.....")
     })
     @Transactional
-    public ResultUtil addStu(@RequestBody StuDetailsReq stu,HttpServletRequest request){
+    public ResultUtil addStu(@RequestBody StuDetailsReq stu){
         try {
-            Integer userIdFormRedis = tokenUtil.getUserIdFormRedis(request);
+            Integer userIdFormRedis = tokenUtil.getUserIdFormRedis();
             if(null == userIdFormRedis){
                 return ResultUtil.tokenErr();
             }
@@ -124,9 +124,9 @@
     @ApiImplicitParams({
             @ApiImplicitParam(name = "Authorization", value = "Bearer +token", required = true, dataType = "String", paramType = "header", defaultValue = "Bearer eyJhbGciOiJIUzUxMiJ9.....")
     })
-    public ResultUtil queryStuList(HttpServletRequest request){
+    public ResultUtil queryStuList(){
         try {
-            Integer userIdFormRedis = tokenUtil.getUserIdFormRedis(request);
+            Integer userIdFormRedis = tokenUtil.getUserIdFormRedis();
             if(null == userIdFormRedis){
                 return ResultUtil.tokenErr();
             }
diff --git a/cloud-server-account/src/main/java/com/dsh/account/controller/StudentController.java b/cloud-server-account/src/main/java/com/dsh/account/controller/StudentController.java
new file mode 100644
index 0000000..674b0e8
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/controller/StudentController.java
@@ -0,0 +1,40 @@
+package com.dsh.account.controller;
+
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.dsh.account.entity.TStudent;
+import com.dsh.account.service.TStudentService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 14:59
+ */
+@RestController
+@RequestMapping("")
+public class StudentController {
+
+    @Autowired
+    private TStudentService studentService;
+
+
+    /**
+     * 获取用户学员列表
+     * @param appUserId
+     * @return
+     */
+    @ResponseBody
+    @PostMapping("/student/queryStudentList")
+    public List<TStudent> queryStudentList(@RequestBody Integer appUserId){
+        try {
+            List<TStudent> list = studentService.list(new QueryWrapper<TStudent>().eq("appUserId", appUserId).eq("state", 1));
+            return list;
+        }catch (Exception e){
+            e.printStackTrace();
+            return new ArrayList<>();
+        }
+    }
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/entity/TAppUser.java b/cloud-server-account/src/main/java/com/dsh/account/entity/TAppUser.java
index 02bdfc1..5c64cd6 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/entity/TAppUser.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/entity/TAppUser.java
@@ -127,6 +127,10 @@
      * 用户头像
      */
     private String headImg;
+    /**
+     * 添加时间
+     */
+    private Date insertTime;
 
 
 }
diff --git a/cloud-server-account/src/main/java/com/dsh/account/entity/VipPayment.java b/cloud-server-account/src/main/java/com/dsh/account/entity/VipPayment.java
new file mode 100644
index 0000000..c6da1e9
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/entity/VipPayment.java
@@ -0,0 +1,76 @@
+package com.dsh.account.entity;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.dsh.account.util.UUIDUtil;
+import lombok.Data;
+
+import java.text.SimpleDateFormat;
+import java.util.Date;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 9:58
+ */
+@Data
+@TableName("t_vip_payment")
+public class VipPayment {
+    /**
+     * 主键
+     */
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+    /**
+     * 流水号
+     */
+    @TableField("code")
+    private String code;
+    /**
+     * 用户id
+     */
+    @TableField("appUserId")
+    private Integer appUserId;
+    /**
+     * 支付金额
+     */
+    @TableField("amount")
+    private Double amount;
+    /**
+     * 支付方式(1=微信,2=支付宝)
+     */
+    @TableField("payType")
+    private Integer payType;
+    /**
+     * 支付状态(1=待支付,2=已支付)
+     */
+    @TableField("payStatus")
+    private Integer payStatus;
+    /**
+     * 支付时间
+     */
+    @TableField("payTime")
+    private Date payTime;
+    /**
+     * 第三方流水号
+     */
+    @TableField("orderNumber")
+    private String orderNumber;
+    /**
+     * 状态(1=正常,2=冻结,3=删除)
+     */
+    @TableField("state")
+    private Integer state;
+    /**
+     * 添加时间
+     */
+    @TableField("insertTime")
+    private Date insertTime;
+
+
+    public static String CODE(){
+        SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmssSSS");
+        return sdf.format(new Date()) + UUIDUtil.getNumberRandom(3);
+    }
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/feignclient/course/model/QueryStoreList.java b/cloud-server-account/src/main/java/com/dsh/account/feignclient/course/model/QueryStoreList.java
new file mode 100644
index 0000000..83a429c
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/feignclient/course/model/QueryStoreList.java
@@ -0,0 +1,22 @@
+package com.dsh.account.feignclient.course.model;
+
+import lombok.Data;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/28 9:08
+ */
+@Data
+public class QueryStoreList {
+    private String provinceCode;
+
+    private String cityCode;
+
+    public QueryStoreList() {
+    }
+
+    public QueryStoreList(String provinceCode, String cityCode) {
+        this.provinceCode = provinceCode;
+        this.cityCode = cityCode;
+    }
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/feignclient/other/StoreClient.java b/cloud-server-account/src/main/java/com/dsh/account/feignclient/other/StoreClient.java
new file mode 100644
index 0000000..0495a35
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/feignclient/other/StoreClient.java
@@ -0,0 +1,24 @@
+package com.dsh.account.feignclient.other;
+
+import com.dsh.account.feignclient.course.model.QueryStoreList;
+import com.dsh.account.feignclient.other.model.Store;
+import org.springframework.cloud.openfeign.FeignClient;
+import org.springframework.web.bind.annotation.PostMapping;
+
+import java.util.List;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 15:54
+ */
+@FeignClient(value = "mb-cloud-other")
+public interface StoreClient {
+
+
+    /**
+     * 获取门店列表
+     * @return
+     */
+    @PostMapping("/store/queryStoreList")
+    List<Store> queryStoreList(QueryStoreList queryStoreList);
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/feignclient/other/model/Store.java b/cloud-server-account/src/main/java/com/dsh/account/feignclient/other/model/Store.java
new file mode 100644
index 0000000..fea492f
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/feignclient/other/model/Store.java
@@ -0,0 +1,94 @@
+package com.dsh.account.feignclient.other.model;
+
+import lombok.Data;
+
+import java.math.BigDecimal;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 15:55
+ */
+@Data
+public class Store {
+    private Integer id;
+    /**
+     * 门店名称
+     */
+    private String name;
+    /**
+     * 门店店长id
+     */
+    private Integer storeStaffId;
+    /**
+     * 城市管理员id
+     */
+    private Integer cityManagerId;
+    /**
+     * 省
+     */
+    private String province;
+    /**
+     * 省编号
+     */
+    private String provinceCode;
+    /**
+     * 市
+     */
+    private String city;
+    /**
+     * 市编号
+     */
+    private String cityCode;
+    /**
+     * 联系电话
+     */
+    private String phone;
+    /**
+     * 详细地址
+     */
+    private String address;
+    /**
+     * 纬度
+     */
+    private String lat;
+    /**
+     * 经度
+     */
+    private String lon;
+    /**
+     * 营业开始时间
+     */
+    private String startTime;
+    /**
+     * 营业结束时间
+     */
+    private String endTime;
+    /**
+     * 封面图
+     */
+    private String coverDrawing;
+    /**
+     * 实景图
+     */
+    private String realPicture;
+    /**
+     * 门店介绍
+     */
+    private String introduce;
+    /**
+     * 福利图片
+     */
+    private String welfarePicture;
+    /**
+     * 开始上课图片
+     */
+    private String classPicture;
+    /**
+     * 评分
+     */
+    private BigDecimal score;
+    /**
+     * 状态(1=正常,2=冻结,3=删除)
+     */
+    private Integer state;
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/mapper/TAppUserMapper.java b/cloud-server-account/src/main/java/com/dsh/account/mapper/TAppUserMapper.java
index d77da72..407daca 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/mapper/TAppUserMapper.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/mapper/TAppUserMapper.java
@@ -14,4 +14,10 @@
  */
 public interface TAppUserMapper extends BaseMapper<TAppUser> {
 
+
+    /**
+     * 定时任务修改到期会员的状态
+     */
+    void membershipEnd();
+
 }
diff --git a/cloud-server-account/src/main/java/com/dsh/account/mapper/VipPaymentMapper.java b/cloud-server-account/src/main/java/com/dsh/account/mapper/VipPaymentMapper.java
new file mode 100644
index 0000000..7cdfae5
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/mapper/VipPaymentMapper.java
@@ -0,0 +1,11 @@
+package com.dsh.account.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.dsh.account.entity.VipPayment;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 10:02
+ */
+public interface VipPaymentMapper extends BaseMapper<VipPayment> {
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/model/JoinPlayPaiVo.java b/cloud-server-account/src/main/java/com/dsh/account/model/JoinPlayPaiVo.java
new file mode 100644
index 0000000..4ada461
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/model/JoinPlayPaiVo.java
@@ -0,0 +1,22 @@
+package com.dsh.account.model;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 15:36
+ */
+@Data
+public class JoinPlayPaiVo {
+    @ApiModelProperty("是否是年度会员(0=否,1=是)")
+    private Integer isVip;
+    @ApiModelProperty("门店id")
+    private Integer storeId;
+    @ApiModelProperty("门店名称")
+    private String name;
+    @ApiModelProperty("门店经度")
+    private String lon;
+    @ApiModelProperty("门店纬度")
+    private String lat;
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/service/IVipPaymentService.java b/cloud-server-account/src/main/java/com/dsh/account/service/IVipPaymentService.java
new file mode 100644
index 0000000..4355c9d
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/service/IVipPaymentService.java
@@ -0,0 +1,29 @@
+package com.dsh.account.service;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.dsh.account.entity.VipPayment;
+import com.dsh.account.util.ResultUtil;
+
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 10:03
+ */
+public interface IVipPaymentService extends IService<VipPayment> {
+
+
+    /**
+     * 购买年度会员
+     * @param uid
+     * @return
+     * @throws Exception
+     */
+    ResultUtil addVipPayment(Integer uid, Integer payType) throws Exception;
+
+
+    /**
+     * 购买年度会员回调处理
+     * @throws Exception
+     */
+    ResultUtil addVipPaymentCallback(String code, String orderNumber) throws Exception;
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/service/TAppUserService.java b/cloud-server-account/src/main/java/com/dsh/account/service/TAppUserService.java
index e823be6..58f08bf 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/service/TAppUserService.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/service/TAppUserService.java
@@ -2,6 +2,7 @@
 
 import com.dsh.account.entity.TAppUser;
 import com.dsh.account.model.AddAppUserVo;
+import com.dsh.account.model.JoinPlayPaiVo;
 import com.dsh.account.model.LoginSMSCodeVo;
 import com.dsh.account.model.LoginWeChatVo;
 import com.dsh.account.model.vo.classDetails.classInsVo.ClassInfoVo;
@@ -74,4 +75,20 @@
      * @throws Exception
      */
     ResultUtil updatePassword(String phone, String code, String password) throws Exception;
+
+
+    /**
+     * 定时任务修改到期会员的状态
+     */
+    void membershipEnd();
+
+
+    /**
+     * 获取加入玩湃首页数据
+     * @param lon
+     * @param lat
+     * @return
+     * @throws Exception
+     */
+    JoinPlayPaiVo queryJoinPlayPai(Integer uid, String lon, String lat) throws Exception;
 }
diff --git a/cloud-server-account/src/main/java/com/dsh/account/service/impl/TAppUserServiceImpl.java b/cloud-server-account/src/main/java/com/dsh/account/service/impl/TAppUserServiceImpl.java
index 0a3793d..6bb7506 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/service/impl/TAppUserServiceImpl.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/service/impl/TAppUserServiceImpl.java
@@ -8,12 +8,16 @@
 import com.dsh.account.enums.WeeksEnum;
 import com.dsh.account.feignclient.course.CoursePaymentClient;
 import com.dsh.account.feignclient.course.model.CourseOfStoreVo;
+import com.dsh.account.feignclient.course.model.QueryStoreList;
 import com.dsh.account.feignclient.course.model.StuCourseResp;
 import com.dsh.account.feignclient.other.ImgConfigClient;
+import com.dsh.account.feignclient.other.StoreClient;
+import com.dsh.account.feignclient.other.model.Store;
 import com.dsh.account.feignclient.other.model.TImgConfig;
 import com.dsh.account.mapper.TAppUserMapper;
 import com.dsh.account.mapper.TStudentMapper;
 import com.dsh.account.model.AddAppUserVo;
+import com.dsh.account.model.JoinPlayPaiVo;
 import com.dsh.account.model.LoginSMSCodeVo;
 import com.dsh.account.model.LoginWeChatVo;
 import com.dsh.account.model.vo.classDetails.CourseVenue;
@@ -29,6 +33,7 @@
 
 import javax.annotation.Resource;
 import java.util.ArrayList;
+import java.util.Date;
 import java.util.List;
 import java.util.Map;
 import java.util.stream.Collectors;
@@ -45,7 +50,7 @@
 public class TAppUserServiceImpl extends ServiceImpl<TAppUserMapper, TAppUser> implements TAppUserService {
 
 
-    @Autowired
+    @Resource
     private TStudentMapper tsmapper;
 
     @Resource
@@ -63,8 +68,11 @@
     @Autowired
     private JwtTokenUtil jwtTokenUtil;
 
-    @Autowired
+    @Resource
     private CoursePaymentClient paymentClient;
+
+    @Resource
+    private StoreClient storeClient;
 
 
 
@@ -245,6 +253,7 @@
                 tAppUser.setCityCode(cityCode);
             }
         }
+        tAppUser.setInsertTime(new Date());
         this.baseMapper.insert(tAppUser);
         return ResultUtil.success();
     }
@@ -346,6 +355,7 @@
                         tAppUser.setCityCode(cityCode);
                     }
                 }
+                tAppUser.setInsertTime(new Date());
                 this.baseMapper.insert(tAppUser);
             }
         }
@@ -403,4 +413,50 @@
         this.updateById(tAppUser);
         return ResultUtil.success();
     }
+
+
+    /**
+     * 定时任务修改到期会员的状态
+     */
+    @Override
+    public void membershipEnd() {
+        this.baseMapper.membershipEnd();
+    }
+
+
+    /**
+     * 获取加入玩湃首页数据
+     * @param lon
+     * @param lat
+     * @return
+     * @throws Exception
+     */
+    @Override
+    public JoinPlayPaiVo queryJoinPlayPai(Integer uid, String lon, String lat) throws Exception {
+        TAppUser appUser = this.getById(uid);
+        JoinPlayPaiVo joinPlayPaiVo = new JoinPlayPaiVo();
+        joinPlayPaiVo.setIsVip(appUser.getIsVip());
+
+        Map<String, String> geocode = gdMapGeocodingUtil.geocode(lon, lat);
+        if(null != geocode){
+            String provinceCode = geocode.get("provinceCode");
+            String cityCode = geocode.get("cityCode");
+            List<Store> stores = storeClient.queryStoreList(new QueryStoreList(provinceCode, cityCode));
+            Store s = null;
+            Double d = 0D;
+            for (Store store : stores) {
+                Map<String, Double> distance = GeodesyUtil.getDistance(lon + "," + lat, store.getLon() + "," + store.getLat());
+                Double wgs84 = distance.get("WGS84");
+                if(s == null || d.compareTo(wgs84) < 0){
+                    s = store;
+                    d = wgs84;
+                }
+            }
+            joinPlayPaiVo.setName(s.getName());
+            joinPlayPaiVo.setLon(s.getLon());
+            joinPlayPaiVo.setLat(s.getLat());
+            joinPlayPaiVo.setStoreId(s.getId());
+        }
+        return joinPlayPaiVo;
+    }
 }
diff --git a/cloud-server-account/src/main/java/com/dsh/account/service/impl/VipPaymentServiceImpl.java b/cloud-server-account/src/main/java/com/dsh/account/service/impl/VipPaymentServiceImpl.java
new file mode 100644
index 0000000..63232b4
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/service/impl/VipPaymentServiceImpl.java
@@ -0,0 +1,260 @@
+package com.dsh.account.service.impl;
+
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.dsh.account.entity.TAppUser;
+import com.dsh.account.entity.VipPayment;
+import com.dsh.account.mapper.VipPaymentMapper;
+import com.dsh.account.service.IVipPaymentService;
+import com.dsh.account.service.TAppUserService;
+import com.dsh.account.util.PayMoneyUtil;
+import com.dsh.account.util.ResultUtil;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.util.Calendar;
+import java.util.Date;
+import java.util.Map;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 10:03
+ */
+@Service
+public class VipPaymentServiceImpl extends ServiceImpl<VipPaymentMapper, VipPayment> implements IVipPaymentService {
+
+    @Autowired
+    private TAppUserService appUserService;
+
+    @Autowired
+    private PayMoneyUtil payMoneyUtil;
+
+
+
+    /**
+     * 购买年度会员
+     * @param uid
+     * @return
+     * @throws Exception
+     */
+    @Override
+    public ResultUtil addVipPayment(Integer uid, Integer payType) throws Exception {
+        VipPayment vipPayment = new VipPayment();
+        vipPayment.setCode(VipPayment.CODE());
+        vipPayment.setAmount(199D);
+        vipPayment.setAppUserId(uid);
+        vipPayment.setInsertTime(new Date());
+        vipPayment.setPayStatus(1);
+        vipPayment.setState(1);
+        this.baseMapper.insert(vipPayment);
+        if(payType == 1){//微信
+            return weixinpay(vipPayment);
+        }
+        if(payType == 2){//支付宝
+            return alipay(vipPayment);
+        }
+        return ResultUtil.success();
+    }
+
+
+    /**
+     * 微信
+     * @param vipPayment
+     * @return
+     * @throws Exception
+     */
+    public ResultUtil weixinpay(VipPayment vipPayment) throws Exception{
+        String code = vipPayment.getCode();
+        ResultUtil weixinpay = payMoneyUtil.weixinpay("购买年度会员", "", code, vipPayment.getAmount().toString(),
+                "/base/appUser/addVipPaymentWeChatCallback", "APP");
+        if(weixinpay.getCode() == 200){
+            new Thread(new Runnable() {
+                @Override
+                public void run() {
+                    try {
+                        int num = 1;
+                        int wait = 0;
+                        while (num <= 10){
+                            int min = 5000;
+                            wait += (min * num);
+                            VipPayment vipPayment1 = VipPaymentServiceImpl.this.getOne(new QueryWrapper<VipPayment>().eq("code", code));
+                            if(vipPayment1.getPayStatus() != 1){
+                                return;
+                            }
+
+                            /**
+                             * SUCCESS--支付成功
+                             * REFUND--转入退款
+                             * NOTPAY--未支付
+                             * CLOSED--已关闭
+                             * REVOKED--已撤销(刷卡支付)
+                             * USERPAYING--用户支付中
+                             * PAYERROR--支付失败(其他原因,如银行返回失败)
+                             * ACCEPT--已接收,等待扣款
+                             */
+                            ResultUtil<Map<String, String>> resultUtil = payMoneyUtil.queryWXOrder(code, "");
+                            if(resultUtil.getCode() == 200){
+                                Map<String, String> map = resultUtil.getData();
+                                String trade_type = map.get("trade_type");
+                                String trade_state = map.get("trade_state");
+                                String transaction_id = map.get("transaction_id");
+                                if("REFUND".equals(trade_state) || "NOTPAY".equals(trade_state) || "CLOSED".equals(trade_state) || "REVOKED".equals(trade_state) || "PAYERROR".equals(trade_state)){
+                                    vipPayment1.setState(3);
+                                    VipPaymentServiceImpl.this.updateById(vipPayment1);
+                                    return;
+                                }
+                                if("SUCCESS".equals(trade_state)){
+                                    vipPayment1.setPayStatus(2);
+                                    vipPayment1.setPayTime(new Date());
+                                    vipPayment1.setOrderNumber(transaction_id);
+                                    VipPaymentServiceImpl.this.updateById(vipPayment1);
+
+                                    TAppUser appUser = appUserService.getById(vipPayment1.getAppUserId());
+                                    Date vipEndTime = appUser.getVipEndTime();
+                                    if(null == vipEndTime){
+                                        vipEndTime = new Date();
+                                    }
+                                    Calendar calendar = Calendar.getInstance();
+                                    calendar.setTime(vipEndTime);
+                                    calendar.set(Calendar.YEAR, calendar.get(Calendar.YEAR) + 1);
+                                    appUser.setVipEndTime(calendar.getTime());
+                                    appUserService.updateById(appUser);
+                                    return;
+                                }
+                                if("USERPAYING".equals(trade_state) || "ACCEPT".equals(trade_state)){
+                                    Thread.sleep(wait);
+                                    num++;
+                                }
+                            }else{
+                                Thread.sleep(wait);
+                                num++;
+                            }
+                            if(10 == num){
+                                vipPayment1.setState(3);
+                                VipPaymentServiceImpl.this.updateById(vipPayment1);
+                            }
+                        }
+                    }catch (Exception e){
+                        e.printStackTrace();
+                    }
+                }
+            }).start();
+        }
+        return weixinpay;
+    }
+
+
+    /**
+     * 支付宝
+     * @param vipPayment
+     * @return
+     * @throws Exception
+     */
+    public ResultUtil alipay(VipPayment vipPayment) throws Exception{
+        String code = vipPayment.getCode();
+        ResultUtil alipay = payMoneyUtil.alipay("购买年度会员", "", code, vipPayment.getAmount().toString(),
+                "/base/appUser/addVipPaymentAliCallback");
+        if(alipay.getCode() == 200){
+            new Thread(new Runnable() {
+                @Override
+                public void run() {
+                    try {
+                        int num = 1;
+                        int wait = 0;
+                        while (num <= 10){
+                            int min = 5000;
+                            wait += (min * num);
+                            VipPayment vipPayment1 = VipPaymentServiceImpl.this.getOne(new QueryWrapper<VipPayment>().eq("code", code));
+                            if(vipPayment1.getPayStatus() != 1){
+                                return;
+                            }
+
+                            /**
+                             * 交易状态:
+                             * WAIT_BUYER_PAY(交易创建,等待买家付款)、
+                             * TRADE_CLOSED(未付款交易超时关闭,或支付完成后全额退款)、
+                             * TRADE_SUCCESS(交易支付成功)、
+                             * TRADE_FINISHED(交易结束,不可退款)
+                             */
+                            ResultUtil<Map<String, String>> resultUtil = payMoneyUtil.queryALIOrder(code);
+                            if(resultUtil.getCode() == 200){
+                                Map<String, String> map = resultUtil.getData();
+                                String tradeStatus = map.get("tradeStatus");
+                                String tradeNo = map.get("tradeNo");
+                                if("TRADE_CLOSED".equals(tradeStatus) || "TRADE_FINISHED".equals(tradeStatus)){
+                                    vipPayment1.setState(3);
+                                    VipPaymentServiceImpl.this.updateById(vipPayment1);
+                                    return;
+                                }
+                                if("TRADE_SUCCESS".equals(tradeStatus)){
+                                    vipPayment1.setPayStatus(2);
+                                    vipPayment1.setPayTime(new Date());
+                                    vipPayment1.setOrderNumber(tradeNo);
+                                    VipPaymentServiceImpl.this.updateById(vipPayment1);
+
+                                    TAppUser appUser = appUserService.getById(vipPayment1.getAppUserId());
+                                    Date vipEndTime = appUser.getVipEndTime();
+                                    if(null == vipEndTime){
+                                        vipEndTime = new Date();
+                                    }
+                                    Calendar calendar = Calendar.getInstance();
+                                    calendar.setTime(vipEndTime);
+                                    calendar.set(Calendar.YEAR, calendar.get(Calendar.YEAR) + 1);
+                                    appUser.setVipEndTime(calendar.getTime());
+                                    appUserService.updateById(appUser);
+                                    return;
+                                }
+                                if("WAIT_BUYER_PAY".equals(tradeStatus)){
+                                    Thread.sleep(wait);
+                                    num++;
+                                }
+                            }else{
+                                Thread.sleep(wait);
+                                num++;
+                            }
+                            if(10 == num){
+                                vipPayment1.setState(3);
+                                VipPaymentServiceImpl.this.updateById(vipPayment1);
+                            }
+                        }
+                    }catch (Exception e){
+                        e.printStackTrace();
+                    }
+                }
+            }).start();
+        }
+        return alipay;
+    }
+
+
+
+    /**
+     * 购买年度会员支付回调处理
+     * @param code
+     * @param orderNumber
+     * @throws Exception
+     */
+    @Override
+    public ResultUtil addVipPaymentCallback(String code, String orderNumber) throws Exception {
+        VipPayment vipPayment1 = VipPaymentServiceImpl.this.getOne(new QueryWrapper<VipPayment>().eq("code", code));
+        if(vipPayment1.getPayStatus() != 1){
+            return ResultUtil.success();
+        }
+        vipPayment1.setPayStatus(2);
+        vipPayment1.setPayTime(new Date());
+        vipPayment1.setOrderNumber(orderNumber);
+        VipPaymentServiceImpl.this.updateById(vipPayment1);
+
+        TAppUser appUser = appUserService.getById(vipPayment1.getAppUserId());
+        Date vipEndTime = appUser.getVipEndTime();
+        if(null == vipEndTime){
+            vipEndTime = new Date();
+        }
+        Calendar calendar = Calendar.getInstance();
+        calendar.setTime(vipEndTime);
+        calendar.set(Calendar.YEAR, calendar.get(Calendar.YEAR) + 1);
+        appUser.setVipEndTime(calendar.getTime());
+        appUserService.updateById(appUser);
+        return ResultUtil.success();
+    }
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/util/GDMapGeocodingUtil.java b/cloud-server-account/src/main/java/com/dsh/account/util/GDMapGeocodingUtil.java
index 1b136d5..16d9bfb 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/util/GDMapGeocodingUtil.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/util/GDMapGeocodingUtil.java
@@ -21,9 +21,6 @@
 
     private String key = "fb131ad2dbfb3f39d7d37d244b92aa2d";
 
-    @Autowired
-    private HttpClientUtil httpClientUtil;
-
 
     /**
      * 将行政区域名称转化为坐标
@@ -53,12 +50,10 @@
 
         String url = "https://restapi.amap.com/v3/geocode/geo?key=" + key + "&output=JSON";
         url += "&address=" + province + (ToolUtil.isNotEmpty(city) ? city : "") + (ToolUtil.isNotEmpty(county) ? county : "") + (ToolUtil.isNotEmpty(address) ? address : "");
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
         JSONObject jsonObject = JSON.parseObject(httpResult.getData());
         String status = jsonObject.getString("status");
         List<String> list = new ArrayList<>();
-
-//        gdInterfaceService.saveData("https://restapi.amap.com/v3/geocode/geo", "行政区域转经纬度");
 
         if(status.equals("1")){
             JSONArray geocodes = jsonObject.getJSONArray("geocodes");
@@ -77,12 +72,10 @@
     public Map<String, Object> geocoding(String address) throws Exception{
         Map<String, Object> map = new HashMap<>();
         String url = "https://restapi.amap.com/v3/geocode/geo?key=" + key + "&output=JSON&address=" + address;
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
         JSONObject jsonObject = JSON.parseObject(httpResult.getData());
         String status = jsonObject.getString("status");
         List<String> list = new ArrayList<>();
-
-//        gdInterfaceService.saveData("https://restapi.amap.com/v3/geocode/geo", "行政区域转经纬度");
 
         if(status.equals("1")){
             JSONArray geocodes = jsonObject.getJSONArray("geocodes");
@@ -107,11 +100,9 @@
      */
     public Map<String, String> geocode(String lon, String lan) throws Exception{
         String url = "https://restapi.amap.com/v3/geocode/regeo?key=" + key + "&location=" + lon + "," + lan;
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
         JSONObject jsonObject = JSON.parseObject(httpResult.getData());
         Map<String, String> map = new HashMap<>();
-
-//        gdInterfaceService.saveData("https://restapi.amap.com/v3/geocode/regeo", "经纬度转行政区域");
 
         if(jsonObject.getString("status").equals("1")){
             JSONObject regeocode = jsonObject.getJSONObject("regeocode");
@@ -142,7 +133,7 @@
      */
     public Map<String, String> convert(String locations, String coordsys) throws Exception{
         String url = "https://restapi.amap.com/v3/assistant/coordinate/convert?locations=" + locations + "&coordsys=" + coordsys + "&output=json&key=" + key;
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
         JSONObject jsonObject = JSON.parseObject(httpResult.getData());
         Map<String, String> map = new HashMap<>();
         if("1".equals(jsonObject.getString("status"))){
diff --git a/cloud-server-account/src/main/java/com/dsh/account/util/GeodesyUtil.java b/cloud-server-account/src/main/java/com/dsh/account/util/GeodesyUtil.java
new file mode 100644
index 0000000..101d78f
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/util/GeodesyUtil.java
@@ -0,0 +1,63 @@
+package com.dsh.account.util;
+
+import org.gavaghan.geodesy.Ellipsoid;
+import org.gavaghan.geodesy.GeodeticCalculator;
+import org.gavaghan.geodesy.GeodeticCurve;
+import org.gavaghan.geodesy.GlobalCoordinates;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * 计算两个金纬度坐标之间的直线距离
+ */
+public class GeodesyUtil {
+
+
+    /**
+     * 获取直线距离
+     * @param fromLonLat
+     * @param toLonLat
+     * @return
+     */
+    public static Map<String, Double> getDistance(String fromLonLat, String toLonLat){
+        String[] from = fromLonLat.split(",");
+        String[] to = toLonLat.split(",");
+        GlobalCoordinates source = new GlobalCoordinates(Double.valueOf(from[1]), Double.valueOf(from[0]));
+        GlobalCoordinates target = new GlobalCoordinates(Double.valueOf(to[1]), Double.valueOf(to[0]));
+        double Sphere = getDistanceMeter(source, target, Ellipsoid.Sphere);
+        double WGS84 = getDistanceMeter(source, target, Ellipsoid.WGS84);
+        double GRS80 = getDistanceMeter(source, target, Ellipsoid.GRS80);
+        double GRS67 = getDistanceMeter(source, target, Ellipsoid.GRS67);
+        double ANS = getDistanceMeter(source, target, Ellipsoid.ANS);
+        double WGS72 = getDistanceMeter(source, target, Ellipsoid.WGS72);
+        double Clarke1858 = getDistanceMeter(source, target, Ellipsoid.Clarke1858);
+        double Clarke1880 = getDistanceMeter(source, target, Ellipsoid.Clarke1880);
+//        System.out.println("Sphere坐标系计算结果:"+Sphere + "米");
+//        System.out.println("WGS84坐标系计算结果:"+WGS84 + "米");
+//        System.out.println("GRS80坐标系计算结果:"+GRS80 + "米");
+//        System.out.println("GRS67坐标系计算结果:"+GRS67 + "米");
+//        System.out.println("ANS坐标系计算结果:"+ANS + "米");
+//        System.out.println("WGS72坐标系计算结果:"+WGS72 + "米");
+//        System.out.println("Clarke1858坐标系计算结果:"+Clarke1858 + "米");
+//        System.out.println("Clarke1880坐标系计算结果:"+Clarke1880 + "米");
+        Map<String, Double> map = new HashMap<>();
+        map.put("Sphere", Sphere);
+        map.put("WGS84", WGS84);
+        map.put("GRS80", GRS80);
+        map.put("GRS67", GRS67);
+        map.put("ANS", ANS);
+        map.put("WGS72", WGS72);
+        map.put("Clarke1858", Clarke1858);
+        map.put("Clarke1880", Clarke1880);
+        return map;
+    }
+
+
+    private static double getDistanceMeter(GlobalCoordinates gpsFrom, GlobalCoordinates gpsTo, Ellipsoid ellipsoid){
+        //创建GeodeticCalculator,调用计算方法,传入坐标系、经纬度用于计算距离
+        GeodeticCurve geoCurve = new GeodeticCalculator().calculateGeodeticCurve(ellipsoid, gpsFrom, gpsTo);
+        return geoCurve.getEllipsoidalDistance();
+    }
+
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/util/MD5AndKL.java b/cloud-server-account/src/main/java/com/dsh/account/util/MD5AndKL.java
new file mode 100644
index 0000000..29dcf07
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/util/MD5AndKL.java
@@ -0,0 +1,112 @@
+package com.dsh.account.util;
+
+import java.security.MessageDigest;
+
+public class MD5AndKL {
+	
+	/**
+	 * MD5加码。32位
+	 * 
+	 * @param inStr
+	 * @return
+	 */
+	public static String MD5(String inStr) {
+		MessageDigest md5 = null;
+		try {
+			md5 = MessageDigest.getInstance("MD5");
+		} catch (Exception e) {
+			throw new RuntimeException(e.toString());
+		}
+		byte[] md5Bytes = md5.digest(inStr.getBytes());
+		StringBuffer hexValue = new StringBuffer();
+		for (int i = 0; i < md5Bytes.length; i++) {
+			int val = ((int) md5Bytes[i]) & 0xff;
+			if (val < 16) {
+				hexValue.append("0");
+			}
+			hexValue.append(Integer.toHexString(val));
+		}
+		return hexValue.toString();
+	}
+
+	/**
+	 * 可逆的加密算法
+	 * 
+	 * @param inStr
+	 * @return
+	 */
+	public static String KL(String inStr) {
+		char[] a = inStr.toCharArray();
+		for (int i = 0; i < a.length; i++) {
+			a[i] = (char) (a[i] ^ 't');
+		}
+		String s = new String(a);
+		return s;
+	}
+
+	/**
+	 * 加密后解密
+	 * 
+	 * @param inStr
+	 * @return
+	 */
+	public static String JM(String inStr) {
+		char[] a = inStr.toCharArray();
+		for (int i = 0; i < a.length; i++) {
+			a[i] = (char) (a[i] ^ 't');
+		}
+		String k = new String(a);
+		return k;
+	}
+
+
+
+	private static String byteArrayToHexString(byte b[]) {
+		StringBuffer resultSb = new StringBuffer();
+		for (int i = 0; i < b.length; i++)
+			resultSb.append(byteToHexString(b[i]));
+
+		return resultSb.toString();
+	}
+
+	private static String byteToHexString(byte b) {
+		int n = b;
+		if (n < 0)
+			n += 256;
+		int d1 = n / 16;
+		int d2 = n % 16;
+		return hexDigits[d1] + hexDigits[d2];
+	}
+
+	public static String MD5Encode(String origin, String charsetname) {
+		String resultString = null;
+		try {
+			resultString = new String(origin);
+			MessageDigest md = MessageDigest.getInstance("MD5");
+			if (charsetname == null || "".equals(charsetname)){
+				resultString = byteArrayToHexString(md.digest(resultString.getBytes()));
+			}else{
+				resultString = byteArrayToHexString(md.digest(resultString.getBytes(charsetname)));
+			}
+		} catch (Exception exception) {
+			exception.printStackTrace();
+		}
+		return resultString;
+	}
+
+	private static final String hexDigits[] = { "0", "1", "2", "3", "4", "5",
+			"6", "7", "8", "9", "a", "b", "c", "d", "e", "f" };
+
+	public static void main(String args[]) {
+
+		System.out.println("MD5后再加密:" + KL(MD5("123456")));
+		System.out.println(MD5("123456"));
+		// System.out.println("加密:" + KL(MD5("123456")));
+		// s = KL(s);
+		// System.out.println("解密:" + KL("81dc9bdb52d04dc20036dbd8313ed055"));
+		// System.out.println("解密:" + JM(KL(s)));
+		// System.out.println("解密为MD5后的:" + KL(KL(MD5(s))));
+		// System.out.println(JM("5d62957bb57d3e49dcf48a0df064be4c"));
+		// System.out.println(MD5AndKL.KL(MD5AndKL.MD5("admin"+"87654321")));
+	}
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/util/PayMoneyUtil.java b/cloud-server-account/src/main/java/com/dsh/account/util/PayMoneyUtil.java
new file mode 100644
index 0000000..cd7526a
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/util/PayMoneyUtil.java
@@ -0,0 +1,803 @@
+package com.dsh.account.util;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONObject;
+import com.alipay.api.AlipayApiException;
+import com.alipay.api.AlipayClient;
+import com.alipay.api.DefaultAlipayClient;
+import com.alipay.api.domain.AlipayTradeAppPayModel;
+import com.alipay.api.request.AlipayTradeAppPayRequest;
+import com.alipay.api.request.AlipayTradePrecreateRequest;
+import com.alipay.api.request.AlipayTradeQueryRequest;
+import com.alipay.api.request.AlipayTradeRefundRequest;
+import com.alipay.api.response.AlipayTradeAppPayResponse;
+import com.alipay.api.response.AlipayTradePrecreateResponse;
+import com.alipay.api.response.AlipayTradeQueryResponse;
+import com.alipay.api.response.AlipayTradeRefundResponse;
+import com.dsh.account.util.httpClinet.HttpClientUtil;
+import org.apache.commons.collections.map.HashedMap;
+import org.bouncycastle.jce.provider.BouncyCastleProvider;
+import org.dom4j.Document;
+import org.dom4j.DocumentException;
+import org.dom4j.Element;
+import org.dom4j.io.SAXReader;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.http.HttpHeaders;
+import org.springframework.http.MediaType;
+import org.springframework.stereotype.Component;
+
+import javax.crypto.BadPaddingException;
+import javax.crypto.Cipher;
+import javax.crypto.IllegalBlockSizeException;
+import javax.crypto.NoSuchPaddingException;
+import javax.crypto.spec.SecretKeySpec;
+import javax.servlet.http.HttpServletRequest;
+import java.io.*;
+import java.math.BigDecimal;
+import java.net.InetAddress;
+import java.net.UnknownHostException;
+import java.security.*;
+import java.util.*;
+
+/**
+ * 第三方支付工具类
+ */
+@Component
+public class PayMoneyUtil {
+    //支付宝appid
+    private String aliAppid = "";
+    //支付宝开发者应用私钥
+    private String appPrivateKey = "";
+    //支付宝应用公钥
+    private String alipayPublicKey = "";
+    //支付宝支付公钥
+    private String alipay_public_key = "";
+    //微信appid
+    private String appid = "";
+    //微信商户号
+    private String mchId = "";
+    //微信商户号
+    private String key = "";
+    //支付回调网关地址
+    @Value("${callbackPath}")
+    private String callbackPath;
+    //微信支付证书地址
+    private String wechatPayCertificatesFromPath = "/usr/local/server/app/cert/weixin/apiclient_cert.p12";
+    //微信私钥证书地址
+    private String privateKeyFromPath = "/usr/local/server/app/cert/weixin/apiclient_cert.pem";
+
+
+
+
+    /**
+     * 支付宝支付
+     */
+    public ResultUtil<String> alipay(String body, String subject, String outTradeNo, String amount, String notifyUrl){
+        //实例化客户端
+        AlipayClient alipayClient = new DefaultAlipayClient("https://openapi.alipay.com/gateway.do", aliAppid, appPrivateKey, "json", "UTF-8", alipayPublicKey, "RSA2");
+        //实例化具体API对应的request类,类名称和接口名称对应,当前调用接口名称:alipay.trade.app.pay
+        AlipayTradeAppPayRequest request = new AlipayTradeAppPayRequest();
+        //SDK已经封装掉了公共参数,这里只需要传入业务参数。以下方法为sdk的model入参方式(model和biz_content同时存在的情况下取biz_content)。
+        AlipayTradeAppPayModel model = new AlipayTradeAppPayModel();
+        model.setBody(body);//对一笔交易的具体描述信息。如果是多种商品,请将商品描述字符串累加传给body。
+        model.setSubject(subject);//商品的标题/交易标题/订单标题/订单关键字等。
+        model.setOutTradeNo(outTradeNo);//商户网站唯一订单号
+        model.setTimeoutExpress("30m");
+        model.setTotalAmount(amount);//付款金额
+        model.setProductCode("QUICK_MSECURITY_PAY");
+        request.setBizModel(model);
+        request.setNotifyUrl(callbackPath + notifyUrl);
+        try {
+            //这里和普通的接口调用不同,使用的是sdkExecute
+            AlipayTradeAppPayResponse response = alipayClient.sdkExecute(request);
+            System.out.println(response.getBody());//就是orderString 可以直接给客户端请求,无需再做处理。
+            return ResultUtil.success(response.getBody());
+        } catch (AlipayApiException e) {
+            e.printStackTrace();
+            return ResultUtil.error("调起支付异常", "");
+        }
+    }
+
+
+    /**
+     * 支付宝扫码支付下单
+     * @param body
+     * @param subject
+     * @param outTradeNo
+     * @param amount
+     * @param notifyUrl
+     * @return
+     */
+    public ResultUtil aliScanCodePay(String body, String subject, String outTradeNo, String amount, String notifyUrl){
+        AlipayClient alipayClient = new DefaultAlipayClient("https://openapi.alipay.com/gateway.do", aliAppid, appPrivateKey, "json", "UTF-8", alipay_public_key, "RSA2"); //获得初始化的AlipayClient
+        AlipayTradePrecreateRequest request = new AlipayTradePrecreateRequest();//创建API对应的request类
+        request.setBizContent("{" +
+                "    \"out_trade_no\":\"" + outTradeNo + "\"," +//商户订单号
+                "    \"total_amount\":\"" + 1 + "\"," +
+                "    \"subject\":\"" + subject + "\"," +
+                "    \"notify_url\":\"" + callbackPath + notifyUrl + "\"," +
+                "    \"body\":\"" + body + "\"," +
+                "    \"store_id\":\"NJ_001\"," +
+                "    \"timeout_express\":\"90m\"}");//订单允许的最晚付款时间
+        AlipayTradePrecreateResponse response = null;
+        try {
+            response = alipayClient.execute(request);
+        } catch (AlipayApiException e) {
+            e.printStackTrace();
+        }
+        JSONObject alipay_trade_precreate_response = JSON.parseObject(response.getBody()).getJSONObject("alipay_trade_precreate_response");
+
+        System.err.print(alipay_trade_precreate_response.getString("qr_code"));
+        return ResultUtil.success(alipay_trade_precreate_response.getString("qr_code"));
+    }
+
+
+    /**
+     * 支付成功后的回调处理逻辑
+     * @param request
+     */
+    public Map<String, String> alipayCallback(HttpServletRequest request){
+        //获取支付宝POST过来反馈信息
+        Map<String,String> params = new HashMap<String,String>();
+        Map requestParams = request.getParameterMap();
+        for (Iterator iter = requestParams.keySet().iterator(); iter.hasNext();) {
+            String name = (String) iter.next();
+            String[] values = (String[]) requestParams.get(name);
+            String valueStr = "";
+            for (int i = 0; i < values.length; i++) {
+                valueStr = (i == values.length - 1) ? valueStr + values[i]
+                        : valueStr + values[i] + ",";
+            }
+            //乱码解决,这段代码在出现乱码时使用。
+            //valueStr = new String(valueStr.getBytes("ISO-8859-1"), "utf-8");
+            params.put(name, valueStr);
+        }
+        //切记alipaypublickey是支付宝的公钥,请去open.alipay.com对应应用下查看。
+        //boolean AlipaySignature.rsaCheckV1(Map<String, String> params, String publicKey, String charset, String sign_type)
+//        try {
+//            boolean flag = AlipaySignature.rsaCheckV1(params, alipayPublicKey, "UTF-8","RSA2");
+//            if(flag){
+                Map<String, String> map = new HashMap<>();
+                String out_trade_no = params.get("out_trade_no");
+                String subject = params.get("subject");
+                String total_amount = params.get("total_amount");
+                String trade_no = params.get("trade_no");
+                map.put("out_trade_no", out_trade_no);//商家订单号
+                map.put("subject", subject);
+                map.put("total_amount", total_amount);
+                map.put("trade_no", trade_no);//支付宝交易号
+                return map;
+//            }
+
+//        } catch (AlipayApiException e) {
+//            e.printStackTrace();
+//        }
+//        return null;
+    }
+
+
+    /**
+     * 支付宝查询订单支付状态
+     * @param out_trade_no
+     * @return
+     * @throws Exception
+     */
+    public ResultUtil<Map<String, String>> queryALIOrder(String out_trade_no) throws Exception{
+        AlipayClient alipayClient = new DefaultAlipayClient("https://openapi.alipay.com/gateway.do",aliAppid, appPrivateKey,"json","UTF-8", alipay_public_key,"RSA2");
+        AlipayTradeQueryRequest request = new AlipayTradeQueryRequest();
+        request.setBizContent("{" +
+                "\"out_trade_no\":\"" + out_trade_no +
+                "\"}");
+        AlipayTradeQueryResponse response = alipayClient.execute(request);
+        if(response.isSuccess()){
+            String tradeStatus = response.getTradeStatus();//交易状态:WAIT_BUYER_PAY(交易创建,等待买家付款)、TRADE_CLOSED(未付款交易超时关闭,或支付完成后全额退款)、TRADE_SUCCESS(交易支付成功)、TRADE_FINISHED(交易结束,不可退款)
+            String tradeNo = response.getTradeNo();
+            Map<String, String> map = new HashMap<>();
+            map.put("tradeStatus", tradeStatus);
+            map.put("tradeNo", tradeNo);
+            return ResultUtil.success(map);
+        } else {
+            return ResultUtil.error(response.getMsg());
+        }
+    }
+
+
+
+    /**
+     * 微信统一下单
+     * @param body          商品描述
+     * @param attach        附加数据
+     * @param out_trade_no  商户订单号
+     * @param total_fee     标价金额
+     * @param notify_url    通知地址
+     * @param tradeType     交易类型
+     * @return
+     */
+    public ResultUtil weixinpay(String body, String attach, String out_trade_no, String total_fee, String notify_url, String tradeType) throws Exception{
+        int i = new BigDecimal(total_fee).multiply(new BigDecimal("100")).intValue();
+        String hostAddress = null;
+        try {
+            hostAddress = InetAddress.getLocalHost().getHostAddress();
+        } catch (UnknownHostException e) {
+            e.printStackTrace();
+        }
+        String nonce_str = UUIDUtil.getRandomCode(16);
+        Map<String, Object> map = new HashMap<>();
+        map.put("appid", appid);
+        map.put("mch_id", mchId);
+        map.put("nonce_str", nonce_str);
+        map.put("body", body);
+        map.put("attach", attach);//存储订单id
+        map.put("out_trade_no", out_trade_no);//存储的订单code
+        map.put("total_fee", i);
+        map.put("spbill_create_ip", hostAddress);
+        map.put("notify_url", callbackPath + notify_url);
+        map.put("trade_type", tradeType);
+        String s = this.weixinSignature(map);
+        map.put("sign", s);
+
+        String url = "https://api.mch.weixin.qq.com/pay/unifiedorder";
+        //设置请求头
+        HttpHeaders headers = new HttpHeaders();
+        headers.setContentType(MediaType.APPLICATION_XML);
+        StringBuffer xmlString = new StringBuffer();
+        Set<String> strings = map.keySet();
+        String[] keys = {};
+        keys = strings.toArray(keys);
+        Arrays.sort(keys);
+        xmlString.append("<xml>");
+        for(int l = 0; l < keys.length; l++){
+            xmlString.append("<" + keys[l] + ">" + map.get(keys[l]) + "</" + keys[l] + ">");
+        }
+        xmlString.append("</xml>");
+
+        Map<String, String> map1 = null;
+        String body1 = HttpClientUtil.pushHttpRequsetXml(url, xmlString.toString(), new HashMap<>()).getData();
+        //将结果xml解析成map
+        body1 = body1.replaceAll("<!\\[CDATA\\[","");
+        body1 = body1.replaceAll("]]>", "");
+        try {
+            map1 = this.xmlToMap(body1, "UTF-8");
+        } catch (UnsupportedEncodingException e) {
+            e.printStackTrace();
+        } catch (DocumentException e) {
+            e.printStackTrace();
+        }
+        String return_code = map1.get("return_code");
+        if("SUCCESS".equals(return_code)){
+            String result_code = map1.get("result_code");
+            if("SUCCESS".equals(result_code)){
+                String type = map1.get("trade_type");
+                switch (type){
+                    case "JSAPI":
+                        break;
+                    case "NATIVE":
+                        String code_url = map1.get("code_url");
+                        return ResultUtil.success(code_url);
+                    case "APP":
+                        String prepay_id = map1.get("prepay_id");
+                        //重新进行签名后返回给前端
+                        Map<String, Object> map2 = new HashMap<>();
+                        map2.put("appid", appid);
+                        map2.put("noncestr", nonce_str);
+                        map2.put("package", "Sign=WXPay");
+                        map2.put("partnerid", mchId);
+                        map2.put("prepayid", prepay_id);
+                        map2.put("timestamp", new Date().getTime() / 1000);
+                        String s1 = this.weixinSignature(map2);
+                        map2.put("sign", s1);
+                        System.err.println(map2);
+                        return ResultUtil.success(map2);
+                }
+                return null;
+            }else{
+                System.err.println(map1.get("err_code_des"));
+                return ResultUtil.error(map1.get("err_code_des"));
+            }
+        }else{
+            System.err.println(map1.get("return_msg") + appid + "----" + mchId);
+            return ResultUtil.error(map1.get("return_msg"), new JSONObject());
+        }
+    }
+
+
+
+
+
+    /**
+     * 微信支付成功后的回调处理
+     * @param request
+     */
+    public Map<String, String> weixinpayCallback(HttpServletRequest request){
+        try {
+            String param = this.getParam(request);
+            param = param.replaceAll("<!\\[CDATA\\[","");
+            param = param.replaceAll("]]>", "");
+            Map<String, String> map = this.xmlToMap(param, "UTF-8");
+            String return_code = map.get("return_code");
+            if("SUCCESS".equals(return_code)){
+                String result_code = map.get("result_code");
+                if("SUCCESS".equals(result_code)){
+                    Map<String, String> map1 = new HashedMap();
+                    map1.put("nonce_str", map.get("nonce_str"));
+                    map1.put("out_trade_no", map.get("out_trade_no"));
+                    map1.put("attach", map.get("attach"));
+                    map1.put("total_fee", map.get("total_fee"));
+                    map1.put("transaction_id", map.get("transaction_id"));//微信支付订单号
+                    String result = "<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>";
+                    map1.put("result", result);
+                    return map1;
+                }else{
+                    System.err.println(map.get("err_code_des"));
+                }
+            }else{
+                System.err.println(map.get("return_msg"));
+            }
+        } catch (IOException e) {
+            e.printStackTrace();
+        } catch (DocumentException e) {
+            e.printStackTrace();
+        }
+        return null;
+    }
+
+
+    /**
+     * 微信扫码收款
+     * @param body              商品描述
+     * @param attach            附加数据
+     * @param nonce_str         随机字符串
+     * @param out_trade_no      商户订单号
+     * @param total_fee         订单金额
+     * @param auth_code         授权码	扫码支付授权码,设备读取用户微信中的条码或者二维码信息(注:用户付款码条形码规则:18位纯数字,以10、11、12、13、14、15开头)
+     * @return
+     */
+    public ResultUtil wxScanQRCodePay(String body, String attach, String nonce_str, String out_trade_no, String total_fee, String auth_code){
+        int i = new BigDecimal(total_fee).multiply(new BigDecimal("100")).intValue();
+        String hostAddress = null;
+        try {
+            InetAddress address = InetAddress.getLocalHost();
+            hostAddress = address.getHostAddress();
+        } catch (UnknownHostException e) {
+            e.printStackTrace();
+        }
+        String randomCode = null;
+        try {
+            randomCode = UUIDUtil.getRandomCode(10);
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+        Map<String, Object> map = new HashMap<>();
+        map.put("appid", appid);
+        map.put("mch_id", mchId);
+        map.put("nonce_str", nonce_str);//存储的支付人员id,员工扫描二维码支付的时候存储的是收款员工id
+        map.put("body", body);
+        map.put("attach", attach);//存储的费用月份数据,员工扫描二维码支付的时候存储的是收费项id
+        map.put("out_trade_no", randomCode + "_" + out_trade_no);//存储的房间id
+        map.put("total_fee", i);
+        map.put("spbill_create_ip", hostAddress);
+        map.put("auth_code", auth_code);
+        String s = this.weixinSignature(map);
+        map.put("sign", s);
+
+        String url = "https://api.mch.weixin.qq.com/pay/unifiedorder";
+        //设置请求头
+        HttpHeaders headers = new HttpHeaders();
+        headers.setContentType(MediaType.APPLICATION_XML);
+        StringBuffer xmlString = new StringBuffer();
+        Set<String> strings = map.keySet();
+        String[] keys = {};
+        keys = strings.toArray(keys);
+        Arrays.sort(keys);
+        xmlString.append("<xml>");
+        for(int l = 0; l < keys.length; l++){
+            xmlString.append("<" + keys[l] + ">" + map.get(keys[l]) + "</" + keys[l] + ">");
+        }
+        xmlString.append("</xml>");
+
+        Map<String, String> map1 = null;
+        String body1 = null;
+        try {
+            body1 = HttpClientUtil.pushHttpRequsetXml(url, xmlString.toString(), new HashMap<>()).getData();
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+        //将结果xml解析成map
+        body1 = body1.replaceAll("<!\\[CDATA\\[","");
+        body1 = body1.replaceAll("]]>", "");
+        try {
+            map1 = this.xmlToMap(body1, "UTF-8");
+        } catch (UnsupportedEncodingException e) {
+            e.printStackTrace();
+        } catch (DocumentException e) {
+            e.printStackTrace();
+        }
+        String return_code = map1.get("return_code");
+        if("SUCCESS".equals(return_code)){
+            String result_code = map1.get("result_code");
+            if("SUCCESS".equals(result_code)){
+                String type = map1.get("trade_type");
+                switch (type){
+                    case "JSAPI":
+                        break;
+                    case "NATIVE":
+                        String code_url = map1.get("code_url");
+                        return ResultUtil.success(code_url);
+                    case "APP":
+                        String prepay_id = map1.get("prepay_id");
+                        //重新进行签名后返回给前端
+                        Map<String, Object> map2 = new HashMap<>();
+                        map2.put("appid", appid);
+                        map2.put("noncestr", nonce_str);
+                        map2.put("package", "Sign=WXPay");
+                        map2.put("partnerid", mchId);
+                        map2.put("prepayid", prepay_id);
+                        map2.put("timestamp", new Date().getTime() + "");
+                        String s1 = this.weixinSignature(map2);
+
+                        map2.put("pac", "Sign=WXPay");
+                        map2.put("sign", s1);
+//                      System.err.println(map2);
+                        return ResultUtil.success(map2);
+                }
+                return null;
+            }else{
+//                System.err.println(map1.get("err_code_des"));
+                return ResultUtil.error(map1.get("err_code_des"));
+            }
+        }else{
+//            System.err.println(map1.get("return_msg") + appid + "----" + mchId);
+            return ResultUtil.error(map1.get("return_msg"), new JSONObject());
+        }
+    }
+
+
+    /**
+     * 支付宝扫码收款
+     * @param data
+     * @return
+     */
+    public Object aliScanQRCodePay(String data){
+        return null;
+    }
+
+
+    /**
+     * 微信退款申请
+     * @param transaction_id    微信订单号。微信生成的订单号,在支付通知中有返回
+     * @param out_refund_no     商户退款单号。商户系统内部的退款单号,商户系统内部唯一,只能是数字、大小写字母_-|*@ ,同一退款单号多次请求只退一笔。
+     * @param total_fee         订单金额。订单总金额,单位为分,只能为整数
+     * @param refund_fee        退款金额。退款总金额,订单总金额,单位为分,只能为整数
+     * @param notify_url        退款结果通知url。异步接收微信支付退款结果通知的回调地址,通知URL必须为外网可访问的url,不允许带参数 如果参数中传了notify_url,则商户平台上配置的回调地址将不会生效。
+     * @return
+     */
+    public Map<String, String> wxRefund(String transaction_id, String out_refund_no, String total_fee, String refund_fee, String notify_url){
+        int tf = new BigDecimal(total_fee).multiply(new BigDecimal("100")).intValue();
+        int rf = new BigDecimal(refund_fee).multiply(new BigDecimal("100")).intValue();
+        String nonce_str = UUIDUtil.getRandomCode();
+        Map<String, Object> map = new HashMap<>();
+        map.put("appid", appid);
+        map.put("mch_id", mchId);
+        map.put("nonce_str", nonce_str);
+        map.put("transaction_id", transaction_id);
+        map.put("out_refund_no", out_refund_no);
+        map.put("total_fee", tf);
+        map.put("refund_fee", rf);
+        map.put("notify_url", callbackPath + notify_url);
+        String s = this.weixinSignature(map);
+        map.put("sign", s);
+
+        String url = "https://api.mch.weixin.qq.com/secapi/pay/refund";
+        //设置请求头
+        HttpHeaders headers = new HttpHeaders();
+        headers.setContentType(MediaType.APPLICATION_XML);
+        StringBuffer xmlString = new StringBuffer();
+        Set<String> strings = map.keySet();
+        String[] keys = {};
+        keys = strings.toArray(keys);
+        Arrays.sort(keys);
+        xmlString.append("<xml>");
+        for(int l = 0; l < keys.length; l++){
+            xmlString.append("<" + keys[l] + ">" + map.get(keys[l]) + "</" + keys[l] + ">");
+        }
+        xmlString.append("</xml>");
+
+        Map<String, String> map1 = null;
+        String body1 = null;
+        try {
+            body1 = HttpClientUtil.pushHttpRequsetXml(url, xmlString.toString(), new HashMap<>()).getData();
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+        //将结果xml解析成map
+        body1 = body1.replaceAll("<!\\[CDATA\\[","");
+        body1 = body1.replaceAll("]]>", "");
+        try {
+            map1 = this.xmlToMap(body1, "UTF-8");
+        } catch (UnsupportedEncodingException e) {
+            e.printStackTrace();
+        } catch (DocumentException e) {
+            e.printStackTrace();
+        }
+        String return_code = map1.get("return_code");
+        Map<String, String> map2 = new HashMap<>();
+        if("SUCCESS".equals(return_code)){
+            String result_code = map1.get("result_code");
+            if("SUCCESS".equals(result_code)){
+                map2.put("return_code", result_code);
+                map2.put("refund_id", String.valueOf(map1.get("refund_id")));//微信退款订单号
+                map2.put("refund_fee", String.valueOf(map1.get("refund_fee")));//退款金额
+                return map2;
+            }else{
+                map2.put("return_code", result_code);
+                map2.put("return_msg", map1.get("err_code_des"));
+                return map2;
+            }
+        }else{
+            map2.put("return_code", return_code);
+            map2.put("return_msg", map1.get("return_msg"));
+            return map2;
+        }
+    }
+
+
+    /**
+     * 微信退款成功后的回调处理
+     * @param request
+     * @return
+     */
+    public Map<String, String> wxRefundCallback(HttpServletRequest request){
+        try {
+            String param = this.getParam(request);
+            param = param.replaceAll("<!\\[CDATA\\[","");
+            param = param.replaceAll("]]>", "");
+            Map<String, String> map = this.xmlToMap(param, "UTF-8");
+            String return_code = map.get("return_code");
+            if("SUCCESS".equals(return_code)){
+                String req_info = map.get("req_info");//加密信息请用商户秘钥进行解密
+                String s = this.wxDecrypt(req_info);
+                s = s.replaceAll("<!\\[CDATA\\[","");
+                s = s.replaceAll("]]>", "");
+                map = this.xmlToMap(s, "UTF-8");
+                Map<String, String> map1 = new HashMap<>();
+                map1.put("refund_id", map.get("refund_id"));
+                map1.put("out_refund_no", map.get("out_refund_no"));
+                return map1;
+            }else{
+//                System.err.println(map.get("return_msg"));
+            }
+        } catch (IOException e) {
+            e.printStackTrace();
+        } catch (DocumentException e) {
+            e.printStackTrace();
+        } catch (NoSuchAlgorithmException e) {
+            e.printStackTrace();
+        } catch (InvalidKeyException e) {
+            e.printStackTrace();
+        } catch (NoSuchPaddingException e) {
+            e.printStackTrace();
+        } catch (BadPaddingException e) {
+            e.printStackTrace();
+        } catch (NoSuchProviderException e) {
+            e.printStackTrace();
+        } catch (IllegalBlockSizeException e) {
+            e.printStackTrace();
+        }
+        return null;
+    }
+
+
+    /**
+     * 支付宝退款
+     * @param trade_no          支付宝交易号
+     * @param refund_amount     退款金额
+     * @return
+     * @throws AlipayApiException
+     */
+    public Map<String, String> aliRefund(String trade_no, String refund_amount) throws AlipayApiException {
+        AlipayClient alipayClient = new DefaultAlipayClient("https://openapi.alipay.com/gateway.do", aliAppid, appPrivateKey,"json","UTF-8", alipay_public_key,"RSA2");
+        AlipayTradeRefundRequest request = new AlipayTradeRefundRequest();
+        JSONObject jsonObject = new JSONObject();
+        jsonObject.put("trade_no", trade_no);
+        jsonObject.put("refund_amount", refund_amount);
+        request.setBizContent(jsonObject.toJSONString());
+        AlipayTradeRefundResponse response = alipayClient.execute(request);
+        Map<String, String> map = new HashMap<>();
+        if(response.isSuccess()){
+            System.out.println("调用成功");
+            String outTradeNo = response.getOutTradeNo();
+            map.put("code", response.getCode());//10000
+            map.put("trade_no", response.getTradeNo());//支付宝交易号
+            map.put("out_trade_no", outTradeNo);//商户订单号
+        } else {
+            System.out.println("调用失败");
+            map.put("code", response.getCode());
+            map.put("msg", response.getSubMsg());
+        }
+        return map;
+    }
+
+
+    /**
+     * 查询微信支付订单
+     * @return
+     * @throws Exception
+     */
+    public ResultUtil<Map<String, String>> queryWXOrder(String out_trade_no, String transaction_id) throws Exception{
+        String url = "https://api.mch.weixin.qq.com/pay/orderquery";
+        String nonce_str = UUIDUtil.getRandomCode(16);
+        Map<String, Object> map = new HashMap<>();
+        map.put("appid", appid);
+        map.put("mch_id", mchId);
+        map.put("out_trade_no", out_trade_no);//商户订单号
+        map.put("transaction_id", transaction_id);//微信订单号
+        map.put("nonce_str", nonce_str);//随机字符串
+        String s = this.weixinSignature(map);
+        map.put("sign", s);
+
+        //设置请求头
+        HttpHeaders headers = new HttpHeaders();
+        headers.setContentType(MediaType.APPLICATION_XML);
+        StringBuffer xmlString = new StringBuffer();
+        Set<String> strings = map.keySet();
+        String[] keys = {};
+        keys = strings.toArray(keys);
+        Arrays.sort(keys);
+        xmlString.append("<xml>");
+        for(int l = 0; l < keys.length; l++){
+            xmlString.append("<" + keys[l] + ">" + map.get(keys[l]) + "</" + keys[l] + ">");
+        }
+        xmlString.append("</xml>");
+
+        Map<String, String> map1 = null;
+        String body1 = HttpClientUtil.pushHttpRequsetXml(url, xmlString.toString(), new HashMap<>()).getData();
+        //将结果xml解析成map
+        body1 = body1.replaceAll("<!\\[CDATA\\[","");
+        body1 = body1.replaceAll("]]>", "");
+        try {
+            map1 = this.xmlToMap(body1, "UTF-8");
+        } catch (UnsupportedEncodingException e) {
+            e.printStackTrace();
+        } catch (DocumentException e) {
+            e.printStackTrace();
+        }
+        String return_code = map1.get("return_code");
+        if("SUCCESS".equals(return_code)){
+            String result_code = map1.get("result_code");
+            if("SUCCESS".equals(result_code)){
+                Map<String, String> map2 = new HashMap<>();
+                map2.put("trade_type", map1.get("trade_type"));
+                map2.put("trade_state", map1.get("trade_state"));//订单状态SUCCESS—支付成功,REFUND—转入退款,NOTPAY—未支付,CLOSED—已关闭,REVOKED—已撤销(刷卡支付),USERPAYING--用户支付中,PAYERROR--支付失败(其他原因,如银行返回失败)
+                map2.put("transaction_id", map1.get("transaction_id"));
+                return ResultUtil.success(map2);
+            }else{
+                System.err.println(map1.get("err_code_des"));
+                return ResultUtil.error(map1.get("err_code_des"));
+            }
+        }else{
+            System.err.println(map1.get("return_msg") + appid + "----" + mchId);
+            return ResultUtil.error(map1.get("return_msg"));
+        }
+    }
+
+
+
+
+    /**
+     * 获取请求内容
+     * @param request
+     * @return
+     * @throws IOException
+     */
+    private String getParam(HttpServletRequest request) throws IOException {
+        // 读取参数
+        InputStream inputStream;
+        StringBuilder sb = new StringBuilder();
+        inputStream = request.getInputStream();
+        String s;
+        BufferedReader in = new BufferedReader(new InputStreamReader(inputStream, "UTF-8"));
+        while ((s = in.readLine()) != null) {
+            sb.append(s);
+        }
+        in.close();
+        inputStream.close();
+        return sb.toString();
+    }
+
+
+    /**
+     * 微信下单的签名算法
+     * @param map
+     * @return
+     */
+    private String weixinSignature(Map<String, Object> map){
+        try {
+            Set<Map.Entry<String, Object>> entries = map.entrySet();
+            List<Map.Entry<String, Object>> infoIds = new ArrayList<Map.Entry<String, Object>>(entries);
+            // 对所有传入参数按照字段名的 ASCII 码从小到大排序(字典序)
+            Collections.sort(infoIds, new Comparator<Map.Entry<String, Object>>() {
+                public int compare(Map.Entry<String, Object> o1, Map.Entry<String, Object> o2) {
+                    return (o1.getKey()).toString().compareTo(o2.getKey());
+                }
+            });
+            // 构造签名键值对的格式
+            StringBuilder sb = new StringBuilder();
+            for (Map.Entry<String, Object> item : infoIds) {
+                if (item.getKey() != null || item.getKey() != "") {
+                    String key = item.getKey();
+                    Object val = item.getValue();
+                    if (!(val == "" || val == null)) {
+                        sb.append(key + "=" + val + "&");
+                    }
+                }
+            }
+            sb.append("key=" + key);
+            String sign = MD5AndKL.MD5Encode(sb.toString(), "UTF-8").toUpperCase(); //注:MD5签名方式
+            return sign;
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+        return null;
+    }
+
+
+
+    /**
+     * 微信退款成功后的解密
+     * @param req_info
+     * @return
+     */
+    private String wxDecrypt(String req_info) throws NoSuchPaddingException, NoSuchAlgorithmException, NoSuchProviderException,
+            InvalidKeyException, BadPaddingException, IllegalBlockSizeException {
+        byte[] decode = Base64.getDecoder().decode(req_info);
+        String sign = MD5AndKL.MD5Encode(key, "UTF-8").toLowerCase();
+        if (Security.getProvider("BC") == null){
+            Security.addProvider(new BouncyCastleProvider());
+        }
+        Cipher cipher = Cipher.getInstance("AES/ECB/PKCS7Padding", "BC");
+        SecretKeySpec secretKeySpec = new SecretKeySpec(sign.getBytes(), "AES");
+        cipher.init(Cipher.DECRYPT_MODE, secretKeySpec);
+        return new String(cipher.doFinal(decode));
+    }
+
+
+    public static void main(String[] ages){
+//        PayMoneyUtil payMoneyUtil = new PayMoneyUtil();
+//        payMoneyUtil.weixinpay("测试", "123", "12.5", "");
+    }
+
+
+    /**
+     * xml转map
+     * @param xml
+     * @param charset
+     * @return
+     * @throws UnsupportedEncodingException
+     * @throws DocumentException
+     */
+    public static Map<String, String> xmlToMap(String xml, String charset) throws UnsupportedEncodingException, DocumentException {
+
+        Map<String, String> respMap = new HashMap<String, String>();
+
+        SAXReader reader = new SAXReader();
+        Document doc = reader.read(new ByteArrayInputStream(xml.getBytes(charset)));
+        Element root = doc.getRootElement();
+        xmlToMap(root, respMap);
+        return respMap;
+    }
+
+    public static Map<String, String> xmlToMap(Element tmpElement, Map<String, String> respMap){
+        if (tmpElement.isTextOnly()) {
+            respMap.put(tmpElement.getName(), tmpElement.getText());
+            return respMap;
+        }
+
+        @SuppressWarnings("unchecked")
+        Iterator<Element> eItor = tmpElement.elementIterator();
+        while (eItor.hasNext()) {
+            Element element = eItor.next();
+            xmlToMap(element, respMap);
+        }
+        return respMap;
+    }
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/util/ResultUtil.java b/cloud-server-account/src/main/java/com/dsh/account/util/ResultUtil.java
index 4feea5c..289ff54 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/util/ResultUtil.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/util/ResultUtil.java
@@ -107,8 +107,8 @@
      * 参数异常
      * @return
      */
-    public static  ResultUtil paranErr(){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", new JSONObject());
+    public static  ResultUtil paranErr(String ages){
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "【" + ages + "】参数异常", new JSONObject());
     }
 
     /**
@@ -116,11 +116,10 @@
      * @return
      */
     public static <T> ResultUtil<T> paranErr(T data){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "SYSTEM_RUN_ERROR", data);
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", data);
     }
 
-    @Autowired
-    private static MessageUtils messageUtils;
+
     /**
      * 运行异常
      * @return
diff --git a/cloud-server-account/src/main/java/com/dsh/account/util/TaskUtil.java b/cloud-server-account/src/main/java/com/dsh/account/util/TaskUtil.java
new file mode 100644
index 0000000..5538b41
--- /dev/null
+++ b/cloud-server-account/src/main/java/com/dsh/account/util/TaskUtil.java
@@ -0,0 +1,43 @@
+package com.dsh.account.util;
+
+import com.dsh.account.entity.TAppUser;
+import com.dsh.account.service.TAppUserService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.scheduling.annotation.Scheduled;
+import org.springframework.stereotype.Component;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 15:26
+ */
+@Component
+public class TaskUtil {
+
+    @Autowired
+    private TAppUserService appUserService;
+
+
+    /**
+     * 每隔一分钟去处理的定时任务
+     */
+    @Scheduled(fixedRate = 1000 * 60)
+    public void taskMinute(){
+        try {
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+    }
+
+
+    /**
+     * 每天的凌晨执行的任务
+     */
+    @Scheduled(cron = "0 0 0 * * *")
+    public void taskDay(){
+        try {
+            appUserService.membershipEnd();
+        }catch (Exception e){
+            e.printStackTrace();
+        }
+    }
+}
diff --git a/cloud-server-account/src/main/java/com/dsh/account/util/TokenUtil.java b/cloud-server-account/src/main/java/com/dsh/account/util/TokenUtil.java
index 113a990..5397637 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/util/TokenUtil.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/util/TokenUtil.java
@@ -2,6 +2,8 @@
 
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Component;
+import org.springframework.web.context.request.RequestContextHolder;
+import org.springframework.web.context.request.ServletRequestAttributes;
 
 import javax.servlet.http.HttpServletRequest;
 
@@ -12,7 +14,9 @@
     private RedisUtil redisUtil;
 
 
-    public Integer getUserIdFormRedis(HttpServletRequest request) throws Exception {
+    public Integer getUserIdFormRedis() {
+        ServletRequestAttributes servletRequestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
+        HttpServletRequest request = servletRequestAttributes.getRequest();
         String requestHeader = request.getHeader("Authorization");
         if (requestHeader != null && requestHeader.startsWith("Bearer ")) {
             requestHeader = requestHeader.substring(requestHeader.indexOf(" ") + 1);
diff --git a/cloud-server-account/src/main/java/com/dsh/account/util/httpClinet/HttpClientUtil.java b/cloud-server-account/src/main/java/com/dsh/account/util/httpClinet/HttpClientUtil.java
index 2237d7c..78738b7 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/util/httpClinet/HttpClientUtil.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/util/httpClinet/HttpClientUtil.java
@@ -1,6 +1,7 @@
 package com.dsh.account.util.httpClinet;
 
 import com.alibaba.fastjson.JSON;
+import com.dsh.account.util.httpClinet.HttpResult;
 import com.fasterxml.jackson.databind.ObjectMapper;
 import org.apache.http.NameValuePair;
 import org.apache.http.client.config.RequestConfig;
@@ -19,7 +20,6 @@
 import org.apache.http.util.EntityUtils;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
-import org.springframework.stereotype.Component;
 
 import javax.net.ssl.SSLContext;
 import java.io.File;
@@ -34,15 +34,14 @@
 /**
  * http工具类
  */
-@Component
 public class HttpClientUtil {
 
     private static Logger logger = LoggerFactory.getLogger(HttpClientUtil.class);
 
-    private PoolingHttpClientConnectionManager connectionManager;
+    private static PoolingHttpClientConnectionManager connectionManager;
 
 
-    public HttpClientUtil(){
+    {
         //1.创建连接池管理器
         connectionManager = new PoolingHttpClientConnectionManager(60000,
                 TimeUnit.MILLISECONDS);
@@ -53,14 +52,14 @@
     /**
      * 创建一个httpClient对象
      */
-    private CloseableHttpClient getHttpCline(){
+    private static CloseableHttpClient getHttpCline(){
         return  HttpClients.custom()
                 .setConnectionManager(connectionManager)
                 .disableAutomaticRetries()
                 .build();
     }
 
-    private RequestConfig getRequestConfig(){
+    private static RequestConfig getRequestConfig(){
         RequestConfig.Builder builder = RequestConfig.custom();
         builder.setSocketTimeout(60000)//3.1设置客户端等待服务端返回数据的超时时间
                 .setConnectTimeout(30000)//3.2设置客户端发起TCP连接请求的超时时间
@@ -76,9 +75,9 @@
      * @param url       请求地址
      * @param params    请求参数
      */
-    private CloseableHttpResponse setPostHttpRequset(String url, Map<String, Object> params, Map<String, String> header, String contentType) throws Exception{
+    private static CloseableHttpResponse setPostHttpRequset(String url, Map<String, Object> params, Map<String, String> header, String contentType) throws Exception{
         HttpPost httpPost = new HttpPost(url);
-        httpPost.setConfig(this.getRequestConfig());
+        httpPost.setConfig(getRequestConfig());
         if(null != header){
             for(String key : header.keySet()){
                 httpPost.setHeader(key, header.get(key));
@@ -110,7 +109,7 @@
      * @param url       请求地址
      * @param params    请求参数
      */
-    private CloseableHttpResponse setGetHttpRequset(String url, Map<String, Object> params, Map<String, String> header) throws Exception{
+    private static CloseableHttpResponse setGetHttpRequset(String url, Map<String, Object> params, Map<String, String> header) throws Exception{
         StringBuffer sb = new StringBuffer();
         String p = "";
         if(null != params){
@@ -140,14 +139,14 @@
      * @param contentType   参数请求方式form/json
      * @return
      */
-    public HttpResult pushHttpRequset(String mothed, String url, Map<String, Object> params, Map<String, String> header, String contentType) throws Exception{
+    public static HttpResult pushHttpRequset(String mothed, String url, Map<String, Object> params, Map<String, String> header, String contentType) throws Exception{
         String randome = UUID.randomUUID().toString();
         SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.S");
         logger.info(sdf.format(new Date()) + "----(" + randome + ")请求参数:" + JSON.toJSONString(params));
         CloseableHttpResponse httpResponse = null;
         switch (mothed){
             case "GET":
-                httpResponse = this.setGetHttpRequset(url, params, header);
+                httpResponse = setGetHttpRequset(url, params, header);
                 break;
             case "POST":
                 httpResponse = setPostHttpRequset(url, params, header, contentType);
@@ -157,7 +156,7 @@
         String content = EntityUtils.toString(httpResponse.getEntity(), "UTF-8");
         logger.info(sdf.format(new Date()) + "----(" + randome + ")返回结果:" + content);
         HttpResult httpResult = HttpResult.getHttpResult(statusCode, content);
-        this.close(httpResponse);
+        close(httpResponse);
         return httpResult;
     }
 
@@ -169,7 +168,7 @@
      * @param header    自定义请求头
      * @return
      */
-    public HttpResult pushHttpRequsetXml(String url, String xml, Map<String, String> header) throws Exception{
+    public static HttpResult pushHttpRequsetXml(String url, String xml, Map<String, String> header) throws Exception{
         HttpPost httpPost = new HttpPost(url);
         httpPost.setConfig(getRequestConfig());
         for(String key : header.keySet()){
@@ -181,7 +180,7 @@
         int statusCode = httpResponse.getStatusLine().getStatusCode();
         String content = EntityUtils.toString(httpResponse.getEntity(), "UTF-8");
         HttpResult httpResult = HttpResult.getHttpResult(statusCode, content);
-        this.close(httpResponse);
+        close(httpResponse);
         return httpResult;
     }
 
@@ -246,7 +245,7 @@
     /**
      * 关闭资源
      */
-    private void close(CloseableHttpResponse httpResponse){
+    private static void close(CloseableHttpResponse httpResponse){
         try {
             if(null != httpResponse){
                 EntityUtils.consume(httpResponse.getEntity());//此处高能,通过源码分析,由EntityUtils是否回收HttpEntity
diff --git a/cloud-server-account/src/main/java/com/dsh/account/util/weChat/WeChatUtil.java b/cloud-server-account/src/main/java/com/dsh/account/util/weChat/WeChatUtil.java
index 858642c..4c7d129 100644
--- a/cloud-server-account/src/main/java/com/dsh/account/util/weChat/WeChatUtil.java
+++ b/cloud-server-account/src/main/java/com/dsh/account/util/weChat/WeChatUtil.java
@@ -45,9 +45,6 @@
     private String webAppSecret;
 
     @Autowired
-    private HttpClientUtil httpClientUtil;
-
-    @Autowired
     private RestTemplate restTemplate;
 
 
@@ -59,7 +56,7 @@
     public Map<String, Object> code2Session(String jscode) throws Exception{
         String url = "https://api.weixin.qq.com/sns/jscode2session?appid=" + wxAppletsAppid + "&secret=" + wxAppletsAppSecret
                 + "&js_code=" + jscode + "&grant_type=authorization_code";
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "form");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "form");
         if(null == httpResult || httpResult.getCode() != 200){
             return null;
         }
@@ -95,7 +92,7 @@
      */
     public String getWxAppletsAccessToken() throws Exception{
         String url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=" + wxAppletsAppid + "&secret=" + wxAppletsAppSecret;
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "form");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "form");
         if(httpResult.getCode() != 200){
             return "";
         }
@@ -111,7 +108,7 @@
      */
     public Map<String, String> webAccessToken(String code) throws Exception{
         String url = "https://api.weixin.qq.com/sns/oauth2/access_token?appid=" + webAppId + "&secret=" + webAppSecret + "&code=" + code + "&grant_type=authorization_code";
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "form");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "form");
         if(httpResult.getCode() != 200){
             return null;
         }
@@ -149,7 +146,7 @@
      */
     public Map<String, Object> getUserInfo(String access_token, String openid) throws Exception{
         String url = "https://api.weixin.qq.com/sns/userinfo?access_token=" + access_token + "&openid=" + openid;
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "form");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "form");
         if(httpResult.getCode() != 200){
             return null;
         }
@@ -191,7 +188,7 @@
         String grantType = "authorization_code";
         String params = "appid=" + officialAccountAppid + "&secret=" + officialAccountAppSecret + "&code=" + code + "&grant_type=" + grantType;
         System.out.println("sssss"+params);
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", "https://api.weixin.qq.com/sns/oauth2/access_token?" + params, null, null, "form");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", "https://api.weixin.qq.com/sns/oauth2/access_token?" + params, null, null, "form");
         if(httpResult.getCode() != 200){
             return null;
         }
@@ -220,7 +217,7 @@
     public String getAccessToken() throws Exception{
         String url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=" + officialAccountAppid
                 + "&secret=" + officialAccountAppSecret;
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "form");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "form");
         if(httpResult.getCode() != 200){
             return null;
         }
@@ -237,7 +234,7 @@
         //获取token
         String acess_token= this.getAccessToken();
         String urlStr = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token=" + acess_token + "&type=jsapi";
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", urlStr, null, null, "form");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", urlStr, null, null, "form");
         if(httpResult.getCode() != 200){
             return null;
         }
@@ -280,7 +277,7 @@
      */
     public Map<String, Object> queryUserInfo(String access_token, String openid) throws Exception{
         String url = "https://api.weixin.qq.com/sns/userinfo?access_token=" + access_token + "&openid=" + openid + "&lang=zh_CN";
-        HttpResult httpResult = httpClientUtil.pushHttpRequset("GET", url, null, null, "form");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "form");
         if(httpResult.getCode() != 200){
             return null;
         }
diff --git a/cloud-server-account/src/main/resources/mapper/TAppUserMapper.xml b/cloud-server-account/src/main/resources/mapper/TAppUserMapper.xml
index 1277a14..e253b64 100644
--- a/cloud-server-account/src/main/resources/mapper/TAppUserMapper.xml
+++ b/cloud-server-account/src/main/resources/mapper/TAppUserMapper.xml
@@ -31,4 +31,9 @@
         <result column="headImg" property="headImg" />
     </resultMap>
 
+
+
+    <update id="membershipEnd">
+        update t_app_user set isVip = 0 where isVip = 1 and now() >= vipEndTime
+    </update>
 </mapper>
diff --git a/cloud-server-account/src/main/resources/mapper/VipPaymentMapper.tld b/cloud-server-account/src/main/resources/mapper/VipPaymentMapper.tld
new file mode 100644
index 0000000..0fb4b33
--- /dev/null
+++ b/cloud-server-account/src/main/resources/mapper/VipPaymentMapper.tld
@@ -0,0 +1,20 @@
+<?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.dsh.account.mapper.VipPaymentMapper">
+
+    <!-- 通用查询映射结果 -->
+    <resultMap id="BaseResultMap" type="com.dsh.account.entity.VipPayment">
+        <id column="id" property="id" />
+        <result column="code" property="code" />
+        <result column="appUserId" property="appUserId" />
+        <result column="amount" property="amount" />
+        <result column="payType" property="payType" />
+        <result column="payStatus" property="payStatus" />
+        <result column="payTime" property="payTime" />
+        <result column="orderNumber" property="orderNumber" />
+        <result column="state" property="state" />
+        <result column="insertTime" property="insertTime" />
+        <result column="isDefault" property="isDefault" />
+    </resultMap>
+
+</mapper>
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/controller/CouponController.java b/cloud-server-activity/src/main/java/com/dsh/activity/controller/CouponController.java
new file mode 100644
index 0000000..dcf1887
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/controller/CouponController.java
@@ -0,0 +1,55 @@
+package com.dsh.activity.controller;
+
+import com.dsh.activity.model.CouponListVo;
+import com.dsh.activity.service.ICouponService;
+import com.dsh.activity.util.ResultUtil;
+import com.dsh.activity.util.TokenUtil;
+import io.swagger.annotations.ApiImplicitParam;
+import io.swagger.annotations.ApiImplicitParams;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 11:27
+ */
+@RestController
+@RequestMapping("")
+public class CouponController {
+
+    @Autowired
+    private ICouponService couponService;
+
+    @Autowired
+    private TokenUtil tokenUtil;
+
+
+
+
+    @ResponseBody
+    @PostMapping("/api/coupon/queryCouponList")
+    @ApiOperation(value = "获取优惠券列表", tags = {"APP-成为会员", ""})
+    @ApiImplicitParams({
+            @ApiImplicitParam(value = "1=积分购买,2=注册赠送", name = "distributionMethod", dataType = "int", required = true),
+            @ApiImplicitParam(name = "Authorization", value = "用户token(Bearer +token)", required = true, dataType = "String", paramType = "header", defaultValue = "Bearer eyJhbGciOiJIUzUxMiJ9.....")
+    })
+    public ResultUtil queryCouponList(@RequestBody Integer distributionMethod){
+        if(null == distributionMethod){
+            return ResultUtil.paranErr("distributionMethod");
+        }
+        try {
+            Integer uid = tokenUtil.getUserIdFormRedis();
+            if(null == uid){
+                return ResultUtil.tokenErr();
+            }
+            List<CouponListVo> listVos = couponService.queryCouponList(uid, distributionMethod);
+            return ResultUtil.success(listVos);
+        }catch (Exception e){
+            e.printStackTrace();
+            return ResultUtil.success();
+        }
+    }
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/entity/Coupon.java b/cloud-server-activity/src/main/java/com/dsh/activity/entity/Coupon.java
new file mode 100644
index 0000000..d25f545
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/entity/Coupon.java
@@ -0,0 +1,144 @@
+package com.dsh.activity.entity;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import java.util.Date;
+
+/**
+ * 优惠券
+ * @author zhibing.pu
+ * @date 2023/6/24 11:04
+ */
+@Data
+@TableName("t_coupon")
+public class Coupon {
+    /**
+     * 主键
+     */
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+    /**
+     * 优惠券名称
+     */
+    @TableField("name")
+    private String name;
+    /**
+     * 优惠券类型(1=满减券,2=代金券,3=体验券)
+     */
+    @TableField("type")
+    private Integer type;
+    /**
+     * 优惠券规则JSON
+     */
+    @TableField("content")
+    private String content;
+    /**
+     * 优惠券说明
+     */
+    @TableField("illustrate")
+    private String illustrate;
+    /**
+     * 发放方式(1=积分购买,2=注册赠送,3=自动发券)
+     */
+    @TableField("distributionMethod")
+    private Integer distributionMethod;
+    /**
+     * 兑换方式(1=积分,2=积分+现金)
+     */
+    @TableField("redemptionMethod")
+    private Integer redemptionMethod;
+    /**
+     * 所需现金
+     */
+    @TableField("cash")
+    private Double cash;
+    /**
+     * 所需积分
+     */
+    @TableField("integral")
+    private Integer integral;
+    /**
+     * 用户人群(1=全部用户,2=年度会员,3=已有学员用户)
+     */
+    @TableField("userPopulation")
+    private Integer userPopulation;
+    /**
+     * 发放数量
+     */
+    @TableField("quantityIssued")
+    private Integer quantityIssued;
+    /**
+     * 限领数量
+     */
+    @TableField("pickUpQuantity")
+    private Integer pickUpQuantity;
+    /**
+     * 开始时间
+     */
+    @TableField("startTime")
+    private Date startTime;
+    /**
+     * 结束时间
+     */
+    @TableField("endTime")
+    private Date endTime;
+    /**
+     * 使用范围(1=全国,2=指定城市,3=指定门店)
+     */
+    @TableField("useScope")
+    private Integer useScope;
+    /**
+     * 省
+     */
+    @TableField("province")
+    private Integer province;
+    /**
+     * 省编号
+     */
+    @TableField("provinceCode")
+    private String provinceCode;
+    /**
+     * 市
+     */
+    @TableField("city")
+    private String city;
+    /**
+     * 市编号
+     */
+    @TableField("cityCode")
+    private String cityCode;
+    /**
+     * 审核状态(1=待审核,2=已通过,3=已拒绝)
+     */
+    @TableField("auditStatus")
+    private Integer auditStatus;
+    /**
+     * 审核人id
+     */
+    @TableField("auditUserId")
+    private Integer auditUserId;
+    /**
+     * 审核备注
+     */
+    @TableField("auditRemark")
+    private String auditRemark;
+    /**
+     * 状态(1=未开始,2=已开始,3=已结束,4=已取消)
+     */
+    @TableField("status")
+    private Integer status;
+    /**
+     * 状态(1=正常,2=冻结,3=删除)
+     */
+    @TableField("state")
+    private Integer state;
+    /**
+     * 添加时间
+     */
+    @TableField("insertTime")
+    private Date insertTime;
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/AppUserClient.java b/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/AppUserClient.java
new file mode 100644
index 0000000..f0ff7d7
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/AppUserClient.java
@@ -0,0 +1,22 @@
+package com.dsh.activity.feginClient.account;
+
+import com.dsh.activity.feginClient.account.model.AppUser;
+import org.springframework.cloud.openfeign.FeignClient;
+import org.springframework.web.bind.annotation.PostMapping;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 14:50
+ */
+@FeignClient("mb-cloud-account")
+public interface AppUserClient {
+
+
+    /**
+     * 根据用户id获取用户信息
+     * @param appUserId
+     * @return
+     */
+    @PostMapping("/base/appUser/queryAppUser")
+    AppUser queryAppUser(Integer appUserId);
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/StudentClient.java b/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/StudentClient.java
new file mode 100644
index 0000000..1ac20a9
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/StudentClient.java
@@ -0,0 +1,24 @@
+package com.dsh.activity.feginClient.account;
+
+import com.dsh.activity.feginClient.account.model.Student;
+import org.springframework.cloud.openfeign.FeignClient;
+import org.springframework.web.bind.annotation.PostMapping;
+
+import java.util.List;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 15:02
+ */
+@FeignClient("mb-cloud-account")
+public interface StudentClient {
+
+
+    /**
+     * 获取用户学员列表
+     * @param appUserId
+     * @return
+     */
+    @PostMapping("/student/queryStudentList")
+    List<Student> queryStudentList(Integer appUserId);
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/model/AppUser.java b/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/model/AppUser.java
new file mode 100644
index 0000000..e358646
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/model/AppUser.java
@@ -0,0 +1,114 @@
+package com.dsh.activity.feginClient.account.model;
+
+import lombok.Data;
+
+import java.util.Date;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 14:51
+ */
+@Data
+public class AppUser {
+    private Integer id;
+    /**
+     * 编号
+     */
+    private String code;
+    /**
+     * 姓名
+     */
+    private String name;
+    /**
+     * 电话
+     */
+    private String phone;
+    /**
+     * 密码
+     */
+    private String password;
+    /**
+     * 生日
+     */
+    private Date birthday;
+    /**
+     * 性别(1=男,2=女)
+     */
+    private Integer gender;
+    /**
+     * 身高
+     */
+    private Double height;
+    /**
+     * 体重
+     */
+    private Double weight;
+    /**
+     * bmi健康值
+     */
+    private Double bmi;
+    /**
+     * 身份证号
+     */
+    private String idCard;
+    /**
+     * 微信openid
+     */
+    private String openid;
+    /**
+     * 省
+     */
+    private String province;
+    /**
+     * 省编号
+     */
+    private String provinceCode;
+    /**
+     * 市
+     */
+    private String city;
+    /**
+     * 市编号
+     */
+    private String cityCode;
+    /**
+     * 是否是年度会员(0=否,1=是)
+     */
+    private Integer isVip;
+    /**
+     * 会员有效期
+     */
+    private Date vipEndTime;
+    /**
+     * 会员等级id
+     */
+    private Integer viplevelId;
+    /**
+     * 推荐用户id
+     */
+    private Integer referralUserId;
+    /**
+     * 销售员id
+     */
+    private Integer salesmanUserId;
+    /**
+     * 状态(1=正常,2=冻结,3=删除)
+     */
+    private Integer state;
+    /**
+     * 剩余积分
+     */
+    private Integer integral;
+    /**
+     * 玩湃币
+     */
+    private Integer playPaiCoins;
+    /**
+     * 用户头像
+     */
+    private String headImg;
+    /**
+     * 添加时间
+     */
+    private Date insertTime;
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/model/Student.java b/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/model/Student.java
new file mode 100644
index 0000000..fa891cd
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/feginClient/account/model/Student.java
@@ -0,0 +1,70 @@
+package com.dsh.activity.feginClient.account.model;
+
+import lombok.Data;
+
+import java.util.Date;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 15:02
+ */
+@Data
+public class Student {
+    private Integer id;
+    /**
+     * 用户id
+     */
+    private Integer appUserId;
+    /**
+     * 学员姓名
+     */
+    private String name;
+    /**
+     * 学员电话
+     */
+    private String phone;
+    /**
+     * 生日
+     */
+    private Date birthday;
+    /**
+     * 性别(1=男,2=女)
+     */
+    private Integer sex;
+    /**
+     * 身高
+     */
+    private Double height;
+    /**
+     * 体重
+     */
+    private Double weight;
+    /**
+     * bmi健康值
+     */
+    private Double bmi;
+    /**
+     * 身份证号
+     */
+    private String idCard;
+    /**
+     * 体侧表
+     */
+    private String lateralSurface;
+    /**
+     * 状态(1=正常,2=冻结,3=删除)
+     */
+    private Integer state;
+    /**
+     * 添加时间
+     */
+    private Date insertTime;
+    /**
+     * 头像
+     */
+    private String headImg;
+    /**
+     * 是否默认 1默认 2不是默认
+     */
+    private Integer isDefault;
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/mapper/CouponMapper.java b/cloud-server-activity/src/main/java/com/dsh/activity/mapper/CouponMapper.java
new file mode 100644
index 0000000..518fb49
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/mapper/CouponMapper.java
@@ -0,0 +1,11 @@
+package com.dsh.activity.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.dsh.activity.entity.Coupon;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 11:22
+ */
+public interface CouponMapper extends BaseMapper<Coupon> {
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/model/CouponListVo.java b/cloud-server-activity/src/main/java/com/dsh/activity/model/CouponListVo.java
new file mode 100644
index 0000000..882772a
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/model/CouponListVo.java
@@ -0,0 +1,26 @@
+package com.dsh.activity.model;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 11:33
+ */
+@Data
+@ApiModel
+public class CouponListVo {
+    @ApiModelProperty("优惠券id")
+    private Integer id;
+    @ApiModelProperty("优惠券名称")
+    private String name;
+    @ApiModelProperty("优惠券类型(1=满减券,2=代金券,3=体验券)")
+    private Integer type;
+    @ApiModelProperty("使用条件")
+    private String useCondition;
+    @ApiModelProperty("优惠内容")
+    private String favorable;
+    @ApiModelProperty("有效时间")
+    private String effectiveTime;
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/service/ICouponService.java b/cloud-server-activity/src/main/java/com/dsh/activity/service/ICouponService.java
new file mode 100644
index 0000000..970ef48
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/service/ICouponService.java
@@ -0,0 +1,23 @@
+package com.dsh.activity.service;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.dsh.activity.entity.Coupon;
+import com.dsh.activity.model.CouponListVo;
+
+import java.util.List;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 11:26
+ */
+public interface ICouponService extends IService<Coupon>{
+
+
+    /**
+     * 获取购买会员支付成功页面的优惠券
+     * @param uid
+     * @return
+     * @throws Exception
+     */
+    List<CouponListVo> queryCouponList(Integer uid, Integer distributionMethod) throws Exception;
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/service/impl/CouponServiceImpl.java b/cloud-server-activity/src/main/java/com/dsh/activity/service/impl/CouponServiceImpl.java
new file mode 100644
index 0000000..294b9ab
--- /dev/null
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/service/impl/CouponServiceImpl.java
@@ -0,0 +1,92 @@
+package com.dsh.activity.service.impl;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONObject;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.dsh.activity.entity.Coupon;
+import com.dsh.activity.feginClient.account.AppUserClient;
+import com.dsh.activity.feginClient.account.StudentClient;
+import com.dsh.activity.feginClient.account.model.AppUser;
+import com.dsh.activity.feginClient.account.model.Student;
+import com.dsh.activity.mapper.CouponMapper;
+import com.dsh.activity.model.CouponListVo;
+import com.dsh.activity.service.ICouponService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import javax.annotation.Resource;
+import java.text.SimpleDateFormat;
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 11:26
+ */
+@Service
+public class CouponServiceImpl extends ServiceImpl<CouponMapper, Coupon> implements ICouponService {
+
+    @Resource
+    private AppUserClient appUserClient;
+
+    @Resource
+    private StudentClient studentClient;
+
+
+
+
+
+
+    /**
+     * 获取购买会员支付成功页面的优惠券
+     * @param uid
+     * @return
+     * @throws Exception
+     */
+    @Override
+    public List<CouponListVo> queryCouponList(Integer uid, Integer distributionMethod) throws Exception {
+        AppUser appUser = appUserClient.queryAppUser(uid);
+        List<CouponListVo> listVos = new ArrayList<>();
+        if(null != appUser){
+            List<Integer> userPopulation = new ArrayList<>();
+            userPopulation.add(1);//全部用户
+            if(1 == appUser.getIsVip()){
+                userPopulation.add(2);//年度会员
+            }
+            List<Student> students = studentClient.queryStudentList(uid);
+            if(students.size() > 0){
+                userPopulation.add(3);//已有学员用户
+            }
+            List<Coupon> list = this.list(new QueryWrapper<Coupon>().eq("distributionMethod", distributionMethod).in("userPopulation", userPopulation)
+                    .eq("auditStatus", 2).eq("status", 2).eq("state", 1)
+                    .last(" and now() between startTime and endTime").orderByDesc("insertTime"));
+            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
+            for (Coupon coupon : list) {
+                CouponListVo couponListVo = new CouponListVo();
+                couponListVo.setId(coupon.getId());
+                couponListVo.setName(coupon.getName());
+                couponListVo.setType(coupon.getType());
+                couponListVo.setEffectiveTime(sdf.format(coupon.getStartTime()) + "-" + sdf.format(coupon.getEndTime()));
+                String content = coupon.getContent();
+                if(coupon.getType() == 1){//满减{"num1":1,"num2":1}
+                    JSONObject jsonObject = JSON.parseObject(content);
+                    couponListVo.setUseCondition("满" + jsonObject.getDouble("num1") + "元可用");
+                    couponListVo.setFavorable(jsonObject.getDouble("num2") + "元");
+                }
+                if(coupon.getType() == 2){//满减{"num1":1}
+                    JSONObject jsonObject = JSON.parseObject(content);
+                    couponListVo.setUseCondition("");
+                    couponListVo.setFavorable(jsonObject.getDouble("num1") + "元");
+                }
+                if(coupon.getType() == 3){//体验券{"num1":1}
+                    JSONObject jsonObject = JSON.parseObject(content);
+                    couponListVo.setUseCondition("");
+                    couponListVo.setFavorable(jsonObject.getString("num1"));
+                }
+                listVos.add(couponListVo);
+            }
+        }
+        return listVos;
+    }
+}
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/util/ResultUtil.java b/cloud-server-activity/src/main/java/com/dsh/activity/util/ResultUtil.java
index 44d0c91..e627936 100644
--- a/cloud-server-activity/src/main/java/com/dsh/activity/util/ResultUtil.java
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/util/ResultUtil.java
@@ -3,7 +3,6 @@
 import com.alibaba.fastjson.JSONObject;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
-import org.springframework.beans.factory.annotation.Autowired;
 
 /**
  * 定义统一返回对象
@@ -107,8 +106,8 @@
      * 参数异常
      * @return
      */
-    public static  ResultUtil paranErr(){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", new JSONObject());
+    public static  ResultUtil paranErr(String ages){
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "【" + ages + "】参数异常", new JSONObject());
     }
 
     /**
@@ -116,11 +115,10 @@
      * @return
      */
     public static <T> ResultUtil<T> paranErr(T data){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "SYSTEM_RUN_ERROR", data);
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", data);
     }
 
-    @Autowired
-    private static MessageUtils messageUtils;
+
     /**
      * 运行异常
      * @return
diff --git a/cloud-server-activity/src/main/java/com/dsh/activity/util/TokenUtil.java b/cloud-server-activity/src/main/java/com/dsh/activity/util/TokenUtil.java
index a3a9866..c954aeb 100644
--- a/cloud-server-activity/src/main/java/com/dsh/activity/util/TokenUtil.java
+++ b/cloud-server-activity/src/main/java/com/dsh/activity/util/TokenUtil.java
@@ -2,6 +2,8 @@
 
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Component;
+import org.springframework.web.context.request.RequestContextHolder;
+import org.springframework.web.context.request.ServletRequestAttributes;
 
 import javax.servlet.http.HttpServletRequest;
 
@@ -12,7 +14,9 @@
     private RedisUtil redisUtil;
 
 
-    public Integer getUserIdFormRedis(HttpServletRequest request) throws Exception {
+    public Integer getUserIdFormRedis() throws Exception {
+        ServletRequestAttributes servletRequestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
+        HttpServletRequest request = servletRequestAttributes.getRequest();
         String requestHeader = request.getHeader("Authorization");
         if (requestHeader != null && requestHeader.startsWith("Bearer ")) {
             requestHeader = requestHeader.substring(requestHeader.indexOf(" ") + 1);
diff --git a/cloud-server-activity/src/main/resources/mapper/CouponMapper.tld b/cloud-server-activity/src/main/resources/mapper/CouponMapper.tld
new file mode 100644
index 0000000..54e765b
--- /dev/null
+++ b/cloud-server-activity/src/main/resources/mapper/CouponMapper.tld
@@ -0,0 +1,34 @@
+<?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.dsh.activity.mapper.CouponMapper">
+
+    <!-- 通用查询映射结果 -->
+    <resultMap id="BaseResultMap" type="com.dsh.activity.entity.Coupon">
+        <id column="id" property="id" />
+        <result column="name" property="name" />
+        <result column="type" property="type" />
+        <result column="content" property="content" />
+        <result column="illustrate" property="illustrate" />
+        <result column="distributionMethod" property="distributionMethod" />
+        <result column="redemptionMethod" property="redemptionMethod" />
+        <result column="cash" property="cash" />
+        <result column="integral" property="integral" />
+        <result column="userPopulation" property="userPopulation" />
+        <result column="quantityIssued" property="quantityIssued" />
+        <result column="pickUpQuantity" property="pickUpQuantity" />
+        <result column="startTime" property="startTime" />
+        <result column="endTime" property="endTime" />
+        <result column="useScope" property="useScope" />
+        <result column="province" property="province" />
+        <result column="provinceCode" property="provinceCode" />
+        <result column="city" property="city" />
+        <result column="cityCode" property="cityCode" />
+        <result column="auditStatus" property="auditStatus" />
+        <result column="auditUserId" property="auditUserId" />
+        <result column="auditRemark" property="auditRemark" />
+        <result column="status" property="status" />
+        <result column="state" property="state" />
+        <result column="insertTime" property="insertTime" />
+    </resultMap>
+
+</mapper>
diff --git a/cloud-server-competition/src/main/java/com/dsh/competition/util/ResultUtil.java b/cloud-server-competition/src/main/java/com/dsh/competition/util/ResultUtil.java
index 13d8eb8..9bb46ad 100644
--- a/cloud-server-competition/src/main/java/com/dsh/competition/util/ResultUtil.java
+++ b/cloud-server-competition/src/main/java/com/dsh/competition/util/ResultUtil.java
@@ -3,7 +3,6 @@
 import com.alibaba.fastjson.JSONObject;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
-import org.springframework.beans.factory.annotation.Autowired;
 
 /**
  * 定义统一返回对象
@@ -107,8 +106,8 @@
      * 参数异常
      * @return
      */
-    public static  ResultUtil paranErr(){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", new JSONObject());
+    public static  ResultUtil paranErr(String ages){
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "【" + ages + "】参数异常", new JSONObject());
     }
 
     /**
@@ -116,11 +115,10 @@
      * @return
      */
     public static <T> ResultUtil<T> paranErr(T data){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "SYSTEM_RUN_ERROR", data);
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", data);
     }
 
-    @Autowired
-    private static MessageUtils messageUtils;
+
     /**
      * 运行异常
      * @return
diff --git a/cloud-server-competition/src/main/java/com/dsh/competition/util/TokenUtil.java b/cloud-server-competition/src/main/java/com/dsh/competition/util/TokenUtil.java
index b86182f..a5ebf2d 100644
--- a/cloud-server-competition/src/main/java/com/dsh/competition/util/TokenUtil.java
+++ b/cloud-server-competition/src/main/java/com/dsh/competition/util/TokenUtil.java
@@ -2,6 +2,8 @@
 
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Component;
+import org.springframework.web.context.request.RequestContextHolder;
+import org.springframework.web.context.request.ServletRequestAttributes;
 
 import javax.servlet.http.HttpServletRequest;
 
@@ -12,7 +14,9 @@
     private RedisUtil redisUtil;
 
 
-    public Integer getUserIdFormRedis(HttpServletRequest request) throws Exception {
+    public Integer getUserIdFormRedis() throws Exception {
+        ServletRequestAttributes servletRequestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
+        HttpServletRequest request = servletRequestAttributes.getRequest();
         String requestHeader = request.getHeader("Authorization");
         if (requestHeader != null && requestHeader.startsWith("Bearer ")) {
             requestHeader = requestHeader.substring(requestHeader.indexOf(" ") + 1);
diff --git a/cloud-server-course/pom.xml b/cloud-server-course/pom.xml
index 583402e..2ba631f 100644
--- a/cloud-server-course/pom.xml
+++ b/cloud-server-course/pom.xml
@@ -95,6 +95,25 @@
             <artifactId>swagger-models</artifactId>
             <version>1.5.22</version>
         </dependency>
+        <dependency>
+            <groupId>org.apache.httpcomponents</groupId>
+            <artifactId>httpclient</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>commons-httpclient</groupId>
+            <artifactId>commons-httpclient</artifactId>
+            <version>3.1</version>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.httpcomponents</groupId>
+            <artifactId>httpmime</artifactId>
+            <version>4.5.2</version>
+        </dependency>
+        <dependency>
+            <groupId>org.gavaghan</groupId>
+            <artifactId>geodesy</artifactId>
+            <version>1.1.3</version>
+        </dependency>
     </dependencies>
 
     <build>
diff --git a/cloud-server-course/src/main/java/com/dsh/course/controller/CourseController.java b/cloud-server-course/src/main/java/com/dsh/course/controller/CourseController.java
index 57b99b2..076c79f 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/controller/CourseController.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/controller/CourseController.java
@@ -3,16 +3,25 @@
 
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.dsh.course.entity.TCourse;
+import com.dsh.course.entity.TCoursePackageType;
 import com.dsh.course.feignclient.model.ExerciseVideo;
+import com.dsh.course.model.BaseVo;
+import com.dsh.course.model.CoursePackageList;
+import com.dsh.course.model.CoursePackageListVo;
+import com.dsh.course.service.TCoursePackageService;
+import com.dsh.course.service.TCoursePackageTypeService;
 import com.dsh.course.service.TCourseService;
+import com.dsh.course.util.ResultUtil;
+import com.dsh.course.util.TokenUtil;
 import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiImplicitParam;
+import io.swagger.annotations.ApiImplicitParams;
+import io.swagger.annotations.ApiOperation;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
+import org.springframework.beans.BeanUtils;
 import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.web.bind.annotation.CrossOrigin;
-import org.springframework.web.bind.annotation.PostMapping;
-import org.springframework.web.bind.annotation.RequestMapping;
-import org.springframework.web.bind.annotation.RestController;
+import org.springframework.web.bind.annotation.*;
 
 import java.util.ArrayList;
 import java.util.List;
@@ -27,6 +36,19 @@
 
     @Autowired
     private TCourseService courseService;
+
+    @Autowired
+    private TCoursePackageService coursePackageService;
+
+    @Autowired
+    private TokenUtil tokenUtil;
+
+    @Autowired
+    private TCoursePackageTypeService coursePackageTypeService;
+
+
+
+
 
 
     @PostMapping("/course/queryList")
@@ -47,4 +69,54 @@
         return videos;
     }
 
+
+    @ResponseBody
+    @PostMapping("/api/course/queryCoursePackageType")
+    @ApiOperation(value = "获取课程类型列表", tags = {"APP-加入玩湃"})
+    @ApiImplicitParams({
+    })
+    public ResultUtil<List<BaseVo>> queryCoursePackageType(){
+        try {
+            List<TCoursePackageType> coursePackageTypes = coursePackageTypeService.list(new QueryWrapper<TCoursePackageType>().eq("state", 1));
+            List<BaseVo> list = new ArrayList<>();
+            coursePackageTypes.forEach(c -> {
+                BaseVo baseVo = new BaseVo();
+                BeanUtils.copyProperties(c, baseVo);
+                list.add(baseVo);
+            });
+            return ResultUtil.success(list);
+        }catch (Exception e){
+            e.printStackTrace();
+            return ResultUtil.runErr();
+        }
+    }
+
+
+
+
+
+    @ResponseBody
+    @PostMapping("/api/course/queryCourseList")
+    @ApiOperation(value = "获取课程列表", tags = {"APP-加入玩湃"})
+    @ApiImplicitParams({
+            @ApiImplicitParam(name = "Authorization", value = "用户token(Bearer +token)", required = true, dataType = "String", paramType = "header", defaultValue = "Bearer eyJhbGciOiJIUzUxMiJ9.....")
+    })
+    public ResultUtil<List<CoursePackageListVo>> queryCourseList(@RequestBody CoursePackageList coursePackageList){
+        try {
+            Integer uid = tokenUtil.getUserIdFormRedis();
+            if(null == uid){
+                return ResultUtil.tokenErr();
+            }
+            List<CoursePackageListVo> coursePackageListVos = coursePackageService.queryCourseList(uid, coursePackageList);
+            return ResultUtil.success(coursePackageListVos);
+        }catch (Exception e){
+            e.printStackTrace();
+            return ResultUtil.runErr();
+        }
+    }
+
+
+
+
+
 }
diff --git a/cloud-server-course/src/main/java/com/dsh/course/entity/CoursePackagePaymentConfig.java b/cloud-server-course/src/main/java/com/dsh/course/entity/CoursePackagePaymentConfig.java
new file mode 100644
index 0000000..6200eec
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/entity/CoursePackagePaymentConfig.java
@@ -0,0 +1,46 @@
+package com.dsh.course.entity;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/29 10:42
+ */
+@Data
+@TableName("t_course_package_payment_config")
+public class CoursePackagePaymentConfig {
+    /**
+     * 主键
+     */
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+    /**
+     * 课包id
+     */
+    @TableField("coursePackageId")
+    private Integer coursePackageId;
+    /**
+     * 支付方式(1=现金,2=玩湃币)
+     */
+    @TableField("payType")
+    private Integer payType;
+    /**
+     * 课时数
+     */
+    @TableField("classHours")
+    private Integer classHours;
+    /**
+     * 现金支付价格
+     */
+    @TableField("cashPayment")
+    private Double cashPayment;
+    /**
+     * 玩湃币价格
+     */
+    @TableField("playPaiCoin")
+    private Integer playPaiCoin;
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/feignclient/account/AppUserClient.java b/cloud-server-course/src/main/java/com/dsh/course/feignclient/account/AppUserClient.java
new file mode 100644
index 0000000..9b037e6
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/feignclient/account/AppUserClient.java
@@ -0,0 +1,21 @@
+package com.dsh.course.feignclient.account;
+
+import com.dsh.course.feignclient.account.model.AppUser;
+import org.springframework.cloud.openfeign.FeignClient;
+import org.springframework.web.bind.annotation.PostMapping;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/29 14:09
+ */
+@FeignClient("mb-cloud-account")
+public interface AppUserClient {
+
+    /**
+     * 根据用户id获取用户信息
+     * @param appUserId
+     * @return
+     */
+    @PostMapping("/base/appUser/queryAppUser")
+    AppUser queryAppUser(Integer appUserId);
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/feignclient/account/model/AppUser.java b/cloud-server-course/src/main/java/com/dsh/course/feignclient/account/model/AppUser.java
new file mode 100644
index 0000000..11a8024
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/feignclient/account/model/AppUser.java
@@ -0,0 +1,114 @@
+package com.dsh.course.feignclient.account.model;
+
+import lombok.Data;
+
+import java.util.Date;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/29 14:09
+ */
+@Data
+public class AppUser {
+    private Integer id;
+    /**
+     * 编号
+     */
+    private String code;
+    /**
+     * 姓名
+     */
+    private String name;
+    /**
+     * 电话
+     */
+    private String phone;
+    /**
+     * 密码
+     */
+    private String password;
+    /**
+     * 生日
+     */
+    private Date birthday;
+    /**
+     * 性别(1=男,2=女)
+     */
+    private Integer gender;
+    /**
+     * 身高
+     */
+    private Double height;
+    /**
+     * 体重
+     */
+    private Double weight;
+    /**
+     * bmi健康值
+     */
+    private Double bmi;
+    /**
+     * 身份证号
+     */
+    private String idCard;
+    /**
+     * 微信openid
+     */
+    private String openid;
+    /**
+     * 省
+     */
+    private String province;
+    /**
+     * 省编号
+     */
+    private String provinceCode;
+    /**
+     * 市
+     */
+    private String city;
+    /**
+     * 市编号
+     */
+    private String cityCode;
+    /**
+     * 是否是年度会员(0=否,1=是)
+     */
+    private Integer isVip;
+    /**
+     * 会员有效期
+     */
+    private Date vipEndTime;
+    /**
+     * 会员等级id
+     */
+    private Integer viplevelId;
+    /**
+     * 推荐用户id
+     */
+    private Integer referralUserId;
+    /**
+     * 销售员id
+     */
+    private Integer salesmanUserId;
+    /**
+     * 状态(1=正常,2=冻结,3=删除)
+     */
+    private Integer state;
+    /**
+     * 剩余积分
+     */
+    private Integer integral;
+    /**
+     * 玩湃币
+     */
+    private Integer playPaiCoins;
+    /**
+     * 用户头像
+     */
+    private String headImg;
+    /**
+     * 添加时间
+     */
+    private Date insertTime;
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/feignclient/other/StoreClient.java b/cloud-server-course/src/main/java/com/dsh/course/feignclient/other/StoreClient.java
new file mode 100644
index 0000000..eb27313
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/feignclient/other/StoreClient.java
@@ -0,0 +1,33 @@
+package com.dsh.course.feignclient.other;
+
+import com.dsh.course.feignclient.other.model.Store;
+import org.springframework.cloud.openfeign.FeignClient;
+import org.springframework.web.bind.annotation.PostMapping;
+
+import java.util.List;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/29 10:09
+ */
+@FeignClient("mb-cloud-other")
+public interface StoreClient {
+
+
+    /**
+     * 根据名称模糊搜索门店
+     * @param name
+     * @return
+     */
+    @PostMapping("/store/queryStoreListByName")
+    List<Store> queryStoreListByName(String name);
+
+
+    /**
+     * 根据门店id获取门店信息
+     * @param id
+     * @return
+     */
+    @PostMapping("/store/queryStoreById")
+    Store queryStoreById(Integer id);
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/feignclient/other/model/Store.java b/cloud-server-course/src/main/java/com/dsh/course/feignclient/other/model/Store.java
new file mode 100644
index 0000000..48b1ea2
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/feignclient/other/model/Store.java
@@ -0,0 +1,94 @@
+package com.dsh.course.feignclient.other.model;
+
+import lombok.Data;
+
+import java.math.BigDecimal;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/29 10:09
+ */
+@Data
+public class Store {
+    private Integer id;
+    /**
+     * 门店名称
+     */
+    private String name;
+    /**
+     * 门店店长id
+     */
+    private Integer storeStaffId;
+    /**
+     * 城市管理员id
+     */
+    private Integer cityManagerId;
+    /**
+     * 省
+     */
+    private String province;
+    /**
+     * 省编号
+     */
+    private String provinceCode;
+    /**
+     * 市
+     */
+    private String city;
+    /**
+     * 市编号
+     */
+    private String cityCode;
+    /**
+     * 联系电话
+     */
+    private String phone;
+    /**
+     * 详细地址
+     */
+    private String address;
+    /**
+     * 纬度
+     */
+    private String lat;
+    /**
+     * 经度
+     */
+    private String lon;
+    /**
+     * 营业开始时间
+     */
+    private String startTime;
+    /**
+     * 营业结束时间
+     */
+    private String endTime;
+    /**
+     * 封面图
+     */
+    private String coverDrawing;
+    /**
+     * 实景图
+     */
+    private String realPicture;
+    /**
+     * 门店介绍
+     */
+    private String introduce;
+    /**
+     * 福利图片
+     */
+    private String welfarePicture;
+    /**
+     * 开始上课图片
+     */
+    private String classPicture;
+    /**
+     * 评分
+     */
+    private BigDecimal score;
+    /**
+     * 状态(1=正常,2=冻结,3=删除)
+     */
+    private Integer state;
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/mapper/CoursePackagePaymentConfigMapper.java b/cloud-server-course/src/main/java/com/dsh/course/mapper/CoursePackagePaymentConfigMapper.java
new file mode 100644
index 0000000..9544749
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/mapper/CoursePackagePaymentConfigMapper.java
@@ -0,0 +1,11 @@
+package com.dsh.course.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.dsh.course.entity.CoursePackagePaymentConfig;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/29 10:44
+ */
+public interface CoursePackagePaymentConfigMapper extends BaseMapper<CoursePackagePaymentConfig> {
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackageMapper.java b/cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackageMapper.java
index 5577bcb..e295c54 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackageMapper.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackageMapper.java
@@ -18,4 +18,6 @@
 
     List<CourseOfStoreVo> queryStoreOfCourse();
 
+
+
 }
diff --git a/cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackagePaymentMapper.java b/cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackagePaymentMapper.java
index 4d8799c..2fa876a 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackagePaymentMapper.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/mapper/TCoursePackagePaymentMapper.java
@@ -18,4 +18,12 @@
 
     List<TCoursePackagePayment> queryAllCoursePackage(@Param("stuId") Integer stuId);
 
+
+    /**
+     * 获取课包购买人数
+     * @param coursePackageId
+     * @return
+     */
+    Integer queryCountNumber(@Param("coursePackageId") Integer coursePackageId);
+
 }
diff --git a/cloud-server-course/src/main/java/com/dsh/course/model/BaseVo.java b/cloud-server-course/src/main/java/com/dsh/course/model/BaseVo.java
new file mode 100644
index 0000000..3df6ed7
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/model/BaseVo.java
@@ -0,0 +1,18 @@
+package com.dsh.course.model;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 16:25
+ */
+@Data
+@ApiModel
+public class BaseVo {
+    @ApiModelProperty("数据id")
+    private Integer id;
+    @ApiModelProperty("名称")
+    private String name;
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/model/CoursePackageList.java b/cloud-server-course/src/main/java/com/dsh/course/model/CoursePackageList.java
new file mode 100644
index 0000000..847cb56
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/model/CoursePackageList.java
@@ -0,0 +1,28 @@
+package com.dsh.course.model;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 17:40
+ */
+@Data
+@ApiModel
+public class CoursePackageList {
+    @ApiModelProperty(value = "经度", dataType = "string", required = true)
+    private String lon;
+    @ApiModelProperty(value = "纬度", dataType = "string", required = true)
+    private String lat;
+    @ApiModelProperty(value = "课程类型id", dataType = "int", required = false)
+    private Integer coursePackageTypeId;
+    @ApiModelProperty(value = "门店id", dataType = "int", required = false)
+    private Integer storeId;
+    @ApiModelProperty(value = "搜索内容", dataType = "string", required = false)
+    private String search;
+    @ApiModelProperty(value = "销量排序(asc=正序,desc=降序)", dataType = "string", required = false)
+    private String salesRanking;
+    @ApiModelProperty(value = "距离排序(asc=正序,desc=降序)", dataType = "string", required = false)
+    private String distanceSort;
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/model/CoursePackageListVo.java b/cloud-server-course/src/main/java/com/dsh/course/model/CoursePackageListVo.java
new file mode 100644
index 0000000..4d62b27
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/model/CoursePackageListVo.java
@@ -0,0 +1,34 @@
+package com.dsh.course.model;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 17:34
+ */
+@Data
+@ApiModel
+public class CoursePackageListVo {
+    @ApiModelProperty("课程id")
+    private Integer id;
+    @ApiModelProperty("门店名称")
+    private String storeName;
+    @ApiModelProperty("课程名称")
+    private String name;
+    @ApiModelProperty("封面图")
+    private String coverDrawing;
+    @ApiModelProperty("上课时间")
+    private String classStartTime;
+    @ApiModelProperty("已报名人数")
+    private Integer applicantsNumber;
+    @ApiModelProperty("原价")
+    private Double originalPrice;
+    @ApiModelProperty("会员价")
+    private Double vipPrice;
+    @ApiModelProperty("支付价")
+    private Double paymentPrice;
+    @ApiModelProperty("距离")
+    private Double distance;
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/service/ICoursePackagePaymentConfigService.java b/cloud-server-course/src/main/java/com/dsh/course/service/ICoursePackagePaymentConfigService.java
new file mode 100644
index 0000000..3512d66
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/service/ICoursePackagePaymentConfigService.java
@@ -0,0 +1,11 @@
+package com.dsh.course.service;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.dsh.course.entity.CoursePackagePaymentConfig;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/29 10:45
+ */
+public interface ICoursePackagePaymentConfigService extends IService<CoursePackagePaymentConfig> {
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackagePaymentService.java b/cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackagePaymentService.java
index de97a51..aa12dce 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackagePaymentService.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackagePaymentService.java
@@ -17,4 +17,11 @@
 
     List<TCoursePackagePayment> queryAllCoursePackage(Integer stuId);
 
+
+    /**
+     * 获取课程购买人数
+     * @param coursePackageId
+     * @return
+     */
+    Integer queryCountNumber(Integer coursePackageId);
 }
diff --git a/cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackageService.java b/cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackageService.java
index 59ee81a..7034949 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackageService.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/service/TCoursePackageService.java
@@ -3,6 +3,8 @@
 import com.baomidou.mybatisplus.extension.service.IService;
 import com.dsh.course.entity.TCoursePackage;
 import com.dsh.course.feignclient.model.CourseOfStoreVo;
+import com.dsh.course.model.CoursePackageList;
+import com.dsh.course.model.CoursePackageListVo;
 
 import java.util.List;
 
@@ -18,4 +20,13 @@
 
     List<CourseOfStoreVo> queryStoreOfCourse();
 
+
+
+    /**
+     * 获取课程列表
+     * @param coursePackageList
+     * @return
+     * @throws Exception
+     */
+    List<CoursePackageListVo> queryCourseList(Integer uid, CoursePackageList coursePackageList) throws Exception;
 }
diff --git a/cloud-server-course/src/main/java/com/dsh/course/service/impl/CoursePackagePaymentConfigServiceImpl.java b/cloud-server-course/src/main/java/com/dsh/course/service/impl/CoursePackagePaymentConfigServiceImpl.java
new file mode 100644
index 0000000..207c72d
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/service/impl/CoursePackagePaymentConfigServiceImpl.java
@@ -0,0 +1,15 @@
+package com.dsh.course.service.impl;
+
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.dsh.course.entity.CoursePackagePaymentConfig;
+import com.dsh.course.mapper.CoursePackagePaymentConfigMapper;
+import com.dsh.course.service.ICoursePackagePaymentConfigService;
+import org.springframework.stereotype.Service;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/29 10:46
+ */
+@Service
+public class CoursePackagePaymentConfigServiceImpl extends ServiceImpl<CoursePackagePaymentConfigMapper, CoursePackagePaymentConfig> implements ICoursePackagePaymentConfigService {
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackagePaymentServiceImpl.java b/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackagePaymentServiceImpl.java
index a868ba2..c4cb6b7 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackagePaymentServiceImpl.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackagePaymentServiceImpl.java
@@ -23,4 +23,14 @@
     public List<TCoursePackagePayment> queryAllCoursePackage(Integer stuId) {
         return this.baseMapper.queryAllCoursePackage(stuId);
     }
+
+    /**
+     * 获取课包购买人数
+     * @param coursePackageId
+     * @return
+     */
+    @Override
+    public Integer queryCountNumber(Integer coursePackageId) {
+        return this.baseMapper.queryCountNumber(coursePackageId);
+    }
 }
diff --git a/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackageServiceImpl.java b/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackageServiceImpl.java
index 2245525..ebc9270 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackageServiceImpl.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCoursePackageServiceImpl.java
@@ -1,13 +1,35 @@
 package com.dsh.course.service.impl;
 
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.dsh.course.entity.CoursePackagePaymentConfig;
 import com.dsh.course.entity.TCoursePackage;
+import com.dsh.course.entity.TCoursePackageDiscount;
+import com.dsh.course.feignclient.account.AppUserClient;
+import com.dsh.course.feignclient.account.model.AppUser;
+import com.dsh.course.feignclient.other.StoreClient;
+import com.dsh.course.feignclient.other.model.Store;
 import com.dsh.course.mapper.TCoursePackageMapper;
 import com.dsh.course.feignclient.model.CourseOfStoreVo;
+import com.dsh.course.model.CoursePackageList;
+import com.dsh.course.model.CoursePackageListVo;
+import com.dsh.course.service.ICoursePackagePaymentConfigService;
+import com.dsh.course.service.TCoursePackageDiscountService;
+import com.dsh.course.service.TCoursePackagePaymentService;
 import com.dsh.course.service.TCoursePackageService;
+import com.dsh.course.util.GDMapGeocodingUtil;
+import com.dsh.course.util.GeodesyUtil;
+import com.dsh.course.util.ToolUtil;
+import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
-import java.util.List;
+import javax.annotation.Resource;
+import java.text.SimpleDateFormat;
+import java.util.*;
+import java.util.stream.Collectors;
 
 /**
  * <p>
@@ -20,8 +42,179 @@
 @Service
 public class TCoursePackageServiceImpl extends ServiceImpl<TCoursePackageMapper, TCoursePackage> implements TCoursePackageService {
 
+    @Resource
+    private StoreClient storeClient;
+
+    @Autowired
+    private GDMapGeocodingUtil gdMapGeocodingUtil;
+
+    @Autowired
+    private TCoursePackagePaymentService coursePackagePaymentService;
+
+    @Autowired
+    private ICoursePackagePaymentConfigService coursePackagePaymentConfigService;
+
+    @Autowired
+    private TCoursePackageDiscountService coursePackageDiscountService;
+
+    @Resource
+    private AppUserClient appUserClient;
+
+
+
+
     @Override
     public List<CourseOfStoreVo> queryStoreOfCourse() {
         return this.baseMapper.queryStoreOfCourse();
     }
+
+
+    /**
+     * 获取课程列表
+     * @param coursePackageList
+     * @return
+     * @throws Exception
+     */
+    @Override
+    public List<CoursePackageListVo> queryCourseList(Integer uid, CoursePackageList coursePackageList) throws Exception {
+        AppUser appUser = appUserClient.queryAppUser(uid);
+        Map<String, String> geocode = gdMapGeocodingUtil.geocode(coursePackageList.getLon(), coursePackageList.getLat());
+        String provinceCode = geocode.get("provinceCode");
+        String cityCode = geocode.get("cityCode");
+        QueryWrapper<TCoursePackage> wrapper = new QueryWrapper<TCoursePackage>().in("status", Arrays.asList(1, 2))
+                .eq("auditStatus", 2).eq("state", 1).eq("provinceCode", provinceCode).eq("cityCode", cityCode);
+        if(null != coursePackageList.getCoursePackageTypeId()){
+            wrapper.eq("coursePackageTypeId", coursePackageList.getCoursePackageTypeId());
+        }
+        if(null != coursePackageList.getStoreId()){
+            wrapper.eq("storeId", coursePackageList.getStoreId());
+        }
+        if(null != coursePackageList.getStoreId()){
+            wrapper.eq("storeId", coursePackageList.getStoreId());
+        }
+        if(ToolUtil.isNotEmpty(coursePackageList.getSearch())){
+            wrapper.like("name", coursePackageList.getSearch());
+            List<Store> stores = storeClient.queryStoreListByName(coursePackageList.getSearch());
+            List<Integer> collect = stores.stream().map(Store::getId).collect(Collectors.toList());
+            if(collect.size() > 0){
+                wrapper.or().in("id", collect);
+            }
+        }
+        List<TCoursePackage> list = this.list(wrapper.last(" order by sort, insertTime desc"));
+        List<CoursePackageListVo> listVos = new ArrayList<>();
+        for (TCoursePackage coursePackage : list) {
+            Store store = storeClient.queryStoreById(coursePackage.getStoreId());
+            Integer integer = coursePackagePaymentService.queryCountNumber(coursePackage.getId());
+            CoursePackagePaymentConfig coursePackagePaymentConfig = coursePackagePaymentConfigService.getOne(new QueryWrapper<CoursePackagePaymentConfig>()
+                    .eq("coursePackageId", coursePackage.getId()).last(" order by if(payType = 1, cashPayment, playPaiCoin)"));
+            CoursePackageListVo coursePackageListVo = new CoursePackageListVo();
+            coursePackageListVo.setId(coursePackage.getId());
+            coursePackageListVo.setName(coursePackage.getName());
+            coursePackageListVo.setStoreName(null != store ? store.getName() : "");
+            coursePackageListVo.setCoverDrawing(coursePackage.getCoverDrawing());
+            coursePackageListVo.setClassStartTime(coursePackage.getClassStartTime() + "-" + coursePackage.getClassEndTime());
+            coursePackageListVo.setApplicantsNumber(integer);
+
+            coursePackageListVo.setOriginalPrice(coursePackagePaymentConfig.getPayType() == 1 ? coursePackagePaymentConfig.getCashPayment() : coursePackagePaymentConfig.getPlayPaiCoin().doubleValue());
+            TCoursePackageDiscount coursePackageDiscount = coursePackageDiscountService.getOne(new QueryWrapper<TCoursePackageDiscount>().eq("coursePackageId", coursePackage.getId()).eq("auditStatus", 2).eq("type", 1));
+            if(1 == appUser.getIsVip() && null != coursePackageDiscount){
+                //{"num1":100}
+                JSONObject jsonObject = JSON.parseObject(coursePackageDiscount.getContent());
+                coursePackageListVo.setVipPrice(jsonObject.getDouble("num1"));
+            }
+            coursePackageDiscount = coursePackageDiscountService.getOne(new QueryWrapper<TCoursePackageDiscount>().eq("coursePackageId", coursePackage.getId()).eq("auditStatus", 2).eq("type", 3));
+            if(null == coursePackageDiscount){
+                coursePackageListVo.setPaymentPrice(coursePackageListVo.getOriginalPrice());
+            }else{
+                SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
+                /**
+                 * [{
+                 * 	"startDate": "2023-01-01 00:00:00",
+                 * 	"endDate": "2023-12-31 23:59:59",
+                 * 	"startTime": "02:00:00",
+                 * 	"endTime": "23:00:00",
+                 * 	"weeks": [1, 2, 7],
+                 * 	"cashPayment": 100
+                 * }]
+                 */
+                JSONArray jsonArray = JSON.parseArray(coursePackageDiscount.getContent());
+                for (int i = 0; i < jsonArray.size(); i++) {
+                    JSONObject jsonObject = jsonArray.getJSONObject(i);
+                    String startDate = jsonObject.getString("startDate");
+                    String endDate = jsonObject.getString("endDate");
+                    String startTime = jsonObject.getString("startTime");
+                    String endTime = jsonObject.getString("endTime");
+                    List<Integer> weeks = jsonObject.getJSONArray("weeks").toJavaList(Integer.class);
+                    Double cashPayment = jsonObject.getDouble("cashPayment");
+                    Date startDate_date = sdf.parse(startDate);
+                    Date endDate_date = sdf.parse(endDate);
+                    long timeMillis = System.currentTimeMillis();
+                    if(timeMillis >= startDate_date.getTime() && timeMillis < endDate_date.getTime()){
+                        Date date = new Date();
+                        Calendar calendar = Calendar.getInstance();
+                        calendar.setTime(date);
+                        int week = calendar.get(Calendar.DAY_OF_WEEK);
+                        boolean isFirstSunday = (calendar.getFirstDayOfWeek() == Calendar.SUNDAY);
+                        if(isFirstSunday){
+                            week = week - 1;
+                            if(week == 0){
+                                week = 7;
+                            }
+                        }
+                        if(!weeks.contains(week)){
+                            continue;
+                        }
+
+                        String[] split = startTime.split(":");
+                        Integer hour1 = Integer.valueOf(split[0]);
+                        Calendar s = Calendar.getInstance();
+                        s.setTime(date);
+                        s.set(Calendar.HOUR_OF_DAY, hour1);
+                        s.set(Calendar.MINUTE, Integer.valueOf(split[1]));
+                        s.set(Calendar.SECOND, Integer.valueOf(split[2]));
+
+                        String[] split1 = endTime.split(":");
+                        Integer hour2 = Integer.valueOf(split1[0]);
+                        Calendar e = Calendar.getInstance();
+                        e.setTime(date);
+                        e.set(Calendar.HOUR_OF_DAY, hour2);
+                        e.set(Calendar.MINUTE, Integer.valueOf(split1[1]));
+                        e.set(Calendar.SECOND, Integer.valueOf(split1[2]));
+
+                        if(hour1 > hour2){
+                            if(s.getTimeInMillis() > date.getTime()){
+                                s.set(Calendar.DAY_OF_YEAR, s.get(Calendar.DAY_OF_YEAR) - 1);
+                            }else{
+                                e.set(Calendar.DAY_OF_YEAR, e.get(Calendar.DAY_OF_YEAR) + 1);
+                            }
+                        }
+                        if(timeMillis >= s.getTimeInMillis() && timeMillis < e.getTimeInMillis()){
+                            coursePackageListVo.setPaymentPrice(cashPayment);
+                        }
+                    }
+                }
+            }
+            Map<String, Double> distance = GeodesyUtil.getDistance(coursePackageList.getLon() + "," + coursePackageList.getLat(), store.getLon() + "," + store.getLat());
+            coursePackageListVo.setDistance(distance.get("WGS84") / 1000);
+            listVos.add(coursePackageListVo);
+        }
+
+        //销量排行
+        if(ToolUtil.isNotEmpty(coursePackageList.getSalesRanking())){
+            Collections.sort(listVos, new Comparator<CoursePackageListVo>() {
+                public int compare(CoursePackageListVo s1, CoursePackageListVo s2) {
+                    return Integer.compare(s1.getApplicantsNumber(), s2.getApplicantsNumber());
+                }
+            });
+        }
+        //距离排行
+        if(ToolUtil.isNotEmpty(coursePackageList.getDistanceSort())){
+            Collections.sort(listVos, new Comparator<CoursePackageListVo>() {
+                public int compare(CoursePackageListVo s1, CoursePackageListVo s2) {
+                    return Double.compare(s1.getDistance(), s2.getDistance());
+                }
+            });
+        }
+        return listVos;
+    }
 }
diff --git a/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCourseServiceImpl.java b/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCourseServiceImpl.java
index 4d41125..5b51cb8 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCourseServiceImpl.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/service/impl/TCourseServiceImpl.java
@@ -6,6 +6,7 @@
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import org.springframework.stereotype.Service;
 
+
 /**
  * <p>
  * 课程 服务实现类
@@ -17,4 +18,6 @@
 @Service
 public class TCourseServiceImpl extends ServiceImpl<TCourseMapper, TCourse> implements TCourseService {
 
+
+
 }
diff --git a/cloud-server-course/src/main/java/com/dsh/course/util/GDMapGeocodingUtil.java b/cloud-server-course/src/main/java/com/dsh/course/util/GDMapGeocodingUtil.java
new file mode 100644
index 0000000..3c9ccea
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/util/GDMapGeocodingUtil.java
@@ -0,0 +1,148 @@
+package com.dsh.course.util;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import com.dsh.course.util.httpClinet.HttpClientUtil;
+import com.dsh.course.util.httpClinet.HttpResult;
+import org.springframework.stereotype.Component;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * 高德地图的地理编码工具类
+ */
+@Component
+public class GDMapGeocodingUtil {
+
+    private String key = "fb131ad2dbfb3f39d7d37d244b92aa2d";
+
+
+    /**
+     * 将行政区域名称转化为坐标
+     * @param province
+     * @param city
+     * @param county
+     * @param address
+     * @return
+     */
+    public Map<String, Object> geocoding(String province, String city, String county, String address) throws Exception{
+        Map<String, Object> map = new HashMap<>();
+        if(ToolUtil.isEmpty(province)){
+            map.put("status", -1);
+            map.put("data", "省不能为空");
+            return map;
+        }
+        if((ToolUtil.isEmpty(city) && ToolUtil.isNotEmpty(county)) || (ToolUtil.isEmpty(city) && ToolUtil.isNotEmpty(address))){
+            map.put("status", -1);
+            map.put("data", "市不能为空");
+            return map;
+        }
+        if((ToolUtil.isEmpty(county) && ToolUtil.isNotEmpty(address))){
+            map.put("status", -1);
+            map.put("data", "县/区不能为空");
+            return map;
+        }
+
+        String url = "https://restapi.amap.com/v3/geocode/geo?key=" + key + "&output=JSON";
+        url += "&address=" + province + (ToolUtil.isNotEmpty(city) ? city : "") + (ToolUtil.isNotEmpty(county) ? county : "") + (ToolUtil.isNotEmpty(address) ? address : "");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        JSONObject jsonObject = JSON.parseObject(httpResult.getData());
+        String status = jsonObject.getString("status");
+        List<String> list = new ArrayList<>();
+
+        if(status.equals("1")){
+            JSONArray geocodes = jsonObject.getJSONArray("geocodes");
+            for(int i = 0; i < geocodes.size(); i++){
+                String location = geocodes.getJSONObject(i).getString("location");
+                list.add(location);
+            }
+        }
+        map.put("status", 0);
+        map.put("data", list);
+        return map;
+    }
+
+
+
+    public Map<String, Object> geocoding(String address) throws Exception{
+        Map<String, Object> map = new HashMap<>();
+        String url = "https://restapi.amap.com/v3/geocode/geo?key=" + key + "&output=JSON&address=" + address;
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        JSONObject jsonObject = JSON.parseObject(httpResult.getData());
+        String status = jsonObject.getString("status");
+        List<String> list = new ArrayList<>();
+
+        if(status.equals("1")){
+            JSONArray geocodes = jsonObject.getJSONArray("geocodes");
+            for(int i = 0; i < geocodes.size(); i++){
+                String location = geocodes.getJSONObject(i).getString("location");
+                list.add(location);
+            }
+        }
+        map.put("status", 0);
+        map.put("data", list);
+        return map;
+    }
+
+
+
+    /**
+     * 根据经纬度获取行政区域信息
+     * @param lon
+     * @param lan
+     * @return
+     * @throws Exception
+     */
+    public Map<String, String> geocode(String lon, String lan) throws Exception{
+        String url = "https://restapi.amap.com/v3/geocode/regeo?key=" + key + "&location=" + lon + "," + lan;
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        JSONObject jsonObject = JSON.parseObject(httpResult.getData());
+        Map<String, String> map = new HashMap<>();
+
+        if(jsonObject.getString("status").equals("1")){
+            JSONObject regeocode = jsonObject.getJSONObject("regeocode");
+            JSONObject addressComponent = regeocode.getJSONObject("addressComponent");
+            String address = regeocode.getString("formatted_address");
+            map.put("address", address);
+            String code = addressComponent.getString("adcode");
+            String province = addressComponent.getString("province");
+            String city = addressComponent.getString("city");
+            String district = addressComponent.getString("district");
+            map.put("province", province);
+            map.put("provinceCode", code.substring(0, 2) + "0000");
+            map.put("city", city);
+            map.put("cityCode", code.substring(0, 4) + "00");
+            map.put("district", district);
+            map.put("districtCode", code);
+        }
+        return map;
+    }
+
+
+    /**
+     * 坐标转换
+     * @param locations 经度和纬度用","分割,经度在前,纬度在后,经纬度小数点后不得超过6位。多个坐标对之间用”|”进行分隔最多支持40对坐标。
+     * @param coordsys  可选值:gps;mapbar;baidu;autonavi(不进行转换)
+     * @return
+     * @throws Exception
+     */
+    public Map<String, String> convert(String locations, String coordsys) throws Exception{
+        String url = "https://restapi.amap.com/v3/assistant/coordinate/convert?locations=" + locations + "&coordsys=" + coordsys + "&output=json&key=" + key;
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        JSONObject jsonObject = JSON.parseObject(httpResult.getData());
+        Map<String, String> map = new HashMap<>();
+        if("1".equals(jsonObject.getString("status"))){
+            map.put("code", jsonObject.getString("infocode"));//"10000"
+            map.put("info", jsonObject.getString("info"));//status为0时,info返回错误原;否则返回“OK”。
+            map.put("locations", jsonObject.getString("locations").split(";")[0]);//转换之后的坐标。若有多个坐标,则用 “;”进行区分和间隔
+        }else{
+            map.put("code", jsonObject.getString("infocode"));
+            map.put("info", jsonObject.getString("info"));//status为0时,info返回错误原;否则返回“OK”。
+        }
+        return map;
+    }
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/util/GeodesyUtil.java b/cloud-server-course/src/main/java/com/dsh/course/util/GeodesyUtil.java
new file mode 100644
index 0000000..f56eae2
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/util/GeodesyUtil.java
@@ -0,0 +1,63 @@
+package com.dsh.course.util;
+
+import org.gavaghan.geodesy.Ellipsoid;
+import org.gavaghan.geodesy.GeodeticCalculator;
+import org.gavaghan.geodesy.GeodeticCurve;
+import org.gavaghan.geodesy.GlobalCoordinates;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * 计算两个金纬度坐标之间的直线距离
+ */
+public class GeodesyUtil {
+
+
+    /**
+     * 获取直线距离
+     * @param fromLonLat
+     * @param toLonLat
+     * @return
+     */
+    public static Map<String, Double> getDistance(String fromLonLat, String toLonLat){
+        String[] from = fromLonLat.split(",");
+        String[] to = toLonLat.split(",");
+        GlobalCoordinates source = new GlobalCoordinates(Double.valueOf(from[1]), Double.valueOf(from[0]));
+        GlobalCoordinates target = new GlobalCoordinates(Double.valueOf(to[1]), Double.valueOf(to[0]));
+        double Sphere = getDistanceMeter(source, target, Ellipsoid.Sphere);
+        double WGS84 = getDistanceMeter(source, target, Ellipsoid.WGS84);
+        double GRS80 = getDistanceMeter(source, target, Ellipsoid.GRS80);
+        double GRS67 = getDistanceMeter(source, target, Ellipsoid.GRS67);
+        double ANS = getDistanceMeter(source, target, Ellipsoid.ANS);
+        double WGS72 = getDistanceMeter(source, target, Ellipsoid.WGS72);
+        double Clarke1858 = getDistanceMeter(source, target, Ellipsoid.Clarke1858);
+        double Clarke1880 = getDistanceMeter(source, target, Ellipsoid.Clarke1880);
+//        System.out.println("Sphere坐标系计算结果:"+Sphere + "米");
+//        System.out.println("WGS84坐标系计算结果:"+WGS84 + "米");
+//        System.out.println("GRS80坐标系计算结果:"+GRS80 + "米");
+//        System.out.println("GRS67坐标系计算结果:"+GRS67 + "米");
+//        System.out.println("ANS坐标系计算结果:"+ANS + "米");
+//        System.out.println("WGS72坐标系计算结果:"+WGS72 + "米");
+//        System.out.println("Clarke1858坐标系计算结果:"+Clarke1858 + "米");
+//        System.out.println("Clarke1880坐标系计算结果:"+Clarke1880 + "米");
+        Map<String, Double> map = new HashMap<>();
+        map.put("Sphere", Sphere);
+        map.put("WGS84", WGS84);
+        map.put("GRS80", GRS80);
+        map.put("GRS67", GRS67);
+        map.put("ANS", ANS);
+        map.put("WGS72", WGS72);
+        map.put("Clarke1858", Clarke1858);
+        map.put("Clarke1880", Clarke1880);
+        return map;
+    }
+
+
+    private static double getDistanceMeter(GlobalCoordinates gpsFrom, GlobalCoordinates gpsTo, Ellipsoid ellipsoid){
+        //创建GeodeticCalculator,调用计算方法,传入坐标系、经纬度用于计算距离
+        GeodeticCurve geoCurve = new GeodeticCalculator().calculateGeodeticCurve(ellipsoid, gpsFrom, gpsTo);
+        return geoCurve.getEllipsoidalDistance();
+    }
+
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/util/ResultUtil.java b/cloud-server-course/src/main/java/com/dsh/course/util/ResultUtil.java
index dad75ca..45a64c6 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/util/ResultUtil.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/util/ResultUtil.java
@@ -3,7 +3,6 @@
 import com.alibaba.fastjson.JSONObject;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
-import org.springframework.beans.factory.annotation.Autowired;
 
 /**
  * 定义统一返回对象
@@ -107,8 +106,8 @@
      * 参数异常
      * @return
      */
-    public static  ResultUtil paranErr(){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", new JSONObject());
+    public static  ResultUtil paranErr(String ages){
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "【" + ages + "】参数异常", new JSONObject());
     }
 
     /**
@@ -116,11 +115,10 @@
      * @return
      */
     public static <T> ResultUtil<T> paranErr(T data){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "SYSTEM_RUN_ERROR", data);
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", data);
     }
 
-    @Autowired
-    private static MessageUtils messageUtils;
+
     /**
      * 运行异常
      * @return
diff --git a/cloud-server-course/src/main/java/com/dsh/course/util/TokenUtil.java b/cloud-server-course/src/main/java/com/dsh/course/util/TokenUtil.java
index 1ffad8f..6cf2371 100644
--- a/cloud-server-course/src/main/java/com/dsh/course/util/TokenUtil.java
+++ b/cloud-server-course/src/main/java/com/dsh/course/util/TokenUtil.java
@@ -2,6 +2,8 @@
 
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Component;
+import org.springframework.web.context.request.RequestContextHolder;
+import org.springframework.web.context.request.ServletRequestAttributes;
 
 import javax.servlet.http.HttpServletRequest;
 
@@ -12,7 +14,9 @@
     private RedisUtil redisUtil;
 
 
-    public Integer getUserIdFormRedis(HttpServletRequest request) throws Exception {
+    public Integer getUserIdFormRedis() throws Exception {
+        ServletRequestAttributes servletRequestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
+        HttpServletRequest request = servletRequestAttributes.getRequest();
         String requestHeader = request.getHeader("Authorization");
         if (requestHeader != null && requestHeader.startsWith("Bearer ")) {
             requestHeader = requestHeader.substring(requestHeader.indexOf(" ") + 1);
diff --git a/cloud-server-course/src/main/java/com/dsh/course/util/httpClinet/HttpClientUtil.java b/cloud-server-course/src/main/java/com/dsh/course/util/httpClinet/HttpClientUtil.java
new file mode 100644
index 0000000..4458ff5
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/util/httpClinet/HttpClientUtil.java
@@ -0,0 +1,267 @@
+package com.dsh.course.util.httpClinet;
+
+import com.alibaba.fastjson.JSON;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import org.apache.http.NameValuePair;
+import org.apache.http.client.config.RequestConfig;
+import org.apache.http.client.entity.UrlEncodedFormEntity;
+import org.apache.http.client.methods.CloseableHttpResponse;
+import org.apache.http.client.methods.HttpGet;
+import org.apache.http.client.methods.HttpPost;
+import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
+import org.apache.http.entity.ContentType;
+import org.apache.http.entity.StringEntity;
+import org.apache.http.impl.client.CloseableHttpClient;
+import org.apache.http.impl.client.HttpClients;
+import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
+import org.apache.http.message.BasicNameValuePair;
+import org.apache.http.ssl.SSLContexts;
+import org.apache.http.util.EntityUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import javax.net.ssl.SSLContext;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.InputStream;
+import java.nio.charset.Charset;
+import java.security.KeyStore;
+import java.text.SimpleDateFormat;
+import java.util.*;
+import java.util.concurrent.TimeUnit;
+
+/**
+ * http工具类
+ */
+public class HttpClientUtil {
+
+    private static Logger logger = LoggerFactory.getLogger(HttpClientUtil.class);
+
+    private static PoolingHttpClientConnectionManager connectionManager;
+
+
+    {
+        //1.创建连接池管理器
+        connectionManager = new PoolingHttpClientConnectionManager(60000,
+                TimeUnit.MILLISECONDS);
+        connectionManager.setMaxTotal(1000);
+        connectionManager.setDefaultMaxPerRoute(50);
+    }
+
+    /**
+     * 创建一个httpClient对象
+     */
+    private static CloseableHttpClient getHttpCline(){
+        return  HttpClients.custom()
+                .setConnectionManager(connectionManager)
+                .disableAutomaticRetries()
+                .build();
+    }
+
+    private static RequestConfig getRequestConfig(){
+        RequestConfig.Builder builder = RequestConfig.custom();
+        builder.setSocketTimeout(60000)//3.1设置客户端等待服务端返回数据的超时时间
+                .setConnectTimeout(30000)//3.2设置客户端发起TCP连接请求的超时时间
+                .setExpectContinueEnabled(true)
+                .setConnectionRequestTimeout(30000);//3.3设置客户端从连接池获取链接的超时时间
+        return builder.build();
+    }
+
+
+
+    /**
+     * 创建一个POST请求实例
+     * @param url       请求地址
+     * @param params    请求参数
+     */
+    private static CloseableHttpResponse setPostHttpRequset(String url, Map<String, Object> params, Map<String, String> header, String contentType) throws Exception{
+        HttpPost httpPost = new HttpPost(url);
+        httpPost.setConfig(getRequestConfig());
+        if(null != header){
+            for(String key : header.keySet()){
+                httpPost.setHeader(key, header.get(key));
+            }
+        }
+        List<NameValuePair> list = new ArrayList<>();
+        if(null != params){
+            Set<String> keys = params.keySet();
+            for(String key : keys){
+                list.add(new BasicNameValuePair(key, null == params.get(key) ? null : params.get(key).toString()));
+            }
+        }
+        switch (contentType){
+            case "form":
+                httpPost.setEntity(new UrlEncodedFormEntity(list, "UTF-8"));
+                break;
+            case "json":
+                ObjectMapper objectMapper = new ObjectMapper();
+                String s =objectMapper.writeValueAsString(params);
+                httpPost.setEntity(new StringEntity(s, ContentType.create(ContentType.APPLICATION_JSON.getMimeType(), Charset.forName("UTF-8"))));
+                break;
+        }
+        return getHttpCline().execute(httpPost);
+    }
+
+
+    /**
+     * 获取get请求实例
+     * @param url       请求地址
+     * @param params    请求参数
+     */
+    private static CloseableHttpResponse setGetHttpRequset(String url, Map<String, Object> params, Map<String, String> header) throws Exception{
+        StringBuffer sb = new StringBuffer();
+        String p = "";
+        if(null != params){
+            Set<String> keys = params.keySet();
+            for(String key : keys){
+                sb.append(key + "=" + params.get(key) + "&");
+            }
+            p = "?" + sb.substring(0, sb.length() - 1);
+        }
+        HttpGet httpGet = new HttpGet(url + p);
+        httpGet.setConfig(getRequestConfig());
+        if(null != header){
+            for(String key : header.keySet()){
+                httpGet.setHeader(key, header.get(key));
+            }
+        }
+        return getHttpCline().execute(httpGet);
+    }
+
+
+    /**
+     * 发送http请求
+     * @param mothed        "GET、POST、PUT、HEAD、DELETE、HEAD、OPTIONS"
+     * @param url           请求地址
+     * @param params        请求参数
+     * @param header        请求头
+     * @param contentType   参数请求方式form/json
+     * @return
+     */
+    public static HttpResult pushHttpRequset(String mothed, String url, Map<String, Object> params, Map<String, String> header, String contentType) throws Exception{
+        String randome = UUID.randomUUID().toString();
+        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.S");
+        logger.info(sdf.format(new Date()) + "----(" + randome + ")请求参数:" + JSON.toJSONString(params));
+        CloseableHttpResponse httpResponse = null;
+        switch (mothed){
+            case "GET":
+                httpResponse = setGetHttpRequset(url, params, header);
+                break;
+            case "POST":
+                httpResponse = setPostHttpRequset(url, params, header, contentType);
+                break;
+        }
+        int statusCode = httpResponse.getStatusLine().getStatusCode();
+        String content = EntityUtils.toString(httpResponse.getEntity(), "UTF-8");
+        logger.info(sdf.format(new Date()) + "----(" + randome + ")返回结果:" + content);
+        HttpResult httpResult = HttpResult.getHttpResult(statusCode, content);
+        close(httpResponse);
+        return httpResult;
+    }
+
+
+    /**
+     * 发送XML请求
+     * @param url       请求地址
+     * @param xml       XML数据
+     * @param header    自定义请求头
+     * @return
+     */
+    public static HttpResult pushHttpRequsetXml(String url, String xml, Map<String, String> header) throws Exception{
+        HttpPost httpPost = new HttpPost(url);
+        httpPost.setConfig(getRequestConfig());
+        for(String key : header.keySet()){
+            httpPost.setHeader(key, header.get(key));
+        }
+        httpPost.setHeader("Content-Type", "application/xml");
+        httpPost.setEntity(new StringEntity(xml, "UTF-8"));
+        CloseableHttpResponse httpResponse = getHttpCline().execute(httpPost);
+        int statusCode = httpResponse.getStatusLine().getStatusCode();
+        String content = EntityUtils.toString(httpResponse.getEntity(), "UTF-8");
+        HttpResult httpResult = HttpResult.getHttpResult(statusCode, content);
+        close(httpResponse);
+        return httpResult;
+    }
+
+
+
+    /**
+     * 请求https发送XML请求
+     * @param url           接口路径
+     * @param xml           内容
+     * @param header        请求头
+     * @param certPassword      证书密码
+     * @param certPath      证书路径
+     * @param certType      证书类型
+     * @return
+     * @throws Exception
+     */
+    public String pushHttpsRequsetXml(String url, String xml, Map<String, String> header, String certPassword, String certPath, String certType) throws Exception{
+        HttpPost httpPost = new HttpPost(url);
+        for(String key : header.keySet()){
+            httpPost.setHeader(key, header.get(key));
+        }
+        httpPost.setHeader("Content-Type", "application/xml");
+        httpPost.setEntity(new StringEntity(xml, "UTF-8"));
+        CloseableHttpClient httpCline = this.initCert(certPassword, certPath, certType);
+        CloseableHttpResponse httpResponse = httpCline.execute(httpPost);
+        String content = null;
+        if(httpResponse.getStatusLine().getStatusCode() == 200){
+            content = EntityUtils.toString(httpResponse.getEntity(), "UTF-8");
+        }else{
+            content = "返回状态码:" + httpResponse.getStatusLine() + "。" + EntityUtils.toString(httpResponse.getEntity());
+        }
+        this.close(httpResponse);
+        httpCline.close();
+        return content;
+    }
+
+
+    /**
+     * 初始化https对象(带证书)
+     * @param key       证书密码
+     * @param certPath  证书路径
+     * @param certType  证书类型
+     * @throws Exception
+     */
+    private CloseableHttpClient initCert(String key, String certPath, String certType) throws Exception {
+        KeyStore keyStore = KeyStore.getInstance(certType);
+        InputStream inputStream = new FileInputStream(new File(certPath));
+        try {
+            keyStore.load(inputStream, key.toCharArray());
+        } finally {
+            inputStream.close();
+        }
+        SSLContext sslcontext = SSLContexts.custom().loadKeyMaterial(keyStore, key.toCharArray()).build();
+        SSLConnectionSocketFactory sslsf =
+                new SSLConnectionSocketFactory(sslcontext, new String[] {"TLSv1"}, null,
+                        SSLConnectionSocketFactory.BROWSER_COMPATIBLE_HOSTNAME_VERIFIER);
+        return HttpClients.custom().setSSLSocketFactory(sslsf).build();
+    }
+
+
+
+    /**
+     * 关闭资源
+     */
+    private static void close(CloseableHttpResponse httpResponse){
+        try {
+            if(null != httpResponse){
+                EntityUtils.consume(httpResponse.getEntity());//此处高能,通过源码分析,由EntityUtils是否回收HttpEntity
+                httpResponse.close();
+            }
+        } catch (Exception e) {
+            e.printStackTrace();
+        }finally {
+            try {
+                if(null != httpResponse){
+                    httpResponse.close();
+                }
+            }catch (Exception e){
+                e.printStackTrace();
+            }
+        }
+    }
+
+
+}
diff --git a/cloud-server-course/src/main/java/com/dsh/course/util/httpClinet/HttpResult.java b/cloud-server-course/src/main/java/com/dsh/course/util/httpClinet/HttpResult.java
new file mode 100644
index 0000000..6540194
--- /dev/null
+++ b/cloud-server-course/src/main/java/com/dsh/course/util/httpClinet/HttpResult.java
@@ -0,0 +1,31 @@
+package com.dsh.course.util.httpClinet;
+
+import lombok.Data;
+
+/**
+ * http请求返回封装
+ */
+@Data
+public class HttpResult {
+    /**
+     * 返回状态码
+     */
+    private Integer code;
+    /**
+     * 返回结果
+     */
+    private String data;
+
+    /**
+     * 返回封装结果
+     * @param code
+     * @param data
+     * @return
+     */
+    public static HttpResult getHttpResult(Integer code, String data){
+        HttpResult httpResult = new HttpResult();
+        httpResult.setCode(code);
+        httpResult.setData(data);
+        return httpResult;
+    }
+}
diff --git a/cloud-server-course/src/main/resources/mapper/CoursePackagePaymentConfigMapper.xml b/cloud-server-course/src/main/resources/mapper/CoursePackagePaymentConfigMapper.xml
new file mode 100644
index 0000000..1cbc1b2
--- /dev/null
+++ b/cloud-server-course/src/main/resources/mapper/CoursePackagePaymentConfigMapper.xml
@@ -0,0 +1,14 @@
+<?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.dsh.course.mapper.CoursePackagePaymentConfigMapper">
+
+    <!-- 通用查询映射结果 -->
+    <resultMap id="BaseResultMap" type="com.dsh.course.entity.CoursePackagePaymentConfig">
+        <id column="id" property="id" />
+        <result column="coursePackageId" property="coursePackageId" />
+        <result column="payType" property="payType" />
+        <result column="classHours" property="classHours" />
+        <result column="cashPayment" property="cashPayment" />
+        <result column="playPaiCoin" property="playPaiCoin" />
+    </resultMap>
+</mapper>
\ No newline at end of file
diff --git a/cloud-server-course/src/main/resources/mapper/TCourseMapper.xml b/cloud-server-course/src/main/resources/mapper/TCourseMapper.xml
index 5e540c0..f54a3be 100644
--- a/cloud-server-course/src/main/resources/mapper/TCourseMapper.xml
+++ b/cloud-server-course/src/main/resources/mapper/TCourseMapper.xml
@@ -15,4 +15,5 @@
         <result column="insertTime" property="insertTime" />
     </resultMap>
 
+
 </mapper>
diff --git a/cloud-server-course/src/main/resources/mapper/TCoursePackagePaymentMapper.xml b/cloud-server-course/src/main/resources/mapper/TCoursePackagePaymentMapper.xml
index 7bbff13..9aee0a7 100644
--- a/cloud-server-course/src/main/resources/mapper/TCoursePackagePaymentMapper.xml
+++ b/cloud-server-course/src/main/resources/mapper/TCoursePackagePaymentMapper.xml
@@ -46,4 +46,12 @@
         WHERE user_id = #{stuId}
     </select>
 
+
+    <select id="queryCountNumber" resultType="int">
+        SELECT
+	    count( 1 ) AS num
+        FROM (
+          SELECT appUserId FROM t_course_package_payment WHERE payStatus = 2 AND state = 1 and coursePackageId = #{coursePackageId} GROUP BY appUserId
+        ) AS aa
+    </select>
 </mapper>
diff --git a/cloud-server-other/pom.xml b/cloud-server-other/pom.xml
index 7a62058..ea54735 100644
--- a/cloud-server-other/pom.xml
+++ b/cloud-server-other/pom.xml
@@ -91,6 +91,20 @@
             <version>2.3.30</version>
         </dependency>
 
+        <dependency>
+            <groupId>org.apache.httpcomponents</groupId>
+            <artifactId>httpclient</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>commons-httpclient</groupId>
+            <artifactId>commons-httpclient</artifactId>
+            <version>3.1</version>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.httpcomponents</groupId>
+            <artifactId>httpmime</artifactId>
+            <version>4.5.2</version>
+        </dependency>
 
     </dependencies>
 
diff --git a/cloud-server-other/src/main/java/com/dsh/other/controller/StoreConfigController.java b/cloud-server-other/src/main/java/com/dsh/other/controller/StoreConfigController.java
new file mode 100644
index 0000000..c68b255
--- /dev/null
+++ b/cloud-server-other/src/main/java/com/dsh/other/controller/StoreConfigController.java
@@ -0,0 +1,57 @@
+package com.dsh.other.controller;
+
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.dsh.other.entity.StoreConfig;
+import com.dsh.other.model.StoreConfigVo;
+import com.dsh.other.service.StoreConfigService;
+import com.dsh.other.util.ResultUtil;
+import io.swagger.annotations.ApiImplicitParam;
+import io.swagger.annotations.ApiImplicitParams;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.BeanUtils;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 16:11
+ */
+@RestController
+@RequestMapping("")
+public class StoreConfigController {
+
+    @Autowired
+    private StoreConfigService storeConfigService;
+
+
+
+    @ResponseBody
+    @PostMapping("/base/store/queryStoreConfig")
+    @ApiOperation(value = "获取门店模块配置", tags = {"APP-加入玩湃"})
+    @ApiImplicitParams({
+            @ApiImplicitParam(value = "门店id", name = "storeId", dataType = "int", required = true),
+    })
+    public ResultUtil<List<StoreConfigVo>> queryStoreConfig(@RequestBody Integer storeId){
+        if(null == storeId){
+            return ResultUtil.paranErr("storeId");
+        }
+        try {
+            List<StoreConfig> list = storeConfigService.list(new QueryWrapper<StoreConfig>().eq("storeId", storeId).orderByAsc("sort"));
+            List<StoreConfigVo> listVo = new ArrayList<>();
+            for (StoreConfig storeConfig : list) {
+                StoreConfigVo storeConfigVo = new StoreConfigVo();
+                BeanUtils.copyProperties(storeConfig, storeConfigVo);
+                listVo.add(storeConfigVo);
+            }
+            return ResultUtil.success(listVo);
+        }catch (Exception e){
+            e.printStackTrace();
+            return ResultUtil.runErr();
+        }
+    }
+
+
+}
diff --git a/cloud-server-other/src/main/java/com/dsh/other/controller/StoreController.java b/cloud-server-other/src/main/java/com/dsh/other/controller/StoreController.java
new file mode 100644
index 0000000..6b51f47
--- /dev/null
+++ b/cloud-server-other/src/main/java/com/dsh/other/controller/StoreController.java
@@ -0,0 +1,108 @@
+package com.dsh.other.controller;
+
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.dsh.other.entity.Store;
+import com.dsh.other.model.BaseVo;
+import com.dsh.other.service.StoreService;
+import com.dsh.other.util.ResultUtil;
+import com.dsh.other.util.ToolUtil;
+import io.swagger.annotations.ApiImplicitParam;
+import io.swagger.annotations.ApiImplicitParams;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 15:42
+ */
+@RestController
+@RequestMapping("")
+public class StoreController {
+
+    @Autowired
+    private StoreService storeService;
+
+
+    /**
+     * 获取门店列表
+     * @param provinceCode
+     * @param cityCode
+     * @return
+     */
+    @ResponseBody
+    @PostMapping("/store/queryStoreList")
+    public List<Store> queryStoreList(@RequestBody String provinceCode, @RequestBody String cityCode){
+        try {
+            return storeService.queryStorsList(provinceCode, cityCode);
+        }catch (Exception e){
+            e.printStackTrace();
+            return new ArrayList<>();
+        }
+    }
+
+
+
+
+
+    @ResponseBody
+    @PostMapping("/base/store/queryStoreLists")
+    @ApiOperation(value = "获取门店列表", tags = {"APP-加入玩湃"})
+    @ApiImplicitParams({
+            @ApiImplicitParam(value = "经纬", name = "lon", dataType = "string", required = true),
+            @ApiImplicitParam(value = "纬度", name = "lat", dataType = "string", required = true),
+    })
+    public ResultUtil<List<BaseVo>> queryStoreLists(@RequestBody String lon, @RequestBody String lat){
+        if(ToolUtil.isEmpty(lon)){
+            return ResultUtil.paranErr("lon");
+        }
+        if(ToolUtil.isEmpty(lat)){
+            return ResultUtil.paranErr("lat");
+        }
+        try {
+            List<BaseVo> baseVos = storeService.queryStoreLists(lon, lat);
+            return ResultUtil.success(baseVos);
+        }catch (Exception e){
+            e.printStackTrace();
+            return ResultUtil.runErr();
+        }
+    }
+
+
+    /**
+     * 根据门店模糊搜索店铺
+     * @param name
+     * @return
+     */
+    @ResponseBody
+    @PostMapping("/store/queryStoreListByName")
+    public List<Store> queryStoreListByName(@RequestBody String name){
+        try {
+            List<Store> stores = storeService.list(new QueryWrapper<Store>().eq("state", 1).like("name", name));
+            return stores;
+        }catch (Exception e){
+            e.printStackTrace();
+            return new ArrayList<>();
+        }
+    }
+
+
+    /**
+     * 根据门店
+     * @param id
+     * @return
+     */
+    @ResponseBody
+    @PostMapping("/store/queryStoreById")
+    public Store queryStoreById(@RequestBody Integer id){
+        try {
+            return storeService.getById(id);
+        }catch (Exception e){
+            e.printStackTrace();
+            return null;
+        }
+    }
+}
diff --git a/cloud-server-other/src/main/java/com/dsh/other/model/BaseVo.java b/cloud-server-other/src/main/java/com/dsh/other/model/BaseVo.java
new file mode 100644
index 0000000..b190377
--- /dev/null
+++ b/cloud-server-other/src/main/java/com/dsh/other/model/BaseVo.java
@@ -0,0 +1,18 @@
+package com.dsh.other.model;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 16:25
+ */
+@Data
+@ApiModel
+public class BaseVo {
+    @ApiModelProperty("数据id")
+    private Integer id;
+    @ApiModelProperty("名称")
+    private String name;
+}
diff --git a/cloud-server-other/src/main/java/com/dsh/other/model/StoreConfigVo.java b/cloud-server-other/src/main/java/com/dsh/other/model/StoreConfigVo.java
new file mode 100644
index 0000000..330fe1c
--- /dev/null
+++ b/cloud-server-other/src/main/java/com/dsh/other/model/StoreConfigVo.java
@@ -0,0 +1,22 @@
+package com.dsh.other.model;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author zhibing.pu
+ * @date 2023/6/24 16:16
+ */
+@Data
+@ApiModel
+public class StoreConfigVo {
+    @ApiModelProperty(" 数据类型(1=报名玩湃课程,2=预约场地,3=报名赛事及活动,4=免费福利,5=线上课程积分,6=购买优惠门票,7=看视频得奖励,8=智慧球场)")
+    private Integer type;
+    @ApiModelProperty("是否开启(0=否,1=是)")
+    private Integer isOpen;
+    @ApiModelProperty("排序")
+    private Integer sort;
+    @ApiModelProperty("背景图")
+    private String backgroundImage;
+}
diff --git a/cloud-server-other/src/main/java/com/dsh/other/service/StoreService.java b/cloud-server-other/src/main/java/com/dsh/other/service/StoreService.java
index 4bd14d7..e9295fc 100644
--- a/cloud-server-other/src/main/java/com/dsh/other/service/StoreService.java
+++ b/cloud-server-other/src/main/java/com/dsh/other/service/StoreService.java
@@ -2,6 +2,9 @@
 
 import com.baomidou.mybatisplus.extension.service.IService;
 import com.dsh.other.entity.Store;
+import com.dsh.other.model.BaseVo;
+
+import java.util.List;
 
 
 /**
@@ -14,4 +17,24 @@
  */
 public interface StoreService extends IService<Store> {
 
+
+    /**
+     * 获取列表数据
+     * @param provinceCode
+     * @param cityCode
+     * @return
+     * @throws Exception
+     */
+    List<Store> queryStorsList(String provinceCode, String cityCode) throws Exception;
+
+
+    /**
+     * 获取门店列表
+     * @param lon
+     * @param lat
+     * @return
+     * @throws Exception
+     */
+    List<BaseVo> queryStoreLists(String lon, String lat) throws Exception;
+
 }
diff --git a/cloud-server-other/src/main/java/com/dsh/other/service/impl/StoreServiceImpl.java b/cloud-server-other/src/main/java/com/dsh/other/service/impl/StoreServiceImpl.java
index 55d882f..ec71bcf 100644
--- a/cloud-server-other/src/main/java/com/dsh/other/service/impl/StoreServiceImpl.java
+++ b/cloud-server-other/src/main/java/com/dsh/other/service/impl/StoreServiceImpl.java
@@ -1,11 +1,21 @@
 package com.dsh.other.service.impl;
 
 
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import com.dsh.other.entity.Store;
 import com.dsh.other.mapper.StoreMapper;
+import com.dsh.other.model.BaseVo;
 import com.dsh.other.service.StoreService;
+import com.dsh.other.util.GDMapGeocodingUtil;
+import com.dsh.other.util.ToolUtil;
+import org.springframework.beans.BeanUtils;
+import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
 
 /**
  * <p>
@@ -18,4 +28,52 @@
 @Service
 public class StoreServiceImpl extends ServiceImpl<StoreMapper,Store> implements StoreService {
 
+    @Autowired
+    private GDMapGeocodingUtil gdMapGeocodingUtil;
+
+
+    /**
+     * 获取列表数据
+     * @param provinceCode
+     * @param cityCode
+     * @return
+     * @throws Exception
+     */
+    @Override
+    public List<Store> queryStorsList(String provinceCode, String cityCode) throws Exception {
+        QueryWrapper objectQueryWrapper = new QueryWrapper<Store>().eq("state", 1);
+        if(ToolUtil.isNotEmpty(provinceCode)){
+            objectQueryWrapper.eq("provinceCode", provinceCode);
+        }
+        if(ToolUtil.isNotEmpty(cityCode)){
+            objectQueryWrapper.eq("cityCode", cityCode);
+        }
+        List<Store> list = this.list(objectQueryWrapper);
+        return list;
+    }
+
+
+    /**
+     * 获取列表数据
+     * @param lon
+     * @param lat
+     * @return
+     * @throws Exception
+     */
+    @Override
+    public List<BaseVo> queryStoreLists(String lon, String lat) throws Exception {
+        Map<String, String> geocode = gdMapGeocodingUtil.geocode(lon, lat);
+        List<BaseVo> list = new ArrayList<>();
+        if(null != geocode){
+            String provinceCode = geocode.get("provinceCode");
+            String cityCode = geocode.get("cityCode");
+            List<Store> stores = this.queryStorsList(provinceCode, cityCode);
+            for (Store store : stores) {
+                BaseVo baseVo = new BaseVo();
+                BeanUtils.copyProperties(store, baseVo);
+                list.add(baseVo);
+            }
+        }
+        return list;
+    }
 }
diff --git a/cloud-server-other/src/main/java/com/dsh/other/util/GDMapGeocodingUtil.java b/cloud-server-other/src/main/java/com/dsh/other/util/GDMapGeocodingUtil.java
new file mode 100644
index 0000000..13f02f7
--- /dev/null
+++ b/cloud-server-other/src/main/java/com/dsh/other/util/GDMapGeocodingUtil.java
@@ -0,0 +1,148 @@
+package com.dsh.other.util;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import com.dsh.other.util.httpClinet.HttpClientUtil;
+import com.dsh.other.util.httpClinet.HttpResult;
+import org.springframework.stereotype.Component;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * 高德地图的地理编码工具类
+ */
+@Component
+public class GDMapGeocodingUtil {
+
+    private String key = "fb131ad2dbfb3f39d7d37d244b92aa2d";
+
+
+    /**
+     * 将行政区域名称转化为坐标
+     * @param province
+     * @param city
+     * @param county
+     * @param address
+     * @return
+     */
+    public Map<String, Object> geocoding(String province, String city, String county, String address) throws Exception{
+        Map<String, Object> map = new HashMap<>();
+        if(ToolUtil.isEmpty(province)){
+            map.put("status", -1);
+            map.put("data", "省不能为空");
+            return map;
+        }
+        if((ToolUtil.isEmpty(city) && ToolUtil.isNotEmpty(county)) || (ToolUtil.isEmpty(city) && ToolUtil.isNotEmpty(address))){
+            map.put("status", -1);
+            map.put("data", "市不能为空");
+            return map;
+        }
+        if((ToolUtil.isEmpty(county) && ToolUtil.isNotEmpty(address))){
+            map.put("status", -1);
+            map.put("data", "县/区不能为空");
+            return map;
+        }
+
+        String url = "https://restapi.amap.com/v3/geocode/geo?key=" + key + "&output=JSON";
+        url += "&address=" + province + (ToolUtil.isNotEmpty(city) ? city : "") + (ToolUtil.isNotEmpty(county) ? county : "") + (ToolUtil.isNotEmpty(address) ? address : "");
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        JSONObject jsonObject = JSON.parseObject(httpResult.getData());
+        String status = jsonObject.getString("status");
+        List<String> list = new ArrayList<>();
+
+        if(status.equals("1")){
+            JSONArray geocodes = jsonObject.getJSONArray("geocodes");
+            for(int i = 0; i < geocodes.size(); i++){
+                String location = geocodes.getJSONObject(i).getString("location");
+                list.add(location);
+            }
+        }
+        map.put("status", 0);
+        map.put("data", list);
+        return map;
+    }
+
+
+
+    public Map<String, Object> geocoding(String address) throws Exception{
+        Map<String, Object> map = new HashMap<>();
+        String url = "https://restapi.amap.com/v3/geocode/geo?key=" + key + "&output=JSON&address=" + address;
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        JSONObject jsonObject = JSON.parseObject(httpResult.getData());
+        String status = jsonObject.getString("status");
+        List<String> list = new ArrayList<>();
+
+        if(status.equals("1")){
+            JSONArray geocodes = jsonObject.getJSONArray("geocodes");
+            for(int i = 0; i < geocodes.size(); i++){
+                String location = geocodes.getJSONObject(i).getString("location");
+                list.add(location);
+            }
+        }
+        map.put("status", 0);
+        map.put("data", list);
+        return map;
+    }
+
+
+
+    /**
+     * 根据经纬度获取行政区域信息
+     * @param lon
+     * @param lan
+     * @return
+     * @throws Exception
+     */
+    public Map<String, String> geocode(String lon, String lan) throws Exception{
+        String url = "https://restapi.amap.com/v3/geocode/regeo?key=" + key + "&location=" + lon + "," + lan;
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        JSONObject jsonObject = JSON.parseObject(httpResult.getData());
+        Map<String, String> map = new HashMap<>();
+
+        if(jsonObject.getString("status").equals("1")){
+            JSONObject regeocode = jsonObject.getJSONObject("regeocode");
+            JSONObject addressComponent = regeocode.getJSONObject("addressComponent");
+            String address = regeocode.getString("formatted_address");
+            map.put("address", address);
+            String code = addressComponent.getString("adcode");
+            String province = addressComponent.getString("province");
+            String city = addressComponent.getString("city");
+            String district = addressComponent.getString("district");
+            map.put("province", province);
+            map.put("provinceCode", code.substring(0, 2) + "0000");
+            map.put("city", city);
+            map.put("cityCode", code.substring(0, 4) + "00");
+            map.put("district", district);
+            map.put("districtCode", code);
+        }
+        return map;
+    }
+
+
+    /**
+     * 坐标转换
+     * @param locations 经度和纬度用","分割,经度在前,纬度在后,经纬度小数点后不得超过6位。多个坐标对之间用”|”进行分隔最多支持40对坐标。
+     * @param coordsys  可选值:gps;mapbar;baidu;autonavi(不进行转换)
+     * @return
+     * @throws Exception
+     */
+    public Map<String, String> convert(String locations, String coordsys) throws Exception{
+        String url = "https://restapi.amap.com/v3/assistant/coordinate/convert?locations=" + locations + "&coordsys=" + coordsys + "&output=json&key=" + key;
+        HttpResult httpResult = HttpClientUtil.pushHttpRequset("GET", url, null, null, "json");
+        JSONObject jsonObject = JSON.parseObject(httpResult.getData());
+        Map<String, String> map = new HashMap<>();
+        if("1".equals(jsonObject.getString("status"))){
+            map.put("code", jsonObject.getString("infocode"));//"10000"
+            map.put("info", jsonObject.getString("info"));//status为0时,info返回错误原;否则返回“OK”。
+            map.put("locations", jsonObject.getString("locations").split(";")[0]);//转换之后的坐标。若有多个坐标,则用 “;”进行区分和间隔
+        }else{
+            map.put("code", jsonObject.getString("infocode"));
+            map.put("info", jsonObject.getString("info"));//status为0时,info返回错误原;否则返回“OK”。
+        }
+        return map;
+    }
+}
diff --git a/cloud-server-other/src/main/java/com/dsh/other/util/ResultUtil.java b/cloud-server-other/src/main/java/com/dsh/other/util/ResultUtil.java
index e84ecdd..6e47fcc 100644
--- a/cloud-server-other/src/main/java/com/dsh/other/util/ResultUtil.java
+++ b/cloud-server-other/src/main/java/com/dsh/other/util/ResultUtil.java
@@ -3,7 +3,6 @@
 import com.alibaba.fastjson.JSONObject;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
-import org.springframework.beans.factory.annotation.Autowired;
 
 /**
  * 定义统一返回对象
@@ -107,8 +106,8 @@
      * 参数异常
      * @return
      */
-    public static  ResultUtil paranErr(){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", new JSONObject());
+    public static  ResultUtil paranErr(String ages){
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "【" + ages + "】参数异常", new JSONObject());
     }
 
     /**
@@ -116,11 +115,10 @@
      * @return
      */
     public static <T> ResultUtil<T> paranErr(T data){
-        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "SYSTEM_RUN_ERROR", data);
+        return ResultUtil.getResult(ResultUtil.PARAM_ERROR, "PARAM_ERROR", data);
     }
 
-    @Autowired
-    private static MessageUtils messageUtils;
+
     /**
      * 运行异常
      * @return
diff --git a/cloud-server-other/src/main/java/com/dsh/other/util/TokenUtil.java b/cloud-server-other/src/main/java/com/dsh/other/util/TokenUtil.java
index 5e5a53d..66d5232 100644
--- a/cloud-server-other/src/main/java/com/dsh/other/util/TokenUtil.java
+++ b/cloud-server-other/src/main/java/com/dsh/other/util/TokenUtil.java
@@ -2,6 +2,8 @@
 
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Component;
+import org.springframework.web.context.request.RequestContextHolder;
+import org.springframework.web.context.request.ServletRequestAttributes;
 
 import javax.servlet.http.HttpServletRequest;
 
@@ -12,7 +14,9 @@
     private RedisUtil redisUtil;
 
 
-    public Integer getUserIdFormRedis(HttpServletRequest request) throws Exception {
+    public Integer getUserIdFormRedis() throws Exception {
+        ServletRequestAttributes servletRequestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
+        HttpServletRequest request = servletRequestAttributes.getRequest();
         String requestHeader = request.getHeader("Authorization");
         if (requestHeader != null && requestHeader.startsWith("Bearer ")) {
             requestHeader = requestHeader.substring(requestHeader.indexOf(" ") + 1);
diff --git a/cloud-server-other/src/main/java/com/dsh/other/util/httpClinet/HttpClientUtil.java b/cloud-server-other/src/main/java/com/dsh/other/util/httpClinet/HttpClientUtil.java
new file mode 100644
index 0000000..f88e02d
--- /dev/null
+++ b/cloud-server-other/src/main/java/com/dsh/other/util/httpClinet/HttpClientUtil.java
@@ -0,0 +1,267 @@
+package com.dsh.other.util.httpClinet;
+
+import com.alibaba.fastjson.JSON;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import org.apache.http.NameValuePair;
+import org.apache.http.client.config.RequestConfig;
+import org.apache.http.client.entity.UrlEncodedFormEntity;
+import org.apache.http.client.methods.CloseableHttpResponse;
+import org.apache.http.client.methods.HttpGet;
+import org.apache.http.client.methods.HttpPost;
+import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
+import org.apache.http.entity.ContentType;
+import org.apache.http.entity.StringEntity;
+import org.apache.http.impl.client.CloseableHttpClient;
+import org.apache.http.impl.client.HttpClients;
+import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
+import org.apache.http.message.BasicNameValuePair;
+import org.apache.http.ssl.SSLContexts;
+import org.apache.http.util.EntityUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import javax.net.ssl.SSLContext;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.InputStream;
+import java.nio.charset.Charset;
+import java.security.KeyStore;
+import java.text.SimpleDateFormat;
+import java.util.*;
+import java.util.concurrent.TimeUnit;
+
+/**
+ * http工具类
+ */
+public class HttpClientUtil {
+
+    private static Logger logger = LoggerFactory.getLogger(HttpClientUtil.class);
+
+    private static PoolingHttpClientConnectionManager connectionManager;
+
+
+    {
+        //1.创建连接池管理器
+        connectionManager = new PoolingHttpClientConnectionManager(60000,
+                TimeUnit.MILLISECONDS);
+        connectionManager.setMaxTotal(1000);
+        connectionManager.setDefaultMaxPerRoute(50);
+    }
+
+    /**
+     * 创建一个httpClient对象
+     */
+    private static CloseableHttpClient getHttpCline(){
+        return  HttpClients.custom()
+                .setConnectionManager(connectionManager)
+                .disableAutomaticRetries()
+                .build();
+    }
+
+    private static RequestConfig getRequestConfig(){
+        RequestConfig.Builder builder = RequestConfig.custom();
+        builder.setSocketTimeout(60000)//3.1设置客户端等待服务端返回数据的超时时间
+                .setConnectTimeout(30000)//3.2设置客户端发起TCP连接请求的超时时间
+                .setExpectContinueEnabled(true)
+                .setConnectionRequestTimeout(30000);//3.3设置客户端从连接池获取链接的超时时间
+        return builder.build();
+    }
+
+
+
+    /**
+     * 创建一个POST请求实例
+     * @param url       请求地址
+     * @param params    请求参数
+     */
+    private static CloseableHttpResponse setPostHttpRequset(String url, Map<String, Object> params, Map<String, String> header, String contentType) throws Exception{
+        HttpPost httpPost = new HttpPost(url);
+        httpPost.setConfig(getRequestConfig());
+        if(null != header){
+            for(String key : header.keySet()){
+                httpPost.setHeader(key, header.get(key));
+            }
+        }
+        List<NameValuePair> list = new ArrayList<>();
+        if(null != params){
+            Set<String> keys = params.keySet();
+            for(String key : keys){
+                list.add(new BasicNameValuePair(key, null == params.get(key) ? null : params.get(key).toString()));
+            }
+        }
+        switch (contentType){
+            case "form":
+                httpPost.setEntity(new UrlEncodedFormEntity(list, "UTF-8"));
+                break;
+            case "json":
+                ObjectMapper objectMapper = new ObjectMapper();
+                String s =objectMapper.writeValueAsString(params);
+                httpPost.setEntity(new StringEntity(s, ContentType.create(ContentType.APPLICATION_JSON.getMimeType(), Charset.forName("UTF-8"))));
+                break;
+        }
+        return getHttpCline().execute(httpPost);
+    }
+
+
+    /**
+     * 获取get请求实例
+     * @param url       请求地址
+     * @param params    请求参数
+     */
+    private static CloseableHttpResponse setGetHttpRequset(String url, Map<String, Object> params, Map<String, String> header) throws Exception{
+        StringBuffer sb = new StringBuffer();
+        String p = "";
+        if(null != params){
+            Set<String> keys = params.keySet();
+            for(String key : keys){
+                sb.append(key + "=" + params.get(key) + "&");
+            }
+            p = "?" + sb.substring(0, sb.length() - 1);
+        }
+        HttpGet httpGet = new HttpGet(url + p);
+        httpGet.setConfig(getRequestConfig());
+        if(null != header){
+            for(String key : header.keySet()){
+                httpGet.setHeader(key, header.get(key));
+            }
+        }
+        return getHttpCline().execute(httpGet);
+    }
+
+
+    /**
+     * 发送http请求
+     * @param mothed        "GET、POST、PUT、HEAD、DELETE、HEAD、OPTIONS"
+     * @param url           请求地址
+     * @param params        请求参数
+     * @param header        请求头
+     * @param contentType   参数请求方式form/json
+     * @return
+     */
+    public static HttpResult pushHttpRequset(String mothed, String url, Map<String, Object> params, Map<String, String> header, String contentType) throws Exception{
+        String randome = UUID.randomUUID().toString();
+        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.S");
+        logger.info(sdf.format(new Date()) + "----(" + randome + ")请求参数:" + JSON.toJSONString(params));
+        CloseableHttpResponse httpResponse = null;
+        switch (mothed){
+            case "GET":
+                httpResponse = setGetHttpRequset(url, params, header);
+                break;
+            case "POST":
+                httpResponse = setPostHttpRequset(url, params, header, contentType);
+                break;
+        }
+        int statusCode = httpResponse.getStatusLine().getStatusCode();
+        String content = EntityUtils.toString(httpResponse.getEntity(), "UTF-8");
+        logger.info(sdf.format(new Date()) + "----(" + randome + ")返回结果:" + content);
+        HttpResult httpResult = HttpResult.getHttpResult(statusCode, content);
+        close(httpResponse);
+        return httpResult;
+    }
+
+
+    /**
+     * 发送XML请求
+     * @param url       请求地址
+     * @param xml       XML数据
+     * @param header    自定义请求头
+     * @return
+     */
+    public static HttpResult pushHttpRequsetXml(String url, String xml, Map<String, String> header) throws Exception{
+        HttpPost httpPost = new HttpPost(url);
+        httpPost.setConfig(getRequestConfig());
+        for(String key : header.keySet()){
+            httpPost.setHeader(key, header.get(key));
+        }
+        httpPost.setHeader("Content-Type", "application/xml");
+        httpPost.setEntity(new StringEntity(xml, "UTF-8"));
+        CloseableHttpResponse httpResponse = getHttpCline().execute(httpPost);
+        int statusCode = httpResponse.getStatusLine().getStatusCode();
+        String content = EntityUtils.toString(httpResponse.getEntity(), "UTF-8");
+        HttpResult httpResult = HttpResult.getHttpResult(statusCode, content);
+        close(httpResponse);
+        return httpResult;
+    }
+
+
+
+    /**
+     * 请求https发送XML请求
+     * @param url           接口路径
+     * @param xml           内容
+     * @param header        请求头
+     * @param certPassword      证书密码
+     * @param certPath      证书路径
+     * @param certType      证书类型
+     * @return
+     * @throws Exception
+     */
+    public String pushHttpsRequsetXml(String url, String xml, Map<String, String> header, String certPassword, String certPath, String certType) throws Exception{
+        HttpPost httpPost = new HttpPost(url);
+        for(String key : header.keySet()){
+            httpPost.setHeader(key, header.get(key));
+        }
+        httpPost.setHeader("Content-Type", "application/xml");
+        httpPost.setEntity(new StringEntity(xml, "UTF-8"));
+        CloseableHttpClient httpCline = this.initCert(certPassword, certPath, certType);
+        CloseableHttpResponse httpResponse = httpCline.execute(httpPost);
+        String content = null;
+        if(httpResponse.getStatusLine().getStatusCode() == 200){
+            content = EntityUtils.toString(httpResponse.getEntity(), "UTF-8");
+        }else{
+            content = "返回状态码:" + httpResponse.getStatusLine() + "。" + EntityUtils.toString(httpResponse.getEntity());
+        }
+        this.close(httpResponse);
+        httpCline.close();
+        return content;
+    }
+
+
+    /**
+     * 初始化https对象(带证书)
+     * @param key       证书密码
+     * @param certPath  证书路径
+     * @param certType  证书类型
+     * @throws Exception
+     */
+    private CloseableHttpClient initCert(String key, String certPath, String certType) throws Exception {
+        KeyStore keyStore = KeyStore.getInstance(certType);
+        InputStream inputStream = new FileInputStream(new File(certPath));
+        try {
+            keyStore.load(inputStream, key.toCharArray());
+        } finally {
+            inputStream.close();
+        }
+        SSLContext sslcontext = SSLContexts.custom().loadKeyMaterial(keyStore, key.toCharArray()).build();
+        SSLConnectionSocketFactory sslsf =
+                new SSLConnectionSocketFactory(sslcontext, new String[] {"TLSv1"}, null,
+                        SSLConnectionSocketFactory.BROWSER_COMPATIBLE_HOSTNAME_VERIFIER);
+        return HttpClients.custom().setSSLSocketFactory(sslsf).build();
+    }
+
+
+
+    /**
+     * 关闭资源
+     */
+    private static void close(CloseableHttpResponse httpResponse){
+        try {
+            if(null != httpResponse){
+                EntityUtils.consume(httpResponse.getEntity());//此处高能,通过源码分析,由EntityUtils是否回收HttpEntity
+                httpResponse.close();
+            }
+        } catch (Exception e) {
+            e.printStackTrace();
+        }finally {
+            try {
+                if(null != httpResponse){
+                    httpResponse.close();
+                }
+            }catch (Exception e){
+                e.printStackTrace();
+            }
+        }
+    }
+
+
+}
diff --git a/cloud-server-other/src/main/java/com/dsh/other/util/httpClinet/HttpResult.java b/cloud-server-other/src/main/java/com/dsh/other/util/httpClinet/HttpResult.java
new file mode 100644
index 0000000..7db2b84
--- /dev/null
+++ b/cloud-server-other/src/main/java/com/dsh/other/util/httpClinet/HttpResult.java
@@ -0,0 +1,31 @@
+package com.dsh.other.util.httpClinet;
+
+import lombok.Data;
+
+/**
+ * http请求返回封装
+ */
+@Data
+public class HttpResult {
+    /**
+     * 返回状态码
+     */
+    private Integer code;
+    /**
+     * 返回结果
+     */
+    private String data;
+
+    /**
+     * 返回封装结果
+     * @param code
+     * @param data
+     * @return
+     */
+    public static HttpResult getHttpResult(Integer code, String data){
+        HttpResult httpResult = new HttpResult();
+        httpResult.setCode(code);
+        httpResult.setData(data);
+        return httpResult;
+    }
+}

--
Gitblit v1.7.1