处理积分下单,及退款

This commit is contained in:
朱耘稷
2021-01-06 20:29:16 +08:00
committed by xuwenbo
parent d6eab7adff
commit 89babb8247
11 changed files with 217 additions and 119 deletions

View File

@ -34,19 +34,19 @@ public class ConfigurerAdapter implements WebMvcConfigurer {
@Value("${file.avatar}") @Value("${file.avatar}")
private String avatar; private String avatar;
// @Bean @Bean
// public CorsFilter corsFilter() { public CorsFilter corsFilter() {
// UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource(); UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
// CorsConfiguration config = new CorsConfiguration(); CorsConfiguration config = new CorsConfiguration();
// config.setAllowCredentials(true); config.setAllowCredentials(true); // 允许cookies跨域
// // 设置允许跨域请求的域名 config.addAllowedOriginPattern("*");// #允许向该服务器提交请求的URI*表示全部允许在SpringMVC中如果设成*会自动转成当前请求头中的Origin
// config.setAllowedOriginPatterns(Arrays.asList("*")); config.addAllowedHeader("*");// #允许访问的头信息,*表示全部
// config.addAllowedOrigin("*"); config.setMaxAge(18000L);// 预检请求的缓存时间(秒),即在这个时间段里,对于相同的跨域请求不会再预检了
// config.addAllowedHeader("*"); config.addAllowedMethod("OPTIONS");// 允许提交请求的方法类型,*表示全部允许
// config.addAllowedMethod("*");
// source.registerCorsConfiguration("/**", config); source.registerCorsConfiguration("/**", config);
// return new CorsFilter(source); return new CorsFilter(source);
// } }
@Override @Override
public void addResourceHandlers(ResourceHandlerRegistry registry) { public void addResourceHandlers(ResourceHandlerRegistry registry) {

View File

@ -1,47 +1,47 @@
package co.yixiang.config; //package co.yixiang.config;
//
/** ///**
* @author LionCity // * @author LionCity
* @date Created in 2020-12-21 13:38 // * @date Created in 2020-12-21 13:38
* @description // * @description
* @modified By // * @modified By
* @version: // * @version:
*/ // */
import java.io.IOException; //import java.io.IOException;
//
import javax.servlet.FilterChain; //import javax.servlet.FilterChain;
import javax.servlet.ServletException; //import javax.servlet.ServletException;
import javax.servlet.http.HttpFilter; //import javax.servlet.http.HttpFilter;
import javax.servlet.http.HttpServletRequest; //import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse; //import javax.servlet.http.HttpServletResponse;
//
import co.yixiang.utils.StringUtils; //import co.yixiang.utils.StringUtils;
import org.springframework.core.annotation.Order; //import org.springframework.core.annotation.Order;
import org.springframework.http.HttpHeaders; //import org.springframework.http.HttpHeaders;
import org.springframework.stereotype.Component; //import org.springframework.stereotype.Component;
//
@Component //@Component
@Order(-9999) //@Order(-9999)
public class CorsFilter extends HttpFilter { //public class CorsFilter extends HttpFilter {
//
/** // /**
* // *
*/ // */
private static final long serialVersionUID = -8387103310559517243L; // private static final long serialVersionUID = -8387103310559517243L;
//
@Override // @Override
protected void doFilter(HttpServletRequest req, HttpServletResponse res, FilterChain chain) throws IOException, ServletException { // protected void doFilter(HttpServletRequest req, HttpServletResponse res, FilterChain chain) throws IOException, ServletException {
//
String origin = req.getHeader(HttpHeaders.ORIGIN); // String origin = req.getHeader(HttpHeaders.ORIGIN);
//
if (!StringUtils.isEmpty(origin)){ // if (!StringUtils.isEmpty(origin)){
res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_ORIGIN, origin); // res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_ORIGIN, origin);
res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_HEADERS, "Origin, x-requested-with, Content-Type, Accept, Authorization"); // res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_HEADERS, "Origin, x-requested-with, Content-Type, Accept, Authorization");
res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_CREDENTIALS, "true"); // res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_CREDENTIALS, "true");
res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_METHODS, "GET, POST, PUT, OPTIONS, DELETE"); // res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_METHODS, "GET, POST, PUT, OPTIONS, DELETE");
res.addHeader(HttpHeaders.ACCESS_CONTROL_EXPOSE_HEADERS, "Cache-Control, Content-Language, Content-Type, Expires, Last-Modified, Pragma"); // res.addHeader(HttpHeaders.ACCESS_CONTROL_EXPOSE_HEADERS, "Cache-Control, Content-Language, Content-Type, Expires, Last-Modified, Pragma");
res.addHeader(HttpHeaders.ACCESS_CONTROL_MAX_AGE, "60"); // res.addHeader(HttpHeaders.ACCESS_CONTROL_MAX_AGE, "60");
} // }
super.doFilter(req, res, chain); // super.doFilter(req, res, chain);
} // }
} //}

