繁体   English   中英

重复使用客户端TCP套接字进行多个HTTP连接

[英]Reuse a Client TCP Socket for Multiple HTTP Connections

大家问候。

我正在Linux 2.6.29-3.ydl61.3上制作ANSI C多线程www-crawler(与HTTP 1.1兼容),并且进展良好。 我在MySQL数据库中有'000个域,可以从中收集页面。 我可以根据需要以保持活动模式打开搜寻器中的任何/所有域。 我使用POSIX线程,没有任何争用或数据争用。

虽然目标服务器似乎已准备好允许我对每个服务器套接字上的页面发出多个并发或顺序请求(因为每个服务器均按预期返回“ Connection:Keep-Alive”),但我实际上无法这样做...我只能提取每个套接字连接一页...即我可以通过文件描述符将典型的HTTP GET请求写入套接字,然后读取响应。 然后在那之后,我只能写入fd,但不再读取! 因此,尽管我每个域有多个(成百上千个)URL……看来我必须继续为每个写/读重新创建到同一服务器的套接字连接(这非常浪费内存,而且速度很慢),而不是仅创建一个客户端TCP连接并继续重复使用fd / socket,直到完成域操作为止。

参见下面的“ netstat --inet -a”的部分输出(请注意,由于不希望有多个本地套接字连接到同一个域,因此每个域都不是并发的):

tcp 0 0 gcell1:38614 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell1:34678 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:34768 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:56085 www。 hihostels.com:http CLOSE_WAIT tcp 0 0 gcell11:34661 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:34785 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:46660 67.225.194.54:http CLOSE_WAIT tcp 0 0 gcell11 :34697 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:37510 www.kenic.or.ke:http CLOSE_WAIT tcp 0 0 gcell11:37516 www.kenic.or.ke:http CLOSE_WAIT tcp 0 0 gcell11:34710 x2web02。 myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:34711 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:46677 67.225.194.54:http CLOSE_WAIT tcp 0 0 gcell11:56513 www.kenic.or.ke:http CLOSE_WAIT tcp 0 0 gcell11:57560 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:46634 67.225.194.54:http CLOSE_WAIT tcp 0 0 gcell11:46607 67.225.194.54:http CLOSE_WAIT tcp 0 0 gcell11:46666 67.225.194.54: http CLOSE_WAIT tcp 0 0 gcell11:37526 www.kenic.or.ke:http CLOSE_WAIT tcp 0 0 gcell11:46673 67.225.194.54:http CLOSE_WAIT tcp 0 0 gcell11:34736 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:57557 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:56395 www.kenic.or.ke:http CLOSE_WAIT tcp 0 0 gcell11:34714 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:34669 x2web02.myhosting.com: http CLOSE_WAIT tcp 0 0 gcell11:34767 x2web02.myhosting.com:http CLOSE_WAIT tcp 0 0 gcell11:43381 ip-72-167-251-99.ip.se:http CLOSE_WAIT

客户端套接字的创建如下(仅部分代码)

if((http_socket_fd = socket (PF_INET, SOCK_STREAM, IPPROTO_TCP))!=SKMG_FAILURE) //typical
...
fcntl(http_socket_fd,SOCK_NONBLOCK); //set to non-block
...
setsockopt(http_socket_fd, SOL_SOCKET, SO_KEEPALIVE, &optval, optlen); //local TCP keep-alive used
...
while(connect(http_socket_fd, (struct sockaddr *)&http_name, sizeof (struct sockaddr_in)) == (-1))
...
return http_socket_fd;

在此之后,我仅在fd上使用写/读。 而且它仅一次往返即可完美运行。

1)如何在每个域的每个HTTP GET读写中重用http_socket_fd ,而无需为每个URL创建一个新的本地TCP套接字? 仅将http_socket_fd传递给每个域的每个页面获取调用就是无法正常工作的原因。 [危急]

2)如何在每个套接字每个域范例的一个线程上向这些服务器发出异步请求? 我运行4个并发线程(我的服务器是双线程),即4个不同的并发域获取。 [非关键]

通常的做法是为每个连接创建一个客户端套接字。 在线程之间共享套接字也是一个坏主意。

除了编写自己的HTTP客户端外,您是否考虑过使用像libcurl这样的提供许多高级功能的库? libcurl站点有一个示例程序 ,该程序使用多个线程下载内容。 还可以查看高性能消息传递框架ZeroMQ ZeroMQ套接字可用于连接到多个服务器并有效下载数据。 (请参阅《指南》 )。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM