Dockerで日本語対応のPuppeteerを動かす

公開日時
更新日時

Dockerを使ってPuppeteerを動かせるようにした。

日本語ページを開く際に文字化けしたので日本語フォントをインストールして対応した。

package.jsonにpuppeteerを追加。

{
  "name": "puppeteer_sample",
  "version": "1.0.0",
  "main": "index.js",
  "dependencies": {
    "puppeteer": "^1.20.0"
  },
  "scripts": {
    "start": "node index.js"
  }
}

空のyarn.lockを追加しておく。

touch yarn.lock

Dockerfileに以下を記述。

# Dockerfile

FROM alpine:edge

RUN apk update

# japanese font
RUN apk add --no-cache curl fontconfig font-noto-cjk \
  && fc-cache -fv

# Installs latest Chromium (76) package.
RUN apk add --no-cache \
      chromium \
      nss \
      freetype \
      freetype-dev \
      harfbuzz \
      ca-certificates \
      ttf-freefont \
      nodejs \
      yarn 

# timezone
RUN apk add --update --no-cache tzdata && \
    cp /usr/share/zoneinfo/Asia/Tokyo /etc/localtime && \
    echo "Asia/Tokyo" > /etc/timezone && \
    apk del tzdata

# Tell Puppeteer to skip installing Chrome. We'll be using the installed package.
ENV PUPPETEER_SKIP_CHROMIUM_DOWNLOAD true

COPY ./package.json /app/package.json
COPY ./yarn.lock /app/yarn.lock
RUN yarn

# Add user so we don't need --no-sandbox.
RUN addgroup -S pptruser && adduser -S -g pptruser pptruser \ && mkdir -p /home/pptruser/Downloads /app \
    && chown -R pptruser:pptruser /home/pptruser \
    && chown -R pptruser:pptruser /app

# Run everything after as non-privileged user.
USER pptruser

WORKDIR /app

CMD ["yarn", "start"]

docker-compose.ymlはこんな感じ。

# docker-compose.yml

version: "3.3"
services:
  datastore:
    image: busybox
    volumes:
      - node_modules:/usr/local/lib/node_modules
  app:
    build: .
    working_dir: "/app"
    tty: true
    stdin_open: true
    volumes:
      - node_modules:/usr/local/lib/node_modules
      - .:/app
    shm_size: 256
    cap_add: # https://github.com/GoogleChrome/puppeteer/blob/master/docs/troubleshooting.md#tips
      - SYS_ADMIN
volumes:
  node_modules:

datastoreにnode_modulesをインストール。

docker-compose run app yarn

あとはpuppeteerを呼び出すコードを書けばDocker上で自由に試せる。

const puppeteer = require('puppeteer');

(async() => {
  const browser = await puppeteer.launch({
    executablePath: "/usr/bin/chromium-browser"
  });
  const page = await browser.newPage();
  await page.goto('http://example.com');
  await page.screenshot({path: 'example.png'});
  await browser.close();
})();

参考


Related #docker

Dockerのデータ保存場所を変更する

/etc/docker/daemon.jsonに追記

docker-composeで最新のログを確認する場合

tailオプションも合わせて指定しよう

docker-compose build時に「no Space Left on Device」が発生

1年前にも同じエラーにハマってた

Windows10 HomeにDockerを入れる

Windows 10 May 2020 UpdateでWSL2が導入されたおかげ