部署到 heroku 而不是本地时获取调用出现 503 错误

编程入门 行业动态 更新时间:2024-10-10 19:18:22

部署到 heroku <a href=https://www.elefans.com/category/jswz/34/1771316.html style=而不是本地时获取调用出现 503 错误"/>

部署到 heroku 而不是本地时获取调用出现 503 错误

问题: 当我在部署到 heroku 后向我的服务器发送特定的 get 请求时,我每次都会收到 503 错误,并且应用程序没有完成我期望的提交操作。该请求专门用于触发 puppeteer 屏幕截图代码并将带有屏幕截图的 zip 文件返回给客户端。这在本地按预期完美运行,只有在部署后才会失败。

值得注意的错误: 我的 heroku 日志在屏幕截图的一半左右产生请求超时错误,代码是 H12。我现在还不清楚造成这种情况的原因是什么,因此解决方案应该是什么(或者甚至如何最好地找出答案)。

应用程序: 我已经构建了一个内部团队应用程序,它接受一个 url,截取该 url 上的所有横幅,然后将它们捆绑在一个 zip 文件中,并将该文件返回给客户端以供下载。

前端代码:

fetch(`/dcsgrab?tearsheetUrl=${screenShotData}`)
      .then((response) => response.json())
      .then((data) => {
        zipBlob = new Blob([new Uint8Array(data.zipFile.data)], {type: "octet/stream"});
        url = window.URL.createObjectURL(zipBlob);
        zipDownload = document.createElement("a");

        setMessageData(data.message);
        setZipData(zipBlob);

        zipDownload.href = url;
        zipDownload.download = "screenshot-download.zip";
        document.body.appendChild(zipDownload);
        zipDownload.click();
      });
  };

后端代码:

app.get('/dcsgrab', (request, response) => {
    const zip = new AdmZip();

    (async () => {
        const browser = await puppeteer.launch({
            headless: true,
            executablePath: executablePath(),
            args: [
              '--no-sandbox',
              '--disable-setuid-sandbox',
              '--single-process',
            ],
        });

        let screenshotCounter = 1;

        const page = await browser.newPage();

        page.setViewport({width: 1280, height: 6000, deviceScaleFactor: PIXEL_DENSITY});

        await page.goto(request.query.tearsheetUrl, { waitUntil: 'networkidle0' });

        /**
       * Checks if the pagination button is active
       * @return {Promise.<Boolean>} Promise which resolves with a true boolean if the button is active
       */
      async function isNextButtonActive() {
        return await page.evaluate((selector) => {
          return !document.querySelector(selector).disabled;
        }, NEXT_SELECTOR);
      }

      /**
       * Clicks the pagination button
       * @return {Promise} Promise which resolves when the element matching selector is successfully clicked. The Promise will be rejected if there is no element matching selector
       */
      async function clickNextButton() {
        return await page.click(NEXT_SELECTOR, {delay: 100});
      }

      /**
       * Waits for the loading spinner widget to go away, indicating the iframes have been added to the page
       * @return {Promise.undefined}
       */
      async function waitForLoadingWidget() {
        return await page.waitForSelector('.preview-loading-widget', {hidden: true}).then(() => {
          console.log('Loading widget is gone');
        })
          .catch(e => {
            console.log(e.message);
          });
      }

      /**
       * Screenshot the creative elements on the current page
       * @return {Promise.<Array>} Promise which resolves with an array of clipping paths
       */
        async function getScreenShots() {
            const rects = await page.$$eval(PREVIEW_SELECTOR, iframes => {
              return Array.from(iframes, (el) => {
                const {x, y, width, height} = el.getBoundingClientRect();

                return {
                  left: x,
                  top: y,
                  width,
                  height,
                  id: el.id,
                };
              });
            }, PREVIEW_SELECTOR).catch(e => {
              console.error(e.message);
            });

            return Promise.all(rects.map(async (rect) => {
              return await page.screenshot({
                clip: {
                  x: rect.left,
                  y: rect.top,
                  width: rect.width,
                  height: rect.height,
                },
              }).then((content) => {
                zip.addFile(`screenshot-${screenshotCounter++}.png`, Buffer.from(content, "utf8"), `screenshot ${screenshotCounter++} saved`);
                console.log(`${rect.id} element captured and stored in zip`);
              })
                .catch((e) => {
                  console.error(e.message);
                });
            }));
        }

        // Wait a bit then take screenshots
      await new Promise(resolve => setTimeout(resolve, DELAY_FOR_ANIMATION));
      await getScreenShots().catch((e) => console.error(e.message));

        // Continue taking screenshots till there are no pages left
      while (await isNextButtonActive()) {
        await clickNextButton();
        await waitForLoadingWidget();
        await new Promise(resolve => setTimeout(resolve, DELAY_FOR_ANIMATION)),
        await getScreenShots().catch((e) => console.error(e.message));
      }

        await browser.close();

        const zipToSend = zip.toBuffer();

        response.json({ 
            message: 'Screenshots are done!\nPlease check the zip file that was just downloaded.',
            zipFile: zipToSend
        });
    })();
});

