测试Activemq artemis队列生产消费ack

前言

这个测试主要是测试ActiveMQ Artemis消息中间件,因为业务的特殊性,需要测试消息一来一回算一次,单次统计结果可以参考上一篇测试的结果。

架构设计

还是采用客户端和服务端再到客户端的形式,毕竟只用本地很容易卡影响结果,消息先从本地发送到服务器,然后从服务器发送回本地,完成一次消息完整的流程。也测试了服务器到服务器的场景,但是是单个服务所以相当于左手换右手的感觉。

测试代码

其余代码参考上一篇笔记

@Log4j2
@Component
public class ListenerAndSendMq {

    private static final String UPDATE_API_STRATEGY_AND_BASKET = "localhost";

    public static AtomicInteger atomicInteger = new AtomicInteger();
    public static AtomicInteger atomicIntegerSingle = new AtomicInteger();
    AtomicReference<Long> start = new AtomicReference<>(0L);
    int cores = Runtime.getRuntime().availableProcessors();

    ThreadPoolExecutor threadPoolExecutor
            = new ThreadPoolExecutor(cores + 2, cores + 2, 60, TimeUnit.SECONDS,
            new LinkedBlockingQueue<>());
//            new ArrayBlockingQueue(10), new BlockPolicy());
//              new SynchronousQueue(), new BlockPolicy());
//            new SynchronousQueue(), new ThreadPoolExecutor.CallerRunsPolicy());

    public static int count = 50000;

    @PostConstruct
    public void receiveApiStrategyCache() {

        log.info("====================receiveApiStrategyCache========cores{}============", cores);
        Messenger.subscribe(UPDATE_API_STRATEGY_AND_BASKET+"/ack", new MessageConsumer() {
            @Override
            public void onMessage(final Message<?> message) {
                if (message instanceof BinaryMessage) {
                    try {
                        final BinaryMessage msg = (BinaryMessage) message;
                        final MessageHeader header = msg.getHeader();
                        final String payload = new String(msg.getPayload());
                        long timestamp = header.getTimestamp();
                        if (atomicIntegerSingle.get() == 0) {
                            start.set(System.nanoTime());
                        }
                        if (atomicIntegerSingle.incrementAndGet() >= count) {
                            log.info("offset:{}ms", System.currentTimeMillis() - timestamp);
                            log.info("消费{}数据总共耗时:{}ms", count, TimeUnit.NANOSECONDS.toMillis(System.nanoTime() - start.get()));
                        }
                        sendMessage(UPDATE_API_STRATEGY_AND_BASKET, payload, header);
                    } catch (Exception e) {
                        log.error(e);
                    }
                }
            }

            @Override
            public void onError(final Message<?> message) {
                log.error("from TOPIC {} error: {}", message.getHeader().getTopic(), message.getPayload());
            }
        });
        Messenger.subscribe(UPDATE_API_STRATEGY_AND_BASKET+"/ack/multiple", new MessageConsumer() {
            @Override
            public void onMessage(final Message<?> message) {
                if (message instanceof BinaryMessage) {
                    threadPoolExecutor.execute(() -> {
                        final BinaryMessage msg = (BinaryMessage) message;
                        final MessageHeader header = msg.getHeader();
                        final String payload = new String(msg.getPayload());
                        long timestamp = header.getTimestamp();
                        if (atomicInteger.get() == 0) {
                            start.set(System.nanoTime());
                        }
                        if (atomicInteger.incrementAndGet() >= count) {
                            log.info("offset:{}ms", System.currentTimeMillis() - timestamp);
                            log.info("消费{}数据总共耗时:{}ms", count, TimeUnit.NANOSECONDS.toMillis(System.nanoTime() - start.get()));
                        }
                        sendMessage(UPDATE_API_STRATEGY_AND_BASKET+"/multiple", payload, header);
                    });
                }
            }

            @Override
            public void onError(final Message<?> message) {
                log.error("from TOPIC {} error: {}", message.getHeader().getTopic(), message.getPayload());
            }
        });
    }

    public void sendMessage(String topic, String world, MessageHeader oldHeader) {
        final MessageHeader header = new MessageHeader(topic, oldHeader.getId(), oldHeader.getTimestamp());
        final BinaryMessage message = new BinaryMessage(header, world.getBytes());
        try {
            Messenger.send(message);
        } catch (final IOException e) {
            log.error("error", e);
        }
    }

}

5000数据测试

异步接收

