如何在木偶操作员请求POST?

时间:2017-11-01 17:31:20

标签: google-chrome http https google-chrome-headless puppeteer

(async() => {
    const browser = await puppeteer.launch();
    const page = await browser.newPage();
    await page.goto('https://www.example.com/search');
    const data = await page.content();
    browser.close();
    res.send(data);
})();

我为send get请求执行此代码。我不明白我应该如何发送post请求?

4 个答案:

答案 0 :(得分:9)

获得正确的“订单”可能有点挑战。文档没有那么多的例子......在示例文件夹中的存储库中有一些多汁的项目,你一定要看一下。

https://github.com/GoogleChrome/puppeteer/tree/master/examples

这是一个例子;将以下内容放入异步块:

    // Create browser instance, and give it a first tab
    const browser = await puppeteer.launch();
    const page = await browser.newPage();

    // Allows you to intercept a request; must appear before
    // your first page.goto()
    await page.setRequestInterception(true);

    // Request intercept handler... will be triggered with 
    // each page.goto() statement
    page.on('request', interceptedRequest => {

        // Here, is where you change the request method and 
        // add your post data
        var data = {
            'method': 'POST',
            'postData': 'paramFoo=valueBar&paramThis=valueThat'
        };

        // Request modified... finish sending! 
        interceptedRequest.continue(data);
    });

    // Navigate, trigger the intercept, and resolve the response
    const response = await page.goto('https://www.example.com/search');     
    const responseBody = await response.text();
    console.log(responseBody);

    // Close the browser - done! 
    await browser.close();

答案 1 :(得分:2)

setRequestInterception / 'request'事件的工作方式有点奇怪。一旦激活,Puppeteer会将POST数据发送到页面上的每个资源,而不仅仅是原始请求的页面。我遇到的问题是,一旦我在Puppeteer中添加了POST数据,我的所有页面资源(脚本,CSS)都无法加载。

由于我只想将POST数据应用于第一个请求,因此该代码对我有用:

// Used for serializing POST parameters from an object
const querystring = require('querystring');

// ...

const browser = await puppeteer.launch();
const page = await browser.newPage();

let postData = {a: 1, b: 2};

await page.setRequestInterception(true);

page.once('request', request => {
    var data = {
        'method': 'POST',
        'postData': querystring.stringify(postData),
        'headers': {
            ...request.headers(),
            'Content-Type': 'application/x-www-form-urlencoded'
        },
    };

    request.continue(data);

    // Immediately disable setRequestInterception, or all other requests will hang
    page.setRequestInterception(false);
});

const response = await page.goto('https://www.example.com/');

答案 2 :(得分:1)

对于POST,您应该执行以下操作:

  • 设置页面的拦截请求: page.setRequestInterception();
  • 通过为'请求'设置处理程序来获取请求对象。 event:page.on(' request',function(){})
  • 将请求的方法(POST)和postData设置为覆盖使用 request.continue([重写])

请在此处查看Puppeteer的API文档:https://github.com/GoogleChrome/puppeteer/blob/HEAD/docs/api.md

答案 3 :(得分:1)

以下是Puppeteer 2.0.0的完整示例:

const puppeteer = require("puppeteer");
const devices = require("puppeteer/DeviceDescriptors");

async function main() {
  const browser = await puppeteer.launch({
    args: ["--enable-features=NetworkService", "--no-sandbox"],
    ignoreHTTPSErrors: true
  });
  const page = await browser.newPage();

  await page.setRequestInterception(true);

  page.once("request", interceptedRequest => {
    interceptedRequest.continue({
      method: "POST",
      postData: "foo=FOO&bar=BAR",
      headers: {
        ...interceptedRequest.headers(),
        "Content-Type": "application/x-www-form-urlencoded"
      }
    });
  });

  const response = await page.goto("https://postman-echo.com/post");

  console.log({
    url: response.url(),
    statusCode: response.status(),
    body: await response.text()
  });

  await browser.close();
}

main();

请注意,如果您选中response.request().method(),它将不会被更新(仍然是GET)