Heroku 日志:

2023-03-23T19:27:43.174105+00:00 heroku[web.1]: Restarting
2023-03-23T19:27:43.189825+00:00 heroku[web.1]: State changed from up to starting
2023-03-23T19:27:44.190045+00:00 heroku[web.1]: Stopping all processes with SIGTERM
2023-03-23T19:27:44.368177+00:00 heroku[web.1]: Process exited with status 143
2023-03-23T19:27:53.000000+00:00 app[api]: Build succeeded
2023-03-23T19:28:07.523862+00:00 heroku[web.1]: Starting process with command `npm start`
2023-03-23T19:28:09.144631+00:00 app[web.1]: 
2023-03-23T19:28:09.144660+00:00 app[web.1]: > [email protected] start
2023-03-23T19:28:09.144661+00:00 app[web.1]: > node server/server.js
2023-03-23T19:28:09.144661+00:00 app[web.1]: 
2023-03-23T19:28:09.428387+00:00 app[web.1]: Server is listening on port 21309
2023-03-23T19:28:09.838525+00:00 heroku[web.1]: State changed from starting to up
2023-03-23T19:28:10.596907+00:00 heroku[router]: at=info method=GET path="/" host=dcsgrab.herokuapp request_id=f0b15bcd-7eb4-4028-b5a9-2a6f76496c05 fwd="24.16.69.155" dyno=web.1 connect=0ms service=86ms status=200 bytes=944 protocol=https
2023-03-23T19:28:10.699774+00:00 heroku[router]: at=info method=GET path="/static/js/main.1910c761.js" host=dcsgrab.herokuapp request_id=e775658f-f56d-4db8-bcb2-71de15b0d87d fwd="24.16.69.155" dyno=web.1 connect=0ms service=4ms status=200 bytes=218121 protocol=https
2023-03-23T19:28:11.706348+00:00 heroku[router]: at=info method=GET path="/static/css/main.69947f1d.css" host=dcsgrab.herokuapp request_id=5340c5b9-b516-4a5a-99f5-851b421b1949 fwd="24.16.69.155" dyno=web.1 connect=0ms service=1ms status=200 bytes=3167 protocol=https
2023-03-23T19:28:11.818395+00:00 heroku[router]: at=info method=GET path="/static/css/main.69947f1d.css.map" host=dcsgrab.herokuapp request_id=ffcf15de-1af4-4dee-83d1-99c0c811c73f fwd="24.16.69.155" dyno=web.1 connect=0ms service=2ms status=200 bytes=5370 protocol=https
2023-03-23T19:28:11.820299+00:00 heroku[router]: at=info method=GET path="/static/js/main.1910c761.js.map" host=dcsgrab.herokuapp request_id=e7c588ad-c085-4a12-bd1b-d3c4433d48de fwd="24.16.69.155" dyno=web.1 connect=0ms service=5ms status=200 bytes=746644 protocol=https
2023-03-23T19:28:11.907618+00:00 heroku[router]: at=info method=GET path="/static/media/essence_mediacom_logo-nobg-color_corrected.764800408369a0f7cf88.png" host=dcsgrab.herokuapp request_id=f1f5ed8c-eda8-46a1-af0f-8e87e8d2d615 fwd="24.16.69.155" dyno=web.1 connect=0ms service=2ms status=200 bytes=16759 protocol=https
2023-03-23T19:28:11.993490+00:00 heroku[router]: at=info method=GET path="/static/media/essencemediacom_icon.a48332799f21c2163415.png" host=dcsgrab.herokuapp request_id=05b087a5-cccc-4efb-9da4-d4b9ae3af678 fwd="24.16.69.155" dyno=web.1 connect=0ms service=2ms status=200 bytes=14971 protocol=https
2023-03-23T19:28:12.189730+00:00 heroku[router]: at=info method=GET path="/essencemediacom_icon.png" host=dcsgrab.herokuapp request_id=5921b175-24b7-43ef-8db8-1a3df51588ad fwd="24.16.69.155" dyno=web.1 connect=0ms service=2ms status=200 bytes=14971 protocol=https
2023-03-23T19:28:12.473057+00:00 heroku[router]: at=info method=GET path="/manifest.json" host=dcsgrab.herokuapp request_id=bfa7629b-b6ad-49c1-a4a0-bffb968bfbb6 fwd="24.16.69.155" dyno=web.1 connect=0ms service=1ms status=200 bytes=787 protocol=https
2023-03-23T19:28:12.555689+00:00 heroku[router]: at=info method=GET path="/logo192.png" host=dcsgrab.herokuapp request_id=174be88c-84fd-4046-8862-35c77bcef675 fwd="24.16.69.155" dyno=web.1 connect=0ms service=1ms status=200 bytes=5622 protocol=https
2023-03-23T19:28:38.626764+00:00 app[web.1]: safe-frame-1 element captured and stored in zip
2023-03-23T19:28:39.116534+00:00 app[web.1]: safe-frame-5 element captured and stored in zip
2023-03-23T19:28:39.497607+00:00 app[web.1]: safe-frame-2 element captured and stored in zip
2023-03-23T19:28:39.954761+00:00 app[web.1]: safe-frame-4 element captured and stored in zip
2023-03-23T19:28:40.270808+00:00 app[web.1]: safe-frame-3 element captured and stored in zip
2023-03-23T19:28:41.373398+00:00 app[web.1]: Loading widget is gone
2023-03-23T19:28:47.380186+00:00 heroku[router]: at=error code=H12 desc="Request timeout" method=GET path="/dcsgrab?tearsheetUrl=" host=dcsgrab.herokuapp request_id=8d21b818-58e6-4f76-bd08-2d00050801b4 fwd="24.16.69.155" dyno=web.1 connect=0ms service=30000ms status=503 bytes=0 protocol=https
2023-03-23T19:28:56.769792+00:00 app[web.1]: safe-frame-8 element captured and stored in zip
2023-03-23T19:28:57.162674+00:00 app[web.1]: safe-frame-7 element captured and stored in zip
2023-03-23T19:28:57.598963+00:00 app[web.1]: safe-frame-6 element captured and stored in zip
2023-03-23T19:28:57.985009+00:00 app[web.1]: safe-frame-9 element captured and stored in zip
2023-03-23T19:28:58.436801+00:00 app[web.1]: safe-frame-10 element captured and stored in zip
2023-03-23T19:28:58.884653+00:00 app[web.1]: Loading widget is gone
回答如下:

查看官方 Heroku 错误代码 H12 它说:

一个 HTTP 请求需要超过 30 秒才能完成

因此您的服务器可能无法在 30 秒内生成响应以命中端点

/dcsgrab
,因此 Heroku 生成了错误。

更多推荐

部署到 heroku 而不是本地时获取调用出现 503 错误

本文发布于:2024-05-13 15:10:26,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1759795.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:而不是   错误   heroku

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!