IT社員3人組によるリレーブログ

某IT企業に勤める同期3人が、日常で思ったことを記録していきます (twitter: @go_mount_blog)

Flask + uWSGIをGAEでデプロイした話

けいです。

 

最近、pythonベースでwebサイトを作成したのですが、その際にいくつかつまづいた箇所があったので記事にしました。

(割と技術ベースな話になります)

 

ちなみに作成したサイトはこんな感じです。

芸能人の好感度をAIで分析したサイトで、作成した背景もブログでまとめているので是非見てください。

 

f:id:go-mount:20200128150700p:plain

f:id:go-mount:20200128150909p:plain

 

ai-net-judge.com

go-mount.hatenablog.com

 

Flask + uWSGI + GAEの組み合わせを選んだ理由

組み合わせを選んだ話は、サイトの要件とほぼ同義なので、要件の話からしていきます。

 

要件を箇条書きでざっと記載します。

  1. フロントエンドもバックエンドもある程度自前で作成したい
  2. pythonで記載したい
  3. GCPGoogle Cloud Platform)を使いたい

 

1. フロントエンドとバックエンドを自前で作成したい

今回の前提みたいな話です。

今回作成するサイトでは、データベースと連携したり、webサイト自体をhtml, css, jsで作ったりする必要があったので、webフレームワークを使いました。

 

2. Pythonで記載したい

Flaskを採用した理由です。

単純にサイトを作成するメンバーが、Pythonを使える人が多かったのでPythonで書けるwebフレームワークを選びました。

 

DjangoPythonだけど...って思われる方もいると思います。

そこは特に深くは考えていませんが、今回のサイトの実装内容的にDjangoだと機能がtoo muchだったので軽量なFlaskにしました。

 

3. GCPを使いたい

これは、GCPを勉強してみたかったからです。

ぼくはAWSの資格は持っていたのですが、GCPの資格も取得したかったので、今回はGCPのGAE(Google App Engine)を使いました。

 

ちなみに、サイトを作成している途中にGCPの資格を取得しました。

資格はProfessional Cloud Architectです。(詳細は別途記事にする予定です)

 

サイトの作成にあたって、GCPを勉強したのですが、下の本が体系的にまとまっていておすすめです。

 

 

最後にuWSGIを選んだ理由は、正直特にありません。

GAEでは、Gunicorn(uWSGIと同じサーバー)を推しているようですが、チャレンジということでuWSGIを使いました。

(全体的にuWSGI+GAEが少ないので、本サイトを参考にしてみてください)

 

実装でつまづいたところ

さて、ここからはそれぞれを実装するうえでつまずいた箇所を記載していきます。

 

Flaskの実装

まず、簡単にFlaskについて説明します。

 

Flaskは先でも述べたWebフレームワークの1つで、HTMLリクエストに対して様々な制御を加えることができます。

基本的には、https://www.xxx.com/みたいなリクエストを受け付けて、htmlファイルを返します。

(HTTPの仕組みは知っているものとして説明しています)

 

f:id:go-mount:20200201195157p:plain

1. HTMLを返す部分

 

上記は本サイトのメインページを返す部分です。

@app.route('/')のカッコ内は、URLの末尾の条件を表しています。

 

例えば、@app.route('/subpage')とした場合、https://www.xxx.com/subpageというリクエストが来たときの処理をその後に記述します。

 

次に、returnの行の「render_template」関数によってhtmlファイルをクライアントに返しています。このとき、index.htmlにFlask上でpythonで生成したhtmlコードやjava scriptを埋め込むことができます。

html=htmlとなっている部分がその箇所です。(詳細はjinja3で検索してみてください)

 

また、index.htmlやCSSJavascriptを置くフォルダ構造が少々特徴的です。

f:id:go-mount:20200201205253p:plain

Flaskのフォルダ構造

 

CSSフォルダを構造化したい場合

