iOS之一个 HTTP 超时问题论述

一个配置导致的HTTP(TCP)连接超时 一个配置导致的HTTP(TCP)连接超时 这个是之前写http服务的时候测试遇到的一个问题。当时这个bug的现象是,办公室内某台安卓手机访问http服务经常出现连接超时,而过一会儿之后又可以使用了。而同时,办公室内的iOS设备,Mac设备又能正常使用服务。甚至登陆到http服务实时监控日志,会发现安卓的设备的请求确实没有到达http服务,没有access日志。 简单抓包 这个时候实在没法... 阅读详情

一个 HTTP 超时问题

最近有同事反映我们的 app 在网络正常的情况下偶尔会出现请求超时。
我的第一反应是某个服务挂掉了(因为最近服务端再搞重构),就反馈给了服务层。
但是服务层的同事排查下来发现 api 层并没有产生异常日志,应该不是服务本身或者依赖的中台服务挂掉了。

定位

想起来 NSURLSession 有个默认的单个Host最大连接数,超过之后会进入排队,可能导致后续服务超时。

Objective-C

/* The maximum number of simultanous persistent connections per host */
@property NSInteger HTTPMaximumConnectionsPerHost;

利用 Xcode 的调试模式来看一下,结果惊掉下巴,随便点了几下就建立了这么多连接

说好的 The default value is 6 in macOS, or 4 in iOS 的呢,难道是Xcode的调试面板有问题吗?再次用 Wireshark 抓包确认一下,得到的结果是确实每次请求都会新建一个连接(主要体现在端口,TLS 协议)。

下面贴 2 个连接的截图

端口 53929

端口 53930

这样肯定是有问题的:

1 HTTP 1.1 默认开启了 Keep-Alive 属性(这点在之前的 Charles 抓包中也有证实),为什么链接没有复用。
2NSURLSession 的默认单个 Host 最大连接数在 iOS 上为 4,为什么会这么多。

直接看代码吧,我们现在项目里有两套网络请求的框架,一套是Objective-C的基于AFNetworking的老代码,一套是为了向Swift迁移新实现,一番折腾,在以前的基础库里找到了这段看似平平无奇的代码:

Objective-C

AFHTTPSessionManager *manager = [[AFHTTPSessionManager alloc] initWithBaseURL:[NSURL URLWithString:@""]];
[manager POST:api parameters:params progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id  _Nullable responseObject) {...}

这段代码的实现里 AFHTTPSessionManager 每次都是新创建出来的,虽然系统默认开启了 Keep-Alive ,但是 TCP 通道并不会复用,相当于一个披着 HTTP 1.1 外衣的 1.0连接,这就回答了第一个疑问。

至于第二个,我重新翻看了官方文档

This limit is per session, so if you use multiple sessions, your app as a whole may exceed this limit. Additionally, depending on your connection to the Internet, a session may use a lower limit than the one you specify.

意思就是这个最大连接数只是一个 NRLSession 的限制。

修复

修复很简单,我们把上面的 Manager 修改成了属性,保证了唯一性。完了使用 Xcode 的 Network 工具再看一下。嗯,看起来是复用了。

到这里,解决了一个连接不复用的问题。分别观察了两个版本的代码一段时间,修改后问题似乎不再出现了,旧版本的话用 Wireshark 抓到了详细的超时的时候的数据包:

看上去问题是去服务端握手的时候服务端没回应,反馈给服务端同事,一开始以为是单个 Linux 主机有个理论上的最大连接数限制 65536之类的问题,后来觉得不可能。最终我们猜测是服务端之前设置了单个 api 的最大连接数,或者说防火墙那边会有一段时间内的单个 ip 的最大连接数限制造成的。这个问题的根本应该是在服务端,但是客户端修复了的连接方式会缓解这个问题。

验证

修改代码上线后,我们观察了 2 个版本,线上没有再报类似的问题了。请求超时的错误率也稍有下降。嗯,最棒的是因为复用了连接 TCP 慢启动,TLS 握手都省了,我们请求时间也缩短了。相当于被动的做了优化

修复前

修复后

代码真不是随便写写,一不小心就埋雷。

其他
我们还发现了 iOS 上关于 TCP 挥手的行为的异常,我们跟踪下来,发现了和其他一些疑似使用原生网络框架的连接,断开连接的时候都不是典型的四次挥手

如图,客户端发送了 FIN ACK 之后并没有等到服务端回复 ACK 和 FIN ACK,直接关闭了连接,之后这个通道再收到任何信息都会回复 RST 通知服务端关闭连接,一开始以为是异常,后来跟踪下来发现并不是,可能是 iOS 内部实现做了优化吧。

