flask學習筆記之大型程式的結構

2021-09-01 16:12:18 字數 4536 閱讀 7652

我們將介紹一種使用包和模組組織大型程式的方式。

flask 程式的基本結構如示例 7-1 所示。

這種結構有4個頂級資料夾:

2) migrations資料夾包含資料庫遷移指令碼

3)單元測試編寫在tests包中

4)venv資料夾包含python虛擬環境

同時還建立了一些新檔案:

程式經常需要設定多個配置。

使用層次結構的配置類。

#config.py:程式的配置

import os

basedir = os.path.abspath(os.path.dirname(__file__))

class config:

secret_key = os.environ.get('secret_key') or 'hard to guess string'

sqlalchemy_commit_on_teardown = true

flasky_mail_subject_prefix = '[flasky]'

flasky_mail_sender = 'flasky admin '

flasky_admin = os.environ.get('flasky_admin')

@staticmethod

pass

class developmentconfig(config):

debug = true

mail_server = 'smtp.googlemail.com'

mail_port = 587

mail_use_tls = true

mail_username = os.environ.get('mail_username')

mail_password = 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:///' + os.path.join(base.dir, 'data-test.sqlite')

class productionconfig(config):

sqlalchemy_database_uri = os.environ.get('database_url') or 'sqlite:///' + os.path.join(base.dir, 'data.sqlite')

config =

基類config中包含通用配置,子類分別定義專用的配置。

secret_key從環境變數中匯入,這樣配置方式更靈活且更安全。

在3個子類中,sqlalchemy_database_uri變數都指定了不同的值,這樣程式就可在不同的環境中執行,每個環境使用不同的資料庫。

config字典中註冊了不同的配置環境,而且還註冊了乙個預設配置。

程式包(可改用程式專用名字)用來儲存程式的所有**、模板和靜態檔案。

在單個檔案中開發程式時,有個很大的缺點,因為程式在全域性作用域中建立,所以無法動態修改配置。

這個問題的解決方法是延遲建立程式例項,把建立過程移到可顯示呼叫的工廠函式中。

from flask import flask, render_template

from flask.ext.bootstrap import bootstrap

from flask.ext.mail import mail

from flask.ext.moment import moment

from flask.ext.sqlalchemy import sqlalchemy

from config import config

bootstrap = bootstrap()

mail = mail()

moment = moment()

db = sqlalchemy()

# 附加路由和自定義的錯誤頁面

工廠函式返回建立的程式例項,現在的工廠函式還缺少路由和自定義的錯誤頁面處理程式。

為了獲得最大的靈活性,程式建立了乙個包,用於儲存藍本。

from flask import blueprint

main = blueprint('main', __name__)#例項化乙個blueprint類物件來建立藍本

from . import views, errors

blueprint類有兩個必須制定的引數:藍本的名字和藍本所在的包或模組。和程式一樣,大多數情況下第二個引數使用python的__name__變數即可。

#...

from .main import main as main_blueprint

錯誤處理程式如下:

from flask import render_template

from . import main

def page_not_found(e)

return render_template(404.html), 404

def internal_server_error(e):

return render_template('500.html'), 500

藍本中的程式路由如下:

from datetime import datetime

from flask import render_template, session, redirect, url_for

from . import main]

from ./forms import nameform

form .. import db

from ../models import user

@main.route('/', methods=['get', 'post'])

def index():

form = nameform()

if form.validate_on_submit():

#....

return redirect(url_for('./index'))

return render_template('index.html', form=form, name=session.get('name'), known=session.get('known', false), current_time=datetime.utcnow())

在藍本中編寫檢視函式有兩點不同:第一,路由修飾器由藍本提供;第二,url_for()函式的用法不同。在普通檔案中,url_for()函式的第乙個引數是路由的端點名,在程式的路由中,預設為檢視函式的名字。

而在藍本中,flask會為藍本中的全部端點加上乙個命名空間,這樣就可以在不同的藍本中使用相同的端點名定義檢視函式,而不會產生衝突。命名空間就是藍本的名字,即blueprint建構函式的第乙個引數。所以使用url_for("main.index"),在藍本中可以簡寫省略藍本名,例如url_for('.index')。

頂級資料夾中的manage.py檔案用於啟動程式。

#manage.py:啟動指令碼

#!/usr/bin/env python

import os

from flask.ext.script import manager, shell

from flask.ext.migrate import migrate, migratecommand

def make_shell_context():

manager.add_command('shell', shell(make_context = make_shell_context))

manager.add_command('db', migratecommand)

if __name__=='__main__':

manager.run()

程式中必須包含乙個requirements.txt檔案,用於記錄所有依賴包及其精確地版本號。

pip freeze>requirements.txt

編寫兩個簡單的測試。

#tests/test_basics.py:單元測試

import unittest

class basicstestcase(unittest.testcase):

def setup(self):

db.create_all()

def teardown(self):

db.session.remove()

db.drop_all()

這個測試使用 python 標準庫中的 unittest 包編寫。 setup() 和 teardown() 方法分別在各測試前後執行,並且名字以 test_ 開頭的函式都作為測試執行。

Flask從入門到精通之大型程式的結構二

在單個檔案中開發程式很方便,但卻有個很大的缺點,因為程式在全域性作用域中建立,所以無法動態修改配置。執行指令碼時,程式例項已經建立,再修改配置為時已晚。這一點對單元測試尤其重要,因為有時為了提高測試覆蓋度,必須在不同的配置環境中執行程式。from flask import flask from fl...

Flask學習筆記

web 發展至今,特別是伺服器端,涉及到的知識 內容,非常廣泛。這對程式設計師的要求會越來越高。如果採用成熟,穩健的框架,那麼一些基礎的工作,比如,網路操作 資料庫訪問 會話管理等都可以讓框架來處理,那麼程式開發人員可以把精力放在具體的業務邏輯上面。使用web框架開發web應用程式可以降低開發難度,...

Flask 學習筆記

因為mac自帶了python2.7,所以這個文章是基於2.7版本的 依賴於兩個外部庫 werkzeug和jinjia2.werkzeug是乙個wsgi工具集,jinjia2負責渲染模版 2.安裝 1 mac osx或linux sudo pip install virtualenv mkdir my...