Java实现商城订单超时取消功能

 更新时间:2019年12月17日 11:50:00   作者:长路漫漫~Gavin  
大多数的B2C商城项目都会有限时活动,当用户下单后都会有支付超时时间,当订单超时后订单的状态就会自动变成已取消 ,这个功能的实现有很多种方法,本文的实现方法适合大多数比较小的商城使用。具体实现方式可以跟随小编一起看看吧

 大多数的B2C商城项目都会有限时活动,当用户下单后都会有支付超时时间,当订单超时后订单的状态就会自动变成已取消 ,这个功能的实现有很多种方法,本文的实现方法适合大多数比较小的商城使用。

实现原理:

     利用 jdk 的 DelayQueue的阻塞队列的特性实现。在项目启动时开启一个线程处理 DelayQueue 队列里弹出的超时订单对象,订单未超时该线程处于等待中。

DelayQueue的简单介绍:

    DelayQueue类的主要作用:是一个无界的BlockingQueue,用于放置实现了Delayed接口的对象,其中的对象只能在其到期时才能从队列中取走。这种队列是有序的,即队头对象的延迟到期时间最长。注意:不能将null元素放置到这种队列中。

实现方式 :

  1.创建一个实现Delayed接口的 order 类并重写compareTo和 getDelay方法

  2.创建一个帮助类OrderCollection(订单的增删查)

  3. 创建CancellOrder类

  在生成订单时将订单号创建时间和过期时间封装成一个实现Delayed接口的对象存入DelayQueue队列中,当该订单支付完成后将该对象从队列中移除,(为了保证不丢失订单建议在项目启动时将数据库中的符合条件的订单初始化到DelayQueue队列中 )

实现代码如下:

/**
 * 类说明
 *
 * @author grl
 * @date 2019年12月16日 新建
 */
public class Order implements Delayed {
  private String orderShopNum;
  /**
  * 1-普通活动 2-限时活动 3-拼购活动
  */
  private int orderType;
  private long orderCreateTime;
  private long expTime;
  public Order(String orderShopNum, int orderType, Date createTime) {
   if (StringUtils.isNotBlank(orderShopNum)) {
     this.orderShopNum = orderShopNum.trim();
   }
   if (createTime == null) {
     this.orderCreateTime = System.currentTimeMillis();
   } else {
     this.orderCreateTime = createTime.getTime();
   }
   this.orderType = orderType;
   if (orderType == 2) {
     this.expTime = TimeUnit.MILLISECONDS.convert(Const.LIMIT_ACTIVITY_EXPIRATION_TIME, TimeUnit.MINUTES)
        + createTime.getTime();
   }if(orderType == 3){
     this.expTime = TimeUnit.MILLISECONDS.convert(Const.LIMIT_GROUP_BUY_EXPIRATION_TIME, TimeUnit.MINUTES)
        + createTime.getTime();
   } else {
     this.expTime = TimeUnit.MILLISECONDS.convert(Const.ORDER_PAYMENT_DEADLINE, TimeUnit.DAYS)
        + createTime.getTime();
   }
  }
  public String getOrderShopNum() {
   return orderShopNum;
  }
  public long getOrderCreateTime() {
   return orderCreateTime;
  }
  public long getExpTime() {
   return expTime;
  }
  public int getOrderType() {
   return orderType;
  }
  @Override
  public int compareTo(Delayed o) {
   return Long.valueOf(this.expTime).compareTo(Long.valueOf(((Order) o).expTime));
  }
  @Override
  public long getDelay(TimeUnit unit) {
   return unit.convert(this.expTime - System.currentTimeMillis(), TimeUnit.MILLISECONDS);
  }
 
}
 
/**
 * 类说明
 *
 * @author grl
 * @date 2019年12月16日 新建
 */
public class OrderCollection {
  /**
  * 订单管理集合
  */
  private static DelayQueue<Order> orderList = new DelayQueue<Order>();
  private OrderCollection() {
  }
  /**
  * 获取订单集合
  * @author grl
  * @return
  */
  protected static DelayQueue getOrderCollection() {
   return orderList;
  } 
  /**
  * 向集合中添加订单
  * 
  * @author grl
  * @param order
  * @return
  */
  public static boolean add(Order order) {
   boolean flag = false;
   if (order != null && StringUtils.isNotBlank(order.getOrderShopNum())) {
     flag = orderList.offer(order);
   }
   return flag;
  }
  /**
  * 从集合中删除订单
  * 
  * @author grl
  * @param orderShopNum
  * @return
  */
  public static boolean remove(String orderShopNum) {
   boolean flag = false;
   Order thisOrder = null;
   if (StringUtils.isNotBlank(orderShopNum)) {
     orderShopNum = orderShopNum.trim();
     for (Order order : orderList) {
      String orderNum = order.getOrderShopNum();
      if (orderNum.equals(orderShopNum)) {
        thisOrder = order;
      }
     }
     if (thisOrder != null) {
      flag = orderList.remove(thisOrder);
     }
   }
   return flag;
  }
  /**
  * 获取订单的过期剩余时间
  * 
  * @author grl
  * @param orderShopNum
  * @param unit
  * @return -1 已经过期
  */
  public static long getDelay(String orderShopNum) {
   long time = -1;
   if (StringUtils.isNotBlank(orderShopNum)) {
     orderShopNum = orderShopNum.trim();
     for (Order order : orderList) {
      String orderNum = order.getOrderShopNum();
      if (orderNum.equals(orderShopNum)) {
        time = order.getDelay(TimeUnit.MILLISECONDS);
        if(time<5000) {
         time = -1;
        }
      }
     }
   }
   return time;
  }
}
 

