File Coverage

blib/lib/BibTeX/Parser/Entry.pm
Criterion Covered Total %
statement 131 160 81.8
branch 44 56 78.5
condition 8 8 100.0
subroutine 23 25 92.0
pod 16 16 100.0
total 222 265 83.7


line stmt bran cond sub pod time code
1             package BibTeX::Parser::Entry;
2             {
3             $BibTeX::Parser::Entry::VERSION = '1.02';
4             }
5              
6 18     18   191648 use warnings;
  18         72  
  18         757  
7 18     18   128 use strict;
  18         48  
  18         497  
8              
9 18     18   1242 use BibTeX::Parser;
  18         50  
  18         737  
10 18     18   9633 use BibTeX::Parser::Author;
  18         68  
  18         11463  
11              
12              
13              
14             sub new {
15 129     129 1 102882 my ($class, $type, $key, $parse_ok, $fieldsref) = @_;
16              
17 129 100       661 my %fields = defined $fieldsref ? %$fieldsref : ();
18 129         282 my $i=0;
19 129         436 foreach my $field (keys %fields) {
20 92 50       261 if ($field !~ /^_/) {
21 92         224 $fields{_fieldnums}->{$field}=$i;
22 92         163 $i++;
23             }
24             }
25 129 100       364 if (defined $type) {
26 92         217 $fields{_type} = uc($type);
27             }
28 129         296 $fields{_key} = $key;
29 129         257 $fields{_parse_ok} = $parse_ok;
30 129         261 $fields{_raw} = '';
31 129         559 return bless \%fields, $class;
32             }
33              
34              
35              
36             sub parse_ok {
37 51     51 1 5545 my $self = shift;
38 51 100       202 if (@_) {
39 34         103 $self->{_parse_ok} = shift;
40             }
41 51         207 $self->{_parse_ok};
42             }
43              
44              
45             sub error {
46 2     2 1 7 my $self = shift;
47 2 50       12 if (@_) {
48 2         14 $self->{_error} = shift;
49 2         9 $self->parse_ok(0);
50             }
51 2 50       6 return $self->parse_ok ? undef : $self->{_error};
52             }
53              
54              
55             sub type {
56 65 100   65 1 1066 if (scalar @_ == 1) {
57             # get
58 28         64 my $self = shift;
59 28         206 return $self->{_type};
60             } else {
61             # set
62 37         128 my ($self, $newval) = @_;
63 37         222 $self->{_type} = uc($newval);
64             }
65             }
66              
67              
68             sub key {
69 75 100   75 1 3385 if (scalar @_ == 1) {
70             # get
71 43         99 my $self = shift;
72 43         199 return $self->{_key};
73             } else {
74             # set
75 32         184 my ($self, $newval) = @_;
76 32         146 $self->{_key} = $newval;
77             }
78              
79             }
80              
81              
82             sub field {
83 331 100   331 1 958 if (scalar @_ == 2) {
84             # get
85 194         451 my ($self, $field) = @_;
86 194         889 return $self->{ lc( $field ) };
87             } else {
88 137         643 my ($self, $key, $value) = @_;
89 137         427 my $field = lc ($key);
90 137         502 $self->{$field} = $value; #_sanitize_field($value);
91 137 100       535 if (!exists($self->{_fieldnums}->{$field})) {
92 136         278 my $num = scalar keys %{$self->{_fieldnums}};
  136         440  
93 136         535 $self->{_fieldnums}->{$field} = $num;
94             }
95             }
96              
97             }
98              
99 18     18   11937 use LaTeX::ToUnicode qw( convert );
  18         112933  
  18         7958  
100              
101              
102             sub cleaned_field {
103 90     90 1 214 my ( $self, $field, @options ) = @_;
104 90 50       184 if ( $field =~ /author|editor/i ) {
105 0         0 return $self->field( $field );
106             } else {
107 90         266 return convert( $self->field( lc $field ), @options );
108             }
109             }
110              
111              
112             sub cleaned_author {
113 1     1 1 2 my $self = shift;
114 1         4 $self->_handle_cleaned_author_editor( [ $self->author ], @_ );
115             }
116              
117              
118             sub cleaned_editor {
119 0     0 1 0 my $self = shift;
120 0         0 $self->_handle_cleaned_author_editor( [ $self->editor ], @_ );
121             }
122              
123             sub _handle_cleaned_author_editor {
124 1     1   3 my ( $self, $authors, @options ) = @_;
125             map {
126 1         3 my $author = $_;
  2         19  
127 2         24 my $new_author = BibTeX::Parser::Author->new;
128             map {
129 4         9 $new_author->$_( convert( $author->$_, @options ) )
130 2         5 } grep { defined $author->$_ } qw( first von last jr );
  8         20  
131 2         8 $new_author;
132             } @$authors;
133             }
134              
135 18     18   234 no LaTeX::ToUnicode;
  18         58  
  18         27056  
