程序员IM SDK开发

IM二分法智能心跳策略

2017-09-08  本文已影响56人  大大大大大先生

IM心跳策略

心跳的字段定义

心跳信息字段

重置心跳

心跳策略图

这里写图片描述

触发心跳上调

心跳上调策略

  1. successHeartList.add(curHeart);successCount++;
  2. if (successCount >= 2) failedCount = 0;心跳连续成功两次,才认为当前心跳在该网络环境下运行稳定
  3. 把当前的心跳信息更新到文件中。
  4. if (stabled == true) stabledSuccessCount++;
  1. 从成功心跳列表中筛选比当前心跳大一级的心跳周期作为当前心跳:curHeart = successHeart;
  2. 如果1没有筛选出结果,则用二分法进行上调:
    (1)curMinHeart = curHeart;
    (2)if (curMaxHeart < curMinHeart) curMaxHeart = curMinHeart;
    (3)curHeart = (curMinHeart + curMaxHeart) / 2;
  1. if (curMaxHeart - curMinHeart <= 10 && stabled == false) curHeart = curMinHeart;
  2. 如果已经达到极值条件(curMaxHeart - curMinHeart <= 10),那么stabled = true;

触发心跳下调

  1. 心跳超时主动断开TCP连接(socket closed),此时应该下调心跳
  2. IM SDK初始化会主动断开TCP并重新连接(socket closed),不应该下调心跳
  3. 本地网络断开造成 TCP连接被动断开(Software caused connection abort,socket closed),这里分为两种情况,第一个是网络切换,那么这时候是网络断开,然后再重新连上的一个过程,应用能明显的感知到这个过程(网络切换广播),TCP连接在网络切换的时候会被动断开,这时候在下调心跳之前要先检测下本地网络是否可用,如果不可用则不进行心跳下调,其实因为本地网络断开导致的TCP断线是不应该下调心跳的,这里多了个检测就是为了在一定程度上过滤掉一部分因为本地网络断开导致的心跳误下调;还有一种是modem其实已经断网了,此时modem可能在进行重连,但是并没有网络切换广播,此时应用层是无感知的,但是TCP连接可以立马感知到,并被动断开,这时候检测本地网络也是可用的(不准),所以这时候会导致心跳误下调,Android sdk接口判断本地网络是否可用其实是不准确的,如果接口返回不可用,那么本地网络一定是不可用的,如果接口返回可用,那网络还不一定真的可用,因为接口检测的只是设备本地网络而已,如果连接上一个假wifi(需要验证密码),那么设备到wifi路由器这段网络是通的,但是wifi路由器到外网是不通的,这时候设备是感知不到的,通过ping才能准确的知道网络是否真的可用,当手机卡欠费的时候,本地接口也是返回网络可用,道理类似
  4. 服务器close造成TCP连接被动断开(read返回-1),此时会下调心跳
  5. 其他网络原因造成的TCP连接被动断开(connection reset等),此时会下调心跳
  6. TLV数据解析错误主动断开TCP连接,不应该下调心跳
  7. 除了以上6中原因会造成TCP断开,如果还有其他原因在成TCP断开,需要检测三个条件才满足心跳下调的条件:第一是当前心跳是否已经启动,第二是当前设备本地网络是否可用,第三是TCP断开前,已经持续连接超过一个最小心跳周期的时间,满足以上三个条件才进行下调心跳,否则不下调

心跳下调策略

  1. 从successHeartList移除当前心跳锁对应的心跳周期;stabledSuccessCount;successCount;failedCount++;
  2. 把当前的心跳信息更新到文件中。
  1. stabled = false;
  2. 从successHeartList筛选比当前心跳小一级的心跳heart
  3. if ((minHeart + curHeart) / 2 < heart) selectedHeart = heart;curHeart = selectedHeart;
  4. 如果没有筛选到适合条件的selectedHeart,那么就进行二分法下调:
    (1)currentMaxHeart = currentHeart;
    (2)currentMinHeart = minHeart;
    (3)currentHeart = (currentMinHeart + currentMaxHeart) / 2;
  1. 从successHeartList筛选比当前心跳小一级的心跳heart;
  2. if ((minHeart + curHeart) / 2 < heart) selectedHeart = heart;curHeart = selectedHeart;
  3. 如果没有筛选到适合条件的selectedHeart,那么就进行二分法下调:
    (1)currentMaxHeart = currentHeart;
    (2)if (currentMaxHeart < curentMinHeart) currentMaxHeart = currentMinHeart;
    (3)currentHeart = (currentMinHeart + currentMaxHeart) / 2;
  1. if (curMaxHeart - curMinHeart <= 10 && stabled == false) currentMinHeart = minHeart;
  2. 之所以加入这个判断是为了当心跳一直失败下调,但是curMinHeart和curMaxHeart又很接近导致二分法无法下调的时候,就直接把curHeart设置成minHeart

稳定心跳

Android机子上存在的问题

上一篇 下一篇

猜你喜欢

热点阅读