File Coverage

blib/lib/Wikibase/Datatype/Struct/Utils.pm
Criterion Covered Total %
statement 58 60 96.6
branch 18 20 90.0
condition 3 3 100.0
subroutine 9 9 100.0
pod 2 2 100.0
total 90 94 95.7


line stmt bran cond sub pod time code
1              
2             use base qw(Exporter);
3 38     38   412039 use strict;
  38         102  
  38         2759  
4 38     38   189 use warnings;
  38         61  
  38         547  
5 38     38   140  
  38         71  
  38         748  
6             use English;
7 38     38   943 use Error::Pure qw(err);
  38         5982  
  38         229  
8 38     38   14374 use List::MoreUtils qw(none);
  38         12642  
  38         1276  
9 38     38   2839  
  38         61968  
  38         230  
10             Readonly::Array our @EXPORT_OK => qw(obj_array_ref2struct struct2snaks_array_ref);
11              
12             our $VERSION = 0.09;
13              
14             my ($snaks_ar, $key, $base_uri, $snak_obj, $struct_snak_obj) = @_;
15              
16 12     12 1 4497 if (! defined $snak_obj) {
17             $snak_obj = 'Wikibase::Datatype::Snak';
18 12 100       32 }
19 11         18 if (! defined $struct_snak_obj) {
20             $struct_snak_obj = 'Wikibase::Datatype::Struct::Snak';
21 12 100       27 }
22 11         16 eval "require $struct_snak_obj";
23             if ($EVAL_ERROR) {
24 12         576 err "Cannot load '$struct_snak_obj'";
25 12 50       53 }
26 0         0  
27             if (! defined $base_uri) {
28             err 'Base URI is required.';
29 12 100       45 }
30 1         5  
31             my $snaks_hr = {
32             $key.'-order' => [],
33 11         39 $key => {},
34             };
35             foreach my $snak_o (@{$snaks_ar}) {
36             if (! $snak_o->isa($snak_obj)) {
37 11         31 err "Object isn't '$snak_obj'.";
  11         25  
38 22 100       85 }
39 1         6  
40             if (! exists $snaks_hr->{$key}->{$snak_o->property}) {
41             $snaks_hr->{$key}->{$snak_o->property} = [];
42 21 100       62 }
43 20         139 if (! @{$snaks_hr->{$key.'-order'}}
44             || none { $_ eq $snak_o->property } @{$snaks_hr->{$key.'-order'}}) {
45 21 100 100     112  
  21         95  
46 15     15   44 push @{$snaks_hr->{$key.'-order'}}, $snak_o->property;
  11         33  
47             }
48 20         73 push @{$snaks_hr->{$key}->{$snak_o->property}},
  20         49  
49             eval $struct_snak_obj.'::obj2struct($snak_o, $base_uri);';
50 21         131 }
  21         38  
