Flask入門その3：webサーバー初心者がFlask+mod-wsgiをmac/ubuntuで動かすまで

# やりたかったこと（できたこと）
* flaskアプリケーションをwebサーバーで公開したい
    * ローカルのmacで動作確認して、awsのec2（ubuntu）で公開

# 環境
* mac
    * OS High Sierra 10.13.1
    * Python 3.6.1
    * Apache 2.4.41
* aws ec2 t2.micro
    * Ubuntu 16.04.3 LTS
    * Python 3.5.2
    * Apache 2.4.18

# 事前知識
* Pythonは慣れてたけど、flaskは初めて
* バックエンドはほとんど知らない
    * webサーバーとパソコンって何が違うんだっけ？レベル
    * ローカルホスト、グローバルIP、プライベートIPとか良く分かんない

# 理解したこと（雰囲気）
※厳密ではないです

* Webサーバーって何ぞや？
    * ブラウザのアドレスバーに自分のIPアドレスが打ち込まれたときに、Webページを返すやつ
    * 他者からはグローバルIPで接続（LAN内ならプライベートIPで可）。自分はlocalhostでも可
    * パソコンにwebサーバーソフト（Apacheとか）入れて起動させれば、ほぼWebサーバー

* flaskだけではだめなのか？
    * 実はflaskだけでも公開は可能（flaskだけでHelloWorld表示できるのは、flaskがwebサーバー機能を持っているから）
    * あくまで確認用の最低限の機能であって、セキュリティーとか処理速度とかがダメなので非推奨らしい

* flask、Apache、wsgiの関係
    * Apacheはwebサーバーとして優秀。基本的なところはApacheにやらせたい
    * flaskにしかできないとこだけflaskにやらせたい
    * webサーバーとflaskとを上手く繋げて動作させるために、wsgiが必要。wsgiはミドルウェアとも考えられる
    * Apache用のwsgiは、mod-wsgiというモジュール名

# 手順概略
ハマって色々やりましたが、基本的な手順は下記（だったと思います）です
（途中で「gccが入ってないからインストールしろ」とか言われることはありえます）

* セットアップ
    * apache2、apache2-devのインストール
    * mod-wsgiのインストール（pip）
        * ec2ではpython3-devもインストールした

* 実行、動作確認
    * コマンドを打つ：mod_wsgi-express start-server
    * ブラウザで確認：　http://localhost:8000
        * ec2の場合は、macのブラウザなどから　http://【グローバルIP】:8000
    
ec2の場合はec2のサービスページにて下記作業が必要です
・セキュリティーグループでカスタムTCPでポート8000を設定
・グローバルIPを確認

各項目の詳細は下部にて。

# apache2、apache2-devのインストール
すでに入れてらっしゃる方も多いと思いますが、なければ入れましょう。
システムによって名前はちょっと違います。詳細は[pypiのmod-wsgi](https://pypi.org/project/mod-wsgi/)ページの「System Requirements」参照

# mod-wsgiのインストール（pip）
概略：GitHubのリポジトリをクローンし、setup.pyを使ってインストールします

GitHubのリポジトリ
https://github.com/GrahamDumpleton/mod_wsgi

をクローンして、そのディレクトリに移動し、下記実行します

```
python3 setup.py install
```
これでpip install mod-wsgiが出来る状態になります。なのでやりましょう

```
pip install mod-wsgi
```

## 注意点
* python2ではなく3が動くように注意しましょう
    * python --versionなどでpython3が動いているか確認
    * 自分のec2の場合は、mod-wsgiのインストールの際にpython3-devを入れないとダメでした
* 他の方法でインストールしたmod-wsgiは邪魔なのでアンイントールしましょう
    * 「apt-get install libapache2-mod-wsgi」などでインストールしたものなど
    * apacheのコンフィグファイルを書き換えていたら元に戻しましょう。実行時にエラーになることがあります
* エラーが出たら、読めるところは頑張って読みましょう
    * configファイルに余計な記述があるとか、モジュールが足りないとかは読めると思います

# 実行、動作確認
下記コマンド実行

```
mod_wsgi-express start-server
```

macのブラウザで「localhost:8000」にアクセス
エラーなくヘビのウィスキー漬けみたいなのが表示されればOKです
ただし、これはまだflask使ってないです
（「apachectl start」ではポート80なので、こちらは完全に別で動いているみたいですね）


##自分で作ったページを表示（flaskなし）

カレントディレクトリに下記ファイルを作ります

```python:test_1.py
def application(env, start_response):
    start_response('200 OK', [('Content-Type','text/html')])
    return [b"Hello World"]
```

そして

```
mod_wsgi-express start-server test_1.py
```
を実行して、localhost:8000を確認しましょう。Hello Worldが表示されていればokです

## flaskとの連携
最後に、flaskとの連携です。最小限の構成とします。
下記2ファイルをカレントディレクトリに作成します

```python:test_2.py
import sys
import os
sys.path.insert(0, os.getcwd())

from test_flask import app as application
```
```python:test_flask.py
from flask import Flask
app = Flask('any name')

@app.route("/")
def hello():
    return "Good Morning, flask"
```

そして

```
mod_wsgi-express start-server test_2.py
```
を実行し、localhost:8000にアクセスします。「Good Morning, flask」が表示されればOKです

ec2でも同じように動き、LAN外のスマホから 【グローバルIP】:8000 にアクセスして表示されることを確認できました
（ec2はセキュリティグループでポート設定するのを忘れていて手こずりましたが）

# 終わりに
以上でヤマは越えたと思います。
flaskとwebサーバーとの連携が想像以上に大変でしたが、これで今度こそ、flaskアプリをすぐに公開できる状態になったはず...！

# 参考
https://pypi.org/project/mod-wsgi/
https://modwsgi.readthedocs.io/en/develop/index.html