標籤:

Flask學習筆記(一)

Flask的用途

Flask是一個Python編寫的Web微框架。 他可以用來構建API。

什麼是API?API是一些預先定義的函數,目的是提供應用程序與開發人員基於某軟體或硬體得以訪問一組常式的能力,而又無需訪問源碼。 也可以通俗的將就是介面,為客戶提供服務的方式。

什麼是Web應用

瀏覽器發送一個HTTP請求,伺服器收到請求,生成一個HTML文件,伺服器把HTML文檔作為HTTP響應的Body發送給瀏覽器。瀏覽器收到HTTP響應,從HTTP Body取出HTML文檔並顯示。

什麼是WSGI

WSGI,全稱 Web Server Gateway Interface,或者 Python Web Server Gateway Interface ,是為 Python 語言定義的 Web 伺服器和 Web 應用程序或框架之間的一種簡單而通用的介面。 WSGI就像是一座橋樑,一邊連著web伺服器,另一邊連著用戶的應用。但是呢,這個橋的功能很弱,有時候還需要別的橋來幫忙才能進行處理。WSGI 的作用如圖所示:

WSGI有兩方:「伺服器」或「網關」一方,以及「應用程序」或「應用框架」一方。服務方調用應用方,提供環境信息,以及一個回調函數(提供給應用程序用來將消息頭傳遞給伺服器方),並接收Web內容作為返回值。

「微」的含義

「微」表示Flask的目標是保持核心簡單而又可擴展。

Flask的設計思路

在Flask中,中心調用對象是一個Flask類的示例。每個Flask應用都必須創建一個該類的實例,並且把模塊的名稱傳遞給該實例。

使用對象的原因: 1. 顯式對象可以保證實例的唯一性。 2. Flask需要包的名稱,當在創建一個Flask實例時,通常會傳遞一個name作為包的名稱。Flask根據包的名稱來載入與模塊相關的正確資源。 3. 顯式往往比隱式好.z這個對象就是你的WSGI應用,你不必再記住其他東西。如果你要實現一個 WSGI 中間件,那麼只要封裝它就可以了

實現一個小應用

from flask import Flask
app=Flask(__name__)

@app.route(/)
def hello_world():
return "Hello World"
if __name__==__main__:
app.run()

啟動該py文件

$ python hello.py
*Running on http://127.0.0.1:5000/

訪問127.0.0.1:5000/可以看到Hello World了

分析上面代碼做了什麼: 1. 導入了Flask類,這個類的實例會是我們的WSGI應用程序 2. 創建該類的實例。 3. 使用route()裝飾器告訴Flask什麼樣的URL能出發我們的函數 4. 這個函數的名字也在生成URL時被特定的函數採用,這個函數返回我們想要顯示在用戶瀏覽器中的信息 5. 最後用run()函數來讓應用運行在本地伺服器上

如果要外部訪問的伺服器

上述運行的伺服器只能在自己的計算機上訪問,網路中其他的地方都不能訪問。在調試模式下,用戶可以在你的計算機上執行任意Python代碼。因此,這個行為是默認的。 如果禁用了debug或信任所在網路的用戶,你可以簡單修改調用run()的方法使你的伺服器公開可用,如下:

app.run(host=0.0.0.0)

這會讓操作系統監聽所有公網ip

調試模式

雖然run()方法適用於啟動本地的開發伺服器,但是每次修改代碼後都要手動重啟,這樣不夠優雅,Flask可以做到更好。如果啟用了調試支持,伺服器會在代碼修改後自動重新載入

有兩種途徑來啟用調試模式。

app.debug=True
app.run()

------
app.run(debug=True)

路由

何為路由

顧名思義就是一條路徑,這條路引領 url 從瀏覽器到WSGI伺服器,然後將處理結果返回到Browser。

在 Flask 框架中 ,路由的作用就是為用戶請求的URL找出其對應的處理函數 。

route()裝飾器把一個函數綁定到對應的URL上

註冊路由

Flask 框架中: 根據HTTP請求的URL在路由表中尋找對應的URL規則,找到對應的視圖函數,並將視圖函數的執行結果返回給WSGI伺服器。註:Flask封裝了一個簡單的開發用的WSGI伺服器,調用run函數時,該伺服器啟動。

