国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁(yè) > 編程 > Python > 正文

在Python中使用Mako模版庫(kù)的簡(jiǎn)單教程

2019-11-25 17:48:09
字體:
來(lái)源:轉(zhuǎn)載
供稿:網(wǎng)友

Mako是一個(gè)高性能的Python模板庫(kù),它的語(yǔ)法和API借鑒了很多其他的模板庫(kù),如Django、Jinja2等等。
基本用法

創(chuàng)建模板并渲染它的最基本的方法是使用 Template 類:
 

from mako.template import Templatet = Template('hello world!')print t.render()

傳給 Template 的文本參數(shù)被編譯為一個(gè)Python模塊。模塊包含一個(gè) render_body() 函數(shù),它產(chǎn)生模板的輸出。調(diào)用 render() 方法時(shí),Mako建立了一個(gè)模板的運(yùn)行環(huán)境,并調(diào)用 render_body() 函數(shù),把輸出保存到緩沖,返回它的字符串內(nèi)容。
render_body() 函數(shù)中可以訪問(wèn)一個(gè)變量集。可以向 render() 方法發(fā)送額外的關(guān)鍵詞參數(shù)來(lái)指定這些變量:
 

from mako.template import Templatet = Template('hello, ${name}!')print t.render(name='yeolar')

render() 方法使Mako創(chuàng)建一個(gè) Context 對(duì)象,它存儲(chǔ)模板可以訪問(wèn)的所有變量和一個(gè)用來(lái)保存輸出的緩沖。也可以自己創(chuàng)建 Context ,用 render_context() 方法使模板用它來(lái)渲染:
 

from mako.template import Templatefrom mako.runtime import Contextfrom StringIO import StringIOt = Template('hello, ${name}!')buf = StringIO()c = Context(buf, name='yeolar')t.render_context(c)print buf.getValue()

使用文件模板

Template 也可以從文件加載模板,使用 filename 參數(shù):
 

from mako.template import Templatet = Template(filename='/docs/tpl.txt')print t.render()

為了提高性能,從文件加載的 Template 還可以在文件系統(tǒng)中將生成的模塊緩存為一般的Python模塊文件(.py文件),這通過(guò)添加 module_directory 參數(shù)實(shí)現(xiàn):

from mako.template import Templatet = Template(filename='/docs/tpl.txt', module_directory='/tmp/mako_modules')print t.render()

上面的代碼渲染后,會(huì)創(chuàng)建一個(gè)/tmp/mako_modules/docs/tpl.txt.py文件,其中包含模塊的源代碼。下次同樣參數(shù)的 Template 創(chuàng)建時(shí),自動(dòng)重用這個(gè)模塊文件。
使用TemplateLookup

到現(xiàn)在的例子都是有關(guān)單個(gè) Template 對(duì)象的用法。如果模板中的代碼要定位其他模板資源,需要某種使用URI來(lái)找到它們的方法。這種需求是由 TemplateLookup 類來(lái)達(dá)到的。這個(gè)類通過(guò)傳入一個(gè)模板查找目錄的列表來(lái)構(gòu)造,然后作為關(guān)鍵詞參數(shù)傳給 Template 對(duì)象:
 

from mako.template import Templatefrom mako.lookup import TemplateLookuplookup = TemplateLookup(directories=['/docs'])t = Template('<%include file="header.txt" /> hello word!', lookup=lookup)

上面創(chuàng)建的模板中包含文件header.txt。為了查找header.txt,傳了一個(gè) TemplateLookup 對(duì)象給它。
通常,應(yīng)用會(huì)以文本文件形式在文件系統(tǒng)上存儲(chǔ)大部分或全部的模板。一個(gè)真正的應(yīng)用會(huì)直接從 TemplateLookup 取得它的模板,使用 get_template() 方法,它接受需要的模板的URI作為參數(shù):
 

from mako.template import Templatefrom mako.lookup import TemplateLookuplookup = TemplateLookup(directories=['/docs'], module_directory='/tmp/mako_modules')def serve_template(t_name, **kwargs):  t = lookup.get_template(t_name)  print t.render(**kwargs)