iOS发送http请求 前言苹果公司在全球开发者大会(WWDC)的一场安全演示会上,公布了一个最后期限——2017 年 1 月 1 日——即 App Store 当中的所有应用必须在这个日期之前启用一项名为 App Transport Security 的重要安全功能。App Transport Security,简称 ATS,是苹果在 iOS 9 当中首次推出的一项安全功能。在启用 ATS 之后,它会强制应用通过 HTT 阅读详情

相关推荐

Delphi移动端开发避坑:TNetHTTPClient在iOS和Android上的超时设置差异详解

本文深入探讨了Delphi移动端开发中TNetHTTPClient组件在iOS和Android平台上的超时设置差异,提供了详细的解决方案和优化实践。通过实际案例和代码示例,帮助开发者避免跨平台网络请求中的常见陷阱,提升应用稳定性和性能。

weixin_30786657的博客 401

HTTPMaximumConnectionsPerHost

[NSURLSessionConfiguration new].HTTPMaximumConnectionsPerHost Summary The maximum number of simultaneous connections to make to a given host. Declaration @property NSInte...

allanGold 1122

掌握iOS网络请求:异步连接、超时处理与自定义请求

本文深入探讨了iOS开发中处理异步连接、超时以及自定义URL请求的技巧。首先介绍了如何在异步连接中设置超时限制,确保应用在网络响应慢时能够及时处理。接着探讨了使用NSURLConnection同步下载内容的方法,并说明了如何在不阻塞主线程的情况下使用同步连接。最后,详细阐述了如何自定义URL请求,包括设置HTTP方法和传递参数,以及发送HTTP请求的各种技巧。

weixin_42186015的博客 425

HttpClient的DefaultMaxConnectionsPerHost 坑

事件背景我在凤巢团队独立搭建和运维的一个高流量的推广实况系统,是通过 HttpClient 调用大搜的实况服务。最近经常出现 Address already in use (Bind failed) 的问题。很明显是一个端口绑定冲突的问题,于是大概排查了一下当前系统的网络连接情况和端口使用情况,发现是有大量 time_wait 的连接一直占用着端口没释放,导致端口被占满(最高的时候 6w+ 个),因此 HttpClient 建立连接的时候会出现申请端口冲突的情况。具体情况如下:于是为了解决 time_wai

嘻哈熊的专栏 1467

ios-基于AFNetworking3.0的请求封装,带有缓存,超时时间.zip

最近很多人问一些基于AFNetworking3.0网络请求的封装,其实不用真的不用封装,唯一需要封装的地方就是客户端做缓存,统一把所有请求做了缓存接口。缓存用的是YYCache。基于AFNetworking的demo 由于上传第一份比较粗心少了一行代码,现在重新上传一份,并且添加了设置超时时间。可以自由设置超时时间和缓存方式

从零开始学版图(二)-----------差分放大电路

从零开始学版图

m0_56112720的博客 8558

MCDownloadManager 常见问题解决方案

MCDownloadManager 常见问题解决方案 项目基础介绍 MCDownloadManager 是一个简单且方便的多任务下载管理器,主要用于 iOS 平台。该项目的主要编程语言是 Objective-C,同时也使用了少量的 Ruby 语言用于 CocoaPods 的集成。MCDownloadManager 支持同时下载多个文件,并提供了速度提示、后台下载和锁屏下载等功能。 新手使用注意事项...

gitblog_01199的博客 749

瑞萨单片机,把CS文件转换为CC

1、打开CC的软件: 点击坐上角的"START" 点击"Create New Project"的"GO": 导入工程: 如下图设置后,点击"Create" 2、进入到CC的开发界面: 可以看到原启动库文件以asm文件的方式直接出现在工程中: 删除新生成的main.c,保留导入的r_main.c(以你自己的代码为准): 注意添加所有的头文件路径: 点击"...

weixin_37611121的博客 1228

服务端设置 http MaxConcurrentConnections 的 坑

开始以为是有病毒或受到攻击,找部分机器重点排查,先是找到部分设备在频繁发送连接到服务器,开始阻止优化,的确一段时间正常了。我们用的是.netCore内置的KestrelServer,同事在调整测试SSL模式下文件上传时,把KeepAliveTimeout设置了一个小时 ,wtf , 去掉后就恢复正常了。然而部分现场有技术人员验证反馈,并没有改变环境,降回上一个版本就正常。一个头两个大,开始看提交代码记录,果不其然,有同事改了服务相关代码,设置了KeepAliveTimeout。

