flask web開發(四)--大型程式的結構
阿新 • • 發佈:2018-12-16
|-flasky |-app/ #四個頂級資料夾之一,flask程式儲存在這個裡面 |-templates/ |-static/ |-main/ |-__init__.py |-errors.py |-forms.py |-views.py #這是程式的路由 |__init__.py |-email.py |-models.py #資料庫模型 |-migrations/ #四個頂級資料夾之一,包含資料庫遷移指令碼 |-tests/ #四個頂級資料夾之一,單元測試編寫在這個包中 |-__init__.py |-test*.py |-venv/ #四個頂級資料夾之一,包含python flask的虛擬環境 |-requirements.txt #列出了所有依賴包,其他電腦中能生成相同的虛擬環境 |-config.py #儲存了配置資訊 |-manage.py #用於啟動程式和其他的程式任務,這個指令碼先建立程式,然後定義了配置
在大型的程式結構裡面,我們不像在單一指令碼中使用簡單的字典狀結構配置,而是使用層次結構的配置類:
import os basedir = os.path.abspath(os.path.dirname(__file__)) class Config: #這是基類,包含了通用設定 MAIL_USERNAME = os.environ.get('MAIL_USERNAME') #這裡不像單一腳本里面使用app.config['MAIL_USERNAME']=...這樣的字典結構 ... @staticmethod def init_app(app): #這個的引數是程式例項,在這個方法中,可以執行對當前環境的配置初始化。 pass class DevelopmentConfig(Config): #三個子類之一 DEBUG = True SQLALCHEMY_DATABASE_URI = os.environ.get('DEV_DATABASE_URL') or \ 'sqlite:///' + os.path.join(basedir, 'data-dev.sqlite') class TestingConfig(Config): #三個子類之一 TESTING = True SQLALCHEMY_DATABASE_URI = os.environ.get('TEST_DATABASE_URL') or \ 'sqlite://' class ProductionConfig(Config): #三個子類之一 SQLALCHEMY_DATABASE_URI = os.environ.get('DATABASE_URL') or \ 'sqlite:///' + os.path.join(basedir, 'data.sqlite') config = { #為四種模式分別指定一個配置類 'development': DevelopmentConfig, 'testing': TestingConfig, 'production': ProductionConfig, 'default': DevelopmentConfig }
基類config包含了通用的配置,子類分別定義了專用的配置,還可以繼續新增其他的配置類。
在上面設定的三個子類中,SQLALCHEMY_DATABASE_URI
變數分別制定了不同的值,這樣的目的是在每個環境中使用不同的資料庫。
app資料夾中 __init__.py
是程式包的構造檔案
構造檔案匯入大多數正在使用的flask拓展,裡面主要是放置:
from flask_sqlalchemy import SQLAlchemy #引入拓展 app = Flask(__name__) app.config.from_object('app.config.DevelopmentConfig') #引入配置 db = SQLAlchemy(app)
我們學習使用工廠函式,延遲建立程式例項,把建立過程移到可顯式呼叫的工廠函式中,這種方法不僅可以給指令碼留出配置程式的時間,還能夠建立多個程式例項。
from flask import Flask
from flask_bootstrap import Bootstrap
from flask_mail import Mail
from flask_moment import Moment
from flask_sqlalchemy import SQLAlchemy
from config import config
bootstrap = Bootstrap()
mail = Mail()
moment = Moment()
db = SQLAlchemy()
def create_app(config_name): #程式的工廠函式,一個引數,程式使用的配置名
app = Flask(__name__)
app.config.from_object(config[config_name]) #使用配置物件提供的方法直接從配置檔案裡面匯入配置
config[config_name].init_app(app)
bootstrap.init_app(app)
mail.init_app(app)
moment.init_app(app)
db.init_app(app)
from .main import main as main_blueprint
app.register_blueprint(main_blueprint) #藍本
return app
在藍本中實現程式的功能:
上面程式碼的註釋中可以看到藍本,現在程式在執行的時候才會建立,執行之後再使用app.route()定義路由就太晚了,所以使用藍本
藍本和程式類似,可以定義路由,但是在藍本中定義路由是休眠狀態,直到藍本註冊到程式上,路由才會真正生效。
建立藍本的方法:
from flask import Blueprint
main = Blueprint('main', __name__) #例項化一個藍本物件可以建立藍本
#第一個引數是藍本的名字,所以這個藍本叫做main
#第二個引數是藍本所在的包或者模組,大多數情況下使用__name__
from . import views, errors #view.py中儲存的是路由,所以這樣就把路由和藍本關聯了起來
藍本已經建立完畢,但是還需要將藍本註冊到程式上:
app.regisiter_blueprint(main_blueprint)
需求檔案: requirements.txt
用於記錄所有依賴包以及其精確的版本號
pip可以自動生成這個檔案:
pip freeze >requirements.txt
如果要建立這個虛擬環境的完全副本,可以安裝檔案內的依賴包建立一個新的虛擬環境:
pip install -r requirements.txt