解决Python httpx 运行过程中无限阻塞的问题

目录
  • Python httpx 运行过程中无限阻塞
    • 1.通过 pm2 部署脚本
    • 2.通过装饰器给函数设置一个最大执行超时时间
  • python爬虫httpx的用法
    • 请求方式

Python httpx 运行过程中无限阻塞

requests 模块只支持 http1,在遇到 http2 的数据接口的时候(某乎的搜索接口),需要采用支持http2 请求的模块(如 httpx、hyper)。

本文是针对 httpx 在请求数据时,出现无限阻塞问题的一些处理方法。

httpx 的 timeout 有 bug,会导致脚本在运行一段时间后,出现线程阻塞卡死的问题(无限 timeout)。

1.通过 pm2 部署脚本

另外启动一个脚本,定时对该脚本进行重启操作。

举个栗子:

import time
import os

while True:
    time.sleep(60 * 60) # 一小时重启一次
    os.system('pm2 restart test')  

这个方法有个不好的地方,在请求过程中,可能需要翻很多页,如果不断重启脚本,可能导致无法翻到最后一页。

2.通过装饰器给函数设置一个最大执行超时时间

当函数执行时间超过某个时间就抛出 TimeOut 异常

from func_timeout import func_set_timeout
import func_timeout
import time

@func_set_timeout(5)  # 函数最大执行时间 5s
def test():
    time.sleep(20)

def run():
    try:
        test()
        print('test 函数执行完成')
    except func_timeout.exceptions.FunctionTimedOut:
        print('test 函数执行超时')
run()

如上面例子那样,在 httpx.Client 所在函数设置一个额外等待时间,当该函数执行时间超过某个时间,就强制抛出 timeout 异常,避免程序无限阻塞。

python爬虫httpx的用法

安装命令:pip install httpx

请求方式

  • GET
import httpx
​
headers = {'user-agent': 'my-app/1.0.0'}
params = {'key1': 'value1', 'key2': 'value2'}
url = 'https://httpbin.org/get'
r = httpx.get(url, headers=headers, params=params)
  • POST
r = httpx.post('https://httpbin.org/post', data={'key': 'value'}) 
  • PUT
r = httpx.put('https://httpbin.org/put', data={'key': 'value'})
  • DELETE
r = httpx.delete('https://httpbin.org/delete') 

以上为个人经验,希望能给大家一个参考,也希望大家多多支持我们。

(0)