View File

@ -6,7 +6,6 @@
package co.yixiang.modules.security.config; package co.yixiang.modules.security.config;
import co.yixiang.annotation.AnonymousAccess; import co.yixiang.annotation.AnonymousAccess;
import co.yixiang.config.CorsFilter;
import co.yixiang.modules.security.security.JwtAccessDeniedHandler; import co.yixiang.modules.security.security.JwtAccessDeniedHandler;
import co.yixiang.modules.security.security.JwtAuthenticationEntryPoint; import co.yixiang.modules.security.security.JwtAuthenticationEntryPoint;
import co.yixiang.modules.security.security.TokenConfigurer; import co.yixiang.modules.security.security.TokenConfigurer;
@ -24,6 +23,7 @@ import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder; import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter; import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import org.springframework.web.filter.CorsFilter;
import org.springframework.web.method.HandlerMethod; import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.mvc.method.RequestMappingInfo; import org.springframework.web.servlet.mvc.method.RequestMappingInfo;
import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping; import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping;

View File

@ -6,9 +6,9 @@ spring:
druid: druid:
type: com.alibaba.druid.pool.DruidDataSource type: com.alibaba.druid.pool.DruidDataSource
driverClassName: com.mysql.cj.jdbc.Driver driverClassName: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://localhost:3306/yshopb2c?serverTimezone=Asia/Shanghai&characterEncoding=utf8&useSSL=false&zeroDateTimeBehavior=convertToNull url: jdbc:mysql://localhost:3366/yshopb2c?serverTimezone=Asia/Shanghai&characterEncoding=utf8&useSSL=false&zeroDateTimeBehavior=convertToNull
username: root username: yshopb2c
password: xxcs@!2019 password: bkfGfAimifjPZtNE
# 初始化配置 # 初始化配置
initial-size: 3 initial-size: 3
@ -41,10 +41,10 @@ spring:
redis: redis:
#数据库索引 #数据库索引
database: 2 database: 5
host: 127.0.0.1 host: 127.0.0.1
port: 6379 port: 6399 # Redis服务器连接端口
password: password: 6379@@6379 # Redis服务器连接密码默认为空
#连接超时时间 #连接超时时间
timeout: 5000 timeout: 5000
@ -87,8 +87,9 @@ swagger:
file: file:
path: /home/yshop/file/ path: /www/wwwroot/thapi.xinxintuan.co/upload/file/
avatar: /home/yshop/avatar/ avatar: /www/wwwroot/thapi.xinxintuan.co/upload/avatar/
# 文件大小 /M # 文件大小 /M
maxSize: 100 maxSize: 100
avatarMaxSize: 5 avatarMaxSize: 5

18
yshop-app/Dockerfile Normal file
View File

