在 Bottle 框架中,使用 route 修饰符将请求路由到与之对应的响应方法。这种特性非常适合路由请求与方法,但却给在 Bottle 中使用类来创建应用带了麻烦。
class SanYou: app = Bottle() @app.route('/') def homepage(self): return "Welcome!" app1 = SanYou().app app2 = SanYou.app
以上代码中无论是 app1 还是 app2,均返回 TypeError: homepage() takes exactly 1 argument (0 given)
这是因为在以上代码中 homepage 没有绑定到 SanYou 实例,即作为路由方法的修饰符,提前封装了实例方法 homepage ,造成 self 不能传入 homepage 方法中,于是 homepage 与 SanYou 实例没有绑定。
class SanYou: app = Bottle() @classmethod @app.route('/') def homepage(cls): return "Welcome!" app = SanYou.app
同理,以上代码中由于路由修饰符会封装类方法,造成 cls 无法传入 homepage 方法中,造成 homepage 不能成为类方法。注意,改变修饰符顺序也无法使得两个修饰符进行正确封装。
class SanYou: app = Bottle() @app.route('/') @classmethod def homepage(cls): return "Welcome!" app = SanYou.app
执行以上代码,你会得到 “TypeError: 'classmethod' object is not callable”。
因此,若想在类中使用修饰符进行路由,那只能使用静态方法,如:
# code 1 class SanYou: app = Bottle() @staticmethod @app.route('/') def homepage(): return "Welcome!" app = SanYou.app ---------------------------------------------- # code 2 class SanYou: app = Bottle() @app.route('/') def homepage(): return "Welcome!" app = SanYou.app
以上两种写法都会正确创建 app ,第一种是规范的静态方法写法。如果想要在 bottle 中使用类来创建应用,同时使用修饰符进行路由,在不重写修饰符的前提下,创建一个全部都是静态方法的类才能满足要求。
如果你不是偏执于修饰符的路由方式,那么就让我们来使用一个看上去更加正常的类来创建应用吧。
在 bottle 中,修饰符路由是它一个特性,但是修饰符本身就是一种语法糖而已,因此让我们暂时放弃这种语法糖,直接使用 route 方法来进行路由。
class SanYou: def homepage(self): return "Welcome!" sanYou = SanYou() app = Bottle() app.route('/')(sanYou.homepage)
"""
bottle中使用route的两种写法
写法一:
@app.route(url)
function()
写法二:
app.route(url)(function)
写法一等同写法二。
"""
在以上代码中,首先将 SanYou 实例化,得到一个 sanYou 实例,然后创建 app,并在这个应用中,将来自 url="/" 的请求路由到 sanYou 的实例方法 homepage 处理。因此,当随着路由地址增加,不妨如下编码以便集中管理路由。
class SanYou: def homepage(self): return "Welcome!" def service(self): return "Hello!" def appRoute(app): sanYou = SanYou() routeDict = { '/': sanYou.homepage, '/home': sanYou.homepage, '/service': sanYou.service, } for url in routeDict: app.route(url)(routeDict[url]) app = Bottle() appRoute(app)
在 appRoute 函数的 routeDict 中,可以很方便地集中配置路由。这种写法是不是让 bottle 看上去不像 bottle ,反而更像是 Django 或 webapp.py 等呢?