Flask中的SERVER_NAME主要做兩件事:
協助Flask在活動的請求(request)之外生成絕對URL(比如郵件中嵌入網站URL) 用于子域名支持很多人誤以為它可以做這兩件事之外的其它事情。
一、第一件事:絕對URL
我們知道,url_for默認情況下是生成相對URL,它有個參數_external,如果設置為真,則會生成一個絕對URL(就是HTTP開頭帶域名等信息的)。若不指定SERVER_NAME,默認使用當前活動的請求(request)來生成URL。
下面舉個例子演示一下:
# filename myapp.pyfrom flask import Flask, url_forapp = Flask(__name__)@app.route('/')def index(): return 'hello flask'@app.route('/test')def test(): return url_for('index', _external=True)if __name__ == '__main__': app.run(debug=True)
1.【情景1】通過瀏覽器訪問
app運行之后,在本地5000端口監聽。
(env) F:/tmp>python myapp.py * Running on http://127.0.0.1:5000/ * Restarting with reloader
若我們通過瀏覽器訪問http://127.0.0.1:5000/test,則返回的內容是:http://127.0.0.1:5000/。
若我們通過瀏覽器訪問http://localhost:5000/test,則返回的內容是:http://localhost:5000/。
可以看出,在未設置SERVER_NAME的情況下,url_for生成的絕對URL是依賴于請求的URL的。下面我們來看看不通過瀏覽器訪問的情況。
2.【情景2】非瀏覽器訪問
這個情景是指不存在request請求的情況。
我們通過Python Shell來模擬:
>>> from myapp import app>>> with app.app_context():... print url_for('index', _external=True)...
Traceback (most recent call last): File "<stdin>", line 2, in <module> File "F:/tmp/env/lib/site-packages/flask/helpers.py", line 287, in url_for raise RuntimeError('Application was not able to create a URL 'RuntimeError: Application was not able to create a URL adapter for request independent URL generation. You might be able to fix this by setting the SERVER_NAMEconfig variable.
上面的意思是說應用程序不能創建一個用于與request不相關的URL生成的URL適配器,可以通過設置SERVER_NAME來解決這個問題。
好,下面我們為SERVER_NAME設置一個值之后再試試:
>>> app.config['SERVER_NAME'] = 'example.com'>>> with app.app_context():... print url_for('index', _external=True)...
http://example.com/
PS: 一般SERVER_NAME設置為網站的域名。
在Flask-Mail相關的文章中有這么一段話:
許多Flask的擴展都是假定自己運行在一個活動的應用和請求上下文中,Flask-Mail的send函數使用到current_app這個上下文了,所以當mail.send()函數在一個線程中執行的時候需要人為的創建一個上下文,所有在send_async_email中使用了app.app_context()來創建一個上下文。
新聞熱點
疑難解答