lizard 1.17.21__py2.py3-none-any.whl → 1.17.22__py2.py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: lizard
3
- Version: 1.17.21
3
+ Version: 1.17.22
4
4
  Summary: A code analyzer without caring the C/C++ header files. It works with Java, C/C++, JavaScript, Python, Ruby, Swift, Objective C. Metrics includes cyclomatic complexity number etc.
5
5
  Home-page: http://www.lizard.ws
6
6
  Download-URL: https://pypi.python.org/lizard/
@@ -25,7 +25,7 @@ lizard_ext/lizardns.py,sha256=8pztUoRS_UWN24MawwxeHEJgYh49id5PWODUBb6O72U,4184
25
25
  lizard_ext/lizardoutside.py,sha256=FGm2tbBZ17-2OCgmQlD-vobUCfQKb0FAygf86eM3xuM,336
26
26
  lizard_ext/lizardstatementcount.py,sha256=xYk6ixSIItSE1BWQXzrWmduFgGhA3VR817SNKLffyVQ,1182
27
27
  lizard_ext/lizardwordcount.py,sha256=2QYXD7-AtkkgAbi9VSidunMbSsGQ7MKYb6IT-bS-cok,7575
28
- lizard_ext/version.py,sha256=3mpAZCQFxtZ-yEx47ZY238MZafb6rPxy9lZff5hymyA,182
28
+ lizard_ext/version.py,sha256=QmsI3yIoC347UVxr6K-y_Psfaao2y0LygMBCtnGJ7hU,182
29
29
  lizard_ext/xmloutput.py,sha256=-cbh0he4O_X-wX56gkv9AnSPNN0qvR7FACqlBeezUS4,5609
30
30
  lizard_languages/__init__.py,sha256=ArNmUrVSU6HFxhDka1-vWMZpVIM39P-gqv6BoOLNMV8,1522
31
31
  lizard_languages/clike.py,sha256=INd5tkvwEVZm7dx2yHG2OIFHZn7JzQGmnT9WQNFZ2XU,11110
@@ -44,7 +44,7 @@ lizard_languages/jsx.py,sha256=DMagQSEvXZwy9AUj8B2l39PqgcAoZntAmEm67IKF7iM,8890
44
44
  lizard_languages/kotlin.py,sha256=v_o2orEzA5gB9vM_0h-E4QXjrc5Yum-0K6W6_laOThc,2844
45
45
  lizard_languages/lua.py,sha256=3nqBcunBzJrhv4Iqaf8xvbyqxZy3aSxJ-IiHimHFlac,1573
46
46
  lizard_languages/objc.py,sha256=2a1teLdaXZBtCeFiIZer1j_sVx9LZ1CbF2XfnqlvLmk,2319
47
- lizard_languages/perl.py,sha256=bSBolem2X6TjINz7pJGO_WhQxc-pAeiun0Q3RDeUOkY,3367
47
+ lizard_languages/perl.py,sha256=A8_WOGC8-I17E9QzyRCiy3fGbzs9Wmgwpqzg_LL-cdQ,11467
48
48
  lizard_languages/php.py,sha256=8OufyR2TIWyf3bXuTmp37Vwf_tEPF4YV5M3i5_jnguA,1377
49
49
  lizard_languages/python.py,sha256=1e0dKbl82z-i_5dswkKaFIV5WuQDKztPHh9UNmSTLyE,3848
50
50
  lizard_languages/ruby.py,sha256=HL1ZckeuUUJU3QSVAOPsG_Zsl0C6X2PX5_VaWqclzkM,2277
@@ -60,9 +60,9 @@ lizard_languages/ttcn.py,sha256=ygjw_raBmPF-4mgoM8m6CAdyEMpTI-n1kZJK1RL4Vxo,2131
60
60
  lizard_languages/typescript.py,sha256=P_rphg5AXJAk9QetmvVKc2911ilPmiRa0Qa5fHWleJg,3829
61
61
  lizard_languages/vue.py,sha256=KXUBUo2R1zNF8Pffrz_KsQEN44m5XFRMoGXylxKUeT0,1038
62
62
  lizard_languages/zig.py,sha256=NX1iyBstBuJFeAGBOAIaRfrmeBREne2HX6Pt4fXZZTQ,586
