Browse Source

complete app api

huodongdong 7 years ago
parent
commit
9585210305
73 changed files with 1850 additions and 112 deletions
  1. 19 12
      rankin-api-web/src/main/java/cn/rankin/apiweb/controller/CollectionController.java
  2. 72 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/controller/CourseController.java
  3. 26 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/controller/LessonController.java
  4. 22 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/controller/SupportController.java
  5. 27 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/controller/TagController.java
  6. 10 8
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/auth/AuthClient.java
  7. 26 18
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/auth/AuthService.java
  8. 10 2
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/collection/CollectionClient.java
  9. 72 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/collection/CollectionService.java
  10. 66 5
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/product/ProductClient.java
  11. 63 5
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/product/ProductService.java
  12. 18 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/resource/ResourceClient.java
  13. 93 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/resource/ResourceService.java
  14. 22 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/tag/TagClient.java
  15. 33 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/tag/TagService.java
  16. 70 2
      rankin-api-web/src/main/java/cn/rankin/apiweb/utils/DTOConverter.java
  17. 1 1
      rankin-api-web/src/main/resources/bootstrap.yml
  18. 22 0
      rankin-data-api/src/main/java/cn/rankin/data/api/app/dto/ItemSearchDTO.java
  19. 36 0
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/CourseDetailVo.java
  20. 22 0
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/CourseVo.java
  21. 4 7
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/ProductVo.java
  22. 5 2
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/GoodsVo.java
  23. 9 2
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/ProductVo.java
  24. 20 0
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/LessonVo.java
  25. 3 3
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/GoodsVo.java
  26. 16 0
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/TagGroupVo.java
  27. 2 4
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/GoodsVo.java
  28. 20 0
      rankin-data-api/src/main/java/cn/rankin/data/api/auth/dto/AuthQueryDTO.java
  29. 17 0
      rankin-data-api/src/main/java/cn/rankin/data/api/auth/dto/InnerAuthDTO.java
  30. 40 0
      rankin-data-api/src/main/java/cn/rankin/data/api/auth/vo/AuthResult.java
  31. 36 0
      rankin-data-api/src/main/java/cn/rankin/data/api/auth/vo/AuthVo.java
  32. 2 0
      rankin-data-api/src/main/java/cn/rankin/data/api/product/dto/SupportDTO.java
  33. 3 0
      rankin-data-api/src/main/java/cn/rankin/data/api/product/entity/Support.java
  34. 42 0
      rankin-data-api/src/main/java/cn/rankin/data/api/product/vo/CourseItemVo.java
  35. 2 0
      rankin-data-api/src/main/java/cn/rankin/data/api/product/vo/CourseSubItemVo.java
  36. 35 0
      rankin-data-api/src/main/java/cn/rankin/data/api/product/vo/SupportItemVo.java
  37. 2 0
      rankin-data-api/src/main/java/cn/rankin/data/api/product/vo/SupportVo.java
  38. 16 0
      rankin-product-service/pom.xml
  39. 2 0
      rankin-product-service/src/main/java/cn/rankin/productservice/ProductServiceApplication.java
  40. 46 0
      rankin-product-service/src/main/java/cn/rankin/productservice/configuration/FeignConfiguration.java
  41. 20 0
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/AppLessonController.java
  42. 32 0
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/AppTagController.java
  43. 44 0
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/CourseController.java
  44. 35 0
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/ItemController.java
  45. 25 0
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/SupportController.java
  46. 26 0
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/auth/AuthController.java
  47. 1 1
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/GoodsController.java
  48. 1 1
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/LessonController.java
  49. 1 1
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/MerchantProductController.java
  50. 1 1
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/ProductController.java
  51. 1 1
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/RecommendController.java
  52. 1 1
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/TagController.java
  53. 1 1
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/TagGroupController.java
  54. 1 1
      rankin-product-service/src/main/java/cn/rankin/productservice/controller/WareController.java
  55. 2 0
      rankin-product-service/src/main/java/cn/rankin/productservice/repository/CourseSubRelationRepository.java
  56. 4 0
      rankin-product-service/src/main/java/cn/rankin/productservice/repository/CourseSupportRelationRepository.java
  57. 3 0
      rankin-product-service/src/main/java/cn/rankin/productservice/repository/GoodsRepository.java
  58. 1 1
      rankin-product-service/src/main/java/cn/rankin/productservice/repository/MerchantProductRepository.java
  59. 4 1
      rankin-product-service/src/main/java/cn/rankin/productservice/repository/ProductTagRelationRepository.java
  60. 4 0
      rankin-product-service/src/main/java/cn/rankin/productservice/repository/PackageProductRelationRepository.java
  61. 3 0
      rankin-product-service/src/main/java/cn/rankin/productservice/repository/TagGroupRepository.java
  62. 10 0
      rankin-product-service/src/main/java/cn/rankin/productservice/service/CourseService.java
  63. 299 0
      rankin-product-service/src/main/java/cn/rankin/productservice/service/ItemService.java
  64. 2 2
      rankin-product-service/src/main/java/cn/rankin/productservice/service/MerchantProductTagRelationService.java
  65. 9 0
      rankin-product-service/src/main/java/cn/rankin/productservice/service/TagGroupService.java
  66. 67 0
      rankin-product-service/src/main/java/cn/rankin/productservice/service/app/AppLessonService.java
  67. 31 0
      rankin-product-service/src/main/java/cn/rankin/productservice/service/auth/AuthClient.java
  68. 98 0
      rankin-product-service/src/main/java/cn/rankin/productservice/service/auth/AuthService.java
  69. 2 1
      rankin-product-service/src/main/java/cn/rankin/productservice/utils/DTOConverter.java
  70. 37 26
      rankin-product-service/src/main/java/cn/rankin/productservice/utils/TestUtil.java
  71. 10 0
      rankin-product-service/src/main/resources/bootstrap.yml
  72. 7 2
      rankin-user-service/src/main/java/cn/rankin/userservice/controller/CollectionController.java
  73. 15 0
      rankin-user-service/src/main/java/cn/rankin/userservice/service/CollectionService.java

+ 19 - 12
rankin-api-web/src/main/java/cn/rankin/apiweb/controller/CollectionController.java

@@ -5,11 +5,11 @@ import cn.rankin.apiweb.service.collection.CollectionService;
 import cn.rankin.common.utils.api.model.APIResult;
 import cn.rankin.common.utils.api.page.Page;
 import cn.rankin.data.api.app.vo.DeviceUserVo;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.user.dto.CollectionDTO;
+import org.apache.commons.lang.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.web.bind.annotation.RequestMapping;
-import org.springframework.web.bind.annotation.RequestMethod;
-import org.springframework.web.bind.annotation.RequestParam;
-import org.springframework.web.bind.annotation.RestController;
+import org.springframework.web.bind.annotation.*;
 
 @RestController
 @RequestMapping(value = "/user/collection")
