File Coverage

blib/lib/PPI/Token.pm
Criterion Covered Total %
statement 150 157 95.5
branch 14 26 53.8
condition n/a
subroutine 53 53 100.0
pod 6 8 75.0
total 223 244 91.3


line stmt bran cond sub pod time code
1             package PPI::Token;
2              
3             =pod
4              
5             =head1 NAME
6              
7             PPI::Token - A single token of Perl source code
8              
9             =head1 INHERITANCE
10              
11             PPI::Token
12             isa PPI::Element
13              
14             =head1 DESCRIPTION
15              
16             C<PPI::Token> is the abstract base class for all Tokens. In PPI terms, a "Token" is
17             a L<PPI::Element> that directly represents bytes of source code.
18              
19             =head1 METHODS
20              
21             =cut
22              
23 67     67   319 use strict;
  67         99  
  67         2347  
24 67     67   657 use Params::Util qw{_INSTANCE};
  67         5834  
  67         2940  
25 67     67   676 use PPI::Element ();
  67         82  
  67         755  
26 67     67   653 use PPI::Exception ();
  67         101  
  67         2842  
27              
28             our $VERSION = '1.284';
29              
30             our @ISA = 'PPI::Element';
31              
32             # We don't load the abstracts, they are loaded
33             # as part of the inheritance process.
34              
35             # Load the token classes
36 67     67   24545 use PPI::Token::BOM ();
  67         146  
  67         1613  
37 67     67   27030 use PPI::Token::Whitespace ();
  67         151  
  67         1884  
38 67     67   24021 use PPI::Token::Comment ();
  67         160  
  67         1415  
39 67     67   22146 use PPI::Token::Pod ();
  67         202  
  67         1761  
40 67     67   22343 use PPI::Token::Number ();
  67         165  
  67         1786  
41 67     67   25117 use PPI::Token::Number::Binary ();
  67         176  
  67         1724  
42 67     67   23225 use PPI::Token::Number::Octal ();
  67         148  
  67         1659  
43 67     67   23057 use PPI::Token::Number::Hex ();
  67         172  
  67         1777  
44 67     67   25001 use PPI::Token::Number::Float ();
  67         155  
  67         1980  
45 67     67   24904 use PPI::Token::Number::Exp ();
  67         143  
  67         1923  
46 67     67   26593 use PPI::Token::Number::Version ();
  67         171  
  67         2071  
47 67     67   27051 use PPI::Token::Word ();
  67         198  
  67         2415  
48 67     67   23828 use PPI::Token::DashedWord ();
  67         161  
  67         2208  
49 67     67   23982 use PPI::Token::Symbol ();
  67         171  
  67         2409  
50 67     67   22800 use PPI::Token::ArrayIndex ();
  67         482  
  67         2577  
51 67     67   23007 use PPI::Token::Magic ();
  67         184  
  67         2650  
52 67     67   24444 use PPI::Token::Quote::Single ();
  67         154  
  67         2562  
53 67     67   25536 use PPI::Token::Quote::Double ();
  67         178  
  67         2584  
54 67     67   24959 use PPI::Token::Quote::Literal ();
  67         170  
  67         2818  
55 67     67   25397 use PPI::Token::Quote::Interpolate ();
  67         157  
  67         2563  
56 67     67   25194 use PPI::Token::QuoteLike::Backtick ();
  67         131  
  67         2477  
57 67     67   23309 use PPI::Token::QuoteLike::Command ();
  67         172  
  67         2749  
58 67     67   24148 use PPI::Token::QuoteLike::Regexp ();
  67         173  
  67         2549  
59 67     67   24448 use PPI::Token::QuoteLike::Words ();
  67         178  
  67         2952  
60 67     67   26354 use PPI::Token::QuoteLike::Readline ();
  67         155  
  67         2890  
61 67     67   24575 use PPI::Token::Regexp::Match ();
  67         146  
  67         2871  
62 67     67   23703 use PPI::Token::Regexp::Substitute ();
  67         146  
  67         2761  
63 67     67   24232 use PPI::Token::Regexp::Transliterate ();
  67         146  
  67         3053  
64 67     67   24150 use PPI::Token::Operator ();
  67         167  
  67         3366  
65 67     67   22395 use PPI::Token::Cast ();
  67         194  
  67         3295  
66 67     67   23003 use PPI::Token::Structure ();
  67         333  
  67         3773  
67 67     67   24202 use PPI::Token::Label ();
  67         156  
  67         3572  
68 67     67   27084 use PPI::Token::HereDoc ();
  67         247  
  67         3969  
69 67     67   22959 use PPI::Token::Separator ();
  67         188  
  67         3556  
70 67     67   22453 use PPI::Token::Data ();
  67         163  
  67         4498  
71 67     67   25922 use PPI::Token::End ();
  67         169  
  67         4212  
72 67     67   22621 use PPI::Token::Prototype ();
  67         161  
  67         3561  
73 67     67   22571 use PPI::Token::Attribute ();
  67         174  
  67         4024  
74 67     67   346 use PPI::Token::Unknown ();
  67         100  
  67         48247  