63
- lizard-1.17.21.dist-info/LICENSE.txt,sha256=05ZjgQ8Cl1dD9p0BhW-Txzkc5rhCogGJVEuf1GT2Y_M,1303
64
- lizard-1.17.21.dist-info/METADATA,sha256=JSVKupJ-s_F1BqRK88FS30969tOc9TaHxPaPlZzXdzo,15753
65
- lizard-1.17.21.dist-info/WHEEL,sha256=Kh9pAotZVRFj97E15yTA4iADqXdQfIVTHcNaZTjxeGM,110
66
- lizard-1.17.21.dist-info/entry_points.txt,sha256=ZBqPhu-J3NoGGW5vn2Gfyoo0vdVlgBgM-wlNm0SGYUQ,39
67
- lizard-1.17.21.dist-info/top_level.txt,sha256=5NTrTaOLhHuTzXaGcZPKfuaOgUv7WafNGe0Zl5aycpg,35
68
- lizard-1.17.21.dist-info/RECORD,,
63
+ lizard-1.17.22.dist-info/LICENSE.txt,sha256=05ZjgQ8Cl1dD9p0BhW-Txzkc5rhCogGJVEuf1GT2Y_M,1303
64
+ lizard-1.17.22.dist-info/METADATA,sha256=DRaFaomcvd6fv88S08lNd74h2nmJLdwXo7b4VBz4g04,15753
65
+ lizard-1.17.22.dist-info/WHEEL,sha256=Kh9pAotZVRFj97E15yTA4iADqXdQfIVTHcNaZTjxeGM,110
66
+ lizard-1.17.22.dist-info/entry_points.txt,sha256=ZBqPhu-J3NoGGW5vn2Gfyoo0vdVlgBgM-wlNm0SGYUQ,39
67
+ lizard-1.17.22.dist-info/top_level.txt,sha256=5NTrTaOLhHuTzXaGcZPKfuaOgUv7WafNGe0Zl5aycpg,35
68
+ lizard-1.17.22.dist-info/RECORD,,
lizard_ext/version.py CHANGED
@@ -3,4 +3,4 @@
3
3
  #
4
4
  # pylint: disable=missing-docstring,invalid-name
5
5
 
6
- version = "1.17.21"
6
+ version = "1.17.22"
lizard_languages/perl.py CHANGED
@@ -19,7 +19,7 @@ class PerlReader(CodeReader, ScriptLanguageMixIn):
19
19
 
20
20
  ext = ['pl', 'pm']
21
21
  language_names = ['perl']
22
- _conditions = set(['if', 'elsif', 'unless', 'while', 'until', 'for', 'foreach', '&&', '||', '?', 'when'])
22
+ _conditions = set(['if', 'elsif', 'unless', 'while', 'until', 'for', 'foreach', '&&', '||', '?', ':', 'when', 'given', 'default', 'do'])
23
23
 
24
24
  def __init__(self, context):
25
25
  super(PerlReader, self).__init__(context)
@@ -64,34 +64,142 @@ class PerlReader(CodeReader, ScriptLanguageMixIn):
64
64
 
65
65
 
66
66
  class PerlStates(CodeStateMachine):
67
- _conditions = set(['if', 'elsif', 'unless', 'while', 'until', 'for', 'foreach'])
67
+ _conditions = set(['if', 'elsif', 'unless', 'while', 'until', 'for', 'foreach', '&&', '||', '?', ':', 'when', 'given', 'default', 'do'])
68
68
 
69
69
  def __init__(self, context):
70
70
  super(PerlStates, self).__init__(context)
71
71
  self.function_name = ''
72
+ self.package_name = ''
73
+ self.variable_name = ''
72
74
  self.brace_count = 0
75
+ self.paren_count = 0
76
+ self.in_attribute = False
77
+ self.anonymous_count = 0
73
78
  self._state = self._state_global
74
79
 
75
80
  def _state_global(self, token):
76
- if token == 'sub':
81
+ if token == 'package':
82
+ self.next(self._state_package_dec)
83
+ elif token == 'sub':
77
84
  self.function_name = ''
78
85
  self.next(self._state_function_dec)
79
86
  elif token == '{':
80
87
  self.brace_count += 1
81
88
  elif token == '}':
82
89
  self.brace_count -= 1
