LoginSignup
9
8

More than 3 years have passed since last update.

AWS Lambdaでスクリーンショットを撮ってS3に保存

Posted at

はじめに

この記事は、mohikanz Advent Calendar 2019の11日目の記事です。
去年は、マイコンネタでした。
今年は、AWSで日頃便利に使わせてもらっている技術ネタについて書きます。

あるプロジェクトで、Webサイトを定期的にキャプチャして、S3に保存しておきたいなぁと言う事があり、それならばサーバレスで挑戦してみようと言うことになり、それをやってみたときの記事になります。
Lambdaは便利ですよね。何よりお安いですし。

必要な知識

  • Python
  • AWS Lambda
  • Selenium

事前準備

headless chromeを使いますので、いくつか事前準備が必要です。

Lambda Layers

Lambdaのファイルサイズ上限に引っかかるので、Lambda Layersにheadless chromeを用意します。
GitHubに置いておきましたので、ご自由にお使いください。
Lambda Layersは、マネジメントコンソールからアップロードが出来ます。

日本語フォント

IPAexフォントがあると文字化けしませんので、あらかじめダウンロードしておいてください。
./fontsディレクトリに保存しておきます。
Lambda Layersに含めると50MBを超えてしまうので、Lambdaの方に追加します。

  • 2書体パック(IPAex明朝(Ver.002.01)、IPAexゴシック(Ver.002.01))

Lambdaの作成

Serverless Frameworkを使って構築します。

$ sls create --template aws-python3 --path headless-chrome
serverless.yml
service: headless-chrome

provider:
  name: aws
  runtime: python3.6
  memorySize: 1600
  timeout: 120
  stage: ${opt:stage, 'dev'}
  region: ap-northeast-1
  # 権限設定
  iamRoleStatements:
    - Effect: "Allow"
      Action:
        - "s3:GetObject"
        - "s3:PutObject"
      Resource: "arn:aws:s3:::headless-chrome-${self:provider.stage}/*"
functions:
 chrome: 
    handler: chrome.lambda_handler
    description: Headless Chrome
    environment:
      TZ: Asia/Tokyo
      STAGE: ${self:provider.stage}
      S3BUCKET: headless-chrome-${self:provider.stage}
    package:
      # フォントを追加する
      include: 
        - '.fonts/**' 
    layers: 
      - arn:aws:lambda:ap-northeast-1:xxxxxxxxxxxx:layer:headless_chrome_python360:1

Lambdaのソースコード

chrome.py
from selenium import webdriver
import boto3
import json
import os
import time


os.environ['HOME'] = '/var/task'


def lambda_handler(event, context):
    options = webdriver.ChromeOptions()
    options.add_argument("--headless")
    options.add_argument("--disable-gpu")
    # options.add_argument("--window-size=3408x2156")
    options.add_argument("--window-size=1704x1078")
    options.add_argument("--disable-application-cache")
    options.add_argument("--disable-infobars")
    options.add_argument("--no-sandbox")
    options.add_argument("--hide-scrollbars")
    options.add_argument("--enable-logging")
    options.add_argument("--log-level=0")
    options.add_argument("--v=99")
    options.add_argument("--single-process")
    options.add_argument("--ignore-certificate-errors")
    options.add_argument("--homedir=/tmp")

    options.binary_location = "/opt/bin/headless-chromium"

    bucket = os.environ.get("S3BUCKET", "")
    s3 = boto3.client('s3')
    driver = webdriver.Chrome(
        "/opt/bin/chromedriver", chrome_options=options)
    driver.get("https://www.google.co.jp")

    time.sleep(5)
    driver.save_screenshot("/tmp/shot.png")
    driver.close()

    s3.upload_file(Filename="/tmp/shot.png",
                   Bucket=bucket,
                   Key="hoge.png")
    return "ok"

実行してみた

$ sls deploy -v
$ sls invoke -f chrome

こんな感じになりました。

hoge.png

さいごに

Seleniumを使いこなせる人は、CI/CDに組み込んだりしてみると、リリースの動作確認まで出来ちゃうので、夢が広がりますね。
chromeはfileプロトコルも使えるので、ローカルに置いたファイル(Lambdaが動いてる実行環境)を使うこともできます。

9
8
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
9
8