Search code examples
dockerpuppeteernestjsgoogle-cloud-run

Puppeteer Error: error while loading shared libraries: libgobject-2.0.so.0


I have a NestJS App deployed on Google Cloud Run which is using puppeteer (V7.0.1) to generate a PDF. Locally, everything is working absolutely fine, but on my Cloud Run Service I keep getting the following error: /usr/app/node_modules/puppeteer/.local-chromium/linux-848005/chrome-linux/chrome: error while loading shared libraries: libgobject-2.0.so.0: cannot open shared object file: No such file or directory

The directory does exist in the Docker container (checked with RUN ls node_modules/.....). Using the Docker code from the puppeteer troubleshooting doc or any other snippet I found on similar issues on the web result in the same error for me.

Dockerfile:

FROM node:12-slim AS base
WORKDIR /usr/app

FROM base AS build
RUN apt-get update \
    && apt-get install -y wget gnupg \
    && wget -q -O - https://dl-ssl.google.com/linux/linux_signing_key.pub | apt-key add - \
    && sh -c 'echo "deb [arch=amd64] http://dl.google.com/linux/chrome/deb/ stable main" >> /etc/apt/sources.list.d/google.list' \
    && apt-get update \
    && apt-get install -y google-chrome-stable fonts-ipafont-gothic fonts-wqy-zenhei fonts-thai-tlwg fonts-kacst fonts-freefont-ttf libxss1 \
      --no-install-recommends \
    && rm -rf /var/lib/apt/lists/*

COPY package.json yarn.lock ./
RUN yarn --prod
COPY . ./
RUN yarn add @nestjs/cli
RUN yarn sass && yarn build && yarn copy-pdf-assets

FROM base
COPY --from=build /usr/app ./
ENV PATH /usr/app/node_modules/.bin:$PATH
CMD yarn start:prod

Generate PDF Function:

//also tried headless: true or false and many other flags that deemed to fix it for others
const browser = await puppeteer.launch({ args: ['--no-sandbox'] }); 

try {
    const page = await browser.newPage();

    await page.setViewport({ height: 792, width: 1039 })
    await page.setContent(this.getTemplate(template, data), {
        waitUntil: ['load', 'domcontentloaded', 'networkidle0']
    });
    await page.addStyleTag({ path: this.resolvePath(`/templates/${template}/styles.css`) })

    await new Promise(resolve => setTimeout(resolve, 500));

    return await page.pdf({ format: 'a4', landscape: true, printBackground: true });
} finally {
    await browser.close();
}

Let me know if you need any other information. Thanks in advance.


Solution

  • To anyone reading this with a similar problem and setup: my mistake was the build step in my docker file. Since I was installing chromium there, instead of the actual run step, puppeteer actually didn't have a chromium instance while running. I just moved the apt-get stuff to the last step of my docker file, that fixed it.

    Edit 2023-05-23:

    Working version of above dockerfile:

    FROM node:12-slim AS base
    WORKDIR /usr/app
    
    FROM base AS build
    COPY package.json yarn.lock ./
    RUN yarn --prod
    COPY . ./
    RUN yarn add @nestjs/cli
    RUN yarn sass && yarn build && yarn copy-pdf-assets
    
    FROM base
    RUN apt-get update \
        && apt-get install -y wget gnupg \
        && wget -q -O - https://dl-ssl.google.com/linux/linux_signing_key.pub | apt-key add - \
        && sh -c 'echo "deb [arch=amd64] http://dl.google.com/linux/chrome/deb/ stable main" >> /etc/apt/sources.list.d/google.list' \
        && apt-get update \
        && apt-get install -y google-chrome-stable fonts-ipafont-gothic fonts-wqy-zenhei fonts-thai-tlwg fonts-kacst fonts-freefont-ttf libxss1 \
          --no-install-recommends \
        && rm -rf /var/lib/apt/lists/*
    COPY --from=build /usr/app ./
    ENV PATH /usr/app/node_modules/.bin:$PATH
    CMD yarn start:prod