相关推荐

  • python实现单线程多任务非阻塞TCP服务端

    本文实例为大家分享了python实现单线程多任务非阻塞TCP服务端的具体代码,供大家参考,具体内容如下 # coding:utf-8 from socket import * # 1.创建服务器socket sock = socket(AF_INET, SOCK_STREAM) # 2.绑定主机和端口 addr = ('', 7788) # sock.bind(addr) # 3. 设置最大监听数目,并发 sock.listen(10) # 4. 设置成非阻塞 sock.setblocking(

  • python 并发编程 阻塞IO模型原理解析

    阻塞IO(blocking IO) 在linux中,默认情况下所有的socket都是blocking,一个典型的读操作流程大概是这样: 当用户进程调用了recvfrom这个系统调用,kernel内核就开始了IO的第一个阶段:准备数据.对于network io( 网络io )来说,很多时候数据在一开始还没有到达(比如,还没有收到一个完整的UDP包),这个时候kernel( 内核 )就要等待足够的数据到来. 等着对方把数据放到自己操作系统内存 而在用户进程这边,整个进程会被阻塞.当kernel一直等

  • Python中使用select模块实现非阻塞的IO

    Socket的英文原义是"孔"或"插座".作为BSD UNIX的进程通信机制,取后一种意思.通常也称作"套接字",用于描述IP地址和端口,是一个通信链的句柄.在Internet上的主机一般运行了多个服务软件,同时提供几种服务.每种服务都打开一个Socket,并绑定到一个端口上,不同的端口对应于不同的服务.Socket正如其英文原意那样,像一个多孔插座.一台主机犹如布满各种插座的房间,每个插座有一个编号,有的插座提供220伏交流电, 有的提供110

  • 解决Python httpx 运行过程中无限阻塞的问题

    目录 Python httpx 运行过程中无限阻塞 1.通过 pm2 部署脚本 2.通过装饰器给函数设置一个最大执行超时时间 python爬虫httpx的用法 请求方式 Python httpx 运行过程中无限阻塞 requests 模块只支持 http1,在遇到 http2 的数据接口的时候(某乎的搜索接口),需要采用支持http2 请求的模块(如 httpx.hyper). 本文是针对 httpx 在请求数据时,出现无限阻塞问题的一些处理方法. httpx 的 timeout 有 bug,会

  • 解决python ThreadPoolExecutor 线程池中的异常捕获问题

    问题 最近写了涉及线程池及线程的 python 脚本,运行过程中发现一个有趣的现象,线程池中的工作线程出现问题,引发了异常,但是主线程没有捕获异常,还在发现 BUG 之前一度以为线程池代码正常返回. 先说重点 这里主要想介绍 python concurrent.futuresthread.ThreadPoolExecutor 线程池中的 worker 引发异常的时候,并不会直接向上抛起异常,而是需要主线程通过调用concurrent.futures.Future.exception(timeou

  • python使用ddt过程中遇到的问题及解决方案【推荐】

    前言: 在使用DDT数据驱动+HTMLTestRunner输出测试报告时遇到过2个问题: 1.生成的测试报告中,用例名称后有dict() -> new empty dictionary 2.使用ddt生成的用例名称无法更改 1.用例名称后有dict() -> new empty dictionary 报告中用例名称后有dict() -> new empty dictionary,如图所示: 解决方案:这是ddt高版本1.2.0的bug 1.cmd先通过pip uninstall ddt

  • 解决pytorch GPU 计算过程中出现内存耗尽的问题

    Pytorch GPU运算过程中会出现:"cuda runtime error(2): out of memory"这样的错误.通常,这种错误是由于在循环中使用全局变量当做累加器,且累加梯度信息的缘故,用官方的说法就是:"accumulate history across your training loop".在默认情况下,开启梯度计算的Tensor变量是会在GPU保持他的历史数据的,所以在编程或者调试过程中应该尽力避免在循环中累加梯度信息. 下面举个栗子: 上代

  • 使用Pycharm在运行过程中,查看每个变量的操作(show variables)

    每个版本的Pycharm的"Show command line afterwards"可能会稍有不同,例如有版本叫:"run with Python console",反正不管名称怎么变,位置基本是没变的,勾选试一下就知道了! 原文: 做图像处理的人一般都用过MATLAB,好用易上手,并且里面封装了大量的算法,并且MATLAB里面有一个很贴心的功能就是你可以随时查看变量的值,以及变量的类型是什么: 在进行代码调试的时候,可以清楚的看到是哪些值出现了问题,但是由于MA

  • 解决python pandas读取excel中多个不同sheet表格存在的问题

    摘要:不同方法读取excel中的多个不同sheet表格性能比较 # 方法1 def read_excel(path): df=pd.read_excel(path,None) print(df.keys()) # for k,v in df.items(): # print(k) # print(v) # print(type(v)) return df # 方法2 def read_excel1(path): data_xls = pd.ExcelFile(path) print(data_x

  • 解决Python获取字典dict中不存在的值时出错问题

    描述:Python2.7中如果想要获取字典中的一个值,但是这个值可能不存在,此时应该加上判断: 举个例子: t= {} if t.get('1'): # right:这种通过key来查询是否存在的方式是比较好的 print(t['1']) print('right') if t['1']: # wrong:这种直接判断是否存在的方式因为会在判断之前调用,所以会报错 print(t['1']) 额外说明: dict.get(key, default=None) 方法详解: Parameters:

  • 解决AndroidStudio无法运行java中的mian方法问题

    前言: 我们都知道Android开发者的必备工具:AndroidStudio.是开发人员用来编译.测试的专用工具.今天在使用Androidstudio时发现了些问题.在3.0版本之前是可以直接运行mian方法来测试的. 今天写了一个java文件准备运行着mian方法时却突然报错了,本想着是升级到4.1版本的问题?后来找到了问题所在,默认配置问题. 如下图: 系统提示app配置有误,无法创建mian方法的task. 解决方案: 修改idea目录下的gradle.xml文件. 现gradle.xml

  • 解决Android加壳过程中mprotect调用失败的原因分析

    目录 问题原由 调用mprotect修改内存失败的现象 mprotect调用失败的原因分析 两种可行的解决方案 小结 问题原由 函数抽取壳是当前最为流行的DEX加壳方式之一,这种加壳方式的主要流程包含两个步骤:一.将DEX中需要保护的函数指令置空(即抽取函数体):二.在应用启动的过程中,HOOK 类的加载过程,比如ClassLinker::LoadMethod函数,然后及时回填指令. 笔者在实现抽取壳的过程中遇到了一个问题,即在步骤二回填指令之前,需要先调用mprotect将目标内存设置为“可写

  • JavaScript运行过程中的“预编译阶段”和“执行阶段”

    javascript相对于其它语言来说是一种弱类型的语言,在其它如java语言中,程序的执行需要有编译的阶段,而在javascript中也有类似的"预编译阶段"(javascript的预编译是以代码块为范围<script></script>,即每遇到一个代码块都会进行  预编译>执行),了解javascript引擎的执行机理,将有助于在写js代码过程中的思路总结 首先科普下javascript中的两种声明方式,var和function,前者声明的是变量,后

随机推荐