由于 Catalyst 使用 Moose,并且 Catalyst::Controller 对象是 Moose 对象,因此您可以将 Moose 角色与它们一起使用。
package Hello::DebugRole;
use Moose::Role;
use MooseX::MethodAttributes::Role;
sub auto :Private {
my ($self, $c) = @_;
$c->log->debug('Hello!');
return 1;
}
1;
我们需要MooseX::MethodAttributes::Role 来启用 CODE 属性。没有它,它会在执行时死掉,如果我们省略 :Private,Catalyst 不会将其视为一个操作,而是将其视为一个本地方法。
这种方法很有意义,因为您可以在一个地方定义您的 auto 操作,该操作非常干燥,并且您可以在所有需要的地方完全重用该代码。
现在您可以在所需的所有控制器中使用它。只需将其放在BEGIN 块中即可。
package Hello::Controller::User;
use Moose;
use namespace::autoclean;
BEGIN { extends 'Catalyst::Controller'; with 'Hello::DebugRole'; }
如果我导航到该控制器,日志将如下所示:
[debug] Path is "user"
[debug] "GET" request for "user/" from "127.0.0.1"
[debug] Hello!
[debug] Response Code: 200; Content-Type: text/html; charset=utf-8; Content-Length: unknown
[info] Request took 0.010909s (91.667/s)
.------------------------------------------------------------+-----------.
| Action | Time |
+------------------------------------------------------------+-----------+
| /user/auto | 0.000237s |
| /user/index | 0.000152s |
| /end | 0.000394s |
'------------------------------------------------------------+-----------'
[info] *** Request 2 (0.286/s) [24045] [Wed Jan 6 16:16:15 2016] ***
但如果我改为导航到 Foobar 控制器,则没有自动操作,也没有 Hello!。
[info] *** Request 3 (0.250/s) [24045] [Wed Jan 6 16:16:20 2016] ***
[debug] Path is "foobar"
[debug] "GET" request for "foobar/" from "127.0.0.1"
[debug] Response Code: 200; Content-Type: text/html; charset=utf-8; Content-Length: unknown
[info] Request took 0.007135s (140.154/s)
.------------------------------------------------------------+-----------.
| Action | Time |
+------------------------------------------------------------+-----------+
| /foobar/index | 0.000181s |
| /end | 0.000179s |
'------------------------------------------------------------+-----------'
请注意,Catalyst 将调用所有涉及的控制器的 auto 操作,因此如果 所有 请求中有一个,它也会执行根控制器的 auto。