136              
137             sub _handle_author_editor {
138 33     33   85 my $type = shift;
139 33         67 my $self = shift;
140 33 50       158 if (@_) {
141 0 0       0 if (@_ == 1) { #single string
142             # my @names = split /\s+and\s+/i, $_[0];
143 0         0 $_[0] =~ s/^\s*//;
144 0         0 $_[0] =~ s/\s*$//;
145 0         0 my @names = BibTeX::Parser::_split_braced_string($_[0],
146             '\s+and\s+');
147 0 0       0 if (!scalar @names) {
148 0         0 $self->error('Bad names in author/editor field');
149 0         0 return;
150             }
151 0         0 $self->{"_$type"} = [map {new BibTeX::Parser::Author $_} @names];
  0         0  
152 0         0 $self->field($type, join " and ", @{$self->{"_$type"}});
  0         0  
153             } else {
154 0         0 $self->{"_$type"} = [];
155 0         0 foreach my $param (@_) {
156 0 0       0 if (ref $param eq "BibTeX::Author") {
157 0         0 push @{$self->{"_$type"}}, $param;
  0         0  
158             } else {
159 0         0 push @{$self->{"_$type"}}, new BibTeX::Parser::Author $param;
  0         0  
160             }
161            
162 0         0 $self->field($type, join " and ", @{$self->{"_$type"}});
  0         0  
163             }
164             }
165             } else {
166 33 100       188 unless ( defined $self->{"_$type"}) {
167 17   100     147 my @names = BibTeX::Parser::_split_braced_string($self->{$type} || "", '\s+and\s+' );
168 17         60 $self->{"_$type"} = [map {new BibTeX::Parser::Author $_} @names];
  32         206  
169             }
170 33         85 return @{$self->{"_$type"}};
  33         245  
171             }
172             }
173              
174              
175              
176             sub author {
177 24     24 1 2468 _handle_author_editor('author', @_);
178             }
179              
180              
181             sub editor {
182 9     9 1 913 _handle_author_editor('editor', @_);
183             }
184              
185              
186             sub fieldlist {
187 1     1 1 5 my $self = shift;
188            
189 1         7 return grep {!/^_/} keys %$self;
  7         39  
190             }
191              
192              
193             sub has {
194 3     3 1 14 my ($self, $field) = @_;
195              
196 3         31 return defined $self->{$field};
197             }
198              
199             sub _sanitize_field {
200 0     0   0 my $value = shift;
201 0         0 for ($value) {
202 0         0 tr/\{\}//d;
203 0         0 s/\\(?!=[ \\])//g;
204 0         0 s/\\\\/\\/g;
205             }
206 0         0 return $value;
207             }
208              
209              
210              
211             sub raw_bibtex {
212 36     36 1 92 my $self = shift;
213 36 50       134 if (@_) {
214 36         155 $self->{_raw} = shift;
215             }
216 36         124 return $self->{_raw};
217             }
218              
219             sub pre {
220 39     39 1 103 my $self = shift;
221 39 100       146 if (@_) {
222 36         136 $self->{_pre} = shift;
223             }
224 39         135 return $self->{_pre};
225             }
226              
227              
228             sub to_string {
229 15     15 1 88 my $self = shift;
230 15         54 my %options=@_;
231 15 100       63 if (!exists($options{canonize_names})) {
232 14         37 $options{canonize_names}=1;
233             }
234 15         157 my @fields = grep {!/^_/} keys %$self;
  180         604  
235             @fields = sort {
236 15         86 $self->{_fieldnums}->{$a} <=>
237 90         328 $self->{_fieldnums}->{$b}} @fields;
238 15         39 my $result = '';
239 15 100       49 if ($options{print_pre}) {
240 3         11 $result .= $self->pre()."\n";
241             }
242 15         54 my $type = $self->type;
243 15 100       53 if (exists($options{type_capitalization})) {
244 3 100       13 if ($options{type_capitalization} eq 'Lowercase') {
245 1         5 $type = lc $type;
246             }
247 3 100       11 if ($options{type_capitalization} eq 'Titlecase') {
248 1         3 $type = ucfirst lc $type;
249             }
250             }
251 15         66 $result .= '@'.$type."{".$self->key.",\n";
252 15         50 foreach my $field (@fields) {
253 73         222 my $value = $self->field($field);
254 73 100 100     277 if ($field eq 'author' && $options{canonize_names}) {
255 14         49 my @names = ($self->author);
256 14         168 $value = join(' and ', @names);
257             }
258 73 100 100     225 if ($field eq 'editor' && $options{canonize_names}) {
259 8         40 my @names = ($self->editor);
260 8         38 $value = join(' and ', @names);
261             }
262 73 100       202 if (exists($options{field_capitalization})) {
263 15 100       40 if ($options{field_capitalization} eq 'Uppercase') {
264 5         9 $field = uc $field;
265             }
266 15 100       35 if ($options{field_capitalization} eq 'Titlecase') {
267 5         15 $field = ucfirst $field;
268             }
269             }
270 73         289 $result .= " $field = {"."$value"."},\n";
271             }
272 15         34 $result .= "}";
273 15         112 return $result;
274             }
275              
276             1; # End of BibTeX::Entry
277              
278             __END__