美文网首页
一次优惠券导出的性能优化过程

一次优惠券导出的性能优化过程

作者: 编写代码的艺术 | 来源:发表于2017-03-29 22:39 被阅读0次

    券是促销系统的必备东西,将券导出Excel文件,也是常见的业务。如果但是导出20w券需要十几分钟,那是不可忍受的。
    导出Excel文件的步骤如下:

    1. 根据预设的数量,生成一批券。
    2. 将券以Excel文件导出。

    我们需要优化每一个步骤!

    如何高效地生成一批券?

    直写db是不可接受的。通过这种方式生成1k张券问题不大,但想要快速生成1w张、20w张,就需要更好的手段。那就是分批次异步生成。
    改进过程如下:
    1、通过类似snowflake算法生成20w券号。
    2、将20w个券号,分成50份,通过rabbitmq以异步的形式出去,委托集群上的所有机器进行消费,将券写入数据库。

    注意事项:

    1. 如果券还未完全生成好,提友好提示用户券正在生成。
    2. 可以使用redis锁,防止券被重复导出。
    3. 消费端做好重复消费的处理。

    有了券之后,如何高效导出为Excel文件?

    答案时采用并发写入。20w张券可以写到4个sheet中,每个sheet最多可容纳63356条件记录(包括标题)。一个sheet对应一个线程,这样就有4个线程同时写入,性能应该会有所提升。
    并发写入要注意2个问题:

    1. 如何计算sheet的数量?如何计算每个sheet需要记录的coupon范围?
      引入Map<Integer,Integer>数据结构。map的长度,就是sheet的数量。key代表coupon的开始位置,value代表结束位置。
    2. 如果控制并发写入?
      使用线程池来执行任务。
      使用CountDownLatch协调子任务。每个子线程完成任务后,更新CountDownLatch,直至为0,则主线程就可以继续执行。

    在此方案上进行压测:导出在小数据量的券,时间是缩短了,但导出到20w张券的时间还是很长。

    经过分析,使用HSSFWorkbook来导出Excel时,HSSFWorkBook会把所有记录留在内存中,建议使用SXSSFWorkbook来解决大数据导出的问题。它可以限制内存保留的记录行数,超过的记录会写入硬盘。适合于适合追加数据的场景,不适合于频繁修改的场景。
    将poi到3.9版本后,替换HSSFWorkBook为SXSSFWorkbook,新的测试结果为:在小数据量的情况下,响应时间是秒级。导出20w张券大约花了10秒。这个时间是可以接受。

    总结

    分而治之是提高性能的常见手段,既可以通过mq来达到目的,也可通过线程池。

    相关文章

      网友评论

          本文标题:一次优惠券导出的性能优化过程

          本文链接:https://www.haomeiwen.com/subject/uplhottx.html