Flaskは、デフォルトではCSSjavascriptのファイルを構造化することができません。

(構造化とは、CSSファイルがたくさんある場合に種類ごとにフォルダ分けすることです)

 

HTMLをbootstrapを使って書くときは、通常CSSJavascriptのファイルはフォルダ分けがされているので、staticフォルダでサブフォルダを切れないのは不便です。

 

Flaskでサブフォルダを切るためには、Blueprint機能を使用します。

Blueprint機能は、フォルダをFlaskに認識させる機能です。(Linuxでいうパスを通す作業のことです)

 

Blueprintの設定は以下です。

 

まず、Main.pyでblueprint関数を記載する

 

f:id:go-mount:20200201214509p:plain

main.pyにblueprint関数を記載

 

このとき、blueprintのモジュールをインポートすること。

 

f:id:go-mount:20200201214612p:plain

Blueprintのモジュールをインポート

 

次に、「setBlueprint.py」というファイルを作成し、ルートフォルダのすぐ下に置き、下記を記載する。

ここでは、staticフォルダのすぐ下に「js」フォルダを作成したい場合の設定です。

 

f:id:go-mount:20200201214241p:plain

Blueprintの設定

以上の設定で、サブフォルダをFlaskが認識できるようになります。

 

webだと意外に情報が少ないので、けっこう書籍がおすすめです。

 

 

uWSGIの実装

uWSGIの設定は簡単です。

uWSGIをインストールし、以下の設定ファイルを作成するだけです。

ちなみに、私の場合はpip3でuWSGI==2.0.18をインストールしました。

 

以下のmyapp.iniファイルを作成し、Flaskのルートフォルダに格納します。

 

f:id:go-mount:20200202144414p:plain

uWSGIの設定ファイル

GAEの実装

最後に、Google App Engineの設定をしていきます。

 

Google App Engineとは?

はじめに、Google App Engineについて簡単に触れたいと思います。

Google App Engineは、Googleが提供する仮想マシンのサービスの1つです。(AWSでいう、Amazon Beanstalkのようなサービスです)

 

仮想マシンのサービスとして、GCPではGoogle Compute Engine、Google Kubernetes Engineなどいくつか提供していますが、Google App Engineは、PaaSサービスであるため、開発者はアプリケーションを作成してデプロイするだけで良いという強みがあります。

 

実際使ってみた印象としては、デプロイするまでの準備に若干手間がかかったものの、それ以降は非常に使い勝手の良いサービスです。

 

Google App Engineの設定

設定は意外にもシンプルです。

自分はけっこう時間がかかってしまったのですが、それはuWSGIのGAEとの設定のドキュメントがあまりなかったためです。

 

GAEの設定は以下3つのファイルを編集します。

 

1. app.yamlの設定

GAEではYAML形式のファイルで実行するファイルや、オプションを設定します。

今回は最もシンプルな、uWSGIの設定のみを記載しています。

 

Google App Engineインスタンスのスケーリング設定もこのファイルで実施できます。

 

f:id:go-mount:20200202140534p:plain

app.yamlの設定

2. requirements.txtの設定

Google App Engineでは、デプロイするアプリケーションの実行に必要なパッケージをこのrequirements.txtに書いてある通り用意します。

 

このファイルは、python使っている方なら、pip freezeコマンドで簡単に作成できます。

先ほどのapp.yamlファイルとともに、ルートフォルダに格納します。

 

Google App Engineのデプロイ

デプロイは非常に簡単です。

下記のコマンドを打つだけです。

f:id:go-mount:20200202150624p:plain

デプロイコマンド

 

GAEでデプロイするためには、SDKのインストールや、GCPのコンソール上での操作が事前に必要となりますが、簡単なので公式ページの操作を参考に実施ください。

 

 

今回の記事は以上です。

今回の記事が皆さんのトラブルシュートや、Flask、GAEを使うきっかけになれば幸いです。