@ -0,0 +1,18 @@
FROM anapsix/alpine-java:8_server-jre_unlimited
MAINTAINER wangiegie@gmail.com
ENV TZ=Asia/Shanghai
ENV JAVA_OPTS="-Xms128m -Xmx256m -Djava.security.egd=file:/dev/./urandom"
RUN ln -sf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone
RUN mkdir -p /yshop-app
WORKDIR /yshop-app
EXPOSE 8008
ADD ./target/yshop-app-3.1.jar ./
CMD java $JAVA_OPTS -jar yshop-app-3.1.jar --spring.profiles.active=dev

View File

@ -0,0 +1,47 @@
package co.yixiang.common.config;
/**
* @author LionCity
* @date Created in 2020-12-21 13:38
* @description
* @modified By
* @version:
*/
import co.yixiang.utils.StringUtils;
import org.springframework.core.annotation.Order;
import org.springframework.http.HttpHeaders;
import org.springframework.stereotype.Component;
import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpFilter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@Component
@Order(-9999)
public class CorsFilter extends HttpFilter {
/**
*
*/
private static final long serialVersionUID = -8387103310559517243L;
@Override
protected void doFilter(HttpServletRequest req, HttpServletResponse res, FilterChain chain) throws IOException, ServletException {
String origin = req.getHeader(HttpHeaders.ORIGIN);
if (!StringUtils.isEmpty(origin)){
res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_ORIGIN, origin);
res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_HEADERS, "Origin, x-requested-with, Content-Type, Accept, Authorization");
res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_CREDENTIALS, "true");
res.addHeader(HttpHeaders.ACCESS_CONTROL_ALLOW_METHODS, "GET, POST, PUT, OPTIONS, DELETE");
res.addHeader(HttpHeaders.ACCESS_CONTROL_EXPOSE_HEADERS, "Cache-Control, Content-Language, Content-Type, Expires, Last-Modified, Pragma");
res.addHeader(HttpHeaders.ACCESS_CONTROL_MAX_AGE, "60");
}
super.doFilter(req, res, chain);
}
}

View File

@ -46,18 +46,18 @@ public class InterceptorConfig implements WebMvcConfigurer {
registry.addInterceptor(this.getPermissionInterceptor()); registry.addInterceptor(this.getPermissionInterceptor());
} }
@Bean // @Bean
public CorsFilter corsFilter() { // public CorsFilter corsFilter() {
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource(); // UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
CorsConfiguration config = new CorsConfiguration(); // CorsConfiguration config = new CorsConfiguration();
config.setAllowCredentials(true); // config.setAllowCredentials(true);
config.addAllowedOrigin("*"); // config.addAllowedOrigin("*");
config.addAllowedHeader("*"); // config.addAllowedHeader("*");
config.addAllowedMethod("*"); // config.addAllowedMethod("*");
source.registerCorsConfiguration("/**", config); // source.registerCorsConfiguration("/**", config);
return new CorsFilter(source); // return new CorsFilter(source);
//
} // }
@Override @Override

View File