hellozp的专栏 580

高速DAC时钟与配置实战:DAC5681Z硬件设计与寄存器编程详解

在高速数据转换系统中,时钟信号是决定系统性能的核心要素,其稳定性和纯净度直接影响数模转换器(DAC)的输出频谱纯度与动态范围。时钟电路的设计原理涉及信号完整性、阻抗匹配与直流偏置,而内部锁相环(PLL)和延迟锁相环(DLL)的配置则是实现精确时序控制的关键技术。这些技术的价值在于,它们共同保障了高速通信、雷达和任意波形生成等应用对信号实时性与精度的严苛要求。本文聚焦于德州仪器(TI)的DAC5681Z,深入解析其外部时钟输入电路的硬件设计要点,包括端接电阻的计算与选型,并详细拆解通过串行外设接口(SPI)对

weixin_30342363的博客 186

Qt+PCL实战:如何用QVTKOpenGLNativeWidget高效渲染3D点云(附完整代码)

本文深入解析了Qt与PCL结合使用QVTKOpenGLNativeWidget进行高效3D点云渲染的实战技术。通过对比传统QVTKWidget,详细介绍了QVTKOpenGLNativeWidget在渲染效率、内存占用和兼容性方面的显著优势,并提供了完整的代码示例和性能优化策略,助力开发者在工业检测、自动驾驶等领域实现更高效的点云可视化。

keras9composer的博客 686

0x80004005错误代码解决方法_win10错误代码大全(附解决方法)

win10错误代码大全(附解决方法)。许多用户朋友在使用windows操作系统的时候经常会出现某些程序或游戏的运行错误却又不知道那一行错误代码是什么意思,可以帮助你及时的查看自己电脑出了什么问题,随时让你查询windows错误代码。windows错误代码大全一、系统错误代码:下载地址0000操作已成功完成。0001错误的函数。0002系统找不到指定的文件。0003系统找不到指定的路径。0...

weixin_39518002的博客 8043

C++结合大漠插件实现DNF自动化脚本:从原理到实战

自动化技术通过模拟用户操作,实现重复性任务的自动执行,其核心原理在于对系统输入输出接口的精确控制。在Windows平台,这通常涉及窗口管理、图像识别与键鼠模拟等技术。这些技术为软件自动化测试、办公流程自动化及特定场景的辅助工具开发提供了工程实践基础。大漠插件作为国内广泛使用的Windows自动化开发组件,封装了上述底层操作,显著降低了开发门槛。通过其提供的COM接口,开发者可以高效实现窗口绑定、后台找图找色及内存读写等关键功能。本文以《地下城与勇士》为例,详细解析如何利用C++集成大漠插件,构建一个稳定、高

weixin_34185512的博客 570

ios系统连接服务器超时时间,ios – 如何解决由HTTP持久连接错误导致的超时问题?...

我最近一直在努力解决HTTP超时问题.经过一个多月的调查,我很确定它是由错误的HTTP持久连接引起的.详情如下:>这是一个iOS应用程序.>大多数用户正在运行iOS 8.>我正在使用NSURLConnection.> iOS 8有一个known keep alive bug但我的是另一个问题.更具体地说,该bug导致NSURLErrorNetworkConnectionLo...

weixin_29898627的博客 1691

CUDA&PCL 点云体素下采样

CUDA&PCL 点云体素下采样

dayuhaitang1的博客 1268

基于深度学习的水果新鲜程度检测系统(UI界面 + YOLOv8/v7/v6/v5代码 + 训练数据集)

本文详细介绍了如何使用YOLO系列模型(YOLOv5、YOLOv6、YOLOv7、YOLOv8)构建水果新鲜度检测系统。通过数据集准备、模型训练、推理过程以及UI界面的实现,我们能够构建一个实时检测水果新鲜度的系统。通过本博客,您可以全面了解如何应用深度学习技术解决实际问题,尤其是在智能监控和食品质量检测领域。

YOLO 815

android 访问超时,ios正常

问题描述:             同一个链接,android 访问总是超时,但是ios是没问题的,很奇怪吧? 但我确实就遇到了,,,,,没办法,遇到了就要解决的,,,百度都烂了不知道怎么搞。,,。,最后在一个论坛中看的,说是怎么回事,其实我都没明白,大体意思是第一次访问时候,httpRequest链接资源没有释放,导致后面访问时候就有问题,不能访问。。。。这里说明一下,我这里的httpClie

仰视未来的专栏 2803

【26美赛F题 To Gen-AI, or Not To Gen-AI】(MCM/ICM)思路解析及代码分享

