cod8a 0.1.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.
- cod8a/__init__.py +3 -0
- cod8a/cli.py +93 -0
- cod8a/cod8a.py +4 -0
- cod8a/dotnet/CodeAnalysis/CodeAnalyzer.csproj +14 -0
- cod8a/dotnet/CodeAnalysis/CodeAnalyzer.csproj.lscache +262 -0
- cod8a/dotnet/CodeAnalysis/Parsers/BaseParser.cs +17 -0
- cod8a/dotnet/CodeAnalysis/Parsers/FileParser.cs +150 -0
- cod8a/dotnet/CodeAnalysis/Parsers/ProjectParser.cs +37 -0
- cod8a/dotnet/CodeAnalysis/Parsers/SolutionParser.cs +17 -0
- cod8a/dotnet/CodeAnalysis/Program.cs +58 -0
- cod8a/dotnet/CodeAnalysis/models/FileStructure.cs +92 -0
- cod8a/dotnet/CodeAnalysis/models/ProjectStructure.cs +29 -0
- cod8a/dotnet/CodeAnalysis/models/SolutionStructure.cs +28 -0
- cod8a/dotnet/Test/CodeAnalyzerTest.csproj +25 -0
- cod8a/dotnet/Test/Mermaid/ClassDiagramTest.cs +71 -0
- cod8a/enums/__init__.py +0 -0
- cod8a/enums/diagram_type.py +10 -0
- cod8a/generators/mermaid/class_diagram.py +165 -0
- cod8a/generators/mermaid/flowchart_diagram.py +51 -0
- cod8a/generators/mermaid/sequence_diagram.py +80 -0
- cod8a/helpers/__init__.py +0 -0
- cod8a/helpers/cli_helper.py +79 -0
- cod8a/models/__init__.py +0 -0
- cod8a/models/models.py +60 -0
- cod8a/parsers/dotnet_parser.py +100 -0
- cod8a/parsers/python_parser.py +138 -0
- cod8a-0.1.0.dist-info/METADATA +134 -0
- cod8a-0.1.0.dist-info/RECORD +31 -0
- cod8a-0.1.0.dist-info/WHEEL +4 -0
- cod8a-0.1.0.dist-info/entry_points.txt +4 -0
- cod8a-0.1.0.dist-info/licenses/LICENSE +21 -0
cod8a/models/models.py
ADDED
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
from typing import List, Optional
|
|
2
|
+
|
|
3
|
+
from pydantic import BaseModel, Field
|
|
4
|
+
from pydantic.dataclasses import dataclass
|
|
5
|
+
|
|
6
|
+
@dataclass
|
|
7
|
+
class UsingDirective:
|
|
8
|
+
id: int
|
|
9
|
+
name: str
|
|
10
|
+
|
|
11
|
+
@dataclass
|
|
12
|
+
class ParameterStructure:
|
|
13
|
+
name: str
|
|
14
|
+
modifier: str
|
|
15
|
+
type: str
|
|
16
|
+
summary: str
|
|
17
|
+
|
|
18
|
+
@dataclass
|
|
19
|
+
class FieldStructure:
|
|
20
|
+
id: int
|
|
21
|
+
name: str
|
|
22
|
+
modifier: str
|
|
23
|
+
type: str
|
|
24
|
+
summary: str
|
|
25
|
+
|
|
26
|
+
@dataclass
|
|
27
|
+
class MethodStructure:
|
|
28
|
+
id: int
|
|
29
|
+
name: str
|
|
30
|
+
modifier: str
|
|
31
|
+
return_type: str
|
|
32
|
+
parameters: List[ParameterStructure]
|
|
33
|
+
summary: str
|
|
34
|
+
|
|
35
|
+
@dataclass
|
|
36
|
+
class Relationship:
|
|
37
|
+
id: int
|
|
38
|
+
type: str
|
|
39
|
+
parent_name: str
|
|
40
|
+
|
|
41
|
+
@dataclass
|
|
42
|
+
class ClassStructure:
|
|
43
|
+
id: int
|
|
44
|
+
name: str
|
|
45
|
+
methods: List[MethodStructure]
|
|
46
|
+
fields: List[FieldStructure]
|
|
47
|
+
type: str
|
|
48
|
+
associated_item: List[Relationship]
|
|
49
|
+
summary: str
|
|
50
|
+
|
|
51
|
+
class FileStructure(BaseModel):
|
|
52
|
+
id: int
|
|
53
|
+
name: str
|
|
54
|
+
using_directives: Optional[List[UsingDirective]] = []
|
|
55
|
+
classes: Optional[List[ClassStructure]] = []
|
|
56
|
+
|
|
57
|
+
|
|
58
|
+
class ProjectStructure(BaseModel):
|
|
59
|
+
name: str
|
|
60
|
+
files: List[FileStructure] = []
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
import subprocess
|
|
2
|
+
import json
|
|
3
|
+
import os
|
|
4
|
+
import shutil
|
|
5
|
+
from typing import Union, List
|
|
6
|
+
from cod8a.models.models import (
|
|
7
|
+
FileStructure, ProjectStructure, ClassStructure,
|
|
8
|
+
MethodStructure, FieldStructure, ParameterStructure,
|
|
9
|
+
UsingDirective, Relationship
|
|
10
|
+
)
|
|
11
|
+
|
|
12
|
+
class DotnetParser:
|
|
13
|
+
def __init__(self, analyzer_path: str):
|
|
14
|
+
self.analyzer_path = analyzer_path
|
|
15
|
+
|
|
16
|
+
def parse(self, path: str) -> Union[FileStructure, ProjectStructure]:
|
|
17
|
+
if not shutil.which("dotnet"):
|
|
18
|
+
raise Exception("The .NET SDK/Runtime is required to analyze C# files. Please install it or ensure it is in your PATH.")
|
|
19
|
+
|
|
20
|
+
abs_path = os.path.abspath(path)
|
|
21
|
+
cwd = os.path.dirname(self.analyzer_path)
|
|
22
|
+
|
|
23
|
+
# Look for a compiled DLL first (production/distribution mode)
|
|
24
|
+
# Expected path: src/cod8a/dotnet/CodeAnalysis/bin/Release/net10.0/CodeAnalyzer.dll
|
|
25
|
+
dll_path = os.path.join(cwd, "bin", "Release", "net10.0", "CodeAnalyzer.dll")
|
|
26
|
+
|
|
27
|
+
if os.path.exists(dll_path):
|
|
28
|
+
args = ["dotnet", dll_path, abs_path]
|
|
29
|
+
else:
|
|
30
|
+
# Fallback to source-level execution (development mode)
|
|
31
|
+
args = ["dotnet", "run", "--project", self.analyzer_path, "--", abs_path]
|
|
32
|
+
|
|
33
|
+
result = subprocess.run(args, capture_output=True, text=True, cwd=cwd)
|
|
34
|
+
if result.returncode != 0:
|
|
35
|
+
raise Exception(f"Dotnet analyzer failed: {result.stderr}")
|
|
36
|
+
|
|
37
|
+
# The C# analyzer might still print some messages to stdout.
|
|
38
|
+
# We find the last line which should be our JSON.
|
|
39
|
+
lines = result.stdout.strip().splitlines()
|
|
40
|
+
json_str = next((line for line in reversed(lines) if line.startswith('{') and line.endswith('}')), None)
|
|
41
|
+
|
|
42
|
+
if not json_str:
|
|
43
|
+
raise Exception(f"Could not find JSON in dotnet analyzer output: {result.stdout}")
|
|
44
|
+
|
|
45
|
+
data = json.loads(json_str)
|
|
46
|
+
|
|
47
|
+
if "Files" in data:
|
|
48
|
+
return self._map_project(data)
|
|
49
|
+
return self._map_file(data)
|
|
50
|
+
|
|
51
|
+
def _map_project(self, data: dict) -> ProjectStructure:
|
|
52
|
+
return ProjectStructure(
|
|
53
|
+
name=data.get("Name", ""),
|
|
54
|
+
files=[self._map_file(f) for f in data.get("Files", [])]
|
|
55
|
+
)
|
|
56
|
+
|
|
57
|
+
def _map_file(self, data: dict) -> FileStructure:
|
|
58
|
+
return FileStructure(
|
|
59
|
+
id=data.get("Id", 0),
|
|
60
|
+
name=data.get("Name", ""),
|
|
61
|
+
using_directives=[UsingDirective(u.get("Id", 0), u.get("Name", "")) for u in data.get("UsingDirectives", []) or []],
|
|
62
|
+
classes=[self._map_class(c) for c in data.get("Classes", []) or []],
|
|
63
|
+
)
|
|
64
|
+
|
|
65
|
+
def _map_class(self, data: dict) -> ClassStructure:
|
|
66
|
+
return ClassStructure(
|
|
67
|
+
id=data.get("Id", 0),
|
|
68
|
+
name=data.get("Name", ""),
|
|
69
|
+
methods=[self._map_method(m) for m in data.get("Methods", []) or []],
|
|
70
|
+
fields=[self._map_field(f) for f in data.get("Fields", []) or []],
|
|
71
|
+
type=data.get("Type", "class"),
|
|
72
|
+
associated_item=[self._map_relationship(r) for r in data.get("Relationships", []) or []],
|
|
73
|
+
summary=data.get("Summary", "")
|
|
74
|
+
)
|
|
75
|
+
|
|
76
|
+
def _map_method(self, data: dict) -> MethodStructure:
|
|
77
|
+
return MethodStructure(
|
|
78
|
+
id=data.get("Id", 0),
|
|
79
|
+
name=data.get("Name", ""),
|
|
80
|
+
modifier=data.get("Modifier", ""),
|
|
81
|
+
return_type=data.get("ReturnType", ""),
|
|
82
|
+
parameters=[ParameterStructure(p.get("Name", ""), p.get("Modifier", ""), p.get("Type", ""), p.get("Summary", "")) for p in data.get("Parameters", []) or []],
|
|
83
|
+
summary=data.get("Summary", "")
|
|
84
|
+
)
|
|
85
|
+
|
|
86
|
+
def _map_field(self, data: dict) -> FieldStructure:
|
|
87
|
+
return FieldStructure(
|
|
88
|
+
id=data.get("Id", 0),
|
|
89
|
+
name=data.get("Name", ""),
|
|
90
|
+
modifier=data.get("Modifier", ""),
|
|
91
|
+
type=data.get("Type", ""),
|
|
92
|
+
summary=data.get("Summary", "")
|
|
93
|
+
)
|
|
94
|
+
|
|
95
|
+
def _map_relationship(self, data: dict) -> Relationship:
|
|
96
|
+
return Relationship(
|
|
97
|
+
id=data.get("Id", 0),
|
|
98
|
+
type=data.get("Type", ""),
|
|
99
|
+
parent_name=data.get("AssociatedItem", "")
|
|
100
|
+
)
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
import ast
|
|
2
|
+
import json
|
|
3
|
+
import os
|
|
4
|
+
from typing import List, Union
|
|
5
|
+
from cod8a.models.models import (
|
|
6
|
+
FileStructure, ClassStructure, MethodStructure,
|
|
7
|
+
FieldStructure, ParameterStructure, ProjectStructure, UsingDirective,
|
|
8
|
+
Relationship
|
|
9
|
+
)
|
|
10
|
+
from dataclasses import asdict
|
|
11
|
+
|
|
12
|
+
class PythonParser:
|
|
13
|
+
def __init__(self):
|
|
14
|
+
self._id_counter = 0
|
|
15
|
+
|
|
16
|
+
def _next_id(self):
|
|
17
|
+
self._id_counter += 1
|
|
18
|
+
return self._id_counter
|
|
19
|
+
|
|
20
|
+
def parse_file(self, file_path: str) -> FileStructure:
|
|
21
|
+
with open(file_path, "r", encoding="utf-8") as f:
|
|
22
|
+
tree = ast.parse(f.read())
|
|
23
|
+
|
|
24
|
+
file_name = os.path.basename(file_path)
|
|
25
|
+
|
|
26
|
+
file_struct = FileStructure(id=self._next_id(), name=file_name)
|
|
27
|
+
|
|
28
|
+
for node in tree.body:
|
|
29
|
+
if isinstance(node, (ast.Import, ast.ImportFrom)):
|
|
30
|
+
file_struct.using_directives.extend(self._parse_import(node))
|
|
31
|
+
elif isinstance(node, ast.ClassDef):
|
|
32
|
+
file_struct.classes.append(self._parse_class(node))
|
|
33
|
+
|
|
34
|
+
return file_struct
|
|
35
|
+
|
|
36
|
+
def _parse_import(self, node) -> List[UsingDirective]:
|
|
37
|
+
directives = []
|
|
38
|
+
if isinstance(node, ast.Import):
|
|
39
|
+
for alias in node.names:
|
|
40
|
+
directives.append(UsingDirective(id=self._next_id(), name=alias.name))
|
|
41
|
+
elif isinstance(node, ast.ImportFrom):
|
|
42
|
+
module = node.module or ""
|
|
43
|
+
for alias in node.names:
|
|
44
|
+
directives.append(UsingDirective(id=self._next_id(), name=f"{module}.{alias.name}"))
|
|
45
|
+
return directives
|
|
46
|
+
|
|
47
|
+
def _parse_class(self, node: ast.ClassDef) -> ClassStructure:
|
|
48
|
+
methods = []
|
|
49
|
+
fields = []
|
|
50
|
+
relationships = []
|
|
51
|
+
summary = ast.get_docstring(node) or ""
|
|
52
|
+
|
|
53
|
+
for base in node.bases:
|
|
54
|
+
if isinstance(base, ast.Subscript):
|
|
55
|
+
base_name = ast.unparse(base.value)
|
|
56
|
+
else:
|
|
57
|
+
base_name = ast.unparse(base)
|
|
58
|
+
|
|
59
|
+
# PEP 544 protocols, standard ABCs, or conventional I-prefixed interfaces
|
|
60
|
+
is_interface = base_name in ("Protocol", "typing.Protocol", "ABC") or (len(base_name) > 1 and base_name[0] == 'I' and base_name[1].isupper())
|
|
61
|
+
rel_type = "Interface" if is_interface else "Class"
|
|
62
|
+
|
|
63
|
+
relationships.append(Relationship(
|
|
64
|
+
id=self._next_id(),
|
|
65
|
+
type=rel_type,
|
|
66
|
+
parent_name=base_name
|
|
67
|
+
))
|
|
68
|
+
|
|
69
|
+
for item in node.body:
|
|
70
|
+
if isinstance(item, ast.FunctionDef):
|
|
71
|
+
methods.append(self._parse_method(item))
|
|
72
|
+
elif isinstance(item, ast.Assign):
|
|
73
|
+
# Basic field extraction from class-level assignments
|
|
74
|
+
for target in item.targets:
|
|
75
|
+
if isinstance(target, ast.Name):
|
|
76
|
+
fields.append(FieldStructure(
|
|
77
|
+
id=self._next_id(),
|
|
78
|
+
name=target.id,
|
|
79
|
+
modifier="private" if target.id.startswith("_") else "public",
|
|
80
|
+
type="", # Type inference is complex, leaving empty for now
|
|
81
|
+
summary=""
|
|
82
|
+
))
|
|
83
|
+
elif isinstance(item, ast.AnnAssign):
|
|
84
|
+
if isinstance(item.target, ast.Name):
|
|
85
|
+
fields.append(FieldStructure(
|
|
86
|
+
id=self._next_id(),
|
|
87
|
+
name=item.target.id,
|
|
88
|
+
modifier="private" if item.target.id.startswith("_") else "public",
|
|
89
|
+
type=ast.unparse(item.annotation),
|
|
90
|
+
summary=""
|
|
91
|
+
))
|
|
92
|
+
|
|
93
|
+
return ClassStructure(
|
|
94
|
+
id=self._next_id(),
|
|
95
|
+
name=node.name,
|
|
96
|
+
methods=methods,
|
|
97
|
+
fields=fields,
|
|
98
|
+
type="class",
|
|
99
|
+
associated_item=relationships,
|
|
100
|
+
summary=summary
|
|
101
|
+
)
|
|
102
|
+
|
|
103
|
+
def _parse_method(self, node: ast.FunctionDef) -> MethodStructure:
|
|
104
|
+
summary = ast.get_docstring(node) or ""
|
|
105
|
+
parameters = []
|
|
106
|
+
|
|
107
|
+
for arg in node.args.args:
|
|
108
|
+
arg_type = ast.unparse(arg.annotation) if arg.annotation else ""
|
|
109
|
+
parameters.append(ParameterStructure(
|
|
110
|
+
name=arg.arg,
|
|
111
|
+
modifier="",
|
|
112
|
+
type=arg_type,
|
|
113
|
+
summary=""
|
|
114
|
+
))
|
|
115
|
+
|
|
116
|
+
return MethodStructure(
|
|
117
|
+
id=self._next_id(),
|
|
118
|
+
name=node.name,
|
|
119
|
+
modifier="private" if node.name.startswith("_") else "public",
|
|
120
|
+
return_type=ast.unparse(node.returns) if node.returns else "",
|
|
121
|
+
parameters=parameters,
|
|
122
|
+
summary=summary
|
|
123
|
+
)
|
|
124
|
+
|
|
125
|
+
def parse_project(self, project_path: str) -> List[FileStructure]:
|
|
126
|
+
files = []
|
|
127
|
+
for root, _, filenames in os.walk(project_path):
|
|
128
|
+
for filename in filenames:
|
|
129
|
+
if filename.endswith(".py"):
|
|
130
|
+
files.append(self.parse_file(os.path.join(root, filename)))
|
|
131
|
+
return files
|
|
132
|
+
|
|
133
|
+
def parse(self, path: str) -> Union[FileStructure | ProjectStructure | List[FileStructure]]:
|
|
134
|
+
isFile = os.path.isfile(path)
|
|
135
|
+
if isFile:
|
|
136
|
+
return self.parse_file(path)
|
|
137
|
+
else:
|
|
138
|
+
return self.parse_project(path)
|
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: cod8a
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: cod8a is a code documentation and visualization tool for Python and .NET projects
|
|
5
|
+
License-Expression: MIT
|
|
6
|
+
License-File: LICENSE
|
|
7
|
+
Keywords: visualization,uml,docs,flowchart,class,sequence,diagram
|
|
8
|
+
Author: Akumbom
|
|
9
|
+
Author-email: akumbom5ma@gmail.com
|
|
10
|
+
Maintainer: Marietta Akumbom
|
|
11
|
+
Requires-Python: >=3.13
|
|
12
|
+
Classifier: Programming Language :: Python :: 3
|
|
13
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
14
|
+
Classifier: Programming Language :: Python :: 3.14
|
|
15
|
+
Requires-Dist: click (>=8.3.3,<9.0.0)
|
|
16
|
+
Requires-Dist: pydantic (>=2.13.3,<3.0.0)
|
|
17
|
+
Description-Content-Type: text/markdown
|
|
18
|
+
|
|
19
|
+
# cod8a
|
|
20
|
+
|
|
21
|
+
cod8a pronounced codetta, is a code documentation and visualization tool for **Python** and **.NET** projects.
|
|
22
|
+
|
|
23
|
+
## Installation
|
|
24
|
+
|
|
25
|
+
### Prerequisites
|
|
26
|
+
|
|
27
|
+
- **[Python 3.9+](https://www.python.org/downloads/)**
|
|
28
|
+
- **[.NET 10.0 Runtime or SDK](https://dotnet.microsoft.com/download/dotnet/10.0)** (Required **only** for C#/.NET analysis)
|
|
29
|
+
|
|
30
|
+
### From PyPI (Recommended for Users)
|
|
31
|
+
|
|
32
|
+
Once published, you can install `cod8a` directly using pip:
|
|
33
|
+
|
|
34
|
+
```bash
|
|
35
|
+
pip install cod8a
|
|
36
|
+
```
|
|
37
|
+
|
|
38
|
+
## Development & Contribution
|
|
39
|
+
|
|
40
|
+
If you want to contribute to the project or run it from source:
|
|
41
|
+
|
|
42
|
+
### Setup
|
|
43
|
+
|
|
44
|
+
1. **Fork** the repository on GitHub.
|
|
45
|
+
2. **Clone** your fork:
|
|
46
|
+
|
|
47
|
+
```bash
|
|
48
|
+
git clone https://github.com/yourusername/cod8a.git
|
|
49
|
+
cd cod8a
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
### Development Options
|
|
53
|
+
|
|
54
|
+
#### 1. Local Setup
|
|
55
|
+
3. **Install** Python dependencies using **[Poetry](https://python-poetry.org/docs/#installation)**:
|
|
56
|
+
|
|
57
|
+
```bash
|
|
58
|
+
poetry install
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
4. **Optional**: Ensure .NET 10.0 is installed (if documenting C#)
|
|
62
|
+
|
|
63
|
+
```bash
|
|
64
|
+
dotnet --version
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
#### 2. VS Code Dev Container (Recommended)
|
|
68
|
+
If you use VS Code, you can skip the local setup by using the provided **Dev Container**. It comes pre-configured with Python 3.13, .NET 10.0, and Poetry.
|
|
69
|
+
- Simply open the project in VS Code and click **"Reopen in Container"** when prompted.
|
|
70
|
+
|
|
71
|
+
#### 3. Docker
|
|
72
|
+
You can also run `cod8a` as a standalone container without installing any dependencies locally:
|
|
73
|
+
|
|
74
|
+
```bash
|
|
75
|
+
# Build the image
|
|
76
|
+
docker build -t cod8a .
|
|
77
|
+
|
|
78
|
+
# Run the tool
|
|
79
|
+
docker run -v $(pwd):/app/data cod8a uml -p /app/data/src
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
## Usage
|
|
83
|
+
|
|
84
|
+
The tool uses a CLI interface to analyze code and generate visualizations.
|
|
85
|
+
|
|
86
|
+
### UML Diagrams
|
|
87
|
+
|
|
88
|
+
Generate Mermaid-compatible diagrams (Class, Sequence, Flowchart):
|
|
89
|
+
|
|
90
|
+
```bash
|
|
91
|
+
# General syntax
|
|
92
|
+
cod8a uml -p <path_to_source> -d <diagram_type>
|
|
93
|
+
|
|
94
|
+
# Generate a class diagram (default)
|
|
95
|
+
cod8a uml -p src/my_project
|
|
96
|
+
|
|
97
|
+
# Generate a sequence diagram
|
|
98
|
+
cod8a uml -p src/my_file.py -d sequence
|
|
99
|
+
|
|
100
|
+
# Generate a flowchart
|
|
101
|
+
cod8a uml -p src/my_logic -d flow
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
#### Diagram Type Options:
|
|
105
|
+
- **Class:** `class`, `c`
|
|
106
|
+
- **Sequence:** `sequence`, `seq`, `s`
|
|
107
|
+
- **Flowchart:** `flowchart`, `flow`, `f`
|
|
108
|
+
|
|
109
|
+
### CLI Options
|
|
110
|
+
|
|
111
|
+
- `-p, --path`: Path to the file or directory to analyze.
|
|
112
|
+
- `-d, --diagram`: Type of diagram to generate (default: `class`).
|
|
113
|
+
- `-o, --output`: Output file path (saves as `.mmd`).
|
|
114
|
+
|
|
115
|
+
### Documentation (In development)
|
|
116
|
+
|
|
117
|
+
*Note: This feature is currently in development.*
|
|
118
|
+
|
|
119
|
+
Generate Markdown documentation from code structure:
|
|
120
|
+
|
|
121
|
+
```bash
|
|
122
|
+
# Not yet implemented
|
|
123
|
+
cod8a doc -p path/to/source
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
## Features
|
|
127
|
+
|
|
128
|
+
- **Mermaid Integration:** Generates high-quality Mermaid.js diagrams for visualization.
|
|
129
|
+
- **Supported Diagrams:** Class, Sequence, and Flowchart diagrams.
|
|
130
|
+
- **C# Support:** Uses a Roslyn-based analyzer targeting **.NET 10.0** to extract deep structural information.
|
|
131
|
+
- **Python Support:** Uses AST-based parsing for Python files.
|
|
132
|
+
- **Markdown Documentation (TODO):** Detailed markdown generation for code documentation is currently in development.
|
|
133
|
+
|
|
134
|
+
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
cod8a/__init__.py,sha256=2G4dr62W9xvYmUDbiAB9Y3aMAHEioMOfgJckiD94pQs,54
|
|
2
|
+
cod8a/cli.py,sha256=0HmL65qdaQhwAiiutSIo8USgs6nvGgJLy17Wu44OD5w,3566
|
|
3
|
+
cod8a/cod8a.py,sha256=gsTYm5tYUf8PXKSWHeQ0VhXYnLSITvkVMgqWLstXdZA,63
|
|
4
|
+
cod8a/dotnet/CodeAnalysis/CodeAnalyzer.csproj,sha256=sVG2GYimAmjczJlgbruBqk9zTe5xcY2rj8LR0NuvT3E,368
|
|
5
|
+
cod8a/dotnet/CodeAnalysis/CodeAnalyzer.csproj.lscache,sha256=rCYzc0WoWAA78d4tXG8-1ocyE4TOaOCJzb-xH2uwd1E,8581
|
|
6
|
+
cod8a/dotnet/CodeAnalysis/models/FileStructure.cs,sha256=uZExZpv7gGXbgd2oSG8y3O_O_XY4ZQaZwLTlugczrl8,4862
|
|
7
|
+
cod8a/dotnet/CodeAnalysis/models/ProjectStructure.cs,sha256=sScQ0FVu9b4cSPyer6nMMnqG5X7jbejSK1x8adQ6PCs,715
|
|
8
|
+
cod8a/dotnet/CodeAnalysis/models/SolutionStructure.cs,sha256=Zlnm9fgpeqiXR0aG71W5UgP41rGip2NvHTuWgxD6NQw,789
|
|
9
|
+
cod8a/dotnet/CodeAnalysis/Parsers/BaseParser.cs,sha256=R8AYxrApeB4_MVNBdLT_XfHQMpBV7u5arQkFMvD8824,446
|
|
10
|
+
cod8a/dotnet/CodeAnalysis/Parsers/FileParser.cs,sha256=rTwz2qZjADEfQWnMonLjjH49Jx9X32F1HPB8eOuVchw,6884
|
|
11
|
+
cod8a/dotnet/CodeAnalysis/Parsers/ProjectParser.cs,sha256=jn80iSgfxK329X1jIzw_vbMb-qbWynPnxVf1pHU3_FM,1040
|
|
12
|
+
cod8a/dotnet/CodeAnalysis/Parsers/SolutionParser.cs,sha256=nPuCS-NjOwCckmlscs4AYN8eK16PYrKb99qdYoO5HEI,411
|
|
13
|
+
cod8a/dotnet/CodeAnalysis/Program.cs,sha256=yf85xUT_bRvzXndjVMG6hV8TmD4k-0lO1KToZezDHNY,2052
|
|
14
|
+
cod8a/dotnet/Test/CodeAnalyzerTest.csproj,sha256=lyoChgy51SvkE7RXn-Hr5l-mdqxHtoS42KpZfwivvtA,739
|
|
15
|
+
cod8a/dotnet/Test/Mermaid/ClassDiagramTest.cs,sha256=U8gCKh7MOJP2ZONQxFtroPzwKuMGWCjjbwuK8BI764I,2242
|
|
16
|
+
cod8a/enums/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
17
|
+
cod8a/enums/diagram_type.py,sha256=b5YQJNbHoGVsR9bKVneSWuo90pbS84h3bfMZGgnbLtk,240
|
|
18
|
+
cod8a/generators/mermaid/class_diagram.py,sha256=n7R14LkpYguAc0OUreTuCDi4hQ-E9zOkK9LggplcyK4,6518
|
|
19
|
+
cod8a/generators/mermaid/flowchart_diagram.py,sha256=PM59a1_Enx73SIfILIzeUl1VqOqGpjV8S6_u6ecjJmo,2037
|
|
20
|
+
cod8a/generators/mermaid/sequence_diagram.py,sha256=OZIdj8kPmNhup1rtp3hdFfT6MsHBsFaVDE8NS4vHrC0,3469
|
|
21
|
+
cod8a/helpers/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
22
|
+
cod8a/helpers/cli_helper.py,sha256=aBqHOEUms6EunAvUTT4u_6811VpxlFjZy8dhet1Ebu0,3316
|
|
23
|
+
cod8a/models/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
24
|
+
cod8a/models/models.py,sha256=nZXTTf4xEvWahOVSM1Bm8nfk1-QzVC_xHAU4GBX74GE,1135
|
|
25
|
+
cod8a/parsers/dotnet_parser.py,sha256=di-3lyccQIuRyg4HgW2YMI0_wPIBJYJU3fymDIatX24,4226
|
|
26
|
+
cod8a/parsers/python_parser.py,sha256=z2eRRgg6ajbZEJfGpWLI_Kc4-QNriils-75xqNFEKcw,5366
|
|
27
|
+
cod8a-0.1.0.dist-info/entry_points.txt,sha256=6p5la6hORzIXOUyNIgvEOrpd_WKAtzM2K6f9c1_KsVQ,65
|
|
28
|
+
cod8a-0.1.0.dist-info/licenses/LICENSE,sha256=V7c7VSiN0ITBMW_RLOzN65ku49BtA8tNYsbyS2427Vg,1099
|
|
29
|
+
cod8a-0.1.0.dist-info/METADATA,sha256=IES0VV_q6R8EhVeLRBIoVw-rtLbFe83uLftJnwF8vgc,3588
|
|
30
|
+
cod8a-0.1.0.dist-info/WHEEL,sha256=eY7nduwzv-ldUxpzbRlxwvC693Hg6PX8bWDjEHjZ_dk,88
|
|
31
|
+
cod8a-0.1.0.dist-info/RECORD,,
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Marietta Ngwe Akumbom
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|