上面的例子中我們創(chuàng)建了一個(gè) TemplateLookup ,它從/docs目錄中查找模板,并把所有的模塊文件存儲(chǔ)到/tmp/mako_modules目錄中。通過(guò)將傳入的URI附加到每個(gè)查找目錄來(lái)定位模板,如傳遞/etc/beans/info.txt,將查找文件/docs/etc/beans/info.txt,如果沒(méi)找到將拋出 TopLevelNotFound 異常。
當(dāng)定位到模板的時(shí)候,傳給 get_template() 調(diào)用的URI也會(huì)作為 Template 的 uri 屬性。 Template 使用這個(gè)URI來(lái)得到模塊文件的名字,因此上面的例子中對(duì)/etc/beans/info.txt會(huì)創(chuàng)建模塊文件/tmp/mako_modules/etc/beans/info.txt.py。
設(shè)置收集的大小

TemplateLookup 還滿足將內(nèi)存中緩存的模板總數(shù)設(shè)為一個(gè)固定的值。默認(rèn)情況 TemplateLookup 大小是不限的。可以用 collection_size 參數(shù)指定一個(gè)固定值:
 

lookup = TemplateLookup(directories=['/docs'], module_directory='/tmp/mako_modules', collection_size=500)

上面的 lookup 將模板加載到內(nèi)存中的上限是500個(gè)。之后,它將使用LRU策略來(lái)清理替換模板。
設(shè)置文件系統(tǒng)檢查

TemplateLookup 的另一個(gè)重要標(biāo)志是 filesystem_checks 。默認(rèn)為 True ,每次 get_template() 方法返回一個(gè)模板,會(huì)比較原始模板文件的修改時(shí)間和模板的最近加載時(shí)間,如果文件更新,就重新加載和編譯模板。在生產(chǎn)系統(tǒng)中,將 filesystem_checks 設(shè)為 False 能獲得一些性能的提升。
使用Unicode和編碼

Template 和 TemplateLookup 可以設(shè)置 output_encoding 和 encoding_errors 參數(shù)來(lái)將輸出編碼為Python支持的編碼格式:
 

from mako.template import Templatefrom mako.lookup import TemplateLookuplookup = TemplateLookup(directories=['/docs'], output_encoding='utf-8', encoding_errors='replace')t = lookup.get_template('foo.txt')print t.render()

使用Python 3時(shí),如果設(shè)置了 output_encoding , render() 方法將返回一個(gè) bytes 對(duì)象,否則返回 string 。
render_unicode() 方法返回模板輸出為Python unicode 對(duì)象,Python 3為 string :
 

print t.render_unicode()

上面的方法沒(méi)有輸出編碼的參數(shù),可以自行編碼:
 

print t.render_unicode().encode('utf-8', 'replace')

注意Mako中模板的底層輸出流是Python Unicode對(duì)象。
處理異常

模板異常可能發(fā)生在兩個(gè)地方。一個(gè)是當(dāng)你查找、解析和編譯模板的時(shí)候,一個(gè)是運(yùn)行模板的時(shí)候。模板運(yùn)行中發(fā)生的異常會(huì)正常在產(chǎn)生問(wèn)題的Python代碼處拋出。Mako有自己的一組異常類,它們主要用于模板構(gòu)造的查找和編譯階段。Mako提供了一些庫(kù)例程用來(lái)對(duì)異常棧提供Mako的信息,并將異常輸出為文本或HTML格式。Python文件名、行號(hào)和代碼片段會(huì)被轉(zhuǎn)換為Mako模板文件名、行號(hào)和代碼片段。Mako模板模塊的行會(huì)被轉(zhuǎn)換為原始的模板文件對(duì)應(yīng)行。

text_error_template() 和 html_error_template() 函數(shù)用于格式化異常跟蹤。它們使用 sys.exc_info() 來(lái)得到最近拋出的異常。這些處理器的用法像下面這樣:
 

from mako import exceptionstry:  t = lookup.get_template(uri)  print t.render()except:  print exceptions.text_error_template().render()或者渲染為HTML:from mako import exceptionstry:  t = lookup.get_template(uri)  print t.render()except:  print exceptions.html_error_template().render()

html_error_template() 模板接受兩個(gè)選項(xiàng):指定 full=False 只渲染HTML的一節(jié),指定 css=False 關(guān)閉默認(rèn)的樣式表。如:
 

print exceptions.html_error_template().render(full=False)

HTML渲染函數(shù)也可以用 format_exceptions 標(biāo)志加到 Template 中。這種情況下,模板在渲染階段的任何異常在輸出中的結(jié)果都會(huì)替換為 html_error_template() 的輸出:
 

t = Template(filename='/foo/bar', format_exceptions=True)print t.render()

注意上面模板的編譯階段發(fā)生在構(gòu)造 Template 時(shí),沒(méi)有定義輸出流。因此查找、解析、編譯階段發(fā)生的異常正常情況下不會(huì)被處理,而是傳播下去。渲染前的追溯不包括Mako形式的行,這意味著渲染前和渲染中發(fā)生的異常會(huì)用不同的方式處理,因此 try/except 可能更常用。

錯(cuò)誤模板函數(shù)使用的底層對(duì)象是 RichTraceback 對(duì)象。這個(gè)對(duì)象也可以直接用來(lái)提供自定義的錯(cuò)誤視圖。下面是一個(gè)用法的樣例:
 

from mako.exceptions import RichTracebacktry:  t = lookup.get_template(uri)  print t.render()except:  traceback = RichTraceback()  for (filename, lineno, function, line) in traceback.traceback:    print 'File %s, line %s, in %s' % (filename, lineno, function)    print line, '/n'  print '%s: %s' % (str(traceback.error.__class__.__name__), traceback.error)

集成Mako
在Django中集成Mako

通過(guò)Django的中間件可以集成Mako。首先需要安裝django-mako模塊。
在Django項(xiàng)目的settings.py文件中,修改 MIDDLEWARE_CLASSES ,添加 djangomako.middleware.MakoMiddleware 。使用 render_to_response() 函數(shù)即可使用:
 

from djangomako.shortcuts import render_to_responsedef hello_view(request):  return render_to_response('hello.txt', {'name': 'yeolar'})

在Tornado中集成Mako

在Tornado中可以直接使用Mako,下面是一個(gè)使用示例:

import tornado.webimport mako.lookupimport mako.templateLOOK_UP = mako.lookup.TemplateLookup(    directories=[TEMPLATE_PATH], module_directory='/tmp/mako',    output_encoding='utf-8', encoding_errors='replace')class BaseHandler(tornado.web.RequestHandler):  def initialize(self, lookup=LOOK_UP):    '''Set template lookup object, Defalut is LOOK_UP'''    self._lookup = lookup  def render_string(self, filename, **kwargs):    '''Override render_string to use mako template.    Like tornado render_string method, this method    also pass request handler environment to template engine.    '''    try:      template = self._lookup.get_template(filename)      env_kwargs = dict(        handler = self,        request = self.request,        current_user = self.current_user,        locale = self.locale,        _ = self.locale.translate,        static_url = self.static_url,        xsrf_form_html = self.xsrf_form_html,        reverse_url = self.application.reverse_url,        )      env_kwargs.update(kwargs)      return template.render(**env_kwargs)    except:      # exception handler      pass  def render(self, filename, **kwargs):    self.finish(self.render_string(filename, **kwargs))
發(fā)表評(píng)論 共有條評(píng)論
用戶名: 密碼:
驗(yàn)證碼: 匿名發(fā)表
主站蜘蛛池模板: 普洱| 芦溪县| 沙洋县| 阿坝县| 光泽县| 桐梓县| 剑川县| 青铜峡市| 贵溪市| 巩留县| 本溪| 彭泽县| 涡阳县| 钦州市| 松江区| 磐石市| 江川县| 五家渠市| 且末县| 北票市| 行唐县| 土默特右旗| 陆良县| 溧水县| 利辛县| 青河县| 雷州市| 双峰县| 乌鲁木齐县| 郯城县| 五华县| 南宫市| 银川市| 德庆县| 台北县| 顺昌县| 右玉县| 万州区| 冀州市| 蓝山县| 林口县|