Flask Web Development —— 模板(下)

作者 | ipython

4、鏈接

任何應(yīng)用程序都有多個路由,必然需要包含鏈接來連接不同的頁面,例如導(dǎo)航欄。

在模板中,對于簡單的路由直接寫URLs做鏈接是非?,嵥槁闊┑模o帶有變量部分的動態(tài)路由建立正確的URLs會變得更加復(fù)雜。此外,在代碼中顯式的寫URLs會在路由上造成不必要的依賴。如果路由重組,模板中的鏈接將被打斷而變得無法訪問。

為了避免這些問題,F(xiàn)lask提供url_for()函數(shù),它會根據(jù)存放在應(yīng)用程序中的URL映射信息來生成URLs。

其最簡單的用法,這個函數(shù)傳入視圖函數(shù)名(或通過app.add_url_route()定義的路由endpoint名)作為它的參數(shù),然后返回它的URL。例如,在當(dāng)前版本的hello.py調(diào)用url_for('index')將返回/。調(diào)用url_for('index', _external=True)將返回一個絕對URL,在該示例中為http://localhost:5000/。

注:相對URLs足以滿足生成鏈接來連接應(yīng)用程序不同的路由。絕對URLs只有在鏈接被用于web瀏覽器的外部才是必須的,例如通過郵件發(fā)送鏈接。

可以使用url_for()并傳遞動態(tài)部分作為關(guān)鍵字參數(shù)來生成動態(tài)URLs。例如,url_for('user', name='join', external=True)會返回http://localhost:5000/user/john。

url_for()可以不限參數(shù)的使用動態(tài)路由。函數(shù)會增加擴展參數(shù)給查詢字符串。例如url_for('index', page=2)會返回/?page=2。

5、靜態(tài)文件

Web應(yīng)用程序不僅僅是由Python代碼和模板組成。大部分的應(yīng)用程序會使用靜態(tài)文件,例如從HTML代碼中引用的圖片、JavaScript源文件和CSS。

你可能需要回憶一下,在第二章中檢查hello.py應(yīng)用程序的URL映射時,有一個static入口在里面。這也是為什么引用定義成/static/<filename>的靜態(tài)文件會被當(dāng)作特殊路由來對待。例如,一個url_for('static', filename='css/style.css', _external=True)調(diào)用會返回http://localhost:5000/static/css/styles.css。

在它的默認(rèn)配置中,F(xiàn)lask會在位于應(yīng)用程序根目錄下名為static的子目錄中尋找靜態(tài)文件??梢栽谶@個目錄下的子目錄組織管理文件。當(dāng)服務(wù)器收到來自之前示例的URL,它會產(chǎn)生一個響應(yīng)包含static/css/styles.css的文件內(nèi)容。

示例3-10展示應(yīng)用程序如何在基礎(chǔ)模板中包含favicon.icon圖標(biāo)并讓瀏覽器將其顯示在地址欄。

示例3-10. templates/base.html:favicon定義

{% block head %}
{{ super() }}
<link rel="shortcut icon" href="{{ url_for('static', filename = 'favicon.ico') }}"
type="image/x-icon">
<link rel="icon" href="{{ url_for('static', filename = 'favicon.ico') }}"
type="image/x-icon"> 
{% endblock %}

圖標(biāo)定義被插入在head塊里的最下面。注意super()是如何保留定義在基礎(chǔ)模板中塊的原始內(nèi)容的。

建議:如果你有克隆在GitHub上的應(yīng)用程序,你現(xiàn)在可以運行g(shù)it checkout 3d來切換到這個版本的應(yīng)用程序。

6、Flask-Moment中的本地化日期和時間

當(dāng)用戶工作在世界各個不同的地方,在web應(yīng)用程序中處理日期和時間就變成了一個比較重要的問題。

服務(wù)器使用統(tǒng)一的時間單位,和每個用戶的位置無關(guān),所以使用世界標(biāo)準(zhǔn)時間(UTC)。對于用戶,看到UTC格式的時間肯定會感到困惑,用戶總是希望看到根據(jù)當(dāng)?shù)亓?xí)慣顯示的日期和時間。

一個優(yōu)雅的解決方案是允許服務(wù)器只發(fā)送UTC時間給web瀏覽器,由瀏覽器轉(zhuǎn)為當(dāng)?shù)貢r間并渲染。Web瀏覽器在這個問題上做的更好,因為他們可以訪問用戶電腦的所在的時區(qū)和地區(qū)設(shè)置。