只考虑接收的情况,假定队列消费很顺畅的情况,不存在处理消息导致消费耗时的情况。

数据量是否处理消息是否二次投递消息客户端类型客户端是否缓存发送消息cpu线程数发送耗时服务器端类型cpu线程数接收耗时最后消息延时服务器端类型cpu线程数接收耗时最后消息延时
5000mac612+2636mscentos88+2467ms373mscentos88+2490ms404ms
5000mac612+2503mscentos88+2634ms503mscentos88+2661ms533ms
5000mac612+2888mscentos88+2726ms378mscentos88+2849ms509ms
5000mac612+2611mscentos88+2424ms111msmac612+2520ms200ms
5000mac612+2694mscentos88+2338ms88msmac612+2605ms362ms
5000mac612+2939mscentos88+2735ms152msmac612+2953ms369ms
异步消费

这里主要是边处理消息和边统计的情况。

数据量是否处理消息是否二次投递消息客户端类型客户端是否缓存发送消息cpu线程数发送耗时服务器端类型cpu线程数接收耗时最后消息延时服务器端类型cpu线程数接收耗时最后消息延时
5000mac612+2821mscentos88+2742ms402mscentos88+2768ms433ms
5000mac612+2664mscentos88+2834ms614mscentos88+2884ms673ms
5000mac612+2759mscentos88+21105ms783mscentos88+21200ms882ms
5000mac612+2600mscentos88+2680ms561msmac612+2666ms435ms
5000mac612+2577mscentos88+2674ms528msmac612+2688ms369ms
5000mac612+2720mscentos88+2963ms718msmac612+2992ms578ms

1万数据测试

异步接收

只考虑接收的情况,假定队列消费很顺畅的情况,不存在处理消息导致消费耗时的情况。

数据量是否处理消息是否二次投递消息客户端类型客户端是否缓存发送消息cpu线程数发送耗时服务器端类型cpu线程数接收耗时最后消息延时服务器端类型cpu线程数接收耗时最后消息延时
10000mac612+2929mscentos88+2841ms460mscentos88+2894ms532ms
10000mac612+2805mscentos88+2767ms482mscentos88+2883ms623ms
10000mac612+21013mscentos88+21005ms692mscentos88+21047ms761ms
10000mac612+2831mscentos88+2913ms622mscentos88+21077ms788ms
10000mac612+2877mscentos88+2725ms133msmac612+21122ms527ms
10000mac612+2860mscentos88+2767ms245msmac612+21277ms747ms
10000mac612+2857mscentos88+2854ms340msmac612+21058ms552ms
异步消费

这里主要是边处理消息和边统计的情况。

注意这里第一阶段1w的数据已经超过1秒了,是因为包含了转发消息的时间,也就是ack

数据量是否处理消息是否二次投递消息客户端类型客户端是否缓存发送消息cpu线程数发送耗时服务器端类型cpu线程数接收耗时最后消息延时服务器端类型cpu线程数接收耗时最后消息延时
10000mac612+2953mscentos88+21336ms832mscentos88+21418ms915ms
10000mac612+2847mscentos88+21322ms1031mscentos88+21411ms1130ms
10000mac612+21038mscentos88+21419ms862mscentos88+21524ms975ms
10000mac612+2820mscentos88+21665ms1297msmac612+21736ms1224ms
10000mac612+2945mscentos88+21812ms1399msmac612+21802ms1222ms
10000mac612+21241mscentos88+21812ms1043msmac612+21246ms878ms

3万数据测试

异步接收

只考虑接收的情况,假定队列消费很顺畅的情况,不存在处理消息导致消费耗时的情况。

数据量是否处理消息是否二次投递消息客户端类型客户端是否缓存发送消息cpu线程数发送耗时服务器端类型cpu线程数接收耗时最后消息延时服务器端类型cpu线程数接收耗时最后消息延时
30000mac612+21534mscentos88+22313ms1298mscentos88+22576ms1572ms
30000mac612+21623mscentos88+22606ms1671mscentos88+22656ms1725ms
30000mac612+21781mscentos88+22599ms1369mscentos88+22732ms1514ms
30000mac612+21656mscentos88+22769ms1630mscentos88+23150ms2018ms
30000mac612+21716mscentos88+22445ms1041msmac612+23600ms2194ms
30000mac612+21561mscentos88+21829ms775msmac612+23377ms2327ms
30000mac612+21447mscentos88+22164ms1032msmac612+23246ms2144ms
异步消费

