Skip to content
Permalink
Browse files

Compose meta methods in predictable order

  • Loading branch information...
niner committed May 1, 2019
1 parent 4af81c3 commit 5ee341cc149aed56ce25a6c1d1bd41c3be49b2ad
Showing with 14 additions and 5 deletions.
  1. +14 −5 src/Perl6/Metamodel/MetaMethodContainer.nqp
@@ -1,6 +1,7 @@
role Perl6::Metamodel::MetaMethodContainer {
# Table of the methods.
has %!meta_methods;
has @!meta_methods;

# Add a meta-method.
method add_meta_method($obj, $name, $code_obj) {
@@ -9,24 +10,32 @@ role Perl6::Metamodel::MetaMethodContainer {
~ "' already has a meta-method '$name'");
}
%!meta_methods{$name} := $code_obj;
nqp::push(@!meta_methods, $code_obj);
}

# Get the meta-methods table: a hash of meta-methods added.
method meta_method_table($obj) {
%!meta_methods
}

# Get the meta-methods in order of declaration.
method meta_methods($obj) {
@!meta_methods
}

# Applies the added meta-methods to the current meta-object instance by
# building a role containing them, and mixing it in.
method compose_meta_methods($obj) {
# Build flattened meta-methods set.
my %meta;
my @meta;
for self.mro($obj) {
if nqp::can($_.HOW, 'meta_method_table') {
for $_.HOW.meta_method_table($obj) -> $meth_info {
my str $name := $meth_info.key;
for $_.HOW.meta_methods($obj) -> $method {
my str $name := $method.name;
unless nqp::existskey(%meta, $name) {
%meta{$name} := $meth_info.value;
%meta{$name} := $method;
nqp::push(@meta, $name);
}
}
}
@@ -36,8 +45,8 @@ role Perl6::Metamodel::MetaMethodContainer {
# compose it into the meta-object..
if %meta {
my $role := $?PACKAGE.HOW.new_type();
for %meta {
$role.HOW.add_method($role, $_.key, $_.value);
for @meta -> $key {
$role.HOW.add_method($role, $key, %meta{$key});
}
$role.HOW.set_body_block($role, sub ($class) {
nqp::list($role, nqp::hash('$?CLASS', $class))

0 comments on commit 5ee341c

Please sign in to comment.
You can’t perform that action at this time.