@@ -19,18 +19,25 @@ public class CollectionController {
     private CollectionService collectionService;
 
     @RequestMapping(method = RequestMethod.POST)
-    public APIResult<Boolean> put(@NeedUser DeviceUserVo user, @RequestParam("pid") String productId) {
-        return null;
+    public APIResult<Boolean> put(@NeedUser DeviceUserVo user, @RequestBody CollectionDTO collectionDTO) {
+        return collectionService.put(user.getUid(), user.getMerchantId(), collectionDTO.getPid());
     }
 
-    @RequestMapping(method = RequestMethod.DELETE)
-    public APIResult<Boolean> delete(@NeedUser DeviceUserVo user, @RequestParam("pid") String productId) {
-        return null;
+    @RequestMapping(value = "/{productId}", method = RequestMethod.DELETE)
+    public APIResult<Boolean> delete(@NeedUser DeviceUserVo user, @PathVariable("productId") String productId) {
+        return collectionService.delete(user.getUid(), productId);
     }
 
     @RequestMapping(method = RequestMethod.GET)
-    public APIResult<Page> getPage(@NeedUser DeviceUserVo user, @RequestParam("tagId") String tagId, @RequestParam("pageNo") Integer pageNo,
-                                   @RequestParam("pageSize") Integer pageSize) {
-        return null;
+    public APIResult<Page<ItemVo>> getPage(@NeedUser DeviceUserVo user, @RequestParam(value = "tagId", required = false) String tagId,
+                                           @RequestParam(value = "pageNo", defaultValue = "0") Integer pageNo,
+                                           @RequestParam(value = "pageSize", defaultValue = "10") Integer pageSize) {
+        String userId = user.getUid();
+        String merchantId = user.getMerchantId();
+        if (StringUtils.isEmpty(tagId)) {
+            return collectionService.getUserCollection(userId, merchantId, pageNo, pageSize);
+        }else {
+            return collectionService.getUserCollection(userId, merchantId, tagId, pageNo, pageSize);
+        }
     }
 }

+ 72 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/controller/CourseController.java

@@ -1,4 +1,76 @@
 package cn.rankin.apiweb.controller;
 
+import cn.rankin.apiweb.assist.resolver.NeedUser;
+import cn.rankin.apiweb.service.auth.AuthService;
+import cn.rankin.apiweb.service.collection.CollectionService;
+import cn.rankin.apiweb.service.product.ProductService;
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.app.vo.CourseDetailVo;
+import cn.rankin.data.api.app.vo.CourseVo;
+import cn.rankin.data.api.app.vo.DeviceUserVo;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.auth.vo.AuthResult;
+import cn.rankin.data.api.user.entity.Collection;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+
+@RestController
+@RequestMapping(value = "/course")
 public class CourseController {
+
+    @Autowired
+    private CollectionService collectionService;
+
+    @Autowired
+    private ProductService productService;
+
+    @Autowired
+    private AuthService authService;
+
+    @RequestMapping(value = "/{courseId}/lessons", method = RequestMethod.GET)
+    public APIResult<CourseVo> getCourseLessons(@NeedUser DeviceUserVo user, @PathVariable("courseId") String courseId) {
+        String userId = user.getUid();
+        String merchantId = user.getMerchantId();
+        APIResult<CourseVo> apiResult = productService.getCourseLessons(courseId);
+        if (!apiResult.getSuccess()) {
+            return apiResult;
+        }
+        CourseVo courseVo = apiResult.getData();
+        Boolean auth = authService.isValid(userId, merchantId, courseId);
+        courseVo.setAuth(auth);
+
+        Boolean isCollected = collectionService.isCollected(userId, courseId);
+        courseVo.setCollected(isCollected);
+        return apiResult;
+    }
+
+    @RequestMapping(value = "/{courseId}/detail", method = RequestMethod.GET)
+    public APIResult<CourseDetailVo> getCourseDetail(@NeedUser DeviceUserVo user, @PathVariable("courseId") String courseId) {
+        String merchantId = user.getMerchantId();
+        String userId = user.getUid();
+        APIResult<CourseDetailVo> courseDetailVoAPIResult = productService.getCourseDetail(courseId, merchantId);
+        CourseDetailVo courseDetailVo = courseDetailVoAPIResult.getData();
+        if (!courseDetailVoAPIResult.getSuccess() || courseDetailVo == null) {
+            return courseDetailVoAPIResult;
+        }
+
+        courseDetailVo.setCollected(collectionService.isCollected(userId, courseId));
+        APIResult<AuthResult> authApiResult = authService.auth(userId, merchantId, courseId);
+        if (authApiResult.getSuccess()) {
+            AuthResult authResult = authApiResult.getData();
+            courseDetailVo.setAuth(authResult.isValid());
+            courseDetailVo.setBeginTime(authResult.getStartTime());
+            courseDetailVo.setEndTime(authResult.getEndTime());
+        }
+
+        return courseDetailVoAPIResult;
+    }
+
+    @RequestMapping(value = "/{courseId}/supports", method = RequestMethod.GET)
+    public APIResult<List<ItemVo>> getSupportByCourseId(@NeedUser DeviceUserVo user, @PathVariable("courseId") String courseId) {
+        String merchantId = user.getMerchantId();
+        return productService.getSupportByCourseId(courseId, merchantId);
+    }
 }

+ 26 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/controller/LessonController.java

@@ -1,4 +1,30 @@
 package cn.rankin.apiweb.controller;
 
+import cn.rankin.apiweb.assist.resolver.NeedUser;
+import cn.rankin.apiweb.service.auth.AuthService;
+import cn.rankin.apiweb.service.product.ProductService;
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.app.vo.DeviceUserVo;
+import cn.rankin.data.api.app.vo.LessonVo;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+@RestController
+@RequestMapping(value = "/lesson")
 public class LessonController {
+
+    @Autowired
+    private ProductService productService;
+
+    @Autowired
+    private AuthService authService;
+
+    @RequestMapping(value = "/{lessonId}", method = RequestMethod.GET)
+    public APIResult<LessonVo> getLesson(@NeedUser DeviceUserVo user, @PathVariable("lessonId") String lessonId, @RequestParam("courseId") String courseId) {
+        String userId = user.getUid();
+        String merchantId = user.getMerchantId();
+        // 加入鉴权
+        Boolean auth = authService.isValid(userId, merchantId, courseId);
+        return productService.getLesson(lessonId, courseId, auth);
+    }
 }

+ 22 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/controller/SupportController.java

@@ -1,4 +1,26 @@
 package cn.rankin.apiweb.controller;
 
+import cn.rankin.apiweb.assist.resolver.NeedUser;
+import cn.rankin.apiweb.service.product.ProductService;
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.app.vo.DeviceUserVo;
+import cn.rankin.data.api.product.vo.SupportItemVo;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.PathVariable;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+import org.springframework.web.bind.annotation.RestController;
+
+@RestController
+@RequestMapping(value = "/support")
 public class SupportController {
+
+    @Autowired
+    private ProductService productService;
+
+    @RequestMapping(value = "/{supportId}", method = RequestMethod.GET)
+    public APIResult<SupportItemVo> getSupport(@NeedUser DeviceUserVo user, @PathVariable("supportId") String supportId) {
+        String merchantId = user.getMerchantId();
+        return productService.getSupport(supportId, merchantId);
+    }
 }

+ 27 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/controller/TagController.java

@@ -1,4 +1,31 @@
 package cn.rankin.apiweb.controller;
 
+import cn.rankin.apiweb.assist.resolver.NeedUser;
+import cn.rankin.apiweb.service.tag.TagService;
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.api.page.Page;
+import cn.rankin.data.api.app.vo.DeviceUserVo;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.app.vo.TagGroupVo;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+@RestController
 public class TagController {
+
+    @Autowired
+    private TagService tagService;
+
+    @RequestMapping(value = "/tagGroup/{code}", method = RequestMethod.GET)
+    public APIResult<TagGroupVo> getTagGroup(@NeedUser DeviceUserVo user, @PathVariable("code") String code) {
+        String merchantId = user.getMerchantId();
+        return tagService.findTagGroupByCode(code, merchantId);
+    }
+
+    @RequestMapping(value = "/tag/{tagId}", method = RequestMethod.GET)
+    public APIResult<Page<ItemVo>> findItemByTagId(@NeedUser DeviceUserVo user, @PathVariable("tagId") String tagId,
+                                                   @RequestParam("pageNo") Integer pageNo, @RequestParam("pageSize") Integer pageSize) {
+        String merchantId = user.getMerchantId();
+        return tagService.findPageByTagId(tagId, merchantId, pageNo, pageSize);
+    }
 }

+ 10 - 8
rankin-api-web/src/main/java/cn/rankin/apiweb/service/auth/AuthClient.java

@@ -1,16 +1,18 @@
 package cn.rankin.apiweb.service.auth;
 
-import cn.rankin.apiweb.entity.AuthResult;
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.auth.dto.InnerAuthDTO;
+import cn.rankin.data.api.auth.vo.AuthResult;
+import org.springframework.cloud.netflix.feign.FeignClient;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
 
+@FeignClient(name = "${service.product.name}")
 public interface AuthClient {
 
     // 鉴权
-    AuthResult auth(String userId, String itemId);
-
-    // 增加时长
-    AuthResult add(String userId, String itemId, Integer day);
-
-    // 缩减时长
-    AuthResult reduce(String userId, String itemId, Integer day);
+    @RequestMapping(value = "/auth", method = RequestMethod.POST)
+    APIResult<AuthResult> auth(@RequestBody InnerAuthDTO authDTO);
 
 }

+ 26 - 18
rankin-api-web/src/main/java/cn/rankin/apiweb/service/auth/AuthService.java

@@ -1,30 +1,38 @@
 package cn.rankin.apiweb.service.auth;
 
-import cn.rankin.apiweb.entity.AuthResult;
-import org.slf4j.LoggerFactory;
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.auth.dto.InnerAuthDTO;
+import cn.rankin.data.api.auth.vo.AuthResult;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
 @Service
-public class AuthService implements AuthClient {
+@Slf4j
+public class AuthService{
 
-    private final static org.slf4j.Logger log = LoggerFactory.getLogger(AuthService.class);
+    @Autowired
+    private AuthClient authClient;
 
-    @Override
-    public AuthResult auth(String userId, String itemId) {
+    public APIResult<AuthResult> auth(String userId, String merchantId, String itemId) {
         log.info("auth vo: {}, item: {}", userId, itemId);
-        AuthResult auth = new AuthResult(itemId, userId, 0, 0L, null);
-        return auth;
+        InnerAuthDTO authDTO = new InnerAuthDTO();
+        authDTO.setItemId(itemId);
+        authDTO.setUserId(userId);
+        authDTO.setMerchantId(merchantId);
+        APIResult<AuthResult> apiResult = authClient.auth(authDTO);
+        return apiResult;
     }
 
-    @Override
-    public AuthResult add(String userId, String itemId, Integer day) {
-        log.info("add vo: {} item: {} day: {}", userId, itemId, day);
-        return new AuthResult(itemId, userId, 0, 0L, null);
-    }
-
-    @Override
-    public AuthResult reduce(String userId, String itemId, Integer day) {
-        log.info("reduce vo: {} item: {} day: {}", userId, itemId, day);
-        return new AuthResult(itemId, userId, 0, 0L, null);
+    public Boolean isValid(String userId, String merchantId, String itemId) {
+        APIResult<AuthResult> apiResult = this.auth(userId, merchantId, itemId);
+        if (!apiResult.getSuccess()) {
+            return Boolean.FALSE;
+        }
+        AuthResult authResult = apiResult.getData();
+        if (authResult == null) {
+            return Boolean.FALSE;
+        }
+        return authResult.isValid();
     }
 }

+ 10 - 2
rankin-api-web/src/main/java/cn/rankin/apiweb/service/collection/CollectionClient.java

@@ -18,7 +18,10 @@ public interface CollectionClient {
     APIResult<Boolean> put(@RequestBody CollectionDTO collectionDTO);
 
     @RequestMapping(value = "/user/collection", method = RequestMethod.GET)
-    APIResult<List<Collection>> getUserCollection(@RequestParam("userId") String userId, @RequestParam("size") Integer size);
+    APIResult<Collection> getCollection(@RequestParam("userId") String userId, @RequestParam("pid") String productId);
+
+    @RequestMapping(value = "/user/collection/list", method = RequestMethod.GET)
+    APIResult<List<Collection>> getUserCollections(@RequestParam("userId") String userId, @RequestParam("size") Integer size);
 
     @RequestMapping(value = "/user/collection", method = RequestMethod.DELETE)
     APIResult<Boolean> delete(@RequestParam("userId") String userId, @RequestParam("pid") String productId);
@@ -30,12 +33,17 @@ public interface CollectionClient {
     class CollectionServiceHystrix implements CollectionClient {
 
         @Override
+        public APIResult<Collection> getCollection(String userId, String productId) {
+            return APIResult.error(ApiWebCode.SERVER_ERROR);
+        }
+
+        @Override
         public APIResult put(CollectionDTO collectionDTO) {
             return APIResult.error(ApiWebCode.SERVER_ERROR);
         }
 
         @Override
-        public APIResult getUserCollection(String userId, Integer size) {
+        public APIResult getUserCollections(String userId, Integer size) {
             return APIResult.error(ApiWebCode.SERVER_ERROR);
         }
 

+ 72 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/service/collection/CollectionService.java

@@ -4,24 +4,42 @@ import cn.rankin.apiweb.code.ApiWebCode;
 import cn.rankin.apiweb.service.product.ProductService;
 import cn.rankin.common.utils.api.model.APIResult;
 import cn.rankin.common.utils.api.model.BaseCode;
+import cn.rankin.common.utils.api.page.Page;
 import cn.rankin.common.utils.enums.BaseStatusEnum;
+import cn.rankin.data.api.app.dto.ItemSearchDTO;
+import cn.rankin.data.api.app.vo.ItemVo;
 import cn.rankin.data.api.product.entity.MerchantProduct;
 import cn.rankin.data.api.user.dto.CollectionDTO;
+import cn.rankin.data.api.user.entity.Collection;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
+import org.springframework.util.CollectionUtils;
+
+import java.util.ArrayList;
+import java.util.List;
 
 
 @Service
 @Slf4j
 public class CollectionService {
 
+    protected static final int MAX_SIZE = 1000;
+
     @Autowired
     private CollectionClient collectionClient;
 
     @Autowired
     private ProductService productService;
 
+    public Boolean isCollected(String userId, String productId) {
+        APIResult<Collection> apiResult = collectionClient.getCollection(userId, productId);
+        if (apiResult.getSuccess() && apiResult.getData() != null) {
+            return Boolean.TRUE;
+        }
+        return Boolean.FALSE;
+    }
+
     public APIResult<Boolean> put(String userId, String merchantId, String productId) {
         APIResult<MerchantProduct> apiResult = productService.getMerchantProduct(productId, merchantId);
         if (!apiResult.getSuccess()) {
@@ -40,7 +58,61 @@ public class CollectionService {
         collectionDTO.setStatus(BaseStatusEnum.NORMAL);
 
         return collectionClient.put(collectionDTO);
+    }
+
+    public APIResult<Boolean> delete(String userId, String productId) {
+        APIResult<Boolean> apiResult = collectionClient.delete(userId, productId);
+        return apiResult;
+    }
+
+    public APIResult<Page<ItemVo>> getUserCollection(String userId, String merchantId, Integer pageNo, Integer pageSize) {
+        APIResult<Page<Collection>> collectionApiResult = collectionClient.getPage(userId, pageNo, pageSize);
+        if (!collectionApiResult.getSuccess()) {
+            return APIResult.error(new BaseCode(collectionApiResult.getCode(), collectionApiResult.getMessage()));
+        }
+        Page<Collection> collectionPage = collectionApiResult.getData();
+        List<Collection> collectionList = collectionPage.getList();
+        if (CollectionUtils.isEmpty(collectionList)) {
+            return APIResult.error(new BaseCode(collectionApiResult.getCode(), collectionApiResult.getMessage()));
+        }
+
+        Page<ItemVo> page = new Page(collectionPage.getTotalSize(), collectionPage.getPageNo(), collectionPage.getPageSize());
+
+        List<String> productIdList = new ArrayList<>();
+        collectionList.forEach(collection -> productIdList.add(collection.getPid()));
+        APIResult<List<ItemVo>> itemApiResult = productService.findItemByIds(merchantId, productIdList);
+        if (!itemApiResult.getSuccess()) {
+            return APIResult.error(new BaseCode(itemApiResult.getCode(), itemApiResult.getMessage()));
+        }
+        List<ItemVo> itemVoList = itemApiResult.getData();
+        page.setList(itemVoList);
+
+        return APIResult.ok(page);
+    }
+
+    public APIResult<Page<ItemVo>> getUserCollection(String userId, String merchantId, String tagId, Integer pageNo, Integer pageSize) {
+        APIResult<List<Collection>> collectionApiResult = collectionClient.getUserCollections(userId, MAX_SIZE);
+        if (!collectionApiResult.getSuccess()) {
+            return APIResult.error(new BaseCode(collectionApiResult.getCode(), collectionApiResult.getMessage()));
+        }
+        List<Collection> collectionList = collectionApiResult.getData();
+        if (CollectionUtils.isEmpty(collectionList)) {
+            return APIResult.ok(new ArrayList<>());
+        }
+        List<String> productIdList = new ArrayList<>();
+        for (Collection collection : collectionList) {
+            String productId = collection.getPid();
+            productIdList.add(productId);
+        }
+
+        ItemSearchDTO itemSearchDTO = new ItemSearchDTO();
+        itemSearchDTO.setMerchantId(merchantId);
+        itemSearchDTO.setTagId(tagId);
+        itemSearchDTO.setProductIdList(productIdList);
+        itemSearchDTO.setPageNo(pageNo);
+        itemSearchDTO.setPageSize(pageSize);
 
+        return productService.findItemPageByIds(itemSearchDTO);
     }
 
 }

+ 66 - 5
rankin-api-web/src/main/java/cn/rankin/apiweb/service/product/ProductClient.java

@@ -2,13 +2,18 @@ package cn.rankin.apiweb.service.product;
 
 import cn.rankin.apiweb.code.ApiWebCode;
 import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.api.page.Page;
+import cn.rankin.data.api.app.dto.ItemSearchDTO;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.product.entity.Course;
+import cn.rankin.data.api.product.entity.Lesson;
 import cn.rankin.data.api.product.entity.MerchantProduct;
 import cn.rankin.data.api.product.entity.Recommend;
+import cn.rankin.data.api.product.vo.CourseItemVo;
+import cn.rankin.data.api.product.vo.SupportItemVo;
 import org.springframework.cloud.netflix.feign.FeignClient;
 import org.springframework.stereotype.Component;
-import org.springframework.web.bind.annotation.RequestMapping;
-import org.springframework.web.bind.annotation.RequestMethod;
-import org.springframework.web.bind.annotation.RequestParam;
+import org.springframework.web.bind.annotation.*;
 
 import java.util.List;
 
@@ -19,7 +24,28 @@ public interface ProductClient {
     APIResult<List<Recommend>> getRecommendCourses(@RequestParam("merchantId") String merchantId);
 
     @RequestMapping(value = "/merchant/product/detail", method = RequestMethod.GET)
-    APIResult<MerchantProduct> getProduct(@RequestParam("pid") String productId, @RequestParam("merchantId") String merchantId);
+    APIResult<MerchantProduct> getMerchantProduct(@RequestParam("pid") String pid, @RequestParam("merchantId") String merchantId);
+
+    @RequestMapping(value = "/app/item/ids", method = RequestMethod.POST)
+    APIResult<List<ItemVo>> findItemByIds(@RequestParam("merchantId") String merchantId, @RequestBody List<String> productIdList);
+
+    @RequestMapping(value = "/app/item/ids/page", method = RequestMethod.POST)
+    APIResult<Page<ItemVo>> findItemPageByIds(@RequestBody ItemSearchDTO itemSearchDTO);
+
+    @RequestMapping(value = "/app/course/{courseId}/lessons", method = RequestMethod.GET)
+    APIResult<Course> getCourseLessons(@PathVariable("courseId") String courseId);
+
+    @RequestMapping(value = "/app/course/{courseId}/detail", method = RequestMethod.GET)
+    APIResult<CourseItemVo> getCourseDetail(@PathVariable("courseId") String courseId, @RequestParam("merchantId") String merchantId);
+
+    @RequestMapping(value = "/app/course/{courseId}/supports", method = RequestMethod.GET)
+    APIResult<List<ItemVo>> getSupportByCourseId(@PathVariable("courseId") String courseId, @RequestParam("merchantId") String merchantId);
+
+    @RequestMapping(value = "/app/support/{supportId}", method = RequestMethod.GET)
+    APIResult<SupportItemVo> getSupport(@PathVariable("supportId") String supportId, @RequestParam("merchantId") String merchantId);
+
+    @RequestMapping(value = "/app/lesson/{lessonId}", method = RequestMethod.GET)
+    APIResult<Lesson> getLesson(@PathVariable("lessonId") String lessonId, @RequestParam("courseId") String courseId);
 
     @Component
     class ProductClientHystrix implements ProductClient {
@@ -30,7 +56,42 @@ public interface ProductClient {
         }
 
         @Override
-        public APIResult getProduct(String productId, String merchantId) {
+        public APIResult getMerchantProduct(String pid, String merchantId) {
+            return APIResult.error(ApiWebCode.SERVER_ERROR);
+        }
+
+        @Override
+        public APIResult findItemByIds(String merchantId, List<String> productIdList) {
+            return APIResult.error(ApiWebCode.SERVER_ERROR);
+        }
+
+        @Override
+        public APIResult findItemPageByIds(ItemSearchDTO itemSearchDTO) {
+            return APIResult.error(ApiWebCode.SERVER_ERROR);
+        }
+
+        @Override
+        public APIResult<Course> getCourseLessons(String courseId) {
+            return APIResult.error(ApiWebCode.SERVER_ERROR);
+        }
+
+        @Override
+        public APIResult<CourseItemVo> getCourseDetail(String courseId, String merchantId) {
+            return APIResult.error(ApiWebCode.SERVER_ERROR);
+        }
+
+        @Override
+        public APIResult<List<ItemVo>> getSupportByCourseId(String courseId, String merchantId) {
+            return APIResult.error(ApiWebCode.SERVER_ERROR);
+        }
+
+        @Override
+        public APIResult<Lesson> getLesson(String lessonId, String courseId) {
+            return APIResult.error(ApiWebCode.SERVER_ERROR);
+        }
+
+        @Override
+        public APIResult getSupport(String supportId, String merchantId) {
             return APIResult.error(ApiWebCode.SERVER_ERROR);
         }
     }

+ 63 - 5
rankin-api-web/src/main/java/cn/rankin/apiweb/service/product/ProductService.java

@@ -1,10 +1,15 @@
 package cn.rankin.apiweb.service.product;
 
+import cn.rankin.apiweb.code.ApiWebCode;
+import cn.rankin.apiweb.service.resource.ResourceService;
 import cn.rankin.common.utils.api.model.APIResult;
 import cn.rankin.common.utils.api.model.BaseCode;
-import cn.rankin.data.api.app.vo.RecommendVo;
-import cn.rankin.data.api.product.entity.MerchantProduct;
-import cn.rankin.data.api.product.entity.Recommend;
+import cn.rankin.common.utils.api.page.Page;
+import cn.rankin.data.api.app.dto.ItemSearchDTO;
+import cn.rankin.data.api.app.vo.*;
+import cn.rankin.data.api.product.entity.*;
+import cn.rankin.data.api.product.vo.CourseItemVo;
+import cn.rankin.data.api.product.vo.SupportItemVo;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
@@ -19,6 +24,9 @@ public class ProductService {
     @Autowired
     private ProductClient productClient;
 
+    @Autowired
+    private ResourceService resourceService;
+
     public APIResult<List<RecommendVo>> getRecommendCourses(String merchantId) {
         APIResult<List<Recommend>> apiResult = productClient.getRecommendCourses(merchantId);
         if (!apiResult.getSuccess()) {
@@ -35,7 +43,57 @@ public class ProductService {
     }
 
     public APIResult<MerchantProduct> getMerchantProduct(String productId, String merchantId) {
-        APIResult<MerchantProduct> apiResult = productClient.getProduct(productId, merchantId);
-        return apiResult;
+        return productClient.getMerchantProduct(productId, merchantId);
+    }
+
+    public APIResult<List<ItemVo>> findItemByIds(String merchantId, List<String> productIdList) {
+        return productClient.findItemByIds(merchantId, productIdList);
+    }
+
+    public APIResult<Page<ItemVo>> findItemPageByIds(ItemSearchDTO itemSearchDTO) {
+        return productClient.findItemPageByIds(itemSearchDTO);
+    }
+
+    public APIResult<CourseVo> getCourseLessons(String courseId) {
+        APIResult<Course> courseAPIResult = productClient.getCourseLessons(courseId);
+        if (!courseAPIResult.getSuccess()) {
+            return APIResult.error(new BaseCode(courseAPIResult.getCode(), courseAPIResult.getMessage()));
+        }
+        Course course = courseAPIResult.getData();
+        CourseVo courseVo = convert(course);
+        return APIResult.ok(courseVo);
+    }
+
+    public APIResult<CourseDetailVo> getCourseDetail(String courseId, String merchantId) {
+        APIResult<CourseItemVo> apiResult = productClient.getCourseDetail(courseId, merchantId);
+        if (!apiResult.getSuccess()) {
+            return APIResult.error(new BaseCode(apiResult.getCode(), apiResult.getMessage()));
+        }
+        CourseItemVo courseItemVo = apiResult.getData();
+        CourseDetailVo courseDetailVo = convert(courseItemVo);
+        return APIResult.ok(courseDetailVo);
+    }
+
+    public APIResult<List<ItemVo>> getSupportByCourseId(String courseId, String merchantId) {
+        return productClient.getSupportByCourseId(courseId, merchantId);
     }
+
+    public APIResult<SupportItemVo> getSupport(String supportId, String merchantId) {
+        return productClient.getSupport(supportId, merchantId);
+    }
+
+    public APIResult<LessonVo> getLesson(String lessonId, String courseId, Boolean auth) {
+        APIResult<Lesson> apiResult = productClient.getLesson(lessonId, courseId);
+        if (!apiResult.getSuccess()) {
+            return APIResult.error(new BaseCode(apiResult.getCode(), apiResult.getMessage()));
+        }
+        Lesson lesson = apiResult.getData();
+        if (lesson.getSort() == 0 || Boolean.TRUE.equals(auth)) {
+            LessonVo lessonVo = resourceService.setWareUrl(lesson);
+            return APIResult.ok(lessonVo);
+
+        }
+        return APIResult.error(ApiWebCode.ACCESS_DENIED);
+    }
+
 }

+ 18 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/service/resource/ResourceClient.java

@@ -0,0 +1,18 @@
+package cn.rankin.apiweb.service.resource;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.vo.resource.ResourceVo;
+import org.springframework.cloud.netflix.feign.FeignClient;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+import org.springframework.web.bind.annotation.RequestParam;
+
+import java.util.List;
+import java.util.Map;
+
+@FeignClient(value = "${service.resource.name}")
+public interface ResourceClient {
+
+    @RequestMapping(value = "/resource/batch", method = RequestMethod.GET)
+    APIResult<Map<String, ResourceVo>> getResourceMap(@RequestParam("id") List<String> ids);
+}

+ 93 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/service/resource/ResourceService.java

@@ -0,0 +1,93 @@
+package cn.rankin.apiweb.service.resource;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.vo.resource.ResourceVo;
+import cn.rankin.data.api.app.vo.CourseWareVo;
+import cn.rankin.data.api.app.vo.LessonVo;
+import cn.rankin.data.api.app.vo.ResourceItemVo;
+import cn.rankin.data.api.product.entity.CourseWare;
+import cn.rankin.data.api.product.entity.Lesson;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.util.CollectionUtils;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import static cn.rankin.apiweb.utils.DTOConverter.convert;
+
+@Service
+@Slf4j
+public class ResourceService {
+
+    @Autowired
+    private ResourceClient resourceClient;
+
+    public Map<String, ResourceVo> getResourceMap(List<String> idList) {
+        Map<String, ResourceVo> resourceVoMap = new HashMap<>();
+        if (CollectionUtils.isEmpty(idList)) {
+            return resourceVoMap;
+        }
+
+        APIResult<Map<String, ResourceVo>> apiResult = resourceClient.getResourceMap(idList);
+        if (!apiResult.getSuccess()) {
+            log.warn("get resource map error!");
+            return resourceVoMap;
+        }else if (apiResult.getData() == null) {
+            log.warn("get resource map empty");
+            return resourceVoMap;
+        }
+
+        return apiResult.getData();
+    }
+
+
+    public LessonVo setWareUrl(Lesson lesson) {
+        LessonVo lessonVo = convert(lesson);
+
+        List<String> wareIdList = new ArrayList<>();
+        List<CourseWare> courseWareList = lesson.getWareList();
+        courseWareList.forEach(e -> {
+            List<String> resourceIdList = e.getResourceList();
+            if (!CollectionUtils.isEmpty(resourceIdList)) {
+                wareIdList.addAll(resourceIdList);
+            }
+        });
+
+        Map<String, ResourceVo> resourceVoMap = getResourceMap(wareIdList);
+        List<CourseWareVo> courseWareVoList = new ArrayList<>();
+        for (CourseWare courseWare : courseWareList) {
+            CourseWareVo courseWareVo = convert(courseWare);
+            List<String> resourceIdList = courseWare.getResourceList();
+            if (CollectionUtils.isEmpty(resourceIdList)) {
+                courseWareVoList.add(courseWareVo);
+                continue;
+            }
+
+            List<ResourceItemVo> resourceVoList = new ArrayList<>();
+            Integer type = 0;
+            for (String resourceId : resourceIdList) {
+                ResourceVo resourceVo = resourceVoMap.get(resourceId);
+                if (resourceVo != null) {
+                    ResourceItemVo resourceItemVo = new ResourceItemVo();
+                    resourceItemVo.setId(resourceVo.getId());
+                    resourceItemVo.setUrl(resourceVo.getUrl());
+                    Integer resourceType = resourceVo.getType();
+                    resourceItemVo.setType(resourceType);
+                    if (resourceType != 0) {
+                        type = 1;
+                    }
+                    resourceVoList.add(resourceItemVo);
+                }
+            }
+            courseWareVo.setList(resourceVoList);
+            courseWareVo.setType(type);
+            courseWareVoList.add(courseWareVo);
+        }
+        lessonVo.setList(courseWareVoList);
+        return lessonVo;
+    }
+}

+ 22 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/service/tag/TagClient.java

@@ -0,0 +1,22 @@
+package cn.rankin.apiweb.service.tag;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.api.page.Page;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.product.entity.TagGroup;
+import org.springframework.cloud.netflix.feign.FeignClient;
+import org.springframework.web.bind.annotation.PathVariable;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+import org.springframework.web.bind.annotation.RequestParam;
+
+@FeignClient(name = "${service.product.name}")
+public interface TagClient {
+
+    @RequestMapping(value = "/app/tagGroup/code/{code}", method = RequestMethod.GET)
+    APIResult<TagGroup> findTagGroupByCode(@PathVariable("code") String code, @RequestParam("merchantId") String merchantId);
+
+    @RequestMapping(value = "/app/tag/item/{tagId}", method = RequestMethod.GET)
+    APIResult<Page<ItemVo>> findPageByTagId(@PathVariable("tagId") String tagId, @RequestParam("merchantId") String merchantId,
+                                            @RequestParam("pageNo") Integer pageNo, @RequestParam("pageSize") Integer pageSize);
+}

+ 33 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/service/tag/TagService.java

@@ -0,0 +1,33 @@
+package cn.rankin.apiweb.service.tag;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.api.model.BaseCode;
+import cn.rankin.common.utils.api.page.Page;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.app.vo.TagGroupVo;
+import cn.rankin.data.api.product.entity.TagGroup;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import static cn.rankin.apiweb.utils.DTOConverter.convert;
+
+@Service
+public class TagService {
+
+    @Autowired
+    private TagClient tagClient;
+
+    public APIResult<TagGroupVo> findTagGroupByCode(String code, String merchantId) {
+        APIResult<TagGroup> apiResult = tagClient.findTagGroupByCode(code, merchantId);
+        if (!apiResult.getSuccess()) {
+            return APIResult.error(new BaseCode(apiResult.getCode(), apiResult.getMessage()));
+        }
+        TagGroup tagGroup = apiResult.getData();
+        TagGroupVo tagGroupVo = convert(tagGroup);
+        return APIResult.ok(tagGroupVo);
+    }
+
+    public APIResult<Page<ItemVo>> findPageByTagId(String tagId, String merchantId, Integer pageNo, Integer pageSize) {
+        return tagClient.findPageByTagId(tagId, merchantId, pageNo, pageSize);
+    }
+}

+ 70 - 2
rankin-api-web/src/main/java/cn/rankin/apiweb/utils/DTOConverter.java

@@ -1,7 +1,14 @@
 package cn.rankin.apiweb.utils;
 
-import cn.rankin.data.api.app.vo.RecommendVo;
-import cn.rankin.data.api.product.entity.Recommend;
+import cn.rankin.data.api.app.vo.*;
+import cn.rankin.data.api.product.entity.*;
+import cn.rankin.data.api.product.vo.CourseItemVo;
+import cn.rankin.data.api.product.vo.CourseSubItemVo;
+import org.springframework.beans.BeanUtils;
+import org.springframework.util.CollectionUtils;
+
+import java.util.ArrayList;
+import java.util.List;
 
 public class DTOConverter {
 
@@ -15,4 +22,65 @@ public class DTOConverter {
         recommendVo.setCoverUrl(recommend.getCoverUrl());
         return recommendVo;
     }
+
+    public static TagGroupVo convert(TagGroup tagGroup) {
+        TagGroupVo tagGroupVo = new TagGroupVo();
+        tagGroupVo.setName(tagGroup.getName());
+        List<TagVo> tagVoList = new ArrayList<>();
+        List<Tag> tagList = tagGroup.getTagList();
+        if (CollectionUtils.isEmpty(tagList)) {
+            return tagGroupVo;
+        }
+        for (Tag tag : tagList) {
+            TagVo tagVo = new TagVo();
+            tagVo.setId(tag.getId());
+            tagVo.setName(tag.getName());
+            tagVoList.add(tagVo);
+        }
+        tagGroupVo.setList(tagVoList);
+        return tagGroupVo;
+    }
+
+    public static CourseVo convert(Course course) {
+        CourseVo courseVo = new CourseVo();
+        courseVo.setBreadCrumb(course.getBreadCrumb());
+        courseVo.setBgUrl(course.getBgUrl());
+        List<CourseSubItemVo> subItemVoList = course.getSubItemList();
+        if (subItemVoList == null) {
+            return courseVo;
+        }
+        List<LessonVo> lessonVoList = new ArrayList<>();
+        for (CourseSubItemVo courseSubItemVo : subItemVoList) {
+            LessonVo lessonVo = new LessonVo();
+            lessonVo.setId(courseSubItemVo.getId());
+            lessonVo.setName(courseSubItemVo.getName());
+            lessonVo.setCode(courseSubItemVo.getCode());
+            lessonVoList.add(lessonVo);
+        }
+        courseVo.setList(lessonVoList);
+        return courseVo;
+    }
+
+    public static CourseDetailVo convert(CourseItemVo courseItemVo) {
+        CourseDetailVo courseDetailVo = new CourseDetailVo();
+        BeanUtils.copyProperties(courseItemVo, courseDetailVo);
+        return courseDetailVo;
+    }
+
+    public static LessonVo convert(Lesson lesson) {
+        LessonVo lessonVo = new LessonVo();
+        lessonVo.setId(lesson.getId());
+        lessonVo.setCode(lesson.getCode());
+        lessonVo.setName(lesson.getName());
+        return lessonVo;
+    }
+
+    public static CourseWareVo convert(CourseWare courseWare) {
+        CourseWareVo courseWareVo = new CourseWareVo();
+        courseWareVo.setId(courseWare.getId());
+        courseWareVo.setCode(courseWare.getCode());
+        courseWareVo.setTitle(courseWare.getName());
+        courseWareVo.setCategory(courseWare.getCategory());
+        return courseWareVo;
+    }
 }

+ 1 - 1
rankin-api-web/src/main/resources/bootstrap.yml

@@ -4,7 +4,7 @@ spring:
   cloud:
     config:
       uri: http://config.rankin.com:8921
-      label: master
+      label: local
       profile: ${profile:dev}
 
 server:

+ 22 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/app/dto/ItemSearchDTO.java

@@ -0,0 +1,22 @@
+package cn.rankin.data.api.app.dto;
+
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+import java.util.List;
+
+@Data
+@ToString
+public class ItemSearchDTO implements Serializable {
+
+    private String merchantId;
+
+    private String tagId;
+
+    private List<String> productIdList;
+
+    private Integer pageNo;
+
+    private Integer pageSize;
+}

+ 36 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/CourseDetailVo.java

@@ -0,0 +1,36 @@
+package cn.rankin.data.api.app.vo;
+
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+import java.util.List;
+
+@Data
+@ToString
+public class CourseDetailVo implements Serializable {
+
+    private String id;
+
+    private String code;
+
+    private String title;
+
+    private String subTitle;
+
+    private String digest;
+
+    private String detail;
+
+    private String bgUrl;
+
+    private Boolean auth;
+
+    private Boolean collected;
+
+    private Long beginTime;
+
+    private Long endTime;
+
+    private List<ItemGoodsVo> goods;
+}

+ 22 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/CourseVo.java

@@ -0,0 +1,22 @@
+package cn.rankin.data.api.app.vo;
+
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+import java.util.List;
+
+@Data
+@ToString
+public class CourseVo implements Serializable {
+
+    private Boolean auth;
+
+    private Boolean collected;
+
+    private String breadCrumb;
+
+    private String bgUrl;
+
+    private List<LessonVo> list;
+}

+ 4 - 7
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/ProductVo.java

@@ -1,6 +1,5 @@
 package cn.rankin.data.api.app.vo;
 
-import cn.rankin.common.utils.enums.ProductTypeEnum;
 import lombok.Data;
 import lombok.ToString;
 
@@ -9,19 +8,17 @@ import java.util.List;
 
 @Data
 @ToString
-public class ProductVo implements Serializable {
+public class CourseWareVo implements Serializable {
 
     private String id;
 
     private String code;
 
-    private ProductTypeEnum type;
+    private String category;
 
     private String title;
 
-    private String subTitle;
+    private Integer type;
 
-    private String coverUrl;
-
-    private List<GoodsVo> goods;
+    private List<ResourceItemVo> list;
 }

+ 5 - 2
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/GoodsVo.java

@@ -4,14 +4,17 @@ import lombok.Data;
 import lombok.ToString;
 
 import java.io.Serializable;
+import java.math.BigDecimal;
 
 @Data
 @ToString
-public class GoodsVo implements Serializable {
+public class ItemGoodsVo implements Serializable {
 
     private String id;
 
     private String chargeUnit;
 
-    private String terminalPrice;
+    private BigDecimal terminalPrice;
+
+    private Boolean isInCart;
 }

+ 9 - 2
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/ProductVo.java

@@ -1,5 +1,6 @@
 package cn.rankin.data.api.app.vo;
 
+import cn.rankin.common.utils.enums.BaseStatusEnum;
 import cn.rankin.common.utils.enums.ProductTypeEnum;
 import lombok.Data;
 import lombok.ToString;
@@ -9,7 +10,7 @@ import java.util.List;
 
 @Data
 @ToString
-public class ProductVo implements Serializable {
+public class ItemVo implements Serializable {
 
     private String id;
 
@@ -21,7 +22,13 @@ public class ProductVo implements Serializable {
 
     private String subTitle;
 
+    private String breadCrumb;
+
     private String coverUrl;
 
-    private List<GoodsVo> goods;
+    private List<String> imgList;
+
+    private BaseStatusEnum status;
+
+    private List<ItemGoodsVo> goods;
 }

+ 20 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/LessonVo.java

@@ -0,0 +1,20 @@
+package cn.rankin.data.api.app.vo;
+
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+import java.util.List;
+
+@Data
+@ToString
+public class LessonVo implements Serializable {
+
+    private String id;
+
+    private String code;
+
+    private String name;
+
+    private List<CourseWareVo> list;
+}

+ 3 - 3
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/GoodsVo.java

@@ -7,11 +7,11 @@ import java.io.Serializable;
 
 @Data
 @ToString
-public class GoodsVo implements Serializable {
+public class ResourceItemVo implements Serializable {
 
     private String id;
 
-    private String chargeUnit;
+    private Integer type;
 
-    private String terminalPrice;
+    private String url;
 }

+ 16 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/TagGroupVo.java

@@ -0,0 +1,16 @@
+package cn.rankin.data.api.app.vo;
+
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+import java.util.List;
+
+@Data
+@ToString
+public class TagGroupVo implements Serializable {
+
+    private String name;
+
+    private List<TagVo> list;
+}

+ 2 - 4
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/GoodsVo.java

@@ -7,11 +7,9 @@ import java.io.Serializable;
 
 @Data
 @ToString
-public class GoodsVo implements Serializable {
+public class TagVo implements Serializable {
 
     private String id;
 
-    private String chargeUnit;
-
-    private String terminalPrice;
+    private String name;
 }

+ 20 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/auth/dto/AuthQueryDTO.java

@@ -0,0 +1,20 @@
+package cn.rankin.data.api.auth.dto;
+
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+import java.util.List;
+
+@Data
+@ToString
+public class AuthQueryDTO implements Serializable {
+
+    private String uid;
+
+    private List<String> pids;
+
+    private String bizCode;
+
+    private Integer type;
+}

+ 17 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/auth/dto/InnerAuthDTO.java

@@ -0,0 +1,17 @@
+package cn.rankin.data.api.auth.dto;
+
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+
+@Data
+@ToString
+public class InnerAuthDTO implements Serializable {
+
+    private String itemId;
+
+    private String userId;
+
+    private String merchantId;
+}

+ 40 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/auth/vo/AuthResult.java

@@ -0,0 +1,40 @@
+package cn.rankin.data.api.auth.vo;
+
+
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+
+@Data
+@ToString
+public class AuthResult implements Serializable {
+
+    private String pid;
+
+    private String userId;
+
+    private Integer type = 2;
+
+    private Long startTime;
+
+    private Long endTime;
+
+    public Long getValidTime() {
+        if (startTime == null || endTime == null) {
+            return null;
+        }
+        return endTime - startTime;
+    }
+
+    public Boolean isValid() {
+        if (endTime == null && startTime != null) {
+            return Boolean.TRUE;
+        }
+        Long validTime = getValidTime();
+        if (validTime == null) {
+            return Boolean.FALSE;
+        }
+        return getValidTime() > 0;
+    }
+}

+ 36 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/auth/vo/AuthVo.java

@@ -0,0 +1,36 @@
+package cn.rankin.data.api.auth.vo;
+
+import cn.rankin.common.utils.enums.BaseStatusEnum;
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+
+@Data
+@ToString
+public class AuthVo implements Serializable {
+
+    private String id;
+
+    private String uid;
+
+    private String gid;
+
+    private String pid;
+
+    private String bizCode;
+
+    private Integer type;
+
+    private String title;
+
+    private BaseStatusEnum status;
+
+    private Long startTime;
+
+    private Long endTime;
+
+    private Long createTime;
+
+    private Long updateTime;
+}

+ 2 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/product/dto/SupportDTO.java

@@ -17,6 +17,8 @@ public class SupportDTO implements Serializable {
 
     private String title;
 
+    private String subTitle;
+
     private String digest;
 
     private String detail;

+ 3 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/product/entity/Support.java

@@ -33,6 +33,9 @@ public class Support implements Serializable {
     @Column
     private String title;
 
+    @Column(name = "sub_title")
+    private String subTitle;
+
     @Column
     private String digest;
 

+ 42 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/product/vo/CourseItemVo.java

@@ -0,0 +1,42 @@
+package cn.rankin.data.api.product.vo;
+
+import cn.rankin.common.utils.enums.BaseStatusEnum;
+import cn.rankin.data.api.app.vo.ItemGoodsVo;
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+import java.util.List;
+
+@Data
+@ToString
+public class CourseItemVo implements Serializable {
+
+    private String id;
+
+    private String code;
+
+    private String name;
+
+    private String title;
+
+    private String subTitle;
+
+    private String breadCrumb;
+
+    private String digest;
+
+    private String detail;
+
+    private String keyword;
+
+    private String coverUrl;
+
+    private String bgUrl;
+
+    private String cpId;
+
+    private BaseStatusEnum status;
+
+    private List<ItemGoodsVo> goods;
+}

+ 2 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/product/vo/CourseSubItemVo.java

@@ -16,6 +16,8 @@ public class CourseSubItemVo implements Serializable{
 
     private String name;
 
+    private String title;
+
     private String digest;
 
     private CourseSubTypeEnum type;

+ 35 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/product/vo/SupportItemVo.java

@@ -0,0 +1,35 @@
+package cn.rankin.data.api.product.vo;
+
+import cn.rankin.data.api.app.vo.ItemGoodsVo;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.product.entity.Support;
+import lombok.Data;
+import lombok.ToString;
+
+import java.io.Serializable;
+import java.util.List;
+
+@Data
+@ToString
+public class SupportItemVo implements Serializable {
+
+    private String id;
+
+    private String code;
+
+    private String title;
+
+    private String subTitle;
+
+    private String detail;
+
+    private String coverUrl;
+
+    private List<String> imgList;
+
+    private List<ItemGoodsVo> goods;
+
+    private List<ItemVo> relatedSupports;
+
+    private List<ItemVo> relatedCourses;
+}

+ 2 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/product/vo/SupportVo.java

@@ -18,6 +18,8 @@ public class SupportVo implements Serializable {
 
     private String title;
 
+    private String subTitle;
+
     private String digest;
 
     private String detail;

+ 16 - 0
rankin-product-service/pom.xml

@@ -39,6 +39,10 @@
             <artifactId>spring-boot-starter-data-jpa</artifactId>
         </dependency>
         <dependency>
+            <groupId>org.springframework.cloud</groupId>
+            <artifactId>spring-cloud-starter-feign</artifactId>
+        </dependency>
+        <dependency>
             <groupId>mysql</groupId>
             <artifactId>mysql-connector-java</artifactId>
         </dependency>
@@ -60,6 +64,18 @@
             <artifactId>rankin-data-api</artifactId>
             <version>0.0.1-SNAPSHOT</version>
         </dependency>
+        <!--httpClient-->
+        <dependency>
+            <groupId>org.apache.httpcomponents</groupId>
+            <artifactId>httpclient</artifactId>
+            <version>4.5.3</version>
+        </dependency>
+
+        <dependency>
+            <groupId>com.netflix.feign</groupId>
+            <artifactId>feign-httpclient</artifactId>
+            <version>RELEASE</version>
+        </dependency>
 	</dependencies>
 
 	<dependencyManagement>

+ 2 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/ProductServiceApplication.java

@@ -4,9 +4,11 @@ import cn.rankin.common.utils.jpa.SimpleJpaRepository;
 import org.springframework.boot.SpringApplication;
 import org.springframework.boot.autoconfigure.SpringBootApplication;
 import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
+import org.springframework.cloud.netflix.feign.EnableFeignClients;
 import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
 
 
+@EnableFeignClients
 @EnableDiscoveryClient
 @SpringBootApplication
 @EnableJpaRepositories(repositoryBaseClass = SimpleJpaRepository.class)

+ 46 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/configuration/FeignConfiguration.java

@@ -0,0 +1,46 @@
+package cn.rankin.productservice.configuration;
+
+import cn.rankin.common.utils.constant.Constant;
+import cn.rankin.common.utils.util.UUIDUtil;
+import feign.Logger;
+import feign.RequestInterceptor;
+import feign.RequestTemplate;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+
+@Slf4j
+@Configuration
+public class FeignConfiguration {
+
+    public static class FeignHeaderInterceptor implements RequestInterceptor {
+        // 设置公共头参数
+        @Override
+        public void apply(RequestTemplate requestTemplate) {
+            requestTemplate.header("bizCode", Constant.BIZ_CODE);
+            requestTemplate.header("requestId", UUIDUtil.getUUID());
+            requestTemplate.header("appCode", Constant.APP_CODE);
+            requestTemplate.header("platform", "3");
+            requestTemplate.header("os", "0");
+            requestTemplate.header("dist", "1112");
+            requestTemplate.header("terminal", "mobile");
+            requestTemplate.header("Content-Type", "application/json");
+            requestTemplate.header("userIp", "123.126.111.3");
+            requestTemplate.header("appVer", "6.1.1");
+            requestTemplate.header("Accept", "application/json, text/javascript, */*");
+            log.info("run header interceptor");
+        }
+    }
+
+    @Bean
+    public FeignHeaderInterceptor feignHeaderInterceptor() {
+        return new FeignHeaderInterceptor();
+    }
+
+    @Bean
+    public Logger.Level feignLoggerLevel() {
+
+        return Logger.Level.HEADERS;
+
+    }
+}

+ 20 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/AppLessonController.java

@@ -0,0 +1,20 @@
+package cn.rankin.productservice.controller.app;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.product.entity.Lesson;
+import cn.rankin.productservice.service.app.AppLessonService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+@RestController
+@RequestMapping(value = "/app/lesson")
+public class AppLessonController {
+
+    @Autowired
+    private AppLessonService lessonService;
+
+    @RequestMapping(value = "/{lessonId}", method = RequestMethod.GET)
+    public APIResult<Lesson> getLesson(@PathVariable("lessonId") String lessonId, @RequestParam("courseId") String coursId) {
+        return lessonService.getLesson(lessonId, coursId);
+    }
+}

+ 32 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/AppTagController.java

@@ -0,0 +1,32 @@
+package cn.rankin.productservice.controller.app;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.api.page.Page;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.product.entity.TagGroup;
+import cn.rankin.productservice.service.ItemService;
+import cn.rankin.productservice.service.TagGroupService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+@RestController
+@RequestMapping(value = "/app")
+public class AppTagController {
+
+    @Autowired
+    private TagGroupService tagGroupService;
+
+    @Autowired
+    private ItemService itemService;
+
+    @RequestMapping(value = "/tagGroup/code/{code}", method = RequestMethod.GET)
+    public APIResult<TagGroup> findTagGroupByCode(@PathVariable("code") String code, @RequestParam("merchantId") String merchantId) {
+        return tagGroupService.findTagGroupByCode(code, merchantId);
+    }
+
+    @RequestMapping(value = "/tag/item/{tagId}", method = RequestMethod.GET)
+    public APIResult<Page<ItemVo>> findItemByTagId(@PathVariable("tagId") String tagId, @RequestParam("merchantId") String merchantId,
+                                                   @RequestParam("pageNo") Integer pageNo, @RequestParam("pageSize") Integer pageSize) {
+        return itemService.findPageByTagId(tagId, merchantId, pageNo, pageSize);
+    }
+}

+ 44 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/CourseController.java

@@ -0,0 +1,44 @@
+package cn.rankin.productservice.controller.app;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.product.entity.Course;
+import cn.rankin.data.api.product.vo.CourseItemVo;
+import cn.rankin.productservice.code.ProductServiceAPICode;
+import cn.rankin.productservice.service.CourseService;
+import cn.rankin.productservice.service.ItemService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+
+@RestController
+@RequestMapping(value = "/app/course")
+public class CourseController {
+
+    @Autowired
+    private CourseService courseService;
+
+    @Autowired
+    private ItemService itemService;
+
+    @RequestMapping(value = "/{courseId}/lessons", method = RequestMethod.GET)
+    public APIResult<Course> getCourseLessons(@PathVariable("courseId") String courseId) {
+        return courseService.getCourseLessons(courseId);
+    }
+
+    @RequestMapping(value = "/{courseId}/detail", method = RequestMethod.GET)
+    public APIResult<CourseItemVo> getCourseItem(@PathVariable("courseId") String courseId, @RequestParam("merchantId") String merchantId) {
+        CourseItemVo courseItemVo = itemService.findCourseItem(courseId, merchantId);
+        if (courseItemVo == null) {
+            return APIResult.error(ProductServiceAPICode.NOT_EXISTS);
+        }
+        return APIResult.ok(courseItemVo);
+    }
+
+    @RequestMapping(value = "/{courseId}/supports", method = RequestMethod.GET)
+    public APIResult<List<ItemVo>> getSupportByCourseId(@PathVariable("courseId") String courseId, @RequestParam("merchantId") String merchantId) {
+        List<ItemVo> itemVoList = itemService.findSupportByCourseId(courseId, merchantId);
+        return APIResult.ok(itemVoList);
+    }
+}

+ 35 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/ItemController.java

@@ -0,0 +1,35 @@
+package cn.rankin.productservice.controller.app;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.api.page.Page;
+import cn.rankin.data.api.app.dto.ItemSearchDTO;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.productservice.service.ItemService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+
+@RestController
+@RequestMapping(value = "/app/item")
+public class ItemController {
+
+    @Autowired
+    private ItemService itemService;
+
+    @RequestMapping(value = "/ids", method = RequestMethod.POST)
+    public APIResult<List<ItemVo>> findByIds(@RequestBody List<String> productIdList, @RequestParam("merchantId") String merchantId) {
+        List<ItemVo> itemVoList = itemService.findByIds(merchantId, productIdList);
+        return APIResult.ok(itemVoList);
+    }
+
+    @RequestMapping(value = "/ids/page", method = RequestMethod.POST)
+    public APIResult<Page<ItemVo>> findPage(@RequestBody ItemSearchDTO itemSearchDTO) {
+        String merchantId = itemSearchDTO.getMerchantId();
+        String tagId = itemSearchDTO.getTagId();
+        List<String> productIdList = itemSearchDTO.getProductIdList();
+        Integer pageNo = itemSearchDTO.getPageNo();
+        Integer pageSize = itemSearchDTO.getPageSize();
+        return itemService.findPageByTagIdAndPids(merchantId, tagId, productIdList, pageNo, pageSize);
+    }
+}

+ 25 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/controller/app/SupportController.java

@@ -0,0 +1,25 @@
+package cn.rankin.productservice.controller.app;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.product.vo.SupportItemVo;
+import cn.rankin.productservice.code.ProductServiceAPICode;
+import cn.rankin.productservice.service.ItemService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+@RestController
+@RequestMapping(value = "/app/support")
+public class SupportController {
+
+    @Autowired
+    private ItemService itemService;
+
+    @RequestMapping(value = "/{supportId}", method = RequestMethod.GET)
+    public APIResult<SupportItemVo> findById(@PathVariable("supportId") String supportId, @RequestParam("merchantId") String merchantId) {
+        SupportItemVo supportItemVo = itemService.findSupportItem(supportId, merchantId);
+        if (supportItemVo == null) {
+            return APIResult.error(ProductServiceAPICode.NOT_EXISTS);
+        }
+        return APIResult.ok(supportItemVo);
+    }
+}

+ 26 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/controller/auth/AuthController.java

@@ -0,0 +1,26 @@
+package cn.rankin.productservice.controller.auth;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.auth.dto.InnerAuthDTO;
+import cn.rankin.data.api.auth.vo.AuthResult;
+import cn.rankin.productservice.service.auth.AuthService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+import org.springframework.web.bind.annotation.RestController;
+
+@RestController
+public class AuthController {
+
+    @Autowired
+    private AuthService authService;
+
+    @RequestMapping(value = "/auth", method = RequestMethod.POST)
+    public APIResult<AuthResult> auth(@RequestBody InnerAuthDTO authDTO) {
+        String userId = authDTO.getUserId();
+        String itemId = authDTO.getItemId();
+        String merchantId = authDTO.getMerchantId();
+        return authService.auth(userId, merchantId, itemId);
+    }
+}

+ 1 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/controller/GoodsController.java

@@ -1,4 +1,4 @@
-package cn.rankin.productservice.controller;
+package cn.rankin.productservice.controller.cms;
 
 import cn.rankin.common.utils.api.model.APIResult;
 import cn.rankin.data.api.product.dto.GoodsDTO;

+ 1 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/controller/LessonController.java

@@ -1,4 +1,4 @@
-package cn.rankin.productservice.controller;
+package cn.rankin.productservice.controller.cms;
 
 import cn.rankin.common.utils.api.model.BaseCode;
 import cn.rankin.common.utils.api.model.APICode;

+ 1 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/controller/MerchantProductController.java

@@ -1,4 +1,4 @@
-package cn.rankin.productservice.controller;
+package cn.rankin.productservice.controller.cms;
 
 import cn.rankin.common.utils.api.model.APIResult;
 import cn.rankin.common.utils.api.page.Page;

+ 1 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/controller/ProductController.java

@@ -1,4 +1,4 @@
-package cn.rankin.productservice.controller;
+package cn.rankin.productservice.controller.cms;
 
 import cn.rankin.common.utils.api.model.APIResult;
 import cn.rankin.common.utils.api.page.Page;

+ 1 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/controller/RecommendController.java

@@ -1,4 +1,4 @@
-package cn.rankin.productservice.controller;
+package cn.rankin.productservice.controller.cms;
 
 import cn.rankin.common.utils.api.model.APIResult;
 import cn.rankin.common.utils.api.page.Page;

+ 1 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/controller/TagController.java

@@ -1,4 +1,4 @@
-package cn.rankin.productservice.controller;
+package cn.rankin.productservice.controller.cms;
 
 import cn.rankin.common.utils.api.model.APIResult;
 import cn.rankin.common.utils.api.page.Page;

+ 1 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/controller/TagGroupController.java

@@ -1,4 +1,4 @@
-package cn.rankin.productservice.controller;
+package cn.rankin.productservice.controller.cms;
 
 import cn.rankin.common.utils.api.model.APIResult;
 import cn.rankin.common.utils.api.page.Page;

+ 1 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/controller/WareController.java

@@ -1,4 +1,4 @@
-package cn.rankin.productservice.controller;
+package cn.rankin.productservice.controller.cms;
 
 import cn.rankin.common.utils.api.model.APICode;
 import cn.rankin.common.utils.api.model.APIResult;

+ 2 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/repository/CourseSubRelationRepository.java

@@ -13,6 +13,8 @@ public interface CourseSubRelationRepository extends BasicJpaRepository<CourseSu
 
     List<CourseSubRelation> findByCourseId(String courseId);
 
+    CourseSubRelation findFirstByCourseIdOrderBySort(String courseId);
+
     @Query(value = "select r from CourseSubRelation r where r.courseId = :courseId and r.status = :status order by r.sort")
     List<CourseSubRelation> findByCourseId(@Param("courseId") String courseId, @Param("status") BaseStatusEnum status);
 

+ 4 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/repository/CourseSupportRelationRepository.java

@@ -3,6 +3,7 @@ package cn.rankin.productservice.repository;
 import cn.rankin.common.utils.enums.BaseStatusEnum;
 import cn.rankin.common.utils.jpa.BasicJpaRepository;
 import cn.rankin.data.api.product.entity.CourseSupportRelation;
+import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.data.jpa.repository.Modifying;
 import org.springframework.data.jpa.repository.Query;
 import org.springframework.data.repository.query.Param;
@@ -15,6 +16,9 @@ public interface CourseSupportRelationRepository extends BasicJpaRepository<Cour
     @Query(value = "select r from CourseSupportRelation r where r.courseId = :courseId and r.status = :status order by r.sort")
     List<CourseSupportRelation> findByCourseId(@Param("courseId") String courseId, @Param("status") BaseStatusEnum status);
 
+    @Query(value = "select r from CourseSupportRelation r where r.supportId = ?1 and r.status = 0 order by r.sort")
+    List<CourseSupportRelation> findBySupportId(String supportId);
+
     List<CourseSupportRelation> findAllByCourseId(String courseId);
 
     @Transactional

+ 3 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/repository/GoodsRepository.java

@@ -16,6 +16,9 @@ public interface GoodsRepository extends BasicJpaRepository<Goods, String> {
     @Query(value = "select g from Goods g where g.pid = ?1 and g.merchantId = ?2 and g.status = 0 and g.pkgId is null order by g.sort")
     List<Goods> findByPidAndMerchantId(String pid, String merchantId);
 
+    @Query(value = "select g from Goods g where g.pid in (?1) and g.merchantId = ?2 and g.status = 0 and g.pkgId is null order by g.sort")
+    List<Goods> findByPidsAndMerchantId(List<String> pids, String merchantId);
+
     @Query(value = "select g from Goods g where g.id in (?1) and g.status = ?2")
     List<Goods> findByIds(List<String> goodIds, BaseStatusEnum status);
 

+ 1 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/repository/MerchantProductRepository.java

@@ -16,7 +16,7 @@ public interface MerchantProductRepository extends BasicJpaRepository<MerchantPr
     List<MerchantProduct> findByPidIn(@Param("pids") List<String> pids);
 
     @Query(value = "select m from MerchantProduct m where m.pid in (?1) and m.merchantId = ?2 order by m.sort")
-    List<MerchantProduct> findByPidsAndMerchantId(List<String> pids, String merchantid);
+    List<MerchantProduct> findByPidsAndMerchantId(List<String> pids, String merchantId);
 
     MerchantProduct findByPidAndMerchantId(String pid, String merchantId);
 

+ 4 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/repository/ProductTagRelationRepository.java

@@ -9,7 +9,7 @@ import org.springframework.data.repository.query.Param;
 
 import java.util.List;
 
-public interface ProductTagRelationRepository extends BasicJpaRepository<MerchantProductTagRelation, String> {
+public interface MerchantProductTagRelationRepository extends BasicJpaRepository<MerchantProductTagRelation, String> {
 
     @Query(value = "select p from MerchantProductTagRelation p where p.tagId = ?1 and p.status = ?2 order by p.sort")
     List<MerchantProductTagRelation> findByTagId(String tagId, BaseStatusEnum status);
@@ -26,6 +26,9 @@ public interface ProductTagRelationRepository extends BasicJpaRepository<Merchan
 
     List<MerchantProductTagRelation> findByPidAndMerchantId(String pid, String merchantId);
 
+    @Query(value = "select * from p_product_tag_relation r where r.tag_id = ?1 and r.pid in (?2) and r.status = 0 order by r.sort limit ?3, ?4", nativeQuery = true)
+    List<MerchantProductTagRelation> findByTagIdAndPids(String tagId, List<String> productIdList, Long start, Integer size);
+
     @Modifying
     @Query(value = "update MerchantProductTagRelation r set r.status = 1 where r.tagId = :tagId")
     Integer deleteByTagId(@Param("tagId") String tagId);

+ 4 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/repository/PackageProductRelationRepository.java

@@ -1,5 +1,6 @@
 package cn.rankin.productservice.repository;
 
+import cn.rankin.common.utils.enums.BaseStatusEnum;
 import cn.rankin.common.utils.jpa.BasicJpaRepository;
 import cn.rankin.data.api.product.entity.PackageProductRelation;
 import org.springframework.data.jpa.repository.Modifying;
@@ -12,6 +13,9 @@ public interface PackageProductRelationRepository extends BasicJpaRepository<Pac
     @Query(value = "select r from PackageProductRelation r where r.pkgId = ?1 and r.status = 0 order by r.sort")
     List<PackageProductRelation> findByPkgId(String pkgId);
 
+    @Query(value = "select r from PackageProductRelation r where r.pid = ?1 and r.status = 0")
+    List<PackageProductRelation> findByPid(String productId);
+
     @Modifying
     @Query(value = "update PackageProductRelation r set r.status = 1 where r.pkgId = ?1")
     Integer deleteByPkgId(String pkgId);

+ 3 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/repository/TagGroupRepository.java

@@ -11,6 +11,9 @@ public interface TagGroupRepository extends BasicJpaRepository<TagGroup, String>
 
     Long countByCode(String code);
 
+    @Query(value = "select g from TagGroup g where g.code = ?1 and g.merchantId = ?2")
+    TagGroup findFirstByCode(String code, String merchantId);
+
     @Modifying
     @Query(value = "update TagGroup g set g.status = 1 where g.id = :id")
     Integer deleteById(@Param("id") String id);

+ 10 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/service/CourseService.java

@@ -63,6 +63,16 @@ public class CourseService {
         return APIResult.ok(course);
     }
 
+    public APIResult<Course> getCourseLessons(String courseId) {
+        Course course = courseRepository.find(courseId);
+        if (course == null) {
+            return APIResult.error(ProductServiceAPICode.NOT_EXISTS);
+        }
+        List<CourseSubItemVo> subItemVoList = this.findSubItemVo(courseId);
+        course.setSubItemList(subItemVoList);
+        return APIResult.ok(course);
+    }
+
     // find sub item by courseId
     public List<CourseSubItemVo> findSubItemVo(String courseId) {
         List<CourseSubItemVo> subItemVoList = new ArrayList<>();

+ 299 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/service/ItemService.java

@@ -0,0 +1,299 @@
+package cn.rankin.productservice.service;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.api.page.Page;
+import cn.rankin.common.utils.enums.BaseStatusEnum;
+import cn.rankin.common.utils.enums.ProductTypeEnum;
+import cn.rankin.common.utils.util.ListUtil;
+import cn.rankin.data.api.app.vo.ItemGoodsVo;
+import cn.rankin.data.api.app.vo.ItemVo;
+import cn.rankin.data.api.product.entity.*;
+import cn.rankin.data.api.product.vo.CourseItemVo;
+import cn.rankin.data.api.product.vo.SupportItemVo;
+import cn.rankin.productservice.repository.*;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.BeanUtils;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.util.CollectionUtils;
+
+import java.util.*;
+
+@Service
+@Slf4j
+public class ItemService {
+
+    @Autowired
+    private MerchantProductRepository merchantProductRepository;
+
+    @Autowired
+    private CourseRepository courseRepository;
+
+    @Autowired
+    private SupportRepository supportRepository;
+
+    @Autowired
+    private GoodsRepository goodsRepository;
+
+    @Autowired
+    private MerchantProductTagRelationRepository merchantProductTagRelationRepository;
+
+    @Autowired
+    private CourseSupportRelationRepository courseSupportRelationRepository;
+
+    @Autowired
+    private SupportReferenceRepository supportReferenceRepository;
+
+    public CourseItemVo findCourseItem(String courseId, String merchantId) {
+        MerchantProduct merchantProduct = merchantProductRepository.findByPidAndMerchantId(courseId, merchantId);
+        if (merchantProduct == null || !BaseStatusEnum.NORMAL.equals(merchantProduct.getStatus())) {
+            return null;
+        }
+        Course course = courseRepository.find(courseId);
+        CourseItemVo courseItemVo = new CourseItemVo();
+        BeanUtils.copyProperties(course, courseItemVo);
+        List<Goods> goodsList = goodsRepository.findByPidAndMerchantId(courseId, merchantId);
+        List<ItemGoodsVo> itemGoodsVoList = new ArrayList<>();
+        for (Goods goods : goodsList) {
+            ItemGoodsVo itemGoodsVo = convert(goods);
+            itemGoodsVoList.add(itemGoodsVo);
+        }
+        courseItemVo.setGoods(itemGoodsVoList);
+        return courseItemVo;
+    }
+
+    public SupportItemVo findSupportItem(String supportId, String merchantId) {
+        MerchantProduct merchantProduct = merchantProductRepository.findByPidAndMerchantId(supportId, merchantId);
+        if (merchantProduct == null || !BaseStatusEnum.NORMAL.equals(merchantProduct.getStatus())) {
+            return null;
+        }
+        Support support = supportRepository.find(supportId);
+        SupportItemVo supportItemVo = new SupportItemVo();
+        BeanUtils.copyProperties(support, supportItemVo);
+        List<Goods> goodsList = goodsRepository.findByPidAndMerchantId(supportId, merchantId);
+        List<ItemGoodsVo> itemGoodsVoList = new ArrayList<>();
+        for (Goods goods : goodsList) {
+            ItemGoodsVo itemGoodsVo = convert(goods);
+            itemGoodsVoList.add(itemGoodsVo);
+        }
+        supportItemVo.setGoods(itemGoodsVoList);
+
+        // 取相关周边
+        List<SupportReference> supportReferenceList = supportReferenceRepository.findByFid(supportId, BaseStatusEnum.NORMAL);
+        if (!CollectionUtils.isEmpty(supportReferenceList)) {
+            List<String> supportIdList = new ArrayList<>();
+            for (SupportReference supportReference : supportReferenceList) {
+                supportIdList.add(supportReference.getTid());
+            }
+            if (!CollectionUtils.isEmpty(supportIdList)) {
+                List<MerchantProduct> merchantProductList = merchantProductRepository.findByPidsAndMerchantId(supportIdList, merchantId);
+                List<String> idList = new ArrayList<>();
+                merchantProductList.forEach(item -> idList.add(item.getPid()));
+                List<Support> supportList = supportRepository.findByIds(idList, BaseStatusEnum.NORMAL);
+                Map<String, Support> supportMap = ListUtil.convert(supportList, "id", Support.class);
+                List<ItemVo> itemVoList = new ArrayList<>();
+                for (String itemId : supportIdList) {
+                    Support item = supportMap.get(itemId);
+                    if (item == null) {
+                        continue;
+                    }
+                    ItemVo itemVo = convert(item);
+                    itemVoList.add(itemVo);
+                }
+                supportItemVo.setRelatedSupports(itemVoList);
+            }
+        }
+
+        // 取相关课程
+        List<CourseSupportRelation> courseSupportRelationList = courseSupportRelationRepository.findBySupportId(supportId);
+        if (!CollectionUtils.isEmpty(courseSupportRelationList)) {
+            List<String> courseIdList = new ArrayList<>();
+            for (CourseSupportRelation relation : courseSupportRelationList) {
+                courseIdList.add(relation.getCourseId());
+            }
+            if (!CollectionUtils.isEmpty(courseIdList)) {
+                List<MerchantProduct> merchantProductList = merchantProductRepository.findByPidsAndMerchantId(courseIdList, merchantId);
+                List<String> idList = new ArrayList<>();
+                merchantProductList.forEach(item -> idList.add(item.getPid()));
+                List<Course> courseList = courseRepository.findByIds(idList, BaseStatusEnum.NORMAL);
+                Map<String, Course> courseMap = ListUtil.convert(courseList, "id", Course.class);
+                List<ItemVo> itemVoList = new ArrayList<>();
+                for (String itemId : courseIdList) {
+                    Course item = courseMap.get(itemId);
+                    if (item == null) {
+                        continue;
+                    }
+                    ItemVo itemVo = convert(item);
+                    itemVoList.add(itemVo);
+                }
+                supportItemVo.setRelatedCourses(itemVoList);
+            }
+        }
+
+        return supportItemVo;
+    }
+
+    public List<ItemVo> findSupportByCourseId(String courseId, String merchantId) {
+        List<CourseSupportRelation> relationList = courseSupportRelationRepository.findByCourseId(courseId, BaseStatusEnum.NORMAL);
+        if (CollectionUtils.isEmpty(relationList)) {
+            return new ArrayList<>();
+        }
+        List<String> productIdList = new ArrayList<>();
+        relationList.forEach(relation -> productIdList.add(relation.getSupportId()));
+        List<ItemVo> itemVoList = this.findByIds(merchantId, productIdList);
+        return itemVoList;
+    }
+
+    public List<ItemVo> findByIds(String merchantId, List<String> productIdList) {
+        if (CollectionUtils.isEmpty(productIdList)) {
+            return new ArrayList<>();
+        }
+        List<MerchantProduct> merchantProductList = merchantProductRepository.findByPidsAndMerchantId(productIdList, merchantId);
+        List<String> courseIdList = new ArrayList<>();
+        List<String> supportIdList = new ArrayList<>();
+        for (MerchantProduct merchantProduct : merchantProductList) {
+            String productId = merchantProduct.getPid();
+            ProductTypeEnum type = merchantProduct.getType();
+            if (type.equals(ProductTypeEnum.COURSE)) {
+                courseIdList.add(productId);
+            } else if (type.equals(ProductTypeEnum.SUPPORT)) {
+                supportIdList.add(productId);
+            }
+        }
+
+        List<Course> courseList = new ArrayList<>();
+        if (!CollectionUtils.isEmpty(courseIdList)) {
+            courseList = courseRepository.findByIds(productIdList);
+        }
+
+        List<Support> supportList = new ArrayList<>();
+        if (!CollectionUtils.isEmpty(supportIdList)) {
+            supportList = supportRepository.findByIds(supportIdList);
+        }
+
+        // 拿产品信息
+        Map<String, ItemVo> itemVoMap = new HashMap<>();
+        for (Course course : courseList) {
+            String productId = course.getId();
+            ItemVo itemVo = convert(course);
+            itemVoMap.put(productId, itemVo);
+        }
+        for (Support support : supportList) {
+            String productId = support.getId();
+            ItemVo itemVo = convert(support);
+            itemVoMap.put(productId, itemVo);
+        }
+
+        // 取商品信息
+        List<Goods> goodsList = goodsRepository.findByPidsAndMerchantId(productIdList, merchantId);
+        Map<String, List<Goods>> goodsMap = new HashMap<>();
+        for (Goods goods : goodsList) {
+            String productId = goods.getPid();
+            if (!goodsMap.containsKey(productId)) {
+                List<Goods> tmpList = new ArrayList<>();
+                tmpList.add(goods);
+                goodsMap.put(productId, tmpList);
+            }else {
+                List<Goods> tmpList = goodsMap.get(productId);
+                tmpList.add(goods);
+            }
+        }
+
+        // 开始组装返回数据了啊
+        List<ItemVo> itemVoList = new ArrayList<>();
+        for (String productId : productIdList) {
+            ItemVo itemVo = itemVoMap.get(productId);
+            if (itemVo == null) {
+                log.error("item not exists, pid={}", productId);
+                continue;
+            }
+            List<Goods> tmpList = goodsMap.get(productId);
+            tmpList.sort(new Comparator<Goods>() {
+                @Override
+                public int compare(Goods o1, Goods o2) {
+                    return o1.getSort() - o2.getSort();
+                }
+            });
+            List<ItemGoodsVo> itemGoodsVoList = new ArrayList<>();
+            for (Goods goods : tmpList) {
+                ItemGoodsVo itemGoodsVo = convert(goods);
+                itemGoodsVoList.add(itemGoodsVo);
+            }
+            itemVo.setGoods(itemGoodsVoList);
+            itemVoList.add(itemVo);
+        }
+
+        return itemVoList;
+    }
+
+    public APIResult<Page<ItemVo>> findPageByTagIdAndPids(String merchantId, String tagId, List<String> productIdList, Integer pageNo, Integer pageSize) {
+        Page<ItemVo> page = new Page((long)productIdList.size(), pageNo, pageSize);
+        List<MerchantProductTagRelation> relationList = merchantProductTagRelationRepository.findByTagIdAndPids(tagId, productIdList, page.getStart(), pageSize);
+        if (CollectionUtils.isEmpty(relationList)) {
+            return APIResult.ok(page);
+        }
+        List<String> currentIdList = new ArrayList<>();
+        for (MerchantProductTagRelation merchantProductTagRelation : relationList) {
+            String productId = merchantProductTagRelation.getPid();
+            currentIdList.add(productId);
+        }
+
+        List<ItemVo> itemVoList = findByIds(merchantId, currentIdList);
+        page.setList(itemVoList);
+        return APIResult.ok(page);
+    }
+
+    public APIResult<Page<ItemVo>> findPageByTagId(String tagId, String merchantId, Integer pageNo, Integer pageSize) {
+        MerchantProductTagRelation relation = new MerchantProductTagRelation();
+        relation.setTagId(tagId);
+        relation.setMerchantId(merchantId);
+        Long total = merchantProductTagRelationRepository.count(relation);
+
+        Page<ItemVo> page = new Page(total, pageNo, pageSize);
+        List<MerchantProductTagRelation> relationList = merchantProductTagRelationRepository.find(relation, page.getStart(), pageSize);
+        if (CollectionUtils.isEmpty(relationList)) {
+            return APIResult.ok(page);
+        }
+
+        List<String> productIdList = new ArrayList<>();
+        for (MerchantProductTagRelation merchantProductTagRelation : relationList) {
+            String productId = merchantProductTagRelation.getPid();
+            productIdList.add(productId);
+        }
+        List<ItemVo> itemVoList = this.findByIds(merchantId, productIdList);
+        page.setList(itemVoList);
+        return APIResult.ok(page);
+    }
+
+    public static ItemVo convert(Course course) {
+        ItemVo itemVo = new ItemVo();
+        itemVo.setId(course.getId());
+        itemVo.setCode(course.getCode());
+        itemVo.setTitle(course.getTitle());
+        itemVo.setSubTitle(course.getSubTitle());
+        itemVo.setBreadCrumb(course.getBreadCrumb());
+        itemVo.setType(course.getType());
+        itemVo.setCoverUrl(course.getCoverUrl());
+        return itemVo;
+    }
+
+    public static ItemVo convert(Support support) {
+        ItemVo itemVo = new ItemVo();
+        itemVo.setId(support.getId());
+        itemVo.setCode(support.getCode());
+        itemVo.setTitle(support.getTitle());
+        itemVo.setSubTitle(support.getSubTitle());
+        itemVo.setType(support.getType());
+        itemVo.setCoverUrl(support.getCoverUrl());
+        itemVo.setImgList(support.getImgList());
+        return itemVo;
+    }
+
+    public static ItemGoodsVo convert(Goods goods) {
+        ItemGoodsVo itemGoodsVo = new ItemGoodsVo();
+        itemGoodsVo.setId(goods.getId());
+        itemGoodsVo.setChargeUnit(goods.getChargeUnit());
+        itemGoodsVo.setTerminalPrice(goods.getTerminalPrice());
+        return itemGoodsVo;
+    }
+}

+ 2 - 2
rankin-product-service/src/main/java/cn/rankin/productservice/service/MerchantProductTagRelationService.java

@@ -3,7 +3,7 @@ package cn.rankin.productservice.service;
 import cn.rankin.common.utils.enums.BaseStatusEnum;
 import cn.rankin.common.utils.util.ListUtil;
 import cn.rankin.data.api.product.entity.MerchantProductTagRelation;
-import cn.rankin.productservice.repository.ProductTagRelationRepository;
+import cn.rankin.productservice.repository.MerchantProductTagRelationRepository;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
@@ -17,7 +17,7 @@ import java.util.List;
 public class MerchantProductTagRelationService {
 
     @Autowired
-    private ProductTagRelationRepository relationRepository;
+    private MerchantProductTagRelationRepository relationRepository;
 
     public List<MerchantProductTagRelation> findByTagId(String tagId) {
         return relationRepository.findByTagId(tagId);

+ 9 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/service/TagGroupService.java

@@ -93,4 +93,13 @@ public class TagGroupService {
         tagGroup.setTagList(tagList);
         return APIResult.ok(tagGroup);
     }
+
+    public APIResult<TagGroup> findTagGroupByCode(String code, String merchantId) {
+        TagGroup tagGroup = tagGroupRepository.findFirstByCode(code, merchantId);
+        if (tagGroup == null) {
+            return APIResult.error(ProductServiceAPICode.NOT_EXISTS);
+        }
+        String groupId = tagGroup.getId();
+        return this.getTagGroup(groupId);
+    }
 }

+ 67 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/service/app/AppLessonService.java

@@ -0,0 +1,67 @@
+package cn.rankin.productservice.service.app;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.enums.BaseStatusEnum;
+import cn.rankin.common.utils.util.ListUtil;
+import cn.rankin.data.api.product.entity.CourseSubRelation;
+import cn.rankin.data.api.product.entity.CourseWare;
+import cn.rankin.data.api.product.entity.Lesson;
+import cn.rankin.data.api.product.entity.LessonWareRelation;
+import cn.rankin.productservice.code.ProductServiceAPICode;
+import cn.rankin.productservice.repository.*;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+
+@Service
+public class AppLessonService {
+
+    @Autowired
+    private LessonRepository lessonRepository;
+
+    @Autowired
+    private WareRepository wareRepository;
+
+    @Autowired
+    private LessonWareRelationRepository lessonWareRelationRepository;
+
+    @Autowired
+    private CourseSubRelationRepository courseSubRelationRepository;
+
+    public APIResult<Lesson> getLesson(String lessonId, String courseId) {
+        Lesson lesson = lessonRepository.find(lessonId);
+        if (lesson == null || !BaseStatusEnum.NORMAL.equals(lesson.getStatus())) {
+            return APIResult.error(ProductServiceAPICode.NOT_EXISTS);
+        }
+
+        // set lesson sort from relation
+        CourseSubRelation courseSubRelation = courseSubRelationRepository.findFirstByCourseIdOrderBySort(courseId);
+        if (courseSubRelation == null) {
+            return APIResult.error(ProductServiceAPICode.error("课程关系不存在"));
+        }
+        lesson.setSort(courseSubRelation.getSort());
+
+        // get courseware id list
+        List<LessonWareRelation> lessonWareRelationList = lessonWareRelationRepository.findByLessonId(lessonId, BaseStatusEnum.NORMAL);
+        List<String> wareIdList = new ArrayList<>();
+        lessonWareRelationList.forEach(relation -> wareIdList.add(relation.getWareId()));
+
+        // get courseware list with sort
+        List<CourseWare> courseWareList = wareRepository.findByIdIn(wareIdList, BaseStatusEnum.NORMAL);
+        Map<String, CourseWare> courseWareMap = ListUtil.convert(courseWareList, "id", CourseWare.class);
+        List<CourseWare> sortWareList = new ArrayList<>();
+        for (String wareId : wareIdList) {
+            CourseWare courseWare = courseWareMap.get(wareId);
+            if (courseWare == null) {
+                continue;
+            }
+            sortWareList.add(courseWare);
+        }
+        lesson.setWareList(sortWareList);
+
+        return APIResult.ok(lesson);
+    }
+}

+ 31 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/service/auth/AuthClient.java

@@ -0,0 +1,31 @@
+package cn.rankin.productservice.service.auth;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.data.api.auth.dto.AuthQueryDTO;
+import cn.rankin.data.api.auth.vo.AuthVo;
+import cn.rankin.productservice.code.ProductServiceAPICode;
+import com.sun.xml.internal.xsom.impl.Ref;
+import org.apache.http.entity.ContentType;
+import org.springframework.cloud.netflix.feign.FeignClient;
+import org.springframework.stereotype.Component;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+
+import java.util.List;
+
+@FeignClient(name = "auth-client", url = "${remote.auth.url}")//, fallback = AuthClient.AuthServiceHystrix.class)
+public interface AuthClient {
+
+    @RequestMapping(value = "/acenter/v1/auth/list", method = RequestMethod.POST, consumes = "application/json")
+    APIResult<List<AuthVo>> auth(@RequestBody AuthQueryDTO authQueryDTO);
+
+//    @Component
+//    class AuthServiceHystrix implements AuthClient {
+//
+//        @Override
+//        public APIResult<List<AuthVo>> auth(AuthQueryDTO authQueryDTO) {
+//            return APIResult.error(ProductServiceAPICode.SERVER_ERROR);
+//        }
+//    }
+}

+ 98 - 0
rankin-product-service/src/main/java/cn/rankin/productservice/service/auth/AuthService.java

@@ -0,0 +1,98 @@
+package cn.rankin.productservice.service.auth;
+
+import cn.rankin.common.utils.api.model.APIResult;
+import cn.rankin.common.utils.api.model.BaseCode;
+import cn.rankin.common.utils.constant.Constant;
+import cn.rankin.data.api.auth.dto.AuthQueryDTO;
+import cn.rankin.data.api.auth.vo.AuthResult;
+import cn.rankin.data.api.auth.vo.AuthVo;
+import cn.rankin.data.api.product.entity.MerchantProduct;
+import cn.rankin.data.api.product.entity.PackageProductRelation;
+import cn.rankin.productservice.repository.MerchantProductRepository;
+import cn.rankin.productservice.repository.PackageProductRelationRepository;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.util.CollectionUtils;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.List;
+
+@Service
+public class AuthService {
+
+    @Autowired
+    private AuthClient authClient;
+
+    @Autowired
+    private PackageProductRelationRepository packageProductRelationRepository;
+
+    @Autowired
+    private MerchantProductRepository merchantProductRepository;
+
+    public APIResult<AuthResult> auth(String userId, String merchantId, String itemId) {
+        AuthResult authResult = new AuthResult();
+        authResult.setPid(itemId);
+        authResult.setUserId(userId);
+        authResult.setType(Constant.ProductType.COURSE);
+
+        List<String> authIdList = new ArrayList<>();
+        authIdList.add(itemId);
+
+        List<PackageProductRelation> relationList = packageProductRelationRepository.findByPid(itemId);
+        for (PackageProductRelation relation : relationList) {
+            String productId = relation.getPkgId();
+            authIdList.add(productId);
+        }
+        List<MerchantProduct> merchantProductList = merchantProductRepository.findByPidsAndMerchantId(authIdList, merchantId);
+        if (CollectionUtils.isEmpty(merchantProductList)) {
+            return APIResult.ok(authResult);
+        }
+
+        List<String> validIdList = new ArrayList<>();
+        merchantProductList.forEach(merchantProduct -> validIdList.add(merchantProduct.getPid()));
+        AuthQueryDTO authQueryDTO = new AuthQueryDTO();
+        authQueryDTO.setUid(userId);
+        authQueryDTO.setPids(validIdList);
+        authQueryDTO.setBizCode(Constant.BIZ_CODE);
+        authQueryDTO.setType(Constant.ProductType.COURSE);
+
+        APIResult<List<AuthVo>> apiResult = authClient.auth(authQueryDTO);
+        if (!apiResult.getSuccess()) {
+            return APIResult.error(new BaseCode(apiResult.getCode(), apiResult.getMessage()));
+        }
+        List<AuthVo> authVoList = apiResult.getData();
+        if (CollectionUtils.isEmpty(authVoList)) {
+            return APIResult.ok(authResult);
+        }
+        Collections.sort(authVoList, new Comparator<AuthVo>() {
+            @Override
+            public int compare(AuthVo o1, AuthVo o2) {
+                Long diff = o1.getStartTime() - o2.getStartTime();
+                if (diff > 0L) {
+                    return 1;
+                }
+                return 0;
+            }
+        });
+        for (int i = 0; i < authVoList.size(); i++) {
+            AuthVo authVo = authVoList.get(i);
+            if (i == 0) {
+                authResult.setStartTime(authVo.getStartTime());
+                authResult.setEndTime(authVo.getEndTime());
+                continue;
+            }
+            Long endTime = authResult.getEndTime();
+            Long startTime = authVo.getStartTime();
+            if (endTime < startTime) {
+                break;
+            }
+            authResult.setEndTime(startTime);
+            if (i == authVoList.size()) {
+                authResult.setEndTime(authVo.getEndTime());
+            }
+        }
+        return APIResult.ok(authResult);
+    }
+}

+ 2 - 1
rankin-product-service/src/main/java/cn/rankin/productservice/utils/DTOConverter.java

@@ -3,6 +3,7 @@ package cn.rankin.productservice.utils;
 import cn.rankin.common.utils.enums.BaseStatusEnum;
 import cn.rankin.common.utils.enums.CourseSubTypeEnum;
 import cn.rankin.common.utils.enums.ProductTypeEnum;
+import cn.rankin.data.api.app.vo.ItemVo;
 import cn.rankin.data.api.product.dto.*;
 import cn.rankin.data.api.product.entity.*;
 import cn.rankin.data.api.product.entity.Package;
@@ -48,7 +49,6 @@ public class DTOConverter {
         CourseSubItemVo subItemVo = new CourseSubItemVo();
         BeanUtils.copyProperties(lesson, subItemVo);
         subItemVo.setType(CourseSubTypeEnum.LESSON);
-
         return subItemVo;
     }
 
@@ -138,4 +138,5 @@ public class DTOConverter {
         pkg.setStatus(packageDTO.getStatus());
         return pkg;
     }
+
 }

+ 37 - 26
rankin-product-service/src/main/java/cn/rankin/productservice/utils/TestUtil.java

@@ -4,9 +4,7 @@ import com.alibaba.fastjson.JSON;
 import org.springframework.util.CollectionUtils;
 
 import java.math.BigDecimal;
-import java.util.ArrayList;
-import java.util.Comparator;
-import java.util.List;
+import java.util.*;
 
 public class TestUtil {
 
@@ -30,29 +28,42 @@ public class TestUtil {
         }
     }
 
+//    public static void main(String[] args) {
+//        List<Item> list1 = new ArrayList<>();
+//        list1.add(new Item(3, 1));
+//        list1.add(new Item(1, 2));
+//        list1.add(new Item(2, 1));
+//        list1.add(new Item(1, 1));
+//        list1.add(new Item(2,2));
+//        list1.add(new Item(3, 2));
+//        list1.sort(Comparator.comparing(Item::getSort));
+//
+//
+////        List<String> list2 = new ArrayList<>();
+////        list2.add("1");
+////        list2.add("2");
+////        list2.add("3");
+//
+////        list1.removeAll(list2);
+////        System.out.println(JSON.toJSONString(list1));
+////        List<String> id = null;
+////        System.out.println(CollectionUtils.isEmpty(id));
+//        BigDecimal a = new BigDecimal("1");
+//        BigDecimal b = new BigDecimal("0.2");
+//        BigDecimal c = a.add(b);
+//        System.out.println(c);
+//    }
     public static void main(String[] args) {
-        List<Item> list1 = new ArrayList<>();
-        list1.add(new Item(3, 1));
-        list1.add(new Item(1, 2));
-        list1.add(new Item(2, 1));
-        list1.add(new Item(1, 1));
-        list1.add(new Item(2,2));
-        list1.add(new Item(3, 2));
-        list1.sort(Comparator.comparing(Item::getSort));
-
-
-//        List<String> list2 = new ArrayList<>();
-//        list2.add("1");
-//        list2.add("2");
-//        list2.add("3");
-
-//        list1.removeAll(list2);
-//        System.out.println(JSON.toJSONString(list1));
-//        List<String> id = null;
-//        System.out.println(CollectionUtils.isEmpty(id));
-        BigDecimal a = new BigDecimal("1");
-        BigDecimal b = new BigDecimal("0.2");
-        BigDecimal c = a.add(b);
-        System.out.println(c);
+        List<Integer> testList = new ArrayList<>();
+        testList.add(5);
+        testList.add(1);
+        testList.add(10);
+        testList.sort(new Comparator<Integer>() {
+            @Override
+            public int compare(Integer o1, Integer o2) {
+                return o1 - o2;
+            }
+        });
+        System.out.println(testList);
     }
 }

+ 10 - 0
rankin-product-service/src/main/resources/bootstrap.yml

@@ -9,3 +9,13 @@ spring:
       
 server:
   port: 8100
+
+feign:
+  httpclient:
+     enabled: true
+  hystrix:
+    enabled: false
+
+#logging:
+#  level:
+#    root: debug

+ 7 - 2
rankin-user-service/src/main/java/cn/rankin/userservice/controller/CollectionController.java

@@ -21,12 +21,17 @@ public class CollectionController {
     @Autowired
     private CollectionService collectionService;
 
-    @RequestMapping(method = RequestMethod.PUT)
+    @RequestMapping(method = RequestMethod.GET)
+    public APIResult<Collection> getCollection(@RequestParam("pid") String productId, @RequestParam("userId") String userId) {
+        return collectionService.getCollection(userId, productId);
+    }
+
+    @RequestMapping(method = RequestMethod.POST)
     public APIResult<Boolean> put(@RequestBody CollectionDTO collectionDTO) {
         return collectionService.put(collectionDTO);
     }
 
-    @RequestMapping(method = RequestMethod.GET)
+    @RequestMapping(value = "/list", method = RequestMethod.GET)
     public APIResult<List<Collection>> getCollections(@RequestParam("userId") String userId, @RequestParam(value = "size", required = false) Integer size) {
         if (StringUtils.isEmpty(userId)) {
             return APIResult.error(UserServiceAPICode.PARAMETER_ERROR);

+ 15 - 0
rankin-user-service/src/main/java/cn/rankin/userservice/service/CollectionService.java

@@ -11,6 +11,7 @@ import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
+import javax.transaction.Transactional;
 import java.util.List;
 
 import static cn.rankin.userservice.utils.DTOConverter.convert;
@@ -22,6 +23,19 @@ public class CollectionService {
     @Autowired
     private CollectionRepository collectionRepository;
 
+    public APIResult<Collection> getCollection(String userId, String productId) {
+        Collection sample = new Collection();
+        sample.setUserId(userId);
+        sample.setPid(productId);
+        sample.setStatus(BaseStatusEnum.NORMAL);
+        Collection collection = collectionRepository.findFirst(sample);
+        if (collection == null) {
+            return APIResult.error(UserServiceAPICode.NOT_EXISTS);
+        }
+        return APIResult.ok(collection);
+    }
+
+    @Transactional
     public APIResult<Boolean> put(CollectionDTO collectionDTO) {
         Collection collection = collectionRepository.findByPidAndUserId(collectionDTO.getPid(), collectionDTO.getUserId());
         if (collection != null) {
@@ -61,6 +75,7 @@ public class CollectionService {
         return APIResult.ok(list);
     }
 
+    @Transactional
     public APIResult<Boolean> delete(String userId, String productId) {
         Integer count = collectionRepository.deleteByPidAndUserId(productId, userId);
         if (count > 0) {