75              
76              
77              
78              
79              
80             #####################################################################
81             # Constructor and Related
82              
83             sub new {
84 376189 50   376189 0 3092869 bless { content => (defined $_[1] ? "$_[1]" : '') }, $_[0];
85             }
86              
87             sub set_class {
88 35312     35312 0 42555 my $self = shift;
89             # @_ or throw Exception("No arguments to set_class");
90 35312 50       69932 my $class = substr( $_[0], 0, 12 ) eq 'PPI::Token::' ? shift : 'PPI::Token::' . shift;
91              
92             # Find out if the current and new classes are complex
93 35312 50       116741 my $old_quote = (ref($self) =~ /\b(?:Quote|Regex)\b/o) ? 1 : 0;
94 35312 50       75125 my $new_quote = ($class =~ /\b(?:Quote|Regex)\b/o) ? 1 : 0;
95              
96             # No matter what happens, we will have to rebless
97 35312         60224 bless $self, $class;
98              
99             # If we are changing to or from a Quote style token, we
100             # can't just rebless and need to do some extra thing
101             # Otherwise, we have done enough
102 35312 50       98915 return $class if ($old_quote - $new_quote) == 0;
103              
104             # Make a new token from the old content, and overwrite the current
105             # token's attributes with the new token's attributes.
106 0         0 my $token = $class->new( $self->{content} );
107 0         0 %$self = %$token;
108              
109             # Return the class as a convenience
110 0         0 return $class;
111             }
112              
113              
114              
115              
116              
117             #####################################################################
118             # PPI::Token Methods
119              
120             =pod
121              
122             =head2 set_content $string
123              
124             The C<set_content> method allows you to set/change the string that the
125             C<PPI::Token> object represents.
126              
127             Returns the string you set the Token to
128              
129             =cut
130              
131             sub set_content {
132 1     1 1 5 $_[0]->{content} = $_[1];
133             }
134              
135             =pod
136              
137             =head2 add_content $string
138              
139             The C<add_content> method allows you to add additional bytes of code
140             to the end of the Token.
141              
142             Returns the new full string after the bytes have been added.
143              
144             =cut
145              
146 1     1 1 6 sub add_content { $_[0]->{content} .= $_[1] }
147              
148             =pod
149              
150             =head2 length
151              
152             The C<length> method returns the length of the string in a Token.
153              
154             =cut
155              
156 7     7 1 180 sub length { CORE::length($_[0]->{content}) }
157              
158              
159              
160              
161              
162             #####################################################################
163             # Overloaded PPI::Element methods
164              
165             sub content {
166 2944912     2944912 1 7880966 $_[0]->{content};
167             }
168              
169             # You can insert either a statement, or a non-significant token.
170             sub insert_before {
171 1     1 1 2 my $self = shift;
172 1 50       10 my $Element = _INSTANCE(shift, 'PPI::Element') or return undef;
173 1 50       7 if ( $Element->isa('PPI::Structure') ) {
    50          
174 0         0 return $self->__insert_before($Element);
175             } elsif ( $Element->isa('PPI::Token') ) {
176 1         4 return $self->__insert_before($Element);
177             }
178 0         0 '';
179             }
180              
181             # As above, you can insert a statement, or a non-significant token
182             sub insert_after {
183 1     1 1 2 my $self = shift;
184 1 50       10 my $Element = _INSTANCE(shift, 'PPI::Element') or return undef;
185 1 50       8 if ( $Element->isa('PPI::Structure') ) {
    50          
186 0         0 return $self->__insert_after($Element);
187             } elsif ( $Element->isa('PPI::Token') ) {
188 1         4 return $self->__insert_after($Element);
189             }
190 0         0 '';
191             }
192              
193              
194              
195              
196              
197             #####################################################################
198             # Tokenizer Methods
199              
200             sub __TOKENIZER__on_line_start() { 1 }
201             sub __TOKENIZER__on_line_end() { 1 }
202             sub __TOKENIZER__on_char() { 'Unknown' }
203              
204              
205              
206              
207              
208             #####################################################################
209             # Lexer Methods
210              
211             sub __LEXER__opens {
212             ref($_[0]) eq 'PPI::Token::Structure'
213             and
214 46499 50   46499   257837 $_[0]->{content} =~ /(?:\(|\[|\{)/
215             }
216              
217             sub __LEXER__closes {
218             ref($_[0]) eq 'PPI::Token::Structure'
219             and
220 193007 100   193007   1021627 $_[0]->{content} =~ /(?:\)|\]|\})/
221             }
222              
223             1;
224              
225             =pod
226              
227             =head1 SUPPORT
228              
229             See the L<support section|PPI/SUPPORT> in the main module.
230              
231             =head1 AUTHOR
232              
233             Adam Kennedy E<lt>adamk@cpan.orgE<gt>
234              
235             =head1 COPYRIGHT
236              
237             Copyright 2001 - 2011 Adam Kennedy.
238              
239             This program is free software; you can redistribute
240             it and/or modify it under the same terms as Perl itself.
241              
242             The full text of the license can be found in the
243             LICENSE file included with this module.
244              
245             =cut