Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support Element getTree convert functions for each TYPE #51

Merged
merged 16 commits into from May 3, 2015
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
16 commits
Select commit Hold shift + click to select a range
a7e1fae
Force internal perl type to the TYPE and add convert_ anonymous sub s…
stdweird Apr 3, 2015
4761550
Add unittest for (and examples of) the new getTree convert_ options
stdweird Apr 3, 2015
c8ab375
Add EDG::WP4::CCM::TextRender, a CAF::TextRender subclass with EDG::W…
stdweird Apr 19, 2015
6c8d00c
Clarify comment on default clause in getTree type switch
stdweird Apr 21, 2015
dad225b
Introduce additional variables in TT via CCM namespace
stdweird Apr 24, 2015
5d49f0e
Add CCM::TT::Scalar class to wrap scalar types and provide access to …
stdweird Apr 26, 2015
df26263
Copy all subdirs (for TT and possible others)
stdweird Apr 26, 2015
27c0e45
getTree convert method options are now array references of anonymous …
stdweird Apr 26, 2015
e549405
CCM::TextRender uses CCM::TT::Scalar instances for the boolena/string…
stdweird Apr 26, 2015
5a1ea71
Set 755 permission so the TT subdir has execut bits (and is usable)
stdweird Apr 26, 2015
5d0e0ee
Add the CCM::TextRender Scalar get_type tests
stdweird Apr 26, 2015
1708bc9
CCM::TT::Scalar refine and test the overloading for non-string operat…
stdweird Apr 27, 2015
20bd123
Remove the default conversion for string/long and double in Element g…
stdweird Apr 29, 2015
27df728
Refactor and add predefined cast convert methods that are implied by …
stdweird Apr 29, 2015
b7b45cf
Cleanup comments in TT Scalar
stdweird Apr 29, 2015
3830674
CCM::TextRender add the escape/unescape methods to the CCM VARIABLES
stdweird May 1, 2015
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
4 changes: 3 additions & 1 deletion pom.xml
Expand Up @@ -79,6 +79,7 @@
<directory>src/main/perl</directory>
<includes>
<include>*.pm</include>
<include>**/*.pm</include>
</includes>
<filtering>true</filtering>
</resource>
Expand Down Expand Up @@ -152,6 +153,7 @@
<directory>src/main/perl</directory>
<includes>
<include>*.pm</include>
<include>**/*.pm</include>
</includes>
<filtering>true</filtering>
</resource>
Expand Down Expand Up @@ -271,7 +273,7 @@
<mappings>
<mapping>
<directory>/usr/lib/perl/EDG/WP4/CCM</directory>
<filemode>644</filemode>
<filemode>755</filemode>
<username>root</username>
<groupname>root</groupname>
<directoryIncluded>false</directoryIncluded>
Expand Down
13 changes: 13 additions & 0 deletions src/main/perl/CCfg.pm
Expand Up @@ -198,6 +198,19 @@ sub getCfgValue ($)
return ($cfg->{$key});
}

# private method to set values, for testing only
sub _setCfgValue
{
my ($key, $value) = @_;
if (defined($cfg->{$key})) {
$cfg->{$key} = $value;
} else {
throw_error("Not a valid config key $key");
}
# Use the method rather then direct call or simply return value
return getCfgValue($key);
}

=pod

=back
Expand Down
77 changes: 69 additions & 8 deletions src/main/perl/Element.pm
Expand Up @@ -542,48 +542,109 @@ Note that links cannot be followed.

If C<depth> is specified (and not C<undef>), only return the next C<depth>
levels of nesting (and use the Element instances as values).
A C<depth == 0> is the element itself, C<depth == 1> is the first level, ...
A C<depth == 0> is the element itself, C<depth == 1> is the first level, ...

Named options

=over

=item convert_boolean

Array ref of anonymous methods to convert the argument
(1 or 0 for resp true and false) to another boolean representation.

=item convert_string

Array ref of anonymous methods to convert the argument
(string value) to another representation/format.

=item convert_long

Array ref of anonymous methods to convert the argument
(integer/long value) to another representation/format.

=item convert_double

Array ref of anonymous methods to convert the argument
(float/double value) to another representation/format.

=back

The arrayref of anonymous methods are applied as follows:
convert methods C<[a, b, c]> will produce C<$new = c(b(a($old)))>.

=cut

