簡単なReact + Flask をExe化して動かしてみたいと思います。
コードの詳細が見たい方はこちらから見てください。
Flask + React でHello World
フォルダの階層はこんな感じです。
app
├── backend
└── main.py
└── frontend
├── node_modules
├── package.json
├── public
├── README.md
├── yarn.lock
└── src
├── その他省略...
├── App.js
└── index.js
FrontendのReact側
こちらはjsファイルをbuildして、できたファイルをbackend側に埋め込んでいきます。
ターミナル操作でapp/frontend/src下に移動しましょう。
$ cd app/frontend/src
buildを行います。
$ yarn build index.js
成功したらapp/frontend/buildフォルダが仕上がると思います。
このbuildフォルダをapp/backend下にコピぺしましょう。
いま現在のフォルダ構成はこんな感じになっています。(変更された場所に「← new」を入れてあります)
app
├── backend
├── build ← new
└── main.py
└── frontend
├── build ← new
├── node_modules
├── package.json
├── public
├── README.md
├── yarn.lock
└── src
├── その他省略...
├── App.js
└── index.js
BackendのFlask側
先ほどbuildしたのでapp/backend/build/index.htmlが出来てます。
そのindex.htmlを返すようにapp/backend/main.pyに変更を加えます。
import sys # 追加
from flask import Flask, request, make_response, jsonify, render_template # 編集
from flask_cors import CORS
# -- 追加 ここから ---------
ROUTE = sys.path[1] if 2 == len(sys.path) else '.'
TEMPLATES = ROUTE + '/build'
STATIC = ROUTE + '/build/static'
# -- ここまで ---------
app = Flask(name, static_folder=STATIC, template_folder=TEMPLATES) # 編集
CORS(app)
# -- 追加 ここから ---------
@app.route('/')
def index():
return render_template('index.html')
# -- ここまで ---------
@app.route('/hello', methods = ['GET'])
def hello():
text = 'Hello World'
response = {'result': text}
return make_response(jsonify(response))
@app.route('/helloworld', methods = ['GET', 'POST'])
def helloworld():
text = 'Hello World'
response = {'result': text}
return make_response(jsonify(response))
@app.route("/post", methods=['GET','POST'])
def parse():
data = request.get_json()
text = data['post_text']
response = {'result': text}
return make_response(jsonify(response))
if name == 'main':
app.run(debug=True, port=5000, threaded=True)
render_templateを追加して、index.htmlを返すよう編集しました。
少しコードの解説をしますと、
Exeで動く場合は実行される場所が違うのでif文で確認してます。
どこで実行されているかを確認するために、print(ROUTE)で確認してみてもいいかもです。
# -- 追加 ここから ---------
ROUTE = sys.path[1] if 2 == len(sys.path) else '.'
TEMPLATES = ROUTE + '/build'
STATIC = ROUTE + '/build/static'
# -- ここまで ---------
# print('ROUTE: ' + ROUTE)
これで準備完了です。
pyinstallerを使ってExe化します。
インストールがまだな方はinstallしてください。
$ pip install pyinstaller
ターミナル操作でapp/backendまで移動します。
$ cd ../../backend
main.pyをpyinstallerします。
$
pyinstaller -F --add-data "build:build" --onefile --clean main.py
最後の行に「3790 INFO: Building EXE from EXE-00.toc completed successfully.」と表示されたら成功です。
新たにapp/backend/dist/mainができます。
このmainファイルが実行可能なExeになっています。
あとはダブルクリックで実行して動かしてみるだけです。
無事に動けばこういう表示がされます。
* Serving Flask app "main" (lazy loading)
* Environment: production
WARNING: Do not use the development server in a production environment.
Use a production WSGI server instead.
* Debug mode: on
* Running on http://127.0.0.1:5000/ (Press CTRL+C to quit)
* Restarting with stat
Chrome等で、http://localhost:5000にアクセスしたらページが表示されるはずです。
最後に
pyinstallerの説明はこちらの方がもう少し詳しく載せてますので、うまくいかない場合等は見てみてください。
Flaskファイルをpyinstallerを使ってExe化してみよう
reactもexe化をする気でしたが、yarn build main.pyで出来た。
「react exe化」が、なかなか良い記事にヒットせずにググるのにも時間がかかりました。
「flask react exe」とかで検索してもなかなか出てこないので出来るまでが大変でした。
時間はかかったが、なんとか出来て良かった!!
以上で、React + Flask をExe化して動かしてみるでした。
コメント