heroku上のPython/flask環境を構築し、ローカルに開発環境構築まで

# はじめに
Paasサービスのherokuを使ってwebアプリを構築する機会があり、そのメモ的なもの。
この記事は、Mac上を開発を行う環境とし、herokuを本番環境として扱った例になります。

# 環境
macOS Monterey 12.2.1
homebrew 3.5.10
Python 3.10.6
git 2.31.0

# herokuとは
まずHerokuとはなんですかということですが。。。

Herokuはアプリの構築、提供、監視、スケールに役立つクラウドプラットフォームで、アイデアを出してから運用を開始するまでのプロセスを迅速に進めることが可能です。また、インフラストラクチャの管理の問題からも解放されます。

だそうです。

つまりサーバはherokuが管理し、我々はアプリケーションだけに意識を置くことができる。

残念なのが無料で使える期間がもうすぐ終わるということ。。。

# 前提作業
前提条件は以下
- homebrewインストール済（まだの方は[こちら](https://qiita.com/ukei2021/items/51cdc9fbd53428708fea)）
- Python/pipインストール済（まだの方は[こちら](https://qiita.com/ukei2021/items/2920ebeefc806714b812)）
- GitClientインストール済
- herokuアカウント登録済（[こちらで普通に登録しましょう](https://id.heroku.com)）

# 作業
ではやっていきましょう。
## homebrewでherokuClIのインストール
brewコマンドでインストールします。
homebrew未インストール方は[こちら](https://qiita.com/ukei2021/items/51cdc9fbd53428708fea)
```
$ brew tap heroku/brew && brew install heroku
```

## herokuコマンドでログイン
下記コマンドをターミナルで実行
```
$ heroku login
```
そうすると以下のようなものが出ますので、Enterを押しておきましょう
```
heroku: Press any key to open up the browser to login or q to exit: 
```
そうするとブラウザが勝手に開き以下の画面が表示されます。
![picture006.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1032988/8161db63-deb2-3ae8-f31d-4bf05baf6de8.png)
「Log In」を押して
この画面が表示されたら登録したユーザ名とパスワードを入力しましょう。
![picture007.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1032988/f406d630-f945-08b0-e639-345edaaa5400.png)

そうすると以下の表示になりますのでターミナルに戻ると・・・
![picture008.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1032988/6242370f-07ec-9a61-ae5f-628f4dd4dc9e.png)

```
Logging in... done
Logged in as xxxxxxx@example.com
```
となればログインオッケーです。

## herokuにアプリ作成
heroku上にアプリケーション（置き場）を作成します
```
$ heroku create     
Creating app... done, ⬢ fathomless-sea-24665
https://fathomless-sea-24665.herokuapp.com/ | https://git.heroku.com/fathomless-sea-24665.git
```
作成できたかの確認
```
$ heroku apps
=== xxxxxxx@example.com Apps
fathomless-sea-24665
```

## herokuのレポジトリへの連携
まず作業フォルダを作成
（ホームディレクトリの直下にtestというフォルダを作っています。）
```
$ mkdir ~/test
$ cd ~/test
```
そこにgitレポジトリを作り、herokuのレポジトリに追加（連携）します
```
$ git init 
$ git remote add heroku https://git.heroku.com/fathomless-sea-24665.git
```


## Flask等のPythonライブラリのインストール
pipでインストールします。
Python/pip未インストールは[こちら](https://qiita.com/ukei2021/items/2920ebeefc806714b812)
```
$ pip install flask
```
また、HTTPサーバをインストール
```
$ pip install gunicorn
```

そして移動してapp.pyを作成します。
```
$ cd ~/test
```

```app.py
from flask import Flask

app=Flask(__name__)

@app.route('/')
def login_get():
	return "Hello World"

if __name__ == '__main__':
	app.run(debug=True)
```

### ローカル実行
ローカルで実行させてみます。
```
$ flask run --debugger --reload
 * Debug mode: off
WARNING: This is a development server. Do not use it in a production deployment. Use a production WSGI server instead.
 * Running on http://127.0.0.1:5000
Press CTRL+C to quit
 * Restarting with stat
 * Debugger is active!
 * Debugger PIN: 931-090-321
```
http://127.0.0.1:5000
にアクセスしましょう
![スクリーンショット 2022-09-09 20.28.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1032988/da983c79-db5e-6bc2-0296-d4bf07cc1c29.png)
Hello Worldが表示されました。

開発環境としてはローカルでこのapp.pyを中心に構築していく想定です。
ただFlaskとしての挙動が知りたいだけならここまでで十分ですが、heroku

## 設定ファイル作成
heroku上で動作させるには以下のファイルが必要です。
- runtime.txt
- requirements.txt
- Procfile

以下のディレクトリに作成していきます。
```
$ cd ~/test
```

### runtime.txt
herokuで実行されるPythonのバージョンを以下のような形で記載します。
```runtime.txt
python-3.10.6
```
### requirements.txt
heroku上でpythonがインストールするパッケージを記載します。
基本的には以下のコマンドで作成できます。
```
pip freeze > requirements.txt
```
```requirements.txt
click==8.1.3
Flask==2.2.2
gunicorn==20.1.0
itsdangerous==2.1.2
Jinja2==3.1.2
joblib==1.1.0
MarkupSafe==2.1.1
numpy==1.23.2
pandas==1.4.4
python-dateutil==2.8.2
pytz==2022.2.1
scikit-learn==1.1.2
scipy==1.9.1
six==1.16.0
threadpoolctl==3.1.0
Werkzeug==2.2.2
```

### Procfile
unicorn(HTTPサーバ)のプロセスを定義します。
```bash:Procfile
web: gunicorn app:app --log-file -
```

## herokuへのデプロイ
デプロイはherokuレポジトリへpushすることです。
なのでpushしてあげましょう。
git addとcommit
```
$ git add .
$ git commit -m "update"
[master (root-commit) c2194ce] update
 4 files changed, 34 insertions(+)
 create mode 100644 Procfile
 create mode 100644 app.py
 create mode 100644 requirements.txt
 create mode 100644 runtime.txt
```
git push
```
$ git push heroku master                       
Enumerating objects: 11, done.
Counting objects: 100% (11/11), done.
Delta compression using up to 8 threads
Compressing objects: 100% (7/7), done.
Writing objects: 100% (11/11), 1.05 KiB | 538.00 KiB/s, done.
Total 11 (delta 1), reused 0 (delta 0), pack-reused 0
remote: Compressing source files... done.
remote: Building source:
~~~~~~~~~~~~中略~~~~~~~~~~~~
remote: 
remote: Verifying deploy.... done.
To https://git.heroku.com/fathomless-sea-24665.git
 * [new branch]      master -> master
```
runtime.txtを含んでないとエラーになったので気を付けてください。

その後以下のコマンドでネット上に公開できます。（HTTPプロセスの起動）
```
heroku open
```
![picture010.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1032988/11c30217-fa55-818f-19d9-9ba5aad11cae.png)

アクセスURLは
```
https://アプリ名.herokuapp.com
```
となっているようです。

ここまでがHerokuへデプロイ/公開までになります。





# おまけ
## herokuレポジトリへの操作
herokuレポジトリへの基本的な操作のみ以下に記載しておきます。
### heroku上のレポジトリにpush
```
$ echo "hoge" > test
$ git add .   
$ git commit -m "first commit"
$ git push heroku master
```

### heroku上のレポジトリをclone
```
$ heroku git:clone --app fathomless-sea-24665
```

### heroku上のレポジトリからpull
```
$ git fetch
$ git pull heroku master
```


# 参考文献
[Heroku CLIのインストール方法](https://labo.kon-ruri.co.jp/heroku-cli-install/)
[Heroku にある既存のアプリを git clone する](https://obel.hatenablog.jp/entry/20180101/1514774203)