如何使用Python和urllib2设置源IP /接口?
不幸的是,正在使用的标准库模块堆栈(urllib2,httplib,socket)为此目的而设计得有些糟糕- 在操作的关键点HTTPConnection.connect(在httplib中)委托给socket.create_connection,这反过来使您没有任何“钩子”在创建套接字实例sock和sock.connect调用之间,您需要在插入sock.bind之前插入sock.connect源IP(我正在广泛传播信息,而不是以这种不密封,过度封装的方式设计抽象- 我我将在本周四的OSCON上以“ Zen和抽象维护的艺术”为标题来谈论这一点-但在这里,您的问题是如何处理我们以这种方式设计的一堆抽象(叹气)。
HTTPConnection.connect
socket.create_connection
sock
sock.connect
sock.bind
当您遇到此类问题时,您只有两个不太好的解决方案:要么复制,粘贴并编辑设计错误的代码,然后在代码中放置原始设计人员无法满足的“钩子”。或“猴子补丁”该代码。GOOD都不是,但是两者都可以,所以至少要感谢我们有这样的选择(通过使用开源和动态语言)。在这种情况下,我想我会去进行猴子补丁(这很糟糕,但是复制和粘贴编码甚至更糟)—一个代码片段,例如:
import socket true_socket = socket.socket def bound_socket(*a, **k): sock = true_socket(*a, **k) sock.bind((sourceIP, 0)) return sock socket.socket = bound_socket
urllib2
true_socket`以避开将来尚未创建的套接字)。第二种替代方法会添加其自身的复杂性以正确编排,因此我在等所有内容解释之前,等待您澄清您是否确实需要此类复杂性。
AKX的好答案是“复制/粘贴/编辑”选项的变体,因此我不需要对此进行太多扩展- 请注意,它并不能完全复制socket.create_connection其connect方法,请参见此处的源代码(页末),并决定create_connection如果您决定采用该功能,则可能希望在复制/粘贴/编辑版本中体现该功能的其他功能。
connect
create_connection