/**
 * 类说明
 *
 * @author grl
 * @date 2019年12月16日 新建
 */
@Component
public class CancellOrder implements Runnable {
  private static final Logger log = LoggerFactory.getLogger(CancellOrder.class);
  @Override
  public void run() {
   while (true) {
     try {
      Order take = OrderCollection.getOrderCollection().take();
      String orderShopNum = take.getOrderShopNum();
      int orderType = take.getOrderType();
      // 业务逻辑操作
     } catch (InterruptedException e) {
      e.printStackTrace();
      log.error("CancellOrder DelayQueue 错误 {}", e.getMessage());
     }
   }
  }
}

总结

以上所述是小编给大家介绍的Java实现商城订单超时取消功能,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对脚本之家网站的支持!
如果你觉得本文对你有帮助,欢迎转载,烦请注明出处,谢谢!

相关文章

  • RabbitMQ中的channel信道、exchange交换机和queue队列详解

    RabbitMQ中的channel信道、exchange交换机和queue队列详解

    这篇文章主要介绍了RabbitMQ中的channel信道、exchange交换机和queue队列详解,connection是指物理的连接,一个client与一个server之间有一个连接,一个连接上可以建立多个channel,可以理解为逻辑上的连接,需要的朋友可以参考下
    2023-08-08
  • Java Hibernate中的查询策略和抓取策略

    Java Hibernate中的查询策略和抓取策略

    Hibernate是一种Java对象关系映射框架,提供了多种查询和抓取策略,用于优化数据库访问性能。查询策略包括延迟加载、立即加载、查询缓存等,抓取策略包括join抓取、子查询抓取、批量抓取等。这些策略可以根据实际应用场景进行选择和配置,提高数据访问的效率和稳定性
    2023-04-04
  • 深度剖析Java中的内存原型及工作原理

    深度剖析Java中的内存原型及工作原理

    这篇文章主要介绍了深度剖析Java中的内存原型及工作原理,本文讲解了java虚拟机内存原型、常量池、Java内存分配中的栈、Java内存分配中的堆等内容,需要的朋友可以参考下
    2015-01-01
  • Java正则表达式处理特殊字符转义的方法

    Java正则表达式处理特殊字符转义的方法

    由于正则表达式定了一些特殊字符,而有时候需要对这些特殊字符进行匹配的话就需要进行转义了,下面这篇文章主要给大家介绍了Java正则表达式处理特殊字符转义的方法,需要的朋友可以参考借鉴,下面来一起看看吧。
    2017-01-01
  • 走进SpringBoot之配置文件与多环境详解

    走进SpringBoot之配置文件与多环境详解

    这篇文章主要介绍了走进SpringBoot之配置文件与多环境,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2019-05-05
  • ElasticSearch之索引模板滚动索引实现详解

    ElasticSearch之索引模板滚动索引实现详解

    这篇文章主要为大家介绍了ElasticSearch之索引模板滚动索引实现详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-04-04
  • Java8 Lamdba函数式推导

    Java8 Lamdba函数式推导

    这篇文章主要介绍了Java8 Lamdba函数式推导,文章围绕主题展开详细的内容介绍,具有一定的参考价值,需要的小伙伴可以参考一下
    2022-08-08
  • springcloud配置ssh的问题及解决方法

    springcloud配置ssh的问题及解决方法

    这篇文章主要介绍了springcloud配置ssh,本文给大家介绍在配置过程中遇到的问题及解决方法,通过结合实例给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2022-03-03
  • springmvc+shiro+maven 实现登录认证与权限授权管理

    springmvc+shiro+maven 实现登录认证与权限授权管理

    Shiro 是一个 Apache 下的一开源项目项目,旨在简化身份验证和授权,下面通过实例代码给大家分享springmvc+shiro+maven 实现登录认证与权限授权管理,感兴趣的朋友一起看看吧
    2017-09-09
  • BeanUtils.copyProperties()所有的空值不复制问题

    BeanUtils.copyProperties()所有的空值不复制问题

    这篇文章主要介绍了BeanUtils.copyProperties()所有的空值不复制问题及解决方案,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-06-06

最新评论