修改wait.data_packets()未完成

This commit is contained in:
g1879 2023-04-21 17:31:27 +08:00
parent a6c49cc3d8
commit 33521f41e4
3 changed files with 36 additions and 19 deletions

View File

@ -14,6 +14,7 @@ from time import perf_counter, sleep, time
from FlowViewer.listener import ResponseData from FlowViewer.listener import ResponseData
from requests import Session from requests import Session
from .commons.web import DataPacket
from .base import BasePage from .base import BasePage
from .chromium_driver import ChromiumDriver from .chromium_driver import ChromiumDriver
from .chromium_element import ChromiumScroll, ChromiumElement, run_js, make_chromium_ele from .chromium_element import ChromiumScroll, ChromiumElement, run_js, make_chromium_ele
@ -1061,14 +1062,19 @@ class NetworkListener(object):
self._single = False self._single = False
self._requests = {} self._requests = {}
def set_targets(self, targets, is_regex=False): self._count = None
self._caught = 0 # 已获取到的数量
def set_targets(self, targets, is_regex=False, count=None):
"""指定要等待的数据包 """指定要等待的数据包
:param targets: 要匹配的数据包url特征可用list等传入多个 :param targets: 要匹配的数据包url特征可用list等传入多个
:param is_regex: 设置的target是否正则表达式 :param is_regex: 设置的target是否正则表达式
:param count: 设置总共等待多少个数据包为None时每个目标等待1个
:return: None :return: None
""" """
if not isinstance(targets, (str, list, tuple, set)): if not isinstance(targets, (str, list, tuple, set)):
raise TypeError('targets只能是str、list、tuple、set。') raise TypeError('targets只能是str、list、tuple、set。')
self._is_regex = is_regex self._is_regex = is_regex
if isinstance(targets, str): if isinstance(targets, str):
self._targets = {targets} self._targets = {targets}
@ -1076,8 +1082,11 @@ class NetworkListener(object):
else: else:
self._targets = set(targets) self._targets = set(targets)
self._single = False self._single = False
self._page.run_cdp('Network.enable') if count is None:
self._count = len(self._targets)
if targets is not None: if targets is not None:
self._page.run_cdp('Network.enable')
self._page.driver.Network.requestWillBeSent = self._requestWillBeSent self._page.driver.Network.requestWillBeSent = self._requestWillBeSent
self._page.driver.Network.responseReceived = self._response_received self._page.driver.Network.responseReceived = self._response_received
self._page.driver.Network.loadingFinished = self._loading_finished self._page.driver.Network.loadingFinished = self._loading_finished
@ -1098,20 +1107,24 @@ class NetworkListener(object):
:return: ResponseData对象或监听结果字典 :return: ResponseData对象或监听结果字典
""" """
if self._targets is None: if self._targets is None:
self.set_targets('', is_regex=self._is_regex) raise RuntimeError('必须先用set_targets()设置等待目标。')
timeout = timeout if timeout is not None else self._page.timeout timeout = timeout if timeout is not None else self._page.timeout
end_time = perf_counter() + timeout end_time = perf_counter() + timeout
while perf_counter() < end_time: while perf_counter() < end_time:
if self._results and (any_one or set(self._results) == self._targets): if self._caught >= self._count or (any_one and self._caught):
break break
sleep(.1) sleep(.1)
if not self._results: if not self._results:
return False r = False
else:
# todo
r = list(self._results.values())[0] if self._single else self._results
r = list(self._results.values())[0] if self._single else self._results
self._results = {} self._results = {}
self._requests = {} self._requests = {}
self._caught = 0
return r return r
def _response_received(self, **kwargs): def _response_received(self, **kwargs):
@ -1140,15 +1153,21 @@ class NetworkListener(object):
rd.method = request['method'] rd.method = request['method']
self._results[target] = rd self._results[target] = rd
self._caught += 1
def _requestWillBeSent(self, **kwargs): def _requestWillBeSent(self, **kwargs):
"""接收到请求时的回调函数""" """接收到请求时的回调函数"""
for target in self._targets: for target in self._targets:
if (self._is_regex and search(target, kwargs['request']['url'])) or ( if (self._is_regex and search(target, kwargs['request']['url'])) or (
not self._is_regex and target in kwargs['request']['url']): not self._is_regex and target in kwargs['request']['url']):
self._requests[kwargs['requestId']] = {'target': target, # self._requests[kwargs['requestId']] = {'target': target,
'post_data': kwargs['request'].get('postData', None), # 'post_data': kwargs['request'].get('postData', None),
'request_headers': kwargs['request']['headers'], # 'request_headers': kwargs['request']['headers'],
'method': kwargs['request']['method']} # 'method': kwargs['request']['method']}
self._requests[kwargs['requestId']] = DataPacket(kwargs['requestId'], self._page.tab_id, target, kwargs)
if kwargs['request'].get('hasPostData', None) and not kwargs['request'].get('postData', None):
pd = self._page.run_cdp('Network.getRequestPostData', requestId=kwargs['requestId'])['postData']
self._requests[kwargs['requestId']].
break break