90
+ elif token == '(':
91
+ self.paren_count += 1
92
+ self.next(self._state_function_call)
93
+ elif token == '$' or token == 'my' or token == 'our' or token == 'local':
94
+ self.variable_name = ''
95
+ self.next(self._state_variable)
96
+
97
+ def _state_package_dec(self, token):
98
+ if not token.isspace():
99
+ self.package_name = token
100
+ self.next(self._state_global)
101
+
102
+ def _state_variable(self, token):
103
+ if token == '$':
104
+ # Skip the $ in variable names
105
+ pass
106
+ elif token == '=':
107
+ self.next(self._state_assignment)
108
+ elif token == ';':
109
+ self.variable_name = ''
110
+ self.next(self._state_global)
111
+ elif not token.isspace() and self.variable_name == '':
112
+ self.variable_name = token
113
+
114
+ def _state_assignment(self, token):
115
+ if token == 'sub':
116
+ self.next(self._state_anon_sub)
117
+ elif token == ';':
118
+ self.variable_name = ''
119
+ self.next(self._state_global)
120
+
121
+ def _state_function_call(self, token):
122
+ if token == 'sub':
123
+ # Inline anonymous subroutine as argument
124
+ self.anonymous_count += 1
125
+ full_name = f"<anonymous>"
126
+ if self.package_name:
127
+ full_name = f"{self.package_name}::{full_name}"
128
+
129
+ self.context.try_new_function(full_name)
130
+ self.context.confirm_new_function()
131
+ self.next(self._state_anon_brace_search)
132
+ elif token == ')':
133
+ self.paren_count -= 1
134
+ if self.paren_count == 0:
135
+ self.next(self._state_global)
136
+ elif token == '(':
137
+ self.paren_count += 1
138
+
139
+ def _state_anon_sub(self, token):
140
+ if token == '{':
141
+ self.brace_count = 1
142
+ full_name = '<anonymous>'
143
+ # Use variable name if available for more readable function names
144
+ if self.variable_name:
145
+ full_name = '$' + self.variable_name
146
+
147
+ if self.package_name:
148
+ full_name = f"{self.package_name}::{full_name}"
149
+
150
+ self.context.try_new_function(full_name)
151
+ self.context.confirm_new_function()
152
+ self.next(self._state_function_body)
83
153
 
84
154
  def _state_function_dec(self, token):
85
155
  if token == '{':
86
156
  self.brace_count = 1
87
157
  if self.function_name:
88
- self.context.try_new_function(self.function_name)
158
+ full_name = self.function_name
159
+ if self.package_name:
160
+ full_name = f"{self.package_name}::{self.function_name}"
161
+ self.context.try_new_function(full_name)
89
162
  self.context.confirm_new_function()
90
163
  self.next(self._state_function_body)
164
+ elif token == ':':
165
+ self.in_attribute = True
91
166
  elif token == ';':
167
+ # Forward declaration like "sub func_name;"
168
+ if self.function_name:
169
+ full_name = self.function_name
170
+ if self.package_name:
171
+ full_name = f"{self.package_name}::{self.function_name}"
172
+ self.context.try_new_function(full_name)
173
+ self.context.confirm_new_function()
174
+ # Empty function body
175
+ self.context.end_of_function()
92
176
  self.next(self._state_global)
177
+ elif token == 'sub':
178
+ # Handle anonymous subroutine like 'callback(sub { ... })'
179
+ self.anonymous_count += 1
180
+ full_name = f"<anonymous>"
181
+ if self.package_name:
182
+ full_name = f"{self.package_name}::{full_name}"
183
+ self.context.try_new_function(full_name)
184
+ self.context.confirm_new_function()
185
+ self.next(self._state_anon_brace_search)
93
186
  elif not token.isspace():
94
- self.function_name = token
187
+ if not self.in_attribute:
188
+ self.function_name = token
189
+ else:
190
+ # Skip attribute name
191
+ self.in_attribute = False
192
+
193
+ def _state_anon_brace_search(self, token):
194
+ if token == '{':
195
+ self.brace_count = 1
196
+ self.next(self._state_function_body)
197
+ elif token == '(':
198
+ self.paren_count += 1
199
+ elif token == ')':
200
+ self.paren_count -= 1
201
+ if self.paren_count == 0:
202
+ self.next(self._state_global)
95
203
 