51              
52             return $snaks_hr;
53             }
54 10         33  
55             my ($struct_hr, $key, $struct_snak_obj) = @_;
56              
57             if (! defined $struct_snak_obj) {
58 20     20 1 7254 $struct_snak_obj = 'Wikibase::Datatype::Struct::Snak';
59             }
60 20 100       55 eval "require $struct_snak_obj";
61 19         35 if ($EVAL_ERROR) {
62             err "Cannot load '$struct_snak_obj'";
63 20         1044 }
64 20 50       80  
65 0         0 my $snaks_ar = [];
66             foreach my $property (@{$struct_hr->{$key.'-order'}}) {
67             push @{$snaks_ar}, map {
68 20         36 eval $struct_snak_obj.'::struct2obj($_)';
69 20         29 } @{$struct_hr->{$key}->{$property}};
  20         78  
70 23         34 if ($EVAL_ERROR) {
71 24         1023 err $EVAL_ERROR;
72 23         32 }
  23         55  
73 23 100       3690 }
74 2         7  
75             return $snaks_ar;
76             }
77              
78 18         101 1;
79              
80              
81             =pod
82              
83             =encoding utf8
84              
85             =head1 NAME
86              
87             Wikibase::Datatype::Struct::Utils - Wikibase structure serialization utilities.
88              
89             =head1 SYNOPSIS
90              
91             use Wikibase::Datatype::Struct::Utils qw(obj_array_ref2struct struct2snaks_array_ref);
92              
93             my $snaks_hr = obj_array_ref2struct($snaks_ar, $key, $base_uri, $snak_obj, $struct_snak_obj);
94             my $snaks_ar = struct2snaks_array_ref($struct_hr, $key, $struct_snak_obj);
95              
96             =head1 SUBROUTINES
97              
98             =head2 C<obj_array_ref2struct>
99              
100             my $snaks_hr = obj_array_ref2struct($snaks_ar, $key, $base_uri, $snak_obj);
101              
102             Helper subroutine for converting list of Snak objects to snaks structure.
103             This subroutine is used in Statement and Reference module.
104             C<$base_uri> is base URI of Wikibase system (e.g. http://test.wikidata.org/entity/).
105             C<$snak_obj> is object for snak (default value is 'Wikibase::Datatype::Snak').
106             C<$struct_snak_obj> is object for struct snak (default value is 'Wikibase::Datatype::Struct::Snak').
107              
108             Returns structure with multiple snaks.
109              
110             =head2 C<struct2snaks_array_ref>
111              
112             my $snaks_ar = struct2snaks_array_ref($struct_hr, $key, $struct_snak_obj);
113              
114             Helper subroutine for converting snaks structure to list of Snak objects.
115             This subroutine is used in Statement and Reference module.
116             C<$struct_snak_obj> is object for struct snak (default value is 'Wikibase::Datatype::Struct::Snak').
117              
118             Returns reference to array with snaks objects.
119              
120             =head1 ERRORS
121              
122             obj_array_ref2struct():
123             Base URI is required.
124             Object isn't 'Wikibase::Datatype::Snak'.
125              
126             struct2snaks_array_ref():
127             From Wikibase::Datatype::Snak::new():
128             From Wikibase::Datatype::Utils::check_required():
129             Parameter 'datatype' is required.
130             Parameter 'datavalue' is required.
131             Parameter 'property' is required.
132             From Wikibase::Datatype::Utils::check_isa():
133             Parameter 'datavalue' must be a 'Wikibase::Datatype::Value::%s' object.
134             Parameter 'datatype' = '%s' isn't supported.
135             Parameter 'property' must begin with 'P' and number after it.
136             Parameter 'snaktype' = '%s' isn't supported.
137             From Wikibase::Datatype::Struct::Snak::struct2obj():
138             From Wikibase::Datatype::Struct::Value::struct2obj():
139             Entity type '%s' is unsupported.
140             Type doesn't exist.
141             Type '%s' is unsupported.
142              
143             =head1 EXAMPLE1
144              
145             use strict;
146             use warnings;
147              
148             use Data::Printer;
149             use Wikibase::Datatype::Snak;
150             use Wikibase::Datatype::Struct::Utils qw(obj_array_ref2struct);
151             use Wikibase::Datatype::Value::Item;
152             use Wikibase::Datatype::Value::String;
153              
154             my $snak1 = Wikibase::Datatype::Snak->new(
155             'datatype' => 'wikibase-item',
156             'datavalue' => Wikibase::Datatype::Value::Item->new(
157             'value' => 'Q5',
158             ),
159             'property' => 'P31',
160             );
161             my $snak2 = Wikibase::Datatype::Snak->new(
162             'datatype' => 'math',
163             'datavalue' => Wikibase::Datatype::Value::String->new(
164             'value' => 'E = m c^2',
165             ),
166             'property' => 'P2534',
167             );
168              
169             # Convert list of snak objects to structure.
170             my $snaks_ar = obj_array_ref2struct([$snak1, $snak2], 'snaks',
171             'http://test.wikidata.org/entity/');
172              
173             # Dump to output.
174             p $snaks_ar;
175              
176             # Output:
177             # \ {
178             # snaks {
179             # P31 [
180             # [0] {
181             # datatype "wikibase-item",
182             # datavalue {
183             # type "wikibase-entityid",
184             # value {
185             # entity-type "item",
186             # id "Q5",
187             # numeric-id 5
188             # }
189             # },
190             # property "P31",
191             # snaktype "value"
192             # }
193             # ],
194             # P2534 [
195             # [0] {
196             # datatype "math",
197             # datavalue {
198             # type "string",
199             # value "E = m c^2"
200             # },
201             # property "P2534",
202             # snaktype "value"
203             # }
204             # ]
205             # },
206             # snaks-order [
207             # [0] "P31",
208             # [1] "P2534"
209             # ]
210             # }
211              
212             =head1 EXAMPLE2
213              
214             use strict;
215             use warnings;
216              
217             use Wikibase::Datatype::Struct::Utils qw(struct2snaks_array_ref);
218              
219             my $struct_hr = {
220             'snaks' => {
221             'P31' => [{
222             'datatype' => 'wikibase-item',
223             'datavalue' => {
224             'type' => 'wikibase-entityid',
225             'value' => {
226             'entity-type' => 'item',
227             'id' => 'Q5',
228             'numeric-id' => 5,
229             },
230             },
231             'property' => 'P31',
232             'snaktype' => 'value',
233              
234             }],
235             'P2534' => [{
236             'datatype' => 'math',
237             'datavalue' => {
238             'type' => 'string',
239             'value' => 'E = m c^2',
240             },
241             'property' => 'P2534',
242             'snaktype' => 'value',
243             }],
244             },
245             'snaks-order' => [
246             'P31',
247             'P2534',
248             ],
249             };
250              
251             # Convert snaks structure to list of Snak objects.
252             my $snaks_ar = struct2snaks_array_ref($struct_hr, 'snaks');
253              
254             # Print out.
255             foreach my $snak (@{$snaks_ar}) {
256             print 'Property: '.$snak->property."\n";
257             print 'Type: '.$snak->datatype."\n";
258             print 'Value: '.$snak->datavalue->value."\n";
259             print "\n";
260             }
261              
262             # Output:
263             # Property: P31
264             # Type: wikibase-item
265             # Value: Q5
266             #
267             # Property: P2534
268             # Type: math
269             # Value: E = m c^2
270             #
271              
272             =head1 DEPENDENCIES
273              
274             L<Error::Pure>,
275             L<Exporter>,
276             L<List::MoreUtils>.
277              
278             =head1 SEE ALSO
279              
280             =over
281              
282             =item L<Wikibase::Datatype::Struct>
283              
284             Wikibase structure serialization.
285              
286             =back
287              
288             =head1 REPOSITORY
289              
290             L<https://github.com/michal-josef-spacek/Wikibase-Datatype-Struct>
291              
292             =head1 AUTHOR
293              
294             Michal Josef Špaček L<mailto:skim@cpan.org>
295              
296             L<http://skim.cz>
297              
298             =head1 LICENSE AND COPYRIGHT
299              
300             © 2020-2022 Michal Josef Špaček
301              
302             BSD 2-Clause License
303              
304             =head1 VERSION
305              
306             0.09
307              
308             =cut