摘要:本文研究生成式人工智能(Gen-AI)对三类职业(STEM、技能型工艺、艺术)的影响,建立量化模型预测未来10-20年岗位需求变化。通过分析AI替代效应($R_{sub}(t)$)和增强效应($R_{enh}(t)$),提出差异化高校课程调整策略:STEM专业需加强AI集成能力,技能型工艺专业应结合智能工具与实操训练,艺术专业需平衡AI创作辅助与原创性培养。模型表明,高校通过针对性课程优化可提升毕业生在AI时代的就业竞争力,为教育决策提供数据支持。(149字)

一键难忘的博客 636

IOS开发之——网络-HTTP请求(4)

一 概述 HTTP网络请求中的几个概念 IOS中发送HTTP请求 HTTP请求示例 二 HTTP网络请求中的几个概念 2.1 URL 什么是URL URL的全称是Uniform Resource Locator,统一资源定位符 通过1个URL,能找到互联网上唯一的1个资源 URL就是资源的地址、位置,互联网上的每个资源都有唯一的URL URL的基本格式 协议://主机地址/路径 http://192.168.0.1/img/a.gif 协议:不同的协议,代表着不同的资源查找方式、资源传输方式

我的博客 1850

Camera2Demo

在Camera2 的基础上进行封装,使得Camera2一堆初始化逻辑与Activity分离,降低耦合度,完成预览拍照并保存的操作

lwip-2.0.3

lwip是瑞典计算机科学院(SICS)的Adam Dunkels 开发的一个小型开源的TCP/IP协议栈。实现的重点是在保持TCP协议主要功能的基础上减少对RAM 的占用。

iPhoneWebServicesClient: 一个用于iOS应用开发的HTTP客户端库

iPhoneWebServicesClient: 一个用于iOS应用开发的HTTP客户端库 iPhoneWebServicesClient This project showcases different transport formats and libraries to consume web services fr...

gitblog_00003的博客 410

TMS_WebGMaps_1.9.8.0_Full_Source

TMS_WebGMaps_1.9.8.0_Full_Source 全源码 delphi cbuilder

ios swift 打造自己的http请求工具

在ios开发中,网络请求是不可以少的,说到网络请求可能用的最多的就是第三方的比人比较有名的AFNetworking、Alamofire等,原生的用的少。今天就用ios提供的原生方法来打造属于自己的一个网络请求工具吧。大神的成长之路,现在就开始起航。 第一步:先建一个类比如叫 Http 如下: //定义请求类型 enum HttpMethod { case GET, ...

anyan9579的博客 170

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

Capacitor iOS 中 HTTP 插件崩溃问题分析与解决方案

在 Capacitor 框架的 iOS 平台上,开发者报告了一个严重的稳定性问题:当应用程序使用 HTTP 插件进行网络请求时,如果请求被中止(aborted),可能会导致应用程序崩溃。这个问题在真实用户场景中随机出现,给开发者带来了很大困扰。 ## 崩溃现象分析 崩溃日志显示,应用程序抛出 `NSInternalInconsistencyException` 异常,具体错误信息为 "This...

gitblog_01023的博客 537

设置请求超时时间(timeoutInterval)不起作用

方法一: 解决办法: AFHTTPSessionManager *manager = [AFHTTPSessionManager manager]; manager.responseSerializer = [AFHTTPResponseSerializer serializer]; // 设置超时时间 [manager.requestSerializer willChangeValue...

qq_28091923的博客 1万+

【iOS网络优化权威教程】:彻底解决超时、断连、卡顿的终极策略

掌握Swift网络编程核心技巧,解决超时、断连、卡顿等常见问题。提供高可用架构设计与真实Swift网络编程示例,适用于高并发请求与弱网环境优化。提升App稳定性与响应速度,值得收藏。

InstrIsle的博客 473

iOS-UIWebview设置超时、加载失败、重新加载等问题解决

iOS开发 UIWebView加载失败 我想重新加载怎么做,使用reload不顶用 解决办法:重新使用loadRequest:设置超时 NSURL *url=[NSURL URLWithString:@"http://www.baidu.com"]; NSURLRequest *request = [[NSURLRequest alloc] initWithURL:url

BearsG 1万+

微信小程序 安卓请求成功 IOS(苹果)请求超时

直接说答案的:我遇到的情况是我接口返回 的自定义http状态码 4401 IOS不认自定义http状态码 直接丢弃掉返回的结果,导致请求超时。 为什么自定义http状态码?天知道。。。

fsdf8sad7的博客 1586
上一篇: SpringBoot 自动装配原理
下一篇: Java内存模型
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值