Is there a Perl module for dynamically converting YAML files to Moose objects at runtime?

I am trying to find a Perl module that converts a YAML file to moose objects without first declaring the structure, which you think you need to do when using MooseX :: YAML . Does anyone know about such a module (or script)?

+4
source share
2 answers

Not.

Moose classes, their attributes and everything that belongs to them have a lot of metadata attached to them. You cannot derive all of this metadata from the data of one instance.

I guess given yaml document how

--- foo: 42 bar: ['moo', 'kooh'] 

which you would expect and return back, which answers calls to the foo and bar method, returning the appropriate values. But how should these accessories behave? Should they be simple reading methods or allow writing? Should they check for any type of constraint? and etc.

If all you really need is what makes an inaccessible data structure accessible as an object, see Data::Hive , Hash::AsObject and similar modules.

If you really want to create the appropriate Moose classes, and either in order with the guesswork to be involved, or perhaps the necessary metadata will be available, you can simply use the meta protocol.

 my $class = Moose::Meta::Class->create_anon_class( attributes => [map { # your particular set of assumptions here Moose::Meta::Attribute->new($_ => (is => 'ro', ...)) } keys %{ $deserialized_yaml }], ); my $instance = $class->name->new($deserialized_yaml); $instance->$some_key_in_the_yaml_document; 
+7
source

If you don’t want to do anything special in your YAML, you can simply configure the correct coercion for your moose classes, and then pass the loaded data to new() . For instance:

 package My::Types; use Moose::Util::TypeConstraints; class_type 'My::Related::Class'; coerce 'My::Related::Class', from 'HashRef', via { My::Related::Class->new(%$_) }; package My::Class; use Moose; has name => (is => 'ro', isa => 'Str'); has related => (is => 'ro', isa => 'My::Related::Class', coerce => 1); package My::Related::Class; use Moose; has flavor => (is => 'ro', isa => 'Str'); 

Then in some YAML:

 name: "An instance of My::Class" related: flavor: "Dangerberry!" 

Then in some code:

 my $obj = My::Class->new(Load($yaml_data)); print ref $obj->related; # My::Related::Class print $obj->related->flavor; # Dangerberry! 

This, of course, is not a whirl, without additional customization of your Moose classes - it's just for building objects. In addition, you need to know which classes are the root objects.

This is probably enough for many simple applications.

+3
source

All Articles