use CLOS; class Bake { method preheat { say "preheating"; } method cook { say "cooking"; } method rest { say "resting"; } } class Cook is Bake { method preheat is before { say "...about to preheat"; } method rest is after { say "...resting done"; } } my $cook = Cook.new; $cook.preheat; say "----"; $cook.cook; say "----"; $cook.rest; #### perl6 -I . Bake.pm ...about to preheat preheating ---- cooking ---- resting ...resting done #### my class CLOSClassHOW is Metamodel::ClassHOW { my Bool %before{Any}; my Bool %after{Any}; multi sub trait_mod:(Routine $r, :$before!) is export { %before{$r} = True; } multi sub trait_mod:(Routine $r, :$after!) is export { %after{$r} = True; } #| find this method in our parents method !find-super-method($obj, $name, *@etc) { my @mro = self.mro($obj); @mro.shift; # skip ourselves for @mro { my %methods = $_.HOW.method_table($_); return %methods{$name} if %methods{$name}:exists; } } method find_method($obj, $name) { my $raw-meth := callsame; my $meth := $raw-meth; if $raw-meth.defined && (%before{$raw-meth} || %after{$raw-meth}) { my $next-meth := self!find-super-method($obj,$name); $meth := -> $c, |args { $raw-meth($obj, |args) if %before{$raw-meth}; my $result := $next-meth($obj, |args) if $next-meth.defined ; $raw-meth($obj, |args) if %after{$raw-meth}; $result; } } $meth; } method publish_method_cache($obj) { # no caching, so we always hit find_method } } my module EXPORTHOW { } EXPORTHOW.WHO. = CLOSClassHOW;