@ -31,7 +31,7 @@ public class StoreIntegralController {
/** /**
* 获取积分产品列表 * 获取积分产品列表
*/ */
@GetMapping("/products") @GetMapping("/products/integral")
@ApiOperation(value = "获取积分产品列表",notes = "获取积分产品列表") @ApiOperation(value = "获取积分产品列表",notes = "获取积分产品列表")
public ApiResult<List<YxStoreProductQueryVo>> goodsList(YxStoreProductQueryParam productQueryParam){ public ApiResult<List<YxStoreProductQueryVo>> goodsList(YxStoreProductQueryParam productQueryParam){
return ApiResult.ok(storeProductService.getGoodsList(productQueryParam)); return ApiResult.ok(storeProductService.getGoodsList(productQueryParam));

View File

@ -13,14 +13,11 @@ import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil; import cn.hutool.core.util.StrUtil;
import co.yixiang.api.ApiResult; import co.yixiang.api.ApiResult;
import co.yixiang.api.YshopException; import co.yixiang.api.YshopException;
import co.yixiang.enums.ShipperCodeEnum; import co.yixiang.enums.*;
import co.yixiang.enums.ShopCommonEnum;
import co.yixiang.logging.aop.log.AppLog; import co.yixiang.logging.aop.log.AppLog;
import co.yixiang.common.aop.NoRepeatSubmit; import co.yixiang.common.aop.NoRepeatSubmit;
import co.yixiang.common.bean.LocalUser; import co.yixiang.common.bean.LocalUser;
import co.yixiang.common.interceptor.AuthCheck; import co.yixiang.common.interceptor.AuthCheck;
import co.yixiang.enums.OrderInfoEnum;
import co.yixiang.enums.OrderLogEnum;
import co.yixiang.modules.mp.domain.YxWechatTemplate; import co.yixiang.modules.mp.domain.YxWechatTemplate;
import co.yixiang.modules.mp.service.YxWechatTemplateService; import co.yixiang.modules.mp.service.YxWechatTemplateService;
import co.yixiang.modules.order.domain.YxStoreOrder; import co.yixiang.modules.order.domain.YxStoreOrder;
@ -177,7 +174,7 @@ public class StoreOrderController {
//开始处理支付 //开始处理支付
//处理金额为0的情况 //处理金额为0的情况
if(order.getPayPrice().compareTo(BigDecimal.ZERO) <= 0){ if(order.getPayPrice().compareTo(BigDecimal.ZERO) <= 0&&!param.getPayType().equals(PayTypeEnum.INTEGRAL.getValue())){
storeOrderService.yuePay(orderId,yxUser.getUid()); storeOrderService.yuePay(orderId,yxUser.getUid());
map.put("payMsg","支付成功"); map.put("payMsg","支付成功");
return ApiResult.ok(map,"支付成功"); return ApiResult.ok(map,"支付成功");
@ -218,7 +215,7 @@ public class StoreOrderController {
map.put("result",orderDTO); map.put("result",orderDTO);
if(storeOrder.getPayPrice().compareTo(BigDecimal.ZERO) <= 0){ if(storeOrder.getPayPrice().compareTo(BigDecimal.ZERO) <= 0&&!param.getPaytype().equals(PayTypeEnum.INTEGRAL.getValue())){
storeOrderService.yuePay(orderId,uid); storeOrderService.yuePay(orderId,uid);
return ApiResult.ok(map,"支付成功"); return ApiResult.ok(map,"支付成功");
} }

View File

@ -5,9 +5,9 @@ spring:
druid: druid:
# 主库数据源 # 主库数据源
master: master:
url: jdbc:mysql://localhost:3306/yshopb2c?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=false&serverTimezone=GMT%2B8 url: jdbc:mysql://localhost:3366/yshopb2c?serverTimezone=Asia/Shanghai&characterEncoding=utf8&useSSL=false&zeroDateTimeBehavior=convertToNull
username: root username: yshopb2c
password: xxcs@!2019 password: bkfGfAimifjPZtNE
# 从库数据源 # 从库数据源
slave: slave:
# 从数据源开关/默认关闭 # 从数据源开关/默认关闭
@ -47,10 +47,10 @@ spring:
config: config:
multi-statement-allow: true multi-statement-allow: true
redis: redis:
host: 127.0.0.1 # Redis服务器地址 host: localhost # Redis服务器地址
database: 2 # Redis数据库索引默认为0 database: 5 # Redis数据库索引默认为0
port: 6379 # Redis服务器连接端口 port: 6399 # Redis服务器连接端口
password: # Redis服务器连接密码默认为空 password: 6379@@6379 # Redis服务器连接密码默认为空
jedis: jedis:
pool: pool:
max-active: 8 # 连接池最大连接数(使用负值表示没有限制) max-active: 8 # 连接池最大连接数(使用负值表示没有限制)
@ -90,8 +90,8 @@ swagger:
# 文件存储路径 # 文件存储路径
file: file:
path: /home/yshop/file/ path: /www/wwwroot/thapi.xinxintuan.co/upload/file/
avatar: /home/yshop/avatar/ avatar: /www/wwwroot/thapi.xinxintuan.co/upload/avatar/
# 文件大小 /M # 文件大小 /M
maxSize: 100 maxSize: 100
avatarMaxSize: 5 avatarMaxSize: 5

View File

@ -906,11 +906,11 @@ public class YxStoreOrderServiceImpl extends BaseServiceImpl<StoreOrderMapper, Y
throw new YshopException("订单不存在"); throw new YshopException("订单不存在");
} }
this.regressionIntegral(order); this.regressionIntegral(order,0);
this.regressionStock(order); this.regressionStock(order,0);
this.regressionCoupon(order); this.regressionCoupon(order,0);
yxStoreOrderMapper.deleteById(order.getId()); yxStoreOrderMapper.deleteById(order.getId());
} }
@ -1610,16 +1610,29 @@ public class YxStoreOrderServiceImpl extends BaseServiceImpl<StoreOrderMapper, Y
if(OrderInfoEnum.PAY_STATUS_1.getValue().equals(orderInfo.getPaid())) { if(OrderInfoEnum.PAY_STATUS_1.getValue().equals(orderInfo.getPaid())) {
throw new YshopException("该订单已支付"); throw new YshopException("该订单已支付");
} }
orderInfo=handleOrder(orderInfo);
YxUserQueryVo userInfo = userService.getYxUserById(uid); orderInfo.getCartInfo().forEach(cart->{
if(cart.getProductInfo().getIsIntegral()==0){
throw new YshopException("该商品不为积分商品");
}
});
YxUser userInfo = userService.getById(uid);
if(userInfo.getIntegral().compareTo(orderInfo.getPayIntegral()) < 0){ if(userInfo.getIntegral().compareTo(orderInfo.getPayIntegral()) < 0){
throw new YshopException("积分不足"); throw new YshopException("积分不足");
} }
//扣除积分 //扣除积分
userService.decIntegral(uid,orderInfo.getPayIntegral().doubleValue()); //userService.decIntegral(uid,orderInfo.getPayIntegral().doubleValue());
BigDecimal newIntegral = NumberUtil.sub(userInfo.getIntegral(), orderInfo.getPayIntegral());
userInfo.setIntegral(newIntegral);
userService.updateById(userInfo);
//增加流水
billService.expend(userInfo.getUid(), "兑换商品", BillDetailEnum.CATEGORY_2.getValue(),
BillDetailEnum.TYPE_8.getValue(),
orderInfo.getPayIntegral().doubleValue(),
newIntegral.doubleValue(),
"兑换商品扣除" + orderInfo.getPayIntegral().doubleValue() + "积分");
//支付成功后处理 //支付成功后处理
this.paySuccess(orderInfo.getOrderId(),PayTypeEnum.INTEGRAL.getValue()); this.paySuccess(orderInfo.getOrderId(),PayTypeEnum.INTEGRAL.getValue());
} }
@ -1731,10 +1744,17 @@ public class YxStoreOrderServiceImpl extends BaseServiceImpl<StoreOrderMapper, Y
* 退回优惠券 * 退回优惠券
* @param order 订单 * @param order 订单
*/ */
private void regressionCoupon(YxStoreOrderQueryVo order) { private void regressionCoupon(YxStoreOrderQueryVo order,Integer type) {
if(OrderInfoEnum.PAY_STATUS_1.equals(order.getPaid()) if(type==0){
|| OrderStatusEnum.STATUS_MINUS_2.getValue().equals(order.getStatus())){ if(OrderInfoEnum.PAY_STATUS_1.getValue().equals(order.getPaid())
return; || OrderStatusEnum.STATUS_MINUS_2.getValue().equals(order.getStatus())){
return;
}
}else{
if(!(OrderInfoEnum.PAY_STATUS_1.getValue().equals(order.getPaid())
&& OrderInfoEnum.REFUND_STATUS_2.getValue().equals(order.getRefundStatus()))){
return;
}
} }
if(order.getCouponId() != null && order.getCouponId() > 0){ if(order.getCouponId() != null && order.getCouponId() > 0){
@ -1760,10 +1780,17 @@ public class YxStoreOrderServiceImpl extends BaseServiceImpl<StoreOrderMapper, Y
* 退回库存 * 退回库存
* @param order 订单 * @param order 订单
*/ */
private void regressionStock(YxStoreOrderQueryVo order) { private void regressionStock(YxStoreOrderQueryVo order,Integer type) {
if(OrderInfoEnum.PAY_STATUS_1.equals(order.getPaid()) if(type==0){
|| OrderStatusEnum.STATUS_MINUS_2.getValue().equals(order.getStatus())){ if(OrderInfoEnum.PAY_STATUS_1.getValue().equals(order.getPaid())
return; || OrderStatusEnum.STATUS_MINUS_2.getValue().equals(order.getStatus())){
return;
}
}else{
if(!(OrderInfoEnum.PAY_STATUS_1.getValue().equals(order.getPaid())
&& OrderInfoEnum.REFUND_STATUS_2.getValue().equals(order.getRefundStatus()))){
return;
}
} }
LambdaQueryWrapper<YxStoreOrderCartInfo> wrapper= new LambdaQueryWrapper<>(); LambdaQueryWrapper<YxStoreOrderCartInfo> wrapper= new LambdaQueryWrapper<>();
wrapper.in(YxStoreOrderCartInfo::getCartId, Arrays.asList(order.getCartId().split(","))); wrapper.in(YxStoreOrderCartInfo::getCartId, Arrays.asList(order.getCartId().split(",")));
@ -1790,11 +1817,19 @@ public class YxStoreOrderServiceImpl extends BaseServiceImpl<StoreOrderMapper, Y
* 退回积分 * 退回积分
* @param order 订单 * @param order 订单
*/ */
private void regressionIntegral(YxStoreOrderQueryVo order) { private void regressionIntegral(YxStoreOrderQueryVo order,Integer type) {
if(OrderInfoEnum.PAY_STATUS_1.getValue().equals(order.getPaid()) if(type==0){
|| OrderStatusEnum.STATUS_MINUS_2.getValue().equals(order.getStatus())){ if(OrderInfoEnum.PAY_STATUS_1.getValue().equals(order.getPaid())
return; || OrderStatusEnum.STATUS_MINUS_2.getValue().equals(order.getStatus())){
return;
}
}else{
if(!(OrderInfoEnum.PAY_STATUS_1.getValue().equals(order.getPaid())
&& OrderInfoEnum.REFUND_STATUS_2.getValue().equals(order.getRefundStatus()))){
return;
}
} }
if(order.getPayIntegral().compareTo(BigDecimal.ZERO)>0){ if(order.getPayIntegral().compareTo(BigDecimal.ZERO)>0){
order.setUseIntegral(order.getPayIntegral()); order.setUseIntegral(order.getPayIntegral());
} }
@ -2189,9 +2224,9 @@ public class YxStoreOrderServiceImpl extends BaseServiceImpl<StoreOrderMapper, Y
@Override @Override
public void retrunStock(String orderId) { public void retrunStock(String orderId) {
YxStoreOrderQueryVo order = this.getOrderInfo(orderId,null); YxStoreOrderQueryVo order = this.getOrderInfo(orderId,null);
this.regressionIntegral(order); this.regressionIntegral(order,1);
this.regressionStock(order); this.regressionStock(order,1);
this.regressionCoupon(order); this.regressionCoupon(order,1);
} }
@Override @Override