tree-sitter-analyzer 1.8.3__py3-none-any.whl → 1.9.0__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.

Potentially problematic release.


This version of tree-sitter-analyzer might be problematic. Click here for more details.

Files changed (64) hide show
  1. tree_sitter_analyzer/__init__.py +1 -1
  2. tree_sitter_analyzer/api.py +4 -4
  3. tree_sitter_analyzer/cli/argument_validator.py +29 -17
  4. tree_sitter_analyzer/cli/commands/advanced_command.py +7 -5
  5. tree_sitter_analyzer/cli/commands/structure_command.py +7 -5
  6. tree_sitter_analyzer/cli/commands/summary_command.py +10 -6
  7. tree_sitter_analyzer/cli/commands/table_command.py +8 -7
  8. tree_sitter_analyzer/cli/info_commands.py +1 -1
  9. tree_sitter_analyzer/cli_main.py +3 -2
  10. tree_sitter_analyzer/core/analysis_engine.py +5 -5
  11. tree_sitter_analyzer/core/cache_service.py +3 -1
  12. tree_sitter_analyzer/core/query.py +17 -5
  13. tree_sitter_analyzer/core/query_service.py +1 -1
  14. tree_sitter_analyzer/encoding_utils.py +3 -3
  15. tree_sitter_analyzer/exceptions.py +61 -50
  16. tree_sitter_analyzer/file_handler.py +3 -0
  17. tree_sitter_analyzer/formatters/base_formatter.py +10 -5
  18. tree_sitter_analyzer/formatters/formatter_registry.py +83 -68
  19. tree_sitter_analyzer/formatters/html_formatter.py +90 -54
  20. tree_sitter_analyzer/formatters/javascript_formatter.py +21 -16
  21. tree_sitter_analyzer/formatters/language_formatter_factory.py +7 -6
  22. tree_sitter_analyzer/formatters/markdown_formatter.py +247 -124
  23. tree_sitter_analyzer/formatters/python_formatter.py +61 -38
  24. tree_sitter_analyzer/formatters/typescript_formatter.py +113 -45
  25. tree_sitter_analyzer/interfaces/mcp_server.py +2 -2
  26. tree_sitter_analyzer/language_detector.py +6 -6
  27. tree_sitter_analyzer/language_loader.py +3 -1
  28. tree_sitter_analyzer/languages/css_plugin.py +120 -61
  29. tree_sitter_analyzer/languages/html_plugin.py +159 -62
  30. tree_sitter_analyzer/languages/java_plugin.py +42 -34
  31. tree_sitter_analyzer/languages/javascript_plugin.py +59 -30
  32. tree_sitter_analyzer/languages/markdown_plugin.py +402 -368
  33. tree_sitter_analyzer/languages/python_plugin.py +111 -64
  34. tree_sitter_analyzer/languages/typescript_plugin.py +241 -132
  35. tree_sitter_analyzer/mcp/server.py +22 -18
  36. tree_sitter_analyzer/mcp/tools/analyze_scale_tool.py +13 -8
  37. tree_sitter_analyzer/mcp/tools/base_tool.py +2 -2
  38. tree_sitter_analyzer/mcp/tools/fd_rg_utils.py +232 -26
  39. tree_sitter_analyzer/mcp/tools/find_and_grep_tool.py +31 -23
  40. tree_sitter_analyzer/mcp/tools/list_files_tool.py +21 -19
  41. tree_sitter_analyzer/mcp/tools/query_tool.py +17 -18
  42. tree_sitter_analyzer/mcp/tools/read_partial_tool.py +30 -31
  43. tree_sitter_analyzer/mcp/tools/search_content_tool.py +131 -77
  44. tree_sitter_analyzer/mcp/tools/table_format_tool.py +29 -16
  45. tree_sitter_analyzer/mcp/utils/file_output_factory.py +64 -51
  46. tree_sitter_analyzer/mcp/utils/file_output_manager.py +34 -24
  47. tree_sitter_analyzer/mcp/utils/gitignore_detector.py +8 -4
  48. tree_sitter_analyzer/models.py +7 -5
  49. tree_sitter_analyzer/plugins/base.py +9 -7
  50. tree_sitter_analyzer/plugins/manager.py +1 -0
  51. tree_sitter_analyzer/queries/css.py +2 -21
  52. tree_sitter_analyzer/queries/html.py +2 -15
  53. tree_sitter_analyzer/queries/markdown.py +30 -41
  54. tree_sitter_analyzer/queries/python.py +20 -5
  55. tree_sitter_analyzer/query_loader.py +5 -5
  56. tree_sitter_analyzer/security/validator.py +114 -86
  57. tree_sitter_analyzer/utils/__init__.py +58 -28
  58. tree_sitter_analyzer/utils/tree_sitter_compat.py +72 -65
  59. tree_sitter_analyzer/utils.py +83 -25
  60. {tree_sitter_analyzer-1.8.3.dist-info → tree_sitter_analyzer-1.9.0.dist-info}/METADATA +19 -5
  61. tree_sitter_analyzer-1.9.0.dist-info/RECORD +109 -0
  62. tree_sitter_analyzer-1.8.3.dist-info/RECORD +0 -109
  63. {tree_sitter_analyzer-1.8.3.dist-info → tree_sitter_analyzer-1.9.0.dist-info}/WHEEL +0 -0
  64. {tree_sitter_analyzer-1.8.3.dist-info → tree_sitter_analyzer-1.9.0.dist-info}/entry_points.txt +0 -0