其實,在Flask裡邊有一個中轉的機制---------endpoint

兩種路由方式

  1. 調用add_url_route()為函數指定一個路由

def test():
return this is test
app.add_url_route(/test,view_func=test)

  1. 用 route 裝飾器將一個url規則綁定到一個視圖函數上

@app.route(/test)
def test():
return this is test

動態路由

要給 URL 添加變數部分,你可以把這些特殊的欄位標記為 , 這個部分將會作為命名參數傳遞到你的函數。規則可以用 指定一個可選的轉換器

@app.route(/user/<username>)
def show_user_profile(username):
# show the user profile for that user
return User %s % username

@app.route(/post/<int:post_id>)
def show_post(post_id):
# show the post with the given id, the id is an integer
return Post %d % post_id

轉換器有下面幾種: int 接受整數 float 接受浮點數 path 和默認的相似,但接受斜線

這裡解釋一下

假如我們要訪問四個文件,目錄結構如上圖所示

@app.route(/file/<fname>)
def v_file(fname):
fullname = os.path.join(/A/B,fname)
f = open(fullname)
content = f.read()
f.close()
return cnt

測試結果表明,/file/a.txt和/file/b.txt都沒有問題,但是/file/C/c.txt和 /file/C/d.txt卻會失敗。 這是因為,默認情況下,在URL規則中的變數被視為不包含/的字元串。/file/C/c.txt 是沒有辦法匹配URL規則/file/的。 如果這裡改為path,則四個文件都可以訪問到

@app.route(/file/<path:fname>)
def v_file(fname):
fullname = os.path.join(/A/B,fname)
f = open(fullname)
content = f.read()
f.close()
return cnt

添加HTTP方法

HTTP有許多不同的訪問 URL 方法。默認情況下,路由只回應 GET 請求,但是通過 route() 裝飾器傳遞 methods 參數可以改變這個行為。例如:

@app.route(/login, methods=[GET, POST])
def login():
if request.method == POST:
do_the_login()
else:
show_the_login_form()

靜態目錄路由

當創建應用實例時,Flask將自動添加一條靜態目錄路由,其訪問點 始終被設置為static,URL規則默認被設置為/static,本地路徑默認被 設置為應用文件夾下的static子文件夾

改變默認的本地路徑 :可以在創建應用對象時使用關鍵字參數static_folder改變 默認的靜態文件夾。例如,你的靜態文件都存放在應用下的assets目錄下, 那麼可以按如下的方式創建應用對象:

app = Flask(name,static_folder=assets)

url_for函數

url_for() 函數最簡單的用法是以視圖函數名(或者app.add_url_route() 定義路由時使用的端點名)作為參數,返回對應的URL。例如,在當前程序中調用url_for(index) 得到的結果是/。調用url_for(index, _ external=True) 返回的則是絕對地址,在這個示例中是http://localhost:5000/

參數分別是 視圖函數 、變數、參數

print url_for(A,name=B,format=c)

輸出

A/B?format=c

下面這個使用_anchor關鍵字可以為生成的URL添加錨點

print url_for(A,_anchor=d)

輸出

/A#d

使用 render_template() 方法來渲染模板。Flask 會在 templates 文件夾里尋找模板。

@main.route(/, methods=[GET, POST])
def index():
return render_template(main/index.html)

這裡不再細講,url_for函數有其他功能, 1. 傳入url_for() 的關鍵字參數不僅限於動態路由中的參數。函數能將任何額外參數添加到查詢字元串中。例如,url_for(index, page=2) 的返回結果是/?page=2。 2. 通過 路由.視圖函數 可以定位到其他界面,例如

<a href="{{ url_for(main.index) }}">首頁</a>

例子

這裡是一些基本的例子:

app.route(/)
def index():
return Index Page

@app.route(/hello)
def hello():
return Hello World

但是,不僅如此!你可以構造含有動態部分的URL,也可以在一個函數上附著多個規則

參考文獻

  1. jianshu.com/p/7adc30e8c
  2. dormousehole.readthedocs.io

推薦閱讀:

Flask 單元測試中遇到的資料庫異常
django + etcd + confd 配置管理平台
寫一本Flask入門教程
《Flask 入門教程》第 10 章:組織你的代碼

TAG:Flask |