有一個優(yōu)秀的客戶端開源庫moment.js,用JavaScript編寫的,用于在瀏覽器上渲染日期和時間。Flask-Moment是一個集成moment.js到Jinja2模板的Flask擴展??梢酝ㄟ^pip來安裝:

(venv) $ pip install flask-moment

示例3-11展示擴展初始化。

示例3-11. hello.py:初始化Flask-Moment

from flask.ext.moment import Moment
moment = Moment(app)

Flask-Moment除了依賴moment.js外,還依賴jquery.js。這兩個庫需要直接包含在HTML文檔,這種情況下你可以選擇使用什么版本,或通過擴展提供的幫助函數(shù)來引用內(nèi)容分發(fā)網(wǎng)絡(luò)(CDN)的測試版本庫。因為Bootstrap已經(jīng)包含了jquery.js,所以只需要將moment.js增加到這個示例中。示例3-12展示這個庫是如何被加載到基礎(chǔ)模板scripts中的。

示例3-12. templates/base.html:導(dǎo)入moment.js庫

{% block scripts %}
{{ super() }}
{{ moment.include_moment() }}
{% endblock %}

為了可以使用時間戳,F(xiàn)lask-Moment創(chuàng)建moment類給模板使用。示例3-13傳遞current_time變量給模板去渲染。

示例3-13. hello.py:增加datetime變量

from datetime import datetime

@app.route('/') 
def index():
    return render_template('index.html', current_time=datetime.utcnow())

示例3-14展示如何在模板中渲染current_time。

示例3-14. templates/index.html:使用Flask-Moment渲染時間戳

<p>The local date and time is {{ moment(current_time).format('LLL') }}.</p>
<p>That was {{ moment(current_time).fromNow(refresh=True) }}</p>

format('LLL')根據(jù)客戶端電腦的時區(qū)和地區(qū)設(shè)置來格式化顯示日期和時間。參數(shù)決定了渲染的樣式,從L到LLL對應(yīng)不同的詳細(xì)級別。format()函數(shù)還可以接受自定義的格式說明符。

fromNow()渲染樣式顯示在第二行,渲染一個相對時間戳并隨著時間的推移自動刷新它。最初這個時間戳將顯示為“幾秒鐘前”,但隨著時間的流逝刷新選項將保持更新,所以如果你離開已打開幾分鐘的頁面你會看到文本變?yōu)椤耙环昼娗啊?,然后“兩分鐘前”,等等?/p>

建議:如果你有克隆在GitHub上的應(yīng)用程序,你現(xiàn)在可以運行g(shù)it checkout 3e來切換到這個版本的應(yīng)用程序。

Flask-Moment通過moment.js實現(xiàn)了format(),fromNow(),fromTime(), calendar(),valueOf()和unix()方法。查閱文檔,了解提供的所有格式化選項。

注:Flask-Moment假定時間戳由服務(wù)端應(yīng)用程序中表示成UTC格式的“naive”datetime對象來處理。參閱標(biāo)準(zhǔn)庫datetime包文檔關(guān)于date和time對象的navie和aware信息。

Flask-Moment渲染的時間戳可以本地化成多種語言。在模板中通過傳遞語言代碼到lang()函數(shù)來選擇語言:

{{ moment.lang('es') }}

學(xué)完本章中討論的所有技術(shù),您應(yīng)該能夠為您的應(yīng)用程序構(gòu)建現(xiàn)代、用戶友好的網(wǎng)頁。下一章涉及模板沒有討論的一個方面:如何通過web表單與用戶進行交互。

原文轉(zhuǎn)自:https://segmentfault.com/a/1190000000760163

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 22年12月更新:個人網(wǎng)站關(guān)停,如果仍舊對舊教程有興趣參考 Github 的markdown內(nèi)容[https://...
    tangyefei閱讀 35,421評論 22 257
  • 第三章 模板 序 為什么要分離 易于維護的代碼,關(guān)鍵在于保持簡單的結(jié)構(gòu)。而我們之前編寫的hello.py雖然簡單,...
    科幻經(jīng)典閱讀 1,612評論 0 6
  • 第三章 模板(Templates) 編寫易于維護的程序的要點在于書寫干凈、良好結(jié)構(gòu)的代碼。你以前所見的代碼都過于...
    易木成華閱讀 1,258評論 0 2
  • Spring Cloud為開發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見模式的工具(例如配置管理,服務(wù)發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,644評論 19 139
  • 這幾天想學(xué)新東西,就看了flask框架,本身對python不太了解,網(wǎng)上的很多教程看了,總是在某些地方卡住。翻到一...
    易木成華閱讀 2,403評論 0 11

友情鏈接更多精彩內(nèi)容