sub getTree
{
my ($self, $depth) = @_;
my ($ret, $el);
my ($self, $depth, %opts) = @_;

my ($ret, $el, $nextdepth);
my $convm = [];

my $nextdepth;
if (defined($depth)) {
return $self if ($depth <= 0);
$nextdepth = $depth - 1;
}

SWITCH:
{
# LIST to array ref
$self->isType(LIST) && do {
$ret = [];
while ($self->hasNextElement) {
$el = $self->getNextElement();
push(@$ret, $el->getTree($nextdepth));
push(@$ret, $el->getTree($nextdepth, %opts));
}
last SWITCH;
};

# NLIST to hashref
$self->isType(NLIST) && do {
$ret = {};
while ($self->hasNextElement) {
$el = $self->getNextElement();
$$ret{$el->getName()} = $el->getTree($nextdepth);
$$ret{$el->getName()} = $el->getTree($nextdepth, %opts);
}
last SWITCH;
};

# BOOLEAN to 1/0
$self->isType(BOOLEAN) && do {
$ret = $self->getValue eq 'true' ? 1 : 0;
$convm = $opts{convert_boolean};
last SWITCH;
};

# Default clause
# No predefined conversion for any other type
$ret = $self->getValue;

last SWITCH;
# STRING
$self->isType(STRING) && do {
$convm = $opts{convert_string};
last SWITCH;
};

# LONG
$self->isType(LONG) && do {
$convm = $opts{convert_long};
last SWITCH;
};

# DOUBLE
$self->isType(DOUBLE) && do {
$convm = $opts{convert_double};
last SWITCH;
};

}

foreach my $method (@$convm) {
if(ref($method) eq 'CODE') {
$ret = $method->($ret);
} else {
throw_error("wrong type ".ref($method)." for convert_method");
}
}

return $ret;
Expand Down
186 changes: 186 additions & 0 deletions src/main/perl/TT/Scalar.pm
@@ -0,0 +1,186 @@
# ${license-info}
# ${developer-info}
# ${author-info}
# ${build-info}

package EDG::WP4::CCM::TT::Scalar;

use strict;
use warnings;

use Readonly;
use Template::VMethods;

use base qw(Exporter);

# Overload the stringification
# Following the 'perldoc overload' section on
# 'Magic Autogeneration'; this should be sufficient
# for the other scalar operations numify (via '0+')
# and logic (via 'bool').
# Enable fallback for the case '$obj+1'
# (instead of defining + operator, numify is used as fallback)
# and others like '$obj eq something'.
use overload '""' => '_stringify', 'fallback' => 1;

our @EXPORT_OK =qw(%ELEMENT_TYPES);

Readonly::Hash our %ELEMENT_TYPES => {
BOOLEAN => 'BOOLEAN',
STRING => 'STRING',
DOUBLE => 'DOUBLE',
LONG => 'LONG',
};

=pod

=head1 NAME

CCM::TT::Scalar - Class to access scalar/property Element attributes within TT.

=head1 DESCRIPTION

This is a wrapper class to access some scalar/property Element attributes
(in particular the type) within TT.

=head2 Methods

=over

=item new

Create a new instance with C<value> and C<type>.

=cut

sub new
{
my ($class, $value, $type) = @_;

# TODO if we limit the types, what sort of error checking do we need?
my $self = {
VALUE => $value,
TYPE => $type,
};
bless $self, $class;

return $self;
}

=pod

=item _stringify

Method called to stringification. Simply returns the data in string context

=cut

sub _stringify
{
my ($self) = @_;
return "$self->{VALUE}";
}

=pod

=item get_type

Return TYPE attribute

=cut

sub get_type
{
my $self = shift;
return $self->{TYPE};
}

=pod

=item get_value

Return value (i.e. the VALUE attribute)
(can be useful in case the overloading behaves unexpected)

=cut

sub get_value
{
my $self = shift;
return $self->{VALUE};
}

=pod

=item is_boolean

Return true if the TYPE is boolean

=cut

sub is_boolean
{
my $self = shift;
return $self->{TYPE} eq $ELEMENT_TYPES{BOOLEAN};
}

=pod

=item is_string

Return true if the TYPE is string

=cut

sub is_string
{
my $self = shift;
return $self->{TYPE} eq $ELEMENT_TYPES{STRING};
}

=pod

=item is_double

Return true if the TYPE is double

=cut

sub is_double
{
my $self = shift;
return $self->{TYPE} eq $ELEMENT_TYPES{DOUBLE};
}

=pod

=item is_long

Return true if the TYPE is long

=cut

sub is_long
{
my $self = shift;
return $self->{TYPE} eq $ELEMENT_TYPES{LONG};
}

# Generate all regular TT scalar methods
# from $Template::VMethods::TEXT_VMETHODS
no strict 'refs';
while (my ($name, $method) = each %{$Template::VMethods::TEXT_VMETHODS}) {
*{$name} = sub {
my ($self, @args) = @_;
return $method->($self->{VALUE}, @args);
}
}
use strict 'refs';

=pod

=back

=cut

1;