View File

@ -244,13 +244,15 @@ class ChromiumBaseWaiter(object):
class NetworkListener(object): class NetworkListener(object):
def __init__(self, page): def __init__(self, page):
self._page: ChromiumBase = ... self._page: ChromiumBase = ...
self._count: int = ...
self._caught: int = ...
self._targets: Union[str, dict] = ... self._targets: Union[str, dict] = ...
self._single: bool = ... self._single: bool = ...
self._results: Union[ResponseData, Dict[str, ResponseData], False] = ... self._results: Union[ResponseData, Dict[str, ResponseData], False] = ...
self._is_regex: bool = ... self._is_regex: bool = ...
self._requests: dict = ... self._requests: dict = ...
def set_targets(self, targets: Union[str, list, tuple, set], is_regex: bool = False) -> None: ... def set_targets(self, targets: Union[str, list, tuple, set], is_regex: bool = False, count: int = None) -> None: ...
def stop(self) -> None: ... def stop(self) -> None: ...

View File

@ -23,7 +23,6 @@ class DataPacket(object):
'url', 'urlFragment', 'method', 'postDataEntries', 'mixedContentType', 'initialPriority', 'url', 'urlFragment', 'method', 'postDataEntries', 'mixedContentType', 'initialPriority',
'referrerPolicy', 'isLinkPreload', 'trustTokenParams', 'isSameSite', 'referrerPolicy', 'isLinkPreload', 'trustTokenParams', 'isSameSite',
'status', 'statusText', 'status', 'statusText',
'securityDetails', 'headersText', 'mimeType', 'requestHeadersText', 'connectionReused', 'connectionId', 'securityDetails', 'headersText', 'mimeType', 'requestHeadersText', 'connectionReused', 'connectionId',
'remoteIPAddress', 'remotePort', 'fromDiskCache', 'fromServiceWorker', 'fromPrefetchCache', 'remoteIPAddress', 'remotePort', 'fromDiskCache', 'fromServiceWorker', 'fromPrefetchCache',
@ -31,18 +30,15 @@ class DataPacket(object):
'protocol', 'securityState', 'protocol', 'securityState',
) )
def __init__(self, request_id, request, response, body, tab, target): def __init__(self, request_id, tab, target, raw_request):
""" """
:param request: request的数据 :param request_id: request id
:param response: response的数据
:param body: response包含的内容
:param tab: 产生这个数据包的tab的id :param tab: 产生这个数据包的tab的id
:param target: 监听目标 :param target: 监听目标
:param raw_request: 原始request数据
""" """
self.requestId = request_id self.requestId = request_id
self.response = CaseInsensitiveDict(response) self._raw_request = raw_request
self.request = CaseInsensitiveDict(request)
self.rawBody = body
self.tab = tab self.tab = tab
self.target = target self.target = target
self._requestHeaders = None self._requestHeaders = None