Puppeteerを使用して、URLをChromeに読み込み、次の情報をキャプチャします。
set-cookie
などの重複ヘッダーを含む)完全な応答本文を取得することが、私にとって問題の原因です。
私が試したこと:
response.buffer
で応答コンテンツを取得します- ナビゲーションでバッファが消去されますgetResponseBodyForInterception
の使用-これは、 encodedLengthにアクセスできなくなった が可能なことを意味し、場合によっては正しいリクエストおよびレスポンスヘッダーの取得に問題がありました理想的には、ソリューションのパフォーマンスへの影響はわずかで、通常のページのロードと機能上の違いはありません。また、Chromeの分岐を避けたいです。
要求ごとに page.setRequestInterception()
を使用して要求インターセプトを有効にできます。次に、 page.on('request')
内で-を使用できます _request-promise-native
_ Puppeteerで request.continue()
を使用してリクエストを続行する前に応答データを収集する仲介者として機能するモジュール。
ここに完全な例があります:
_'use strict';
const puppeteer = require('puppeteer');
const request_client = require('request-promise-native');
(async () => {
const browser = await puppeteer.launch();
const page = await browser.newPage();
const result = [];
await page.setRequestInterception(true);
page.on('request', request => {
request_client({
uri: request.url(),
resolveWithFullResponse: true,
}).then(response => {
const request_url = request.url();
const request_headers = request.headers();
const request_post_data = request.postData();
const response_headers = response.headers;
const response_size = response_headers['content-length'];
const response_body = response.body;
result.Push({
request_url,
request_headers,
request_post_data,
response_headers,
response_size,
response_body,
});
console.log(result);
request.continue();
}).catch(error => {
console.error(error);
request.abort();
});
});
await page.goto('https://example.com/', {
waitUntil: 'networkidle0',
});
await browser.close();
})();
_
要求ログを実際のコンテンツと一緒に書き込めるクイックプロキシサーバーを検索することをお勧めします。
ターゲットのセットアップは、プロキシサーバーがログファイルを書き込むだけで、ログを分析し、必要な情報を検索できるようにすることです。
プロキシが動作している間はリクエストを傍受しないでください(これにより速度が低下します)
発生する可能性のあるパフォーマンスの問題(ロガーセットアップとしてのプロキシを使用)は、主にTLSサポートに関連しています。プロキシセットアップでの高速TLSハンドシェイク、HTTP2プロトコルの許可に注意してください
例えば。 Squidベンチマーク 数百のRPSを処理できることを示します。これはテスト目的には十分なはずです
「 フィドラー 」というツールを使用することをお勧めします。 URL urlを読み込むときに言及したすべての情報をキャプチャします。
これは、操り人形師だけで行うことができます。ナビゲーションで_response.buffer
_がクリアされることを説明している問題は、各リクエストを次々に処理することで回避できます。
以下のコードは _page.setRequestInterception
_ を使用してすべてのリクエストをインターセプトします。現在処理中/待機中のリクエストがある場合、新しいリクエストはキューに入れられます。次に、 response.buffer()
を使用できます。並列要求がないため、他の要求が非同期的にバッファーを消去するという問題はありません。現在処理されている要求/応答が処理されるとすぐに、次の要求が処理されます。
_const puppeteer = require('puppeteer');
(async () => {
const browser = await puppeteer.launch();
const [page] = await browser.pages();
const results = []; // collects all results
let paused = false;
let pausedRequests = [];
const nextRequest = () => { // continue the next request or "unpause"
if (pausedRequests.length === 0) {
paused = false;
} else {
// continue first request in "queue"
(pausedRequests.shift())(); // calls the request.continue function
}
};
await page.setRequestInterception(true);
page.on('request', request => {
if (paused) {
pausedRequests.Push(() => request.continue());
} else {
paused = true; // pause, as we are processing a request now
request.continue();
}
});
page.on('requestfinished', async (request) => {
const response = await request.response();
const responseHeaders = response.headers();
let responseBody;
if (request.redirectChain().length === 0) {
// body can only be access for non-redirect responses
responseBody = await response.buffer();
}
const information = {
url: request.url(),
requestHeaders: request.headers(),
requestPostData: request.postData(),
responseHeaders: responseHeaders,
responseSize: responseHeaders['content-length'],
responseBody,
};
results.Push(information);
nextRequest(); // continue with next request
});
page.on('requestfailed', (request) => {
// handle failed request
nextRequest();
});
await page.goto('...', { waitUntil: 'networkidle0' });
console.log(results);
await browser.close();
})();
_
Chromeを押してから[ネットワーク]タブに移動すると、ウェブサイトが送信するすべてのhttpリクエストが表示されます。言及した詳細を表示できます。