这里主要是边处理消息和边统计的情况。

数据量是否处理消息是否二次投递消息客户端类型客户端是否缓存发送消息cpu线程数发送耗时服务器端类型cpu线程数接收耗时最后消息延时服务器端类型cpu线程数接收耗时最后消息延时
30000mac612+22128mscentos88+24104ms2520mscentos88+24440ms2861ms
30000mac612+21596mscentos88+24268ms3256mscentos88+24678ms3667ms
30000mac612+21618mscentos88+23452ms2299msmac612+23699ms2374ms
30000mac612+21933mscentos88+24345ms3046msmac612+26470ms5017ms
30000mac612+21502mscentos88+23489ms2647msmac612+23940ms2925ms

5万数据测试

异步接收

只考虑接收的情况,假定队列消费很顺畅的情况,不存在处理消息导致消费耗时的情况。

数据量是否处理消息是否二次投递消息客户端类型客户端是否缓存发送消息cpu线程数发送耗时服务器端类型cpu线程数接收耗时最后消息延时服务器端类型cpu线程数接收耗时最后消息延时
50000mac612+225mscentos88+24247ms2704mscentos88+24448ms2928ms
50000mac612+249mscentos88+24101ms2654mscentos88+24253ms2851ms
50000mac612+260mscentos88+25105ms3003mscentos88+26157ms4064ms
50000mac612+22050mscentos88+24397ms2885mscentos88+24555ms3048ms
50000mac612+22461mscentos88+26208ms4479mscentos88+26368ms4715ms
50000mac612+22777mscentos88+23866ms1618mscentos88+24008ms1774ms
50000mac612+22506mscentos88+24335ms2378mscentos88+24597ms2696ms
50000mac612+22474mscentos88+25352ms3353msmac612+27933ms5852ms
50000mac612+22649mscentos88+24247ms1957msmac612+26064ms3777ms
50000mac612+22285mscentos88+23399ms1566msmac612+26006ms4165ms
50000mac612+22120mscentos88+23445ms1657msmac612+25289ms3501ms
异步消费

这里主要是边处理消息和边统计的情况。

数据量是否处理消息是否二次投递消息客户端类型客户端是否缓存发送消息cpu线程数发送耗时服务器端类型cpu线程数接收耗时最后消息延时服务器端类型cpu线程数接收耗时最后消息延时
50000mac612+22083mscentos88+29263ms7614mscentos88+29634ms8340ms
50000mac612+23216mscentos88+27933ms5177mscentos88+28586ms5840ms
50000mac612+22086mscentos88+28101ms6373mscentos88+28794ms7069ms
50000mac612+21857msmac612+212410ms10930msmac612+212622ms277ms
50000mac612+21905mscentos88+27354ms5958msmac612+27950ms6399ms
50000mac612+21984mscentos88+27316ms5931msmac612+27567ms6023ms
50000mac612+21866mscentos88+26693ms5338msmac612+26946ms5436ms

发送大小

1KB
生产10000数据总共耗时:937ms
offset:244ms
消费10000数据总共耗时:717ms
2KB
生产10000数据总共耗时:1552ms
offset:106ms
消费10000数据总共耗时:1248ms
3KB
生产10000数据总共耗时:1929ms
offset:170ms
消费10000数据总共耗时:1642ms
5KB
生产10000数据总共耗时:3000ms
offset:203ms
消费10000数据总共耗时:2753ms
8KB
生产10000数据总共耗时:4484ms
offset:187ms
消费10000数据总共耗时:4220ms
10KB
生产10000数据总共耗时:5501ms
offset:190ms
消费10000数据总共耗时:5239ms
20KB
生产10000数据总共耗时:11443ms
offset:207ms
消费10000数据总共耗时:11190ms
100KB
30KB
生产10000数据总共耗时:17048ms
offset:228ms
消费10000数据总共耗时:16810ms

总结

之前的一篇测试结果发现单个消息1秒一万多条消息是没有压力的,超过了可能产生堆积的情况,最明显的区别就是发送时间和处理时间。

这次主要模拟处理消息然后回复ack的场景,发现大打折扣,消息处理只能达到5千多点。毕竟是一来一回这样的情况,在原来的基础上又发了一次。

另外发现当消息的大小不超过1kb的时候是符合上面的测试结果的,但是超过了1kb,发送也会很耗时。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

查拉图斯特拉talk

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值