Recently, as a personal hobby, I created a program to draw and tweet the seismic intensity distribution map of an earthquake, and I used it to generate images. I think I'll write it as a memorandum because I think it can be used with other things.
Python's framework called ** Selenium ** is used for testing web applications, but it is also used for scraping dynamic sites. Rendering is done with Chrome that runs on CUI called Headless Prouser of Google Chrome.
Since Selenium has a screenshot function, you can create your favorite image with HTML / CSS by setting up a local server and getting the necessary information there.
Python
Selenium
For the time being, Selenium seems to be in Ruby and JS as well. A framework for capturing web pages. The installation method with pip is as follows
pip install selenium
It is not necessary if Chrome is already installed in Windows or Mac, but when executing on VPN etc., it is executed by putting Chrome in Docker.
--Local server
Node.js, Deno, etc. are also OK. This time we will use Flsak, a Python framework.
The source code created this time can be found at here.
This time, create it with Flask and put it together as a container with Docker compose. Therefore, I would like to manage Python modules with pipenv.
Enter the following to install Pipenv and install Flask.
pip install pipenv
pipenv --python 3.8
pipenv install flask
In addition, add files that are not available and do as follows. The directory structure is as follows.
server
├── Dockerfile
├── Pipfile
├── Pipfile.lock
├── run.py
├── static
│ └── css
│ └── style.css
└── templates
└── index.html
Create run.py
, ʻindex.html, and
style.css` as you like.
This time, I will just display the character string GET with the URL parameter on the screen.
The Dockerfile is described as follows. The output port is 5000, but I think it's okay.
Dockerfile
FROM python:3.8
COPY run.py /run.py
COPY templates /templates
COPY static /static
COPY Pipfile /Pipfile
COPY Pipfile.lock /Pipfile.lock
RUN pip install pipenv
RUN pipenv install --system --deploy
EXPOSE 5000
Try pipenv shell && python run.py
, and if it can be displayed normally on a browser etc., it's OK.
Create a program file for generation at the top of the server
directory created earlier.
The directory should look like this.
.
├── docker-compose.yml
├── Dockerfile
├── images
├── main.py
├── Pipfile
├── Pipfile.lock
├── README.md
└── server
The module installed by pipenv is Selenium.
pipenv install selenium
The Dockerfile for image generation is as follows. This also requires Google Chrome to be installed with it.
Dockerfile
FROM python:3.8
COPY main.py /main.py
COPY Pipfile /Pipfile
COPY Pipfile.lock /Pipfile.lock
RUN apt-get update && apt-get install -y unzip
#install google-chrome, vim
RUN wget -q -O - https://dl-ssl.google.com/linux/linux_signing_key.pub | apt-key add && \
echo 'deb [arch=amd64] http://dl.google.com/linux/chrome/deb/ stable main' | tee /etc/apt/sources.list.d/google-chrome.list && \
apt-get update && \
apt-get install -y google-chrome-stable
RUN apt-get install -y vim
#install ChromeDriver
ADD https://chromedriver.storage.googleapis.com/84.0.4147.30/chromedriver_linux64.zip /opt/chrome/
RUN cd /opt/chrome/ && \
unzip chromedriver_linux64.zip
ENV PATH /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/opt/chrome
RUN pip install pipenv
RUN pipenv install --system --deploy
ʻADD https://chromedriver.storage.googleapis.com/84.0.4147.30/chromedriver_linux64.zip / opt / chrome /` requires a link to the current Chrome version
https://chromedriver.storage.googleapis.com/index.html
From, paste the link for the current version.
In addition, create docker-compose.yml
to connect the server container to this container.
docker-compose.yml
version: '3'
services:
server:
container_name: server
build:
context: server
dockerfile: Dockerfile
ports:
- '5000:5000'
tty: true
# restart: always
command: python3 run.py
main:
container_name: main
build: .
tty: true
# restart: always
links:
- server
volumes:
- ./images/:/images/
command: python3 main.py
The important thing here is that if you want to use the generated image outside of Docker, you need to specify the directory to save it in volumes
.
If you look up main.py
as a capture method for Selenium, you will find a lot, but this time we will create it like this.
main.py
import os
from selenium import webdriver
def main():
image_save_path = os.path.join('images', 'image.png')
text = 'Hello'
captcha(image_save_path, text)
def captcha(image_save_path: str, text: str) -> None:
url = f'http://server:5000/?text={text}'
options = webdriver.ChromeOptions()
options.add_argument('--headless')
options.add_argument('--no-sandbox')
driver = webdriver.Chrome(options=options)
driver.set_window_size(1920, 1080)
driver.execute_script("document.body.style.zoom='100%'")
driver.get(url)
driver.implicitly_wait(3)
driver.save_screenshot(image_save_path)
driver.quit()
if __name__ == "__main__":
main()
docker-compose up
If the images are actually generated in the ʻimages` directory, it is successful.
Source code: https://github.com/yuto51942/image-generate
The image is generated in the same way for Earthquake-alert that I recently made as a hobby, so please take a look. I also want Star.
You may be able to generate images with other methods, but I think this method is the most free way to generate various images. Please, try it.
Recommended Posts