@@ -30,7 +30,6 @@ HTML_QUERIES: dict[str, str] = {
30
30
  name: (tag_name) @tag_name
31
31
  (#match? @tag_name "^(area|base|br|col|embed|hr|img|input|link|meta|param|source|track|wbr)$"))) @void_element
32
32
  """,
33
-
34
33
  # --- Attributes ---
35
34
  "attribute": """
36
35
  (attribute
@@ -67,7 +66,6 @@ HTML_QUERIES: dict[str, str] = {
67
66
  (#match? @attr_name "^href$")
68
67
  value: (quoted_attribute_value) @href_value) @href_attribute
69
68
  """,
70
-
71
69
  # --- Text Content ---
72
70
  "text": """
73
71
  (text) @text
@@ -75,12 +73,10 @@ HTML_QUERIES: dict[str, str] = {
75
73
  "raw_text": """
76
74
  (raw_text) @raw_text
77
75
  """,
78
-
79
76
  # --- Comments ---
80
77
  "comment": """
81
78
  (comment) @comment
82
79
  """,
83
-
84
80
  # --- Document Structure ---
85
81
  "doctype": """
86
82
  (doctype) @doctype
@@ -88,7 +84,6 @@ HTML_QUERIES: dict[str, str] = {
88
84
  "document": """
89
85
  (document) @document
90
86
  """,
91
-
92
87
  # --- Semantic Elements ---
93
88
  "heading": """
94
89
  (element
@@ -144,7 +139,6 @@ HTML_QUERIES: dict[str, str] = {
144
139
  name: (tag_name) @tag_name
145
140
  (#match? @tag_name "^(td|th)$"))) @table_cell
146
141
  """,
147
-
148
142
  # --- Structure Elements ---
149
143
  "html": """
150
144
  (element
@@ -218,7 +212,6 @@ HTML_QUERIES: dict[str, str] = {
218
212
  name: (tag_name) @tag_name
219
213
  (#match? @tag_name "^span$"))) @span
220
214
  """,
221
-
222
215
  # --- Form Elements ---
223
216
  "form": """
224
217
  (element
@@ -274,7 +267,6 @@ HTML_QUERIES: dict[str, str] = {
274
267
  name: (tag_name) @tag_name
275
268
  (#match? @tag_name "^legend$"))) @legend
276
269
  """,
277
-
278
270
  # --- Media Elements ---
279
271
  "video": """
280
272
  (element
@@ -312,7 +304,6 @@ HTML_QUERIES: dict[str, str] = {
312
304
  name: (tag_name) @tag_name
313
305
  (#match? @tag_name "^svg$"))) @svg
314
306
  """,
315
-
316
307
  # --- Meta Elements ---
317
308
  "meta": """
318
309
  (element
@@ -356,7 +347,6 @@ HTML_QUERIES: dict[str, str] = {
356
347
  name: (tag_name) @tag_name
357
348
  (#match? @tag_name "^base$"))) @base
358
349
  """,
359
-
360
350
  # --- Script and Style Elements ---
361
351
  "script_element": """
362
352
  (script_element) @script_element
@@ -364,7 +354,6 @@ HTML_QUERIES: dict[str, str] = {
364
354
  "style_element": """
365
355
  (style_element) @style_element
366
356
  """,
367
-
368
357
  # --- Name-only Extraction ---
369
358
  "tag_name": """
370
359
  (tag_name) @tag_name
@@ -507,9 +496,7 @@ def get_html_query(name: str) -> str:
507
496
  """
508
497
  if name not in HTML_QUERIES:
509
498
  available = list(HTML_QUERIES.keys())
510
- raise ValueError(
511
- f"HTML query '{name}' does not exist. Available: {available}"
512
- )
499
+ raise ValueError(f"HTML query '{name}' does not exist. Available: {available}")
513
500
 
514
501
  return HTML_QUERIES[name]
515
502
 
@@ -553,4 +540,4 @@ def get_available_html_queries() -> list[str]:
553
540
  Returns:
554
541
  List of query names
555
542
  """
556
- return list(HTML_QUERIES.keys())
543
+ return list(HTML_QUERIES.keys())
@@ -6,100 +6,81 @@ Tree-sitter queries for extracting Markdown elements including headers,
6
6
  links, code blocks, lists, and other structural elements.
7
7
  """
8
8
 
9
- from typing import Dict, List
10
-
11
9
  # Markdown element extraction queries - simplified for compatibility
12
- MARKDOWN_QUERIES: Dict[str, str] = {
10
+ MARKDOWN_QUERIES: dict[str, str] = {
13
11
  # Headers (H1-H6) - simplified
14
12
  "headers": """
15
13
  (atx_heading) @header
16
14
  (setext_heading) @header
17
15
  """,
18
-
19
16
  # Code blocks - simplified
20
17
  "code_blocks": """
21
18
  (fenced_code_block) @code_block
22
19
  (indented_code_block) @code_block
23
20
  """,
24
-
25
21
  # Inline code - simplified
26
22
  "inline_code": """
27
23
  (inline) @inline
28
24
  """,
29
-
30
25
  # Links - simplified to avoid invalid node types
31
26
  "links": """
32
27
  (inline) @inline
33
28
  """,
34
-
35
29
  # Images - simplified to avoid invalid node types
36
30
  "images": """
37
31
  (inline) @inline
38
32
  """,
39
-
40
33
  # Lists - simplified to avoid invalid node types
41
34
  "lists": """
42
35
  (list) @list
43
36
  (list_item) @list_item
44
37
  """,
45
-
46
38
  # Emphasis and strong - simplified
47
39
  "emphasis": """
48
40
  (inline) @inline
49
41
  """,
50
-
51
42
  # Blockquotes - simplified
52
43
  "blockquotes": """
53
44
  (block_quote) @blockquote
54
45
  """,
55
-
56
46
  # Tables - simplified
57
47
  "tables": """
58
48
  (pipe_table) @table
59
49
  """,
60
-
61
50
  # Horizontal rules - simplified
62
51
  "horizontal_rules": """
63
52
  (thematic_break) @hr
64
53
  """,
65
-
66
54
  # HTML blocks - simplified
67
55
  "html_blocks": """
68
56
  (html_block) @html_block
69
57
  """,
70
-
71
58
  # Inline HTML - simplified
72
59
  "inline_html": """
73
60
  (inline) @inline
74
61
  """,
75
-
76
62
  # Strikethrough - simplified
77
63
  "strikethrough": """
78
64
  (inline) @inline
79
65
  """,
80
-
81
66
  # Task lists - simplified
82
67
  "task_lists": """
83
68
  (list_item) @list_item
84
69
  """,
85
-
86
70
  # Footnotes - simplified
87
71
  "footnotes": """
88
72
  (paragraph) @paragraph
89
73
  (inline) @inline
90
74
  """,
91
-
92
75
  # All text content - simplified
93
76
  "text_content": """
94
77
  (paragraph) @paragraph
95
78
  (inline) @inline
96
79
  """,
97
-
98
80
  # Document structure - simplified
99
81
  "document": """
100
82
  (document) @document
101
83
  """,
102
-
103
84
  # All elements (comprehensive) - simplified
104
85
  "all_elements": """
105
86
  (atx_heading) @heading
@@ -119,10 +100,10 @@ MARKDOWN_QUERIES: Dict[str, str] = {
119
100
  }
120
101
 
121
102
  # Query aliases for convenience
122
- QUERY_ALIASES: Dict[str, str] = {
103
+ QUERY_ALIASES: dict[str, str] = {
123
104
  "heading": "headers",
124
105
  "h1": "headers",
125
- "h2": "headers",
106
+ "h2": "headers",
126
107
  "h3": "headers",
127
108
  "h4": "headers",
128
109
  "h5": "headers",
@@ -157,34 +138,36 @@ QUERY_ALIASES: Dict[str, str] = {
157
138
  "everything": "all_elements",
158
139
  }
159
140
 
141
+
160
142
  def get_query(query_name: str) -> str:
161
143
  """
162
144
  Get a query by name, supporting aliases
163
-
145
+
164
146
  Args:
165
147
  query_name: Name of the query or alias
166
-
148
+
167
149
  Returns:
168
150
  Query string
169
-
151
+
170
152
  Raises:
171
153
  KeyError: If query name is not found
172
154
  """
173
155
  # Check direct queries first
174
156
  if query_name in MARKDOWN_QUERIES:
175
157
  return MARKDOWN_QUERIES[query_name]
176
-
158
+
177
159
  # Check aliases
178
160
  if query_name in QUERY_ALIASES:
179
161
  actual_query = QUERY_ALIASES[query_name]
180
162
  return MARKDOWN_QUERIES[actual_query]
181
-
163
+
182
164
  raise KeyError(f"Unknown query: {query_name}")
183
165
 
184
- def get_available_queries() -> List[str]:
166
+
167
+ def get_available_queries() -> list[str]:
185
168
  """
186
169
  Get list of all available query names including aliases
187
-
170
+
188
171
  Returns:
189
172
  List of query names
190
173
  """
@@ -192,31 +175,35 @@ def get_available_queries() -> List[str]:
192
175
  aliases = list(QUERY_ALIASES.keys())
193
176
  return sorted(queries + aliases)
194
177
 
195
- def get_query_info(query_name: str) -> Dict[str, str]:
178
+
179
+ def get_query_info(query_name: str) -> dict[str, str]:
196
180
  """
197
181
  Get information about a query
198
-
182
+
199
183
  Args:
200
184
  query_name: Name of the query
201
-
185
+
202
186
  Returns:
203
187
  Dictionary with query information
204
188
  """
205
189
  try:
206
190
  query_string = get_query(query_name)
207
191
  is_alias = query_name in QUERY_ALIASES
208
- actual_name = QUERY_ALIASES.get(query_name, query_name) if is_alias else query_name
209
-
192
+ actual_name = (
193
+ QUERY_ALIASES.get(query_name, query_name) if is_alias else query_name
194
+ )
195
+
210
196
  return {
211
197
  "name": query_name,
212
198
  "actual_name": actual_name,
213
199
  "is_alias": is_alias,
214
200
  "query": query_string,
215
- "description": _get_query_description(actual_name)
201
+ "description": _get_query_description(actual_name),
216
202
  }
217
203
  except KeyError:
218
204
  return {"error": f"Query '{query_name}' not found"}
219
205
 
206
+
220
207
  def _get_query_description(query_name: str) -> str:
221
208
  """Get description for a query"""
222
209
  descriptions = {
@@ -237,27 +224,29 @@ def _get_query_description(query_name: str) -> str:
237
224
  "footnotes": "Extract footnote references and definitions",
238
225
  "text_content": "Extract all text content",
239
226
  "document": "Extract document root",
240
- "all_elements": "Extract all Markdown elements"
227
+ "all_elements": "Extract all Markdown elements",
241
228
  }
242
229
  return descriptions.get(query_name, "No description available")
243
230
 
231
+
244
232
  def get_all_queries() -> dict[str, str]:
245
233
  """
246
234
  Get all queries for the query loader
247
-
235
+
248
236
  Returns:
249
237
  Dictionary mapping query names to query strings
250
238
  """
251
239
  # Combine direct queries and aliases
252
240
  all_queries = MARKDOWN_QUERIES.copy()
253
-
241
+
254
242
  # Add aliases that point to actual queries
255
243
  for alias, target in QUERY_ALIASES.items():
256
244
  if target in MARKDOWN_QUERIES:
257
245
  all_queries[alias] = MARKDOWN_QUERIES[target]
258
-
246
+
259
247
  return all_queries
260
248
 
249
+
261
250
  # Export main functions and constants
262
251
  __all__ = [
263
252
  "MARKDOWN_QUERIES",
@@ -265,5 +254,5 @@ __all__ = [
265
254
  "get_query",
266
255
  "get_available_queries",
267
256
  "get_query_info",
268
- "get_all_queries"
269
- ]
257
+ "get_all_queries",
258
+ ]
@@ -726,10 +726,22 @@ ALL_QUERIES["functions"] = {
726
726
  "query": FUNCTIONS,
727
727
  "description": "Search all function definitions (including async)",
728
728
  }
729
- ALL_QUERIES["classes"] = {"query": CLASSES, "description": "Search all class definitions"}
730
- ALL_QUERIES["imports"] = {"query": IMPORTS, "description": "Search all import statements"}
731
- ALL_QUERIES["variables"] = {"query": VARIABLES, "description": "Search all variable assignments"}
732
- ALL_QUERIES["decorators"] = {"query": DECORATORS, "description": "Search all decorators"}
729
+ ALL_QUERIES["classes"] = {
730
+ "query": CLASSES,
731
+ "description": "Search all class definitions",
732
+ }
733
+ ALL_QUERIES["imports"] = {
734
+ "query": IMPORTS,
735
+ "description": "Search all import statements",
736
+ }
737
+ ALL_QUERIES["variables"] = {
738
+ "query": VARIABLES,
739
+ "description": "Search all variable assignments",
740
+ }
741
+ ALL_QUERIES["decorators"] = {
742
+ "query": DECORATORS,
743
+ "description": "Search all decorators",
744
+ }
733
745
  ALL_QUERIES["methods"] = {
734
746
  "query": METHODS,
735
747
  "description": "Search all method definitions within classes",
@@ -742,7 +754,10 @@ ALL_QUERIES["comprehensions"] = {
742
754
  "query": COMPREHENSIONS,
743
755
  "description": "Search list, dictionary, and set comprehensions",
744
756
  }
745
- ALL_QUERIES["comments"] = {"query": COMMENTS, "description": "Search comments and docstrings"}
757
+ ALL_QUERIES["comments"] = {
758
+ "query": COMMENTS,
759
+ "description": "Search comments and docstrings",
760
+ }
746
761
  ALL_QUERIES["type_hints"] = {
747
762
  "query": TYPE_HINTS,
748
763
  "description": "Search type hints and annotations",
@@ -6,7 +6,7 @@ Optimized with enhanced caching and lazy loading for better performance.
6
6
 
7
7
  import importlib
8
8
 
9
- from .utils import log_error, log_warning
9
+ from .utils import log_error
10
10
 
11
11
 
12
12
  class QueryLoader:
@@ -58,10 +58,10 @@ class QueryLoader:
58
58
  # Handle None or empty language - return empty dict without warning
59
59
  if not language or language == "None" or language.strip() == "":
60
60
  return {}
61
-
61
+
62
62
  # Normalize language name
63
63
  language = language.strip().lower()
64
-
64
+
65
65
  if language in self._failed_languages:
66
66
  return {}
67
67
 
@@ -108,7 +108,7 @@ class QueryLoader:
108
108
  # Handle invalid language early
109
109
  if not language or language == "None" or language.strip() == "":
110
110
  return None
111
-
111
+
112
112
  queries = self.load_language_queries(language)
113
113
 
114
114
  if query_name in queries:
@@ -140,7 +140,7 @@ class QueryLoader:
140
140
  # Handle invalid language early
141
141
  if not language or language == "None" or language.strip() == "":
142
142
  return []
143
-
143
+
144
144
  queries = self.load_language_queries(language)
145
145
  return list(queries.keys())
146
146