96
204
  def _state_function_body(self, token):
97
205
  if token == '{':
@@ -100,4 +208,108 @@ class PerlStates(CodeStateMachine):
100
208
  self.brace_count -= 1
101
209
  if self.brace_count == 0:
102
210
  self.context.end_of_function()
103
- self.next(self._state_global)
211
+ self.next(self._state_global)
212
+ elif token == '?':
213
+ # Ternary operator increases complexity
214
+ self.context.add_condition()
215
+ elif token == ':':
216
+ # Colon part of ternary operator also increases complexity
217
+ self.context.add_condition()
218
+ elif token == 'sub':
219
+ # Check if it's a nested named subroutine or anonymous
220
+ self.next(self._state_nested_sub_dec)
221
+ elif token == '(':
222
+ # Track function calls inside function body
223
+ self.paren_count += 1
224
+ self.next(self._state_nested_call)
225
+
226
+ def _state_nested_sub_dec(self, token):
227
+ if token.isspace():
228
+ return
229
+ elif token == '{':
230
+ # Anonymous sub
231
+ self.brace_count += 1
232
+ self.anonymous_count += 1
233
+ anon_name = f"<anonymous>"
234
+ if self.package_name:
235
+ anon_name = f"{self.package_name}::{anon_name}"
236
+ self.context.add_condition() # Count sub as a condition
237
+ self.next(self._state_function_body)
238
+ else:
239
+ # Named nested sub
240
+ nested_func_name = token
241
+ full_name = nested_func_name
242
+ if self.package_name:
243
+ full_name = f"{self.package_name}::{nested_func_name}"
244
+
245
+ # Save current function state
246
+ saved_func_context = self.context
247
+
248
+ # Create a new function for the nested sub
249
+ self.context.try_new_function(full_name)
250
+ self.context.confirm_new_function()
251
+ self.next(self._state_nested_named_sub_brace_search)
252
+
253
+ def _state_nested_named_sub_brace_search(self, token):
254
+ if token == '{':
255
+ self.brace_count = 1
256
+ self.next(self._state_nested_sub_body)
257
+ elif token.isspace():
258
+ return
259
+ elif token == ':':
260
+ # Handle attributes in nested sub
261
+ self.in_attribute = True
262
+ return
263
+ elif token == ';':
264
+ # Forward declaration
265
+ self.context.end_of_function()
266
+ self.next(self._state_function_body)
267
+
268
+ def _state_nested_sub_body(self, token):
269
+ if token == '{':
270
+ self.brace_count += 1
271
+ elif token == '}':
272
+ self.brace_count -= 1
273
+ if self.brace_count == 0:
274
+ # End the nested function
275
+ self.context.end_of_function()
276
+ # Return to parent function
277
+ self.next(self._state_function_body)
278
+
279
+ def _state_nested_call(self, token):
280
+ if token == 'sub':
281
+ # Inline anonymous subroutine as argument
282
+ self.anonymous_count += 1
283
+ full_name = f"<anonymous>"
284
+ if self.package_name:
285
+ full_name = f"{self.package_name}::{full_name}"
286
+
287
+ self.context.try_new_function(full_name)
288
+ self.context.confirm_new_function()
289
+ self.next(self._state_nested_anon_search)
290
+ elif token == ')':
291
+ self.paren_count -= 1
292
+ if self.paren_count == 0:
293
+ self.next(self._state_function_body)
294
+ elif token == '(':
295
+ self.paren_count += 1
296
+
297
+ def _state_nested_anon_search(self, token):
298
+ if token == '{':
299
+ self.brace_count += 1
300
+ self.next(self._state_nested_anon_body)
301
+ elif token == '(':
302
+ self.paren_count += 1
303
+ elif token == ')':
304
+ self.paren_count -= 1
305
+ if self.paren_count == 0:
306
+ self.next(self._state_function_body)
307
+
308
+ def _state_nested_anon_body(self, token):
309
+ if token == '{':
310
+ self.brace_count += 1
311
+ elif token == '}':
312
+ self.brace_count -= 1
313
+ if self.brace_count == 1: # Back to outer function level
314
+ self.context.end_of_function()
315
+ self.next(self._state_function_body)