File Coverage

inc/YAML/Types.pm
Criterion Covered Total %
statement 21 157 13.3
branch 0 48 0.0
condition 0 5 0.0
subroutine 7 22 31.8
pod n/a
total 28 232 12.0


line stmt bran cond sub pod time code
1             #line 1
2 2     2   8 package YAML::Types;
  2         3  
  2         12  
3             use YAML::Mo;
4              
5             our $VERSION = '0.80';
6 2     2   9  
  2         3  
  2         128  
7             use YAML::Node;
8              
9             # XXX These classes and their APIs could still use some refactoring,
10             # but at least they work for now.
11             #-------------------------------------------------------------------------------
12 2     2   9 package YAML::Type::blessed;
  2         2  
  2         7  
13             use YAML::Mo; # XXX
14              
15 0     0     sub yaml_dump {
16 0           my $self = shift;
17 0           my ($value) = @_;
18 2     2   11 my ($class, $type) = YAML::Mo::Object->node_info($value);
  2         12  
  2         1093  
19 0           no strict 'refs';
20 0   0       my $kind = lc($type) . ':';
21             my $tag = ${$class . '::ClassTag'} ||
22 0 0         "!perl/$kind$class";
    0          
23 0           if ($type eq 'REF') {
24 0           YAML::Node->new(
25             {(&YAML::VALUE, ${$_[0]})}, $tag
26             );
27             }
28 0           elsif ($type eq 'SCALAR') {
29 0           $_[1] = $$value;
30             YAML::Node->new($_[1], $tag);
31 0           } else {
32             YAML::Node->new($value, $tag);
33             }
34             }
35              
36             #-------------------------------------------------------------------------------
37             package YAML::Type::undef;
38              
39 0     0     sub yaml_dump {
40             my $self = shift;
41             }
42              
43 0     0     sub yaml_load {
44             my $self = shift;
45             }
46              
47             #-------------------------------------------------------------------------------
48             package YAML::Type::glob;
49              
50 0     0     sub yaml_dump {
51 0           my $self = shift;
52 0           my $ynode = YAML::Node->new({}, '!perl/glob:');
53 0           for my $type (qw(PACKAGE NAME SCALAR ARRAY HASH CODE IO)) {
  0            
54 0 0         my $value = *{$_[0]}{$type};
55 0 0         $value = $$value if $type eq 'SCALAR';
56 0 0         if (defined $value) {
57 0           if ($type eq 'IO') {
58             my @stats = qw(device inode mode links uid gid rdev size
59 0           atime mtime ctime blksize blocks);
60 0           undef $value;
61 0           $value->{stat} = YAML::Node->new({});
  0            
  0            
62 0           map {$value->{stat}{shift @stats} = $_} stat(*{$_[0]});
  0            
63             $value->{fileno} = fileno(*{$_[0]});
64 0           {
  0            
65 0           local $^W;
  0            
66             $value->{tell} = tell(*{$_[0]});
67             }
68 0           }
69             $ynode->{$type} = $value;
70             }
71 0           }
72             return $ynode;
73             }
74              
75 0     0     sub yaml_load {
76 0           my $self = shift;
77 0           my ($node, $class, $loader) = @_;
78 0 0         my ($name, $package);
79 0           if (defined $node->{NAME}) {
80 0           $name = $node->{NAME};
81             delete $node->{NAME};
82             }
83 0           else {
84 0           $loader->warn('YAML_LOAD_WARN_GLOB_NAME');
85             return undef;
86 0 0         }
87 0           if (defined $node->{PACKAGE}) {
88 0           $package = $node->{PACKAGE};
89             delete $node->{PACKAGE};
90             }
91 0           else {
92             $package = 'main';
93 2     2   10 }
  2         2  
  2         659  
94 0 0         no strict 'refs';
95 0           if (exists $node->{SCALAR}) {
  0            
96 0           *{"${package}::$name"} = \$node->{SCALAR};
97             delete $node->{SCALAR};
98 0           }
99 0 0         for my $elem (qw(ARRAY HASH CODE IO)) {
100 0 0         if (exists $node->{$elem}) {
101 0           if ($elem eq 'IO') {
102 0           $loader->warn('YAML_LOAD_WARN_GLOB_IO');
103 0           delete $node->{IO};
104             next;
105 0           }
  0            
106 0           *{"${package}::$name"} = $node->{$elem};
107             delete $node->{$elem};
108             }
109 0           }
110 0           for my $elem (sort keys %$node) {
111             $loader->warn('YAML_LOAD_WARN_BAD_GLOB_ELEM', $elem);
112 0           }
  0            
113             return *{"${package}::$name"};
114             }
115              
116             #-------------------------------------------------------------------------------
117             package YAML::Type::code;
118              
119             my $dummy_warned = 0;
120             my $default = '{ "DUMMY" }';
121              
122 0     0     sub yaml_dump {
123 0           my $self = shift;
124 0           my $code;
125 0           my ($dumpflag, $value) = @_;
126 0           my ($class, $type) = YAML::Mo::Object->node_info($value);
127 0 0         my $tag = "!perl/code";
128 0 0         $tag .= ":$class" if defined $class;
129 0           if (not $dumpflag) {
130             $code = $default;
131             }
132 0 0         else {
133 2     2   10 bless $value, "CODE" if $class;
  2         4  
  2         1644  
  0            
134 0 0         eval { use B::Deparse };
135 0           return if $@;
136 0           my $deparse = B::Deparse->new();
137 0           eval {
138 0           local $^W = 0;
139             $code = $deparse->coderef2text($value);
140 0 0         };
141 0 0         if ($@) {
142 0           warn YAML::YAML_DUMP_WARN_DEPARSE_FAILED() if $^W;
143             $code = $default;
144 0 0         }
145 0           bless $value, $class if $class;
146 0           chomp $code;
147             $code .= "\n";
148 0           }
149 0           $_[2] = $code;
150             YAML::Node->new($_[2], $tag);
151             }
152              
153 0     0     sub yaml_load {
154 0           my $self = shift;
155 0 0         my ($node, $class, $loader) = @_;
156 0           if ($loader->load_code) {
157 0 0         my $code = eval "package main; sub $node";
158 0           if ($@) {
159 0     0     $loader->warn('YAML_LOAD_WARN_PARSE_CODE', $@);
  0            
160             return sub {};
161             }
162 0 0         else {
163 0           CORE::bless $code, $class if $class;
164             return $code;
165             }
166             }
167 0 0   0     else {
  0            
168 0     0     return CORE::bless sub {}, $class if $class;
  0            
169             return sub {};
170             }
171             }
172              
173             #-------------------------------------------------------------------------------
174             package YAML::Type::ref;
175              
176 0     0     sub yaml_dump {
177 0           my $self = shift;
  0            
178             YAML::Node->new({(&YAML::VALUE, ${$_[0]})}, '!perl/ref')
179             }
180              
181 0     0     sub yaml_load {
182 0           my $self = shift;
183 0 0         my ($node, $class, $loader) = @_;
184             $loader->die('YAML_LOAD_ERR_NO_DEFAULT_VALUE', 'ptr')
185 0           unless exists $node->{&YAML::VALUE};
186             return \$node->{&YAML::VALUE};
187             }
188              
189             #-------------------------------------------------------------------------------
190             package YAML::Type::regexp;
191              
192             # XXX Be sure to handle blessed regexps (if possible)
193 0     0     sub yaml_dump {
194             die "YAML::Type::regexp::yaml_dump not currently implemented";
195             }
196              
197 0           use constant _QR_TYPES => {
198 0           '' => sub { qr{$_[0]} },
199 0           x => sub { qr{$_[0]}x },
200 0           i => sub { qr{$_[0]}i },
201 0           s => sub { qr{$_[0]}s },
202 0           m => sub { qr{$_[0]}m },
203 0           ix => sub { qr{$_[0]}ix },
204 0           sx => sub { qr{$_[0]}sx },
205 0           mx => sub { qr{$_[0]}mx },
206 0           si => sub { qr{$_[0]}si },
207 0           mi => sub { qr{$_[0]}mi },
208 0           ms => sub { qr{$_[0]}sm },
209 0           six => sub { qr{$_[0]}six },
210 0           mix => sub { qr{$_[0]}mix },
211 0           msx => sub { qr{$_[0]}msx },
212 0           msi => sub { qr{$_[0]}msi },
213 2     2   13 msix => sub { qr{$_[0]}msix },
  2         4  
  2         552  
214             };
215              
216 0     0     sub yaml_load {
217 0           my $self = shift;
218 0 0         my ($node, $class) = @_;
219 0           return qr{$node} unless $node =~ /^\(\?([\^\-xism]*):(.*)\)\z/s;
220 0           my ($flags, $re) = ($1, $2);
221 0           $flags =~ s/-.*//;
222 0   0 0     $flags =~ s/^\^//;
  0            
223 0           my $sub = _QR_TYPES->{$flags} || sub { qr{$_[0]} };
224 0 0         my $qr = &$sub($re);
225 0           bless $qr, $class if length $class;
226             return $qr;
227             }
228              
229             1;
230              
231             __END__