|
11 | 11 | from functools import singledispatchmethod |
12 | 12 | from gitingest.schemas import Source, FileSystemFile, FileSystemDirectory, FileSystemSymlink |
13 | 13 | from gitingest.schemas.filesystem import SEPARATOR |
| 14 | +from jinja2 import Environment, BaseLoader |
14 | 15 |
|
15 | 16 | if TYPE_CHECKING: |
16 | 17 | from gitingest.schemas import IngestionQuery |
|
21 | 22 | ] |
22 | 23 |
|
23 | 24 |
|
24 | | -class Formatter: |
25 | | - @singledispatchmethod |
26 | | - def format(self, node: Source, query): |
27 | | - return f"{getattr(node, 'content', '')}" |
28 | | - |
29 | | - @format.register |
30 | | - def _(self, node: FileSystemFile, query): |
31 | | - return ( |
32 | | - f"{SEPARATOR}\n" |
33 | | - f"{node.name}\n" |
34 | | - f"{SEPARATOR}\n\n" |
35 | | - f"{node.content}" |
36 | | - ) |
37 | | - |
38 | | - @format.register |
39 | | - def _(self, node: FileSystemDirectory, query): |
40 | | - formatted = [] |
41 | | - for child in node.children: |
42 | | - formatted.append(self.format(child, query)) |
43 | | - return "\n".join(formatted) |
44 | | - |
45 | | - @format.register |
46 | | - def _(self, node: FileSystemSymlink, query): |
47 | | - target = getattr(node, 'target', None) |
48 | | - target_str = f" -> {target}" if target else "" |
49 | | - return ( |
50 | | - f"{SEPARATOR}\n" |
51 | | - f"{node.name}{target_str}\n" |
52 | | - f"{SEPARATOR}\n" |
53 | | - ) |
54 | | - |
55 | | -class DefaultFormatter(Formatter): |
56 | | - pass |
57 | | - |
58 | 25 | # Backward compatibility |
59 | 26 |
|
60 | 27 | def _create_summary_prefix(query: IngestionQuery, *, single_file: bool = False) -> str: |
@@ -199,3 +166,71 @@ def _format_token_count(text: str) -> str | None: |
199 | 166 | return f"{total_tokens / threshold:.1f}{suffix}" |
200 | 167 |
|
201 | 168 | return str(total_tokens) |
| 169 | + |
| 170 | +# Rename JinjaFormatter to DefaultFormatter throughout the file |
| 171 | +class DefaultFormatter: |
| 172 | + def __init__(self): |
| 173 | + self.env = Environment(loader=BaseLoader()) |
| 174 | + |
| 175 | + @singledispatchmethod |
| 176 | + def format(self, node: Source, query): |
| 177 | + return f"{getattr(node, 'content', '')}" |
| 178 | + |
| 179 | + @singledispatchmethod |
| 180 | + def summary(self, node: Source, query): |
| 181 | + # Default summary: just the name |
| 182 | + return f"{getattr(node, 'name', '')}" |
| 183 | + |
| 184 | + @format.register |
| 185 | + def _(self, node: FileSystemFile, query): |
| 186 | + template = \ |
| 187 | +""" |
| 188 | +{{ SEPARATOR }} |
| 189 | +{{ node.name }} |
| 190 | +{{ SEPARATOR }} |
| 191 | +
|
| 192 | +{{ node.content }} |
| 193 | +""" |
| 194 | + file_template = self.env.from_string(template) |
| 195 | + return file_template.render(SEPARATOR=SEPARATOR, node=node, query=query, formatter=self) |
| 196 | + |
| 197 | + @format.register |
| 198 | + def _(self, node: FileSystemDirectory, query): |
| 199 | + template = \ |
| 200 | +""" |
| 201 | +{% for child in node.children %} |
| 202 | +{{ formatter.format(child, query) }} |
| 203 | +{% endfor %} |
| 204 | +""" |
| 205 | + dir_template = self.env.from_string(template) |
| 206 | + return dir_template.render(node=node, query=query, formatter=self) |
| 207 | + |
| 208 | + @summary.register |
| 209 | + def _(self, node: FileSystemDirectory, query): |
| 210 | + template = """ |
| 211 | +{%- macro render_tree(node, prefix='', is_last=True) -%} |
| 212 | + {{ prefix }}{{ '└── ' if is_last else '├── ' }}{{ node.name }}{% if node.type == 'directory' %}/{% endif %} |
| 213 | + {%- if node.type == 'directory' and node.children %} |
| 214 | + {%- for i, child in enumerate(node.children) %} |
| 215 | + {{ render_tree(child, prefix + (' ' if is_last else '│ '), i == (node.children | length - 1)) }} |
| 216 | + {%- endfor %} |
| 217 | + {%- endif %} |
| 218 | +{%- endmacro %} |
| 219 | +
|
| 220 | +Directory structure: |
| 221 | +{{ render_tree(node) }} |
| 222 | +""" |
| 223 | + summary_template = self.env.from_string(template) |
| 224 | + return summary_template.render(node=node, query=query, formatter=self) |
| 225 | + |
| 226 | + |
| 227 | + @format.register |
| 228 | + def _(self, node: FileSystemSymlink, query): |
| 229 | + template = \ |
| 230 | +""" |
| 231 | +{{ SEPARATOR }} |
| 232 | +{{ node.name }}{% if node.target %} -> {{ node.target }}{% endif %} |
| 233 | +{{ SEPARATOR }} |
| 234 | +""" |
| 235 | + symlink_template = self.env.from_string(template) |
| 236 | + return symlink_template.render(SEPARATOR=SEPARATOR, node=node, query=query, formatter=self) |
0 commit comments