NAME

Mock::Data - Extensible toolkit for generating mock data

SYNOPSIS

  # load it up with data from plugins
  my $mockdata= Mock::Data->new([qw/ Num Text Contact /]);
  
  # generate or pick data from sets
  say $mockdata->integer;    # returns a random integer
  say $mockdata->first_name; # returns a random entry from the first_name set
  
  # Can pass parameters to generators
  say $mockdata->integer({ max => 50 });
  
  # Can define new collections (with autoload method) on the fly
  $mockdata->merge_generators(
	stuff => [ 'things', 'junk', 'clutter' ],
  );
  say $mockdata->stuff; # returns random element of stuff collection
  
  # Template notation makes it easy to combine patterns/collections
  say $mockdata->merge_generators(
    business_suffix => [ 'Inc.', 'llc.', 'gmbh.' ],
    business_name => [
      '{surname} {industry} {business_suffix}',
      '{surname} and {surname} {business_suffix}',
    ]
  );

DESCRIPTION

This module is a generator of mock data. It takes good ideas seen in Data::Faker, Mock::Populate, and other similar modules, and combines them into a cohesive extensible design.

Each mock data generator is called as a method on an instance of Mock::Data. This allows generators to store persistent state between calls. It also allows them to be configured with per-instance settings.

ATTRIBUTES

This module defines a minimal number of attributes, to leave most of the method namespace available for the generators themselves. All subclasses and custom generators should attempt to use the existing attributes instead of defining new ones.

generators

my $generator_hashref= $mock->generators;
$mock->generators( $new_hashref );  # clears cache

This is a hashref of named things which can generate mock data. The things can be coderefs, arrayrefs (select random element of the array) or instance of "Mock::Data::Generator". The data specified here may be cached in various ways after a generator has been called, so any time you modify it you should use the methods "set_generators" or "merge_generators". However, you may modify it directly and then write the new (or same) hashref to this attribute as an argument, which will clear the cache.

generator_state

sub my_generator {
  $_[0]->generator_state->{__PACKAGE__.'.foo'}= $my_state;
}

This is a hashref where generators can store temporary data. If the instance of Mock::Data is cloned, this hashref will be deep-cloned. Other hashref fields of the Mock::Data object are not deep-cloned, aside from the generators field which is cloned one level deep.

Keys in this hash should be prefixed with either the name of the generator or name of the package the generator was implemented from.

METHODS

Note: All generators may be called as methods, thanks to AUTOLOAD.

new

$mock= Mock::Data->new(\@package_list);
$mock= Mock::Data->new({
  generators => \%generator_set,
  with => \@package_list,
  
});

Construct a new instance of Mock::Data. If called as a method of an object, this will clone the existing instance, applying generators on top of the set already present.

Arguments:

with => \@package_list

This lets you specify a list of packages whose generators should be pulled into the new object. The plugins may also change the class of the object returned.

generators => \%set

This specifies a set of generators that should be the initial value of the "generators" attribute. If this is specified to "new" called on an instance, the generators will be merged with the ones for the instance as per "add_generators".

clone

$mockdata2= $mockdata->clone;

Calling clone on a Mock::Data instance returns a new Mock::Data of the same class with the same plugins and a deep-clone of the "generator_state" and a shallow clone of the "generators" set. This may not have the desied effect if one of your generators is storing state outside of the "generator_state" hashref.

clone does not take any arguments. If you wish to modify the object at the same time as cloning a previous one, call "new" on the previous object instance.

add_generators

$mockdata->add_generators( $name => $spec, ... )

Set one or more named generators. Arguments can be given as a hashref or a list of key/value pairs. $spec can be a coderef, an arrayref (of options) or an instance of Mock::Data::Generator. If a previous generator existed by the same name, it will be replaced.

If the $name of the generator is a package-qualified name, the generator is added under both the long and short name. For example, merge_generators( 'MyPlugin::gen' => \&gen ) will register \&gen as both 'MyPlugin::gen' and an alias of 'gen'. However, 'gen' will only be added if it didn't already exist. This allows plugins to refer to eachother's names without collisions.

Returns $mockdata, for chaining.

Use this method instead of directly modifying the generators hashref so that this module can perform proper cache management.

merge_generators

$mock->merge_generators( $name => $spec, ... )

Same as "add_generators", but if a generator of that name already exists, replace it with a generator that returns both possible sets of results. If the old generator was a coderef, it will be replaced with a new generator that calls the old coderef 50% of the time. If the old generator and new generator are both arrayrefs, the merged generator will be a concatenation of the arrays.

Returns $mock, for chaining.

Use this method instead of directly modifying the generators hashref so that this module can perform proper cache management.

call_generator

$mock->call_generator($name, \%named_params, @positional_params);

This is a more direct way to invoke a generator. The more convenient way of calling the generator name as a method of the object uses AUTOLOAD to call this method.

EXPORTS

Mock::Data can export symbols from Mock::Data::Util. See that module for a complete reference for each function.

uniform_set(@items)

Return a Mock::Data::Set that selects from a set of values or other generators.

weighted_set($item => $weight, ...)

Like uniform_set, but allows you to specify a probability multiplier for each element.

inflate_template($template)

For a string, interpolate template notation and return either a constant scalar or a Mock::Data::Generator.

coerce_generator($specification)

Take any $specification that Mock::Data knows how to process, and return a Mock::Data::Generator for it.

mock_data_subclass($class_or_object, @class_list)

Return a new class (or re-blessed object) that inherits from all classes in the list.

SEE ALSO

AUTHOR

Michael Conrad <mike@nrdvana.net>

VERSION

version 0.00_001

COPYRIGHT AND LICENSE

This software is copyright (c) 2021 by Michael Conrad.

This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself.