ai-cr 2.0.0.dev2__py3-none-any.whl → 2.0.2__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.
- {ai_cr-2.0.0.dev2.dist-info → ai_cr-2.0.2.dist-info}/LICENSE +21 -21
- {ai_cr-2.0.0.dev2.dist-info → ai_cr-2.0.2.dist-info}/METADATA +13 -5
- ai_cr-2.0.2.dist-info/RECORD +26 -0
- {ai_cr-2.0.0.dev2.dist-info → ai_cr-2.0.2.dist-info}/WHEEL +1 -1
- gito/__main__.py +4 -4
- gito/bootstrap.py +66 -66
- gito/cli.py +217 -255
- gito/commands/__init__.py +1 -1
- gito/commands/fix.py +157 -157
- gito/commands/gh_post_review_comment.py +63 -0
- gito/commands/{gh_comment.py → gh_react_to_comment.py} +194 -157
- gito/commands/repl.py +5 -2
- gito/config.toml +453 -415
- gito/constants.py +12 -9
- gito/core.py +288 -239
- gito/gh_api.py +35 -0
- gito/issue_trackers.py +49 -15
- gito/pipeline.py +82 -70
- gito/pipeline_steps/jira.py +57 -83
- gito/pipeline_steps/linear.py +85 -0
- gito/project_config.py +73 -71
- gito/report_struct.py +134 -133
- gito/utils.py +226 -214
- ai_cr-2.0.0.dev2.dist-info/RECORD +0 -23
- {ai_cr-2.0.0.dev2.dist-info → ai_cr-2.0.2.dist-info}/entry_points.txt +0 -0
gito/report_struct.py
CHANGED
@@ -1,133 +1,134 @@
|
|
1
|
-
import json
|
2
|
-
import logging
|
3
|
-
from dataclasses import dataclass, field, asdict
|
4
|
-
from datetime import datetime
|
5
|
-
from enum import StrEnum
|
6
|
-
from pathlib import Path
|
7
|
-
|
8
|
-
import microcore as mc
|
9
|
-
from colorama import Fore, Style, Back
|
10
|
-
from microcore.utils import file_link
|
11
|
-
import textwrap
|
12
|
-
|
13
|
-
from .constants import JSON_REPORT_FILE_NAME
|
14
|
-
from .project_config import ProjectConfig
|
15
|
-
from .utils import syntax_hint, block_wrap_lr, max_line_len
|
16
|
-
|
17
|
-
|
18
|
-
@dataclass
|
19
|
-
class Issue:
|
20
|
-
@dataclass
|
21
|
-
class AffectedCode:
|
22
|
-
start_line: int = field()
|
23
|
-
end_line: int | None = field(default=None)
|
24
|
-
file: str = field(default="")
|
25
|
-
proposal: str = field(default="")
|
26
|
-
affected_code: str = field(default="")
|
27
|
-
|
28
|
-
@property
|
29
|
-
def syntax_hint(self) -> str:
|
30
|
-
return syntax_hint(self.file)
|
31
|
-
|
32
|
-
id: str = field()
|
33
|
-
title: str = field()
|
34
|
-
details: str = field(default="")
|
35
|
-
severity: int | None = field(default=None)
|
36
|
-
confidence: int | None = field(default=None)
|
37
|
-
tags: list[str] = field(default_factory=list)
|
38
|
-
file: str = field(default="")
|
39
|
-
affected_lines: list[AffectedCode] = field(default_factory=list)
|
40
|
-
|
41
|
-
def __post_init__(self):
|
42
|
-
self.affected_lines = [
|
43
|
-
Issue.AffectedCode(**dict(file=self.file) | i)
|
44
|
-
for i in self.affected_lines
|
45
|
-
]
|
46
|
-
|
47
|
-
def github_code_link(self, github_env: dict) -> str:
|
48
|
-
url = (
|
49
|
-
f"https://github.com/{github_env['github_repo']}"
|
50
|
-
f"/blob/{github_env['github_pr_sha_or_branch']}"
|
51
|
-
f"/{self.file}"
|
52
|
-
)
|
53
|
-
if self.affected_lines:
|
54
|
-
url += f"#L{self.affected_lines[0].start_line}"
|
55
|
-
if self.affected_lines[0].end_line:
|
56
|
-
url += f"-L{self.affected_lines[0].end_line}"
|
57
|
-
return url
|
58
|
-
|
59
|
-
|
60
|
-
@dataclass
|
61
|
-
class Report:
|
62
|
-
class Format(StrEnum):
|
63
|
-
MARKDOWN = "md"
|
64
|
-
CLI = "cli"
|
65
|
-
|
66
|
-
issues: dict[str, list[Issue]] = field(default_factory=dict)
|
67
|
-
summary: str = field(default="")
|
68
|
-
number_of_processed_files: int = field(default=0)
|
69
|
-
total_issues: int = field(init=False)
|
70
|
-
created_at: str = field(default_factory=lambda: datetime.now().strftime("%Y-%m-%d %H:%M:%S"))
|
71
|
-
model: str = field(default_factory=lambda: mc.config().MODEL)
|
72
|
-
pipeline_out: dict = field(default_factory=dict)
|
73
|
-
|
74
|
-
@property
|
75
|
-
def plain_issues(self):
|
76
|
-
return [
|
77
|
-
issue
|
78
|
-
for file, issues in self.issues.items()
|
79
|
-
for issue in issues
|
80
|
-
]
|
81
|
-
|
82
|
-
def __post_init__(self):
|
83
|
-
issue_id: int = 0
|
84
|
-
for file in self.issues.keys():
|
85
|
-
self.issues[file] = [
|
86
|
-
Issue(
|
87
|
-
**{
|
88
|
-
"id": (issue_id := issue_id + 1),
|
89
|
-
"file": file,
|
90
|
-
} | issue
|
91
|
-
)
|
92
|
-
for issue in self.issues[file]
|
93
|
-
]
|
94
|
-
self.total_issues = issue_id
|
95
|
-
|
96
|
-
def save(self, file_name: str = ""):
|
97
|
-
file_name = file_name or JSON_REPORT_FILE_NAME
|
98
|
-
with open(file_name, "w") as f:
|
99
|
-
json.dump(asdict(self), f, indent=4)
|
100
|
-
logging.info(f"Report saved to {mc.utils.file_link(file_name)}")
|
101
|
-
|
102
|
-
@staticmethod
|
103
|
-
def load(file_name: str | Path = ""):
|
104
|
-
with open(file_name or JSON_REPORT_FILE_NAME, "r") as f:
|
105
|
-
data = json.load(f)
|
106
|
-
data.pop("total_issues", None)
|
107
|
-
return Report(**data)
|
108
|
-
|
109
|
-
def render(
|
110
|
-
self,
|
111
|
-
config: ProjectConfig = None,
|
112
|
-
report_format: Format = Format.MARKDOWN,
|
113
|
-
) -> str:
|
114
|
-
config = config or ProjectConfig.load()
|
115
|
-
template = getattr(config, f"report_template_{report_format}")
|
116
|
-
return mc.prompt(
|
117
|
-
template,
|
118
|
-
report=self,
|
119
|
-
ui=mc.ui,
|
120
|
-
Fore=Fore,
|
121
|
-
Style=Style,
|
122
|
-
Back=Back,
|
123
|
-
file_link=file_link,
|
124
|
-
textwrap=textwrap,
|
125
|
-
block_wrap_lr=block_wrap_lr,
|
126
|
-
max_line_len=max_line_len,
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
print(
|
1
|
+
import json
|
2
|
+
import logging
|
3
|
+
from dataclasses import dataclass, field, asdict
|
4
|
+
from datetime import datetime
|
5
|
+
from enum import StrEnum
|
6
|
+
from pathlib import Path
|
7
|
+
|
8
|
+
import microcore as mc
|
9
|
+
from colorama import Fore, Style, Back
|
10
|
+
from microcore.utils import file_link
|
11
|
+
import textwrap
|
12
|
+
|
13
|
+
from .constants import JSON_REPORT_FILE_NAME, HTML_TEXT_ICON
|
14
|
+
from .project_config import ProjectConfig
|
15
|
+
from .utils import syntax_hint, block_wrap_lr, max_line_len
|
16
|
+
|
17
|
+
|
18
|
+
@dataclass
|
19
|
+
class Issue:
|
20
|
+
@dataclass
|
21
|
+
class AffectedCode:
|
22
|
+
start_line: int = field()
|
23
|
+
end_line: int | None = field(default=None)
|
24
|
+
file: str = field(default="")
|
25
|
+
proposal: str = field(default="")
|
26
|
+
affected_code: str = field(default="")
|
27
|
+
|
28
|
+
@property
|
29
|
+
def syntax_hint(self) -> str:
|
30
|
+
return syntax_hint(self.file)
|
31
|
+
|
32
|
+
id: str = field()
|
33
|
+
title: str = field()
|
34
|
+
details: str = field(default="")
|
35
|
+
severity: int | None = field(default=None)
|
36
|
+
confidence: int | None = field(default=None)
|
37
|
+
tags: list[str] = field(default_factory=list)
|
38
|
+
file: str = field(default="")
|
39
|
+
affected_lines: list[AffectedCode] = field(default_factory=list)
|
40
|
+
|
41
|
+
def __post_init__(self):
|
42
|
+
self.affected_lines = [
|
43
|
+
Issue.AffectedCode(**dict(file=self.file) | i)
|
44
|
+
for i in self.affected_lines
|
45
|
+
]
|
46
|
+
|
47
|
+
def github_code_link(self, github_env: dict) -> str:
|
48
|
+
url = (
|
49
|
+
f"https://github.com/{github_env['github_repo']}"
|
50
|
+
f"/blob/{github_env['github_pr_sha_or_branch']}"
|
51
|
+
f"/{self.file}"
|
52
|
+
)
|
53
|
+
if self.affected_lines:
|
54
|
+
url += f"#L{self.affected_lines[0].start_line}"
|
55
|
+
if self.affected_lines[0].end_line:
|
56
|
+
url += f"-L{self.affected_lines[0].end_line}"
|
57
|
+
return url
|
58
|
+
|
59
|
+
|
60
|
+
@dataclass
|
61
|
+
class Report:
|
62
|
+
class Format(StrEnum):
|
63
|
+
MARKDOWN = "md"
|
64
|
+
CLI = "cli"
|
65
|
+
|
66
|
+
issues: dict[str, list[Issue]] = field(default_factory=dict)
|
67
|
+
summary: str = field(default="")
|
68
|
+
number_of_processed_files: int = field(default=0)
|
69
|
+
total_issues: int = field(init=False)
|
70
|
+
created_at: str = field(default_factory=lambda: datetime.now().strftime("%Y-%m-%d %H:%M:%S"))
|
71
|
+
model: str = field(default_factory=lambda: mc.config().MODEL)
|
72
|
+
pipeline_out: dict = field(default_factory=dict)
|
73
|
+
|
74
|
+
@property
|
75
|
+
def plain_issues(self):
|
76
|
+
return [
|
77
|
+
issue
|
78
|
+
for file, issues in self.issues.items()
|
79
|
+
for issue in issues
|
80
|
+
]
|
81
|
+
|
82
|
+
def __post_init__(self):
|
83
|
+
issue_id: int = 0
|
84
|
+
for file in self.issues.keys():
|
85
|
+
self.issues[file] = [
|
86
|
+
Issue(
|
87
|
+
**{
|
88
|
+
"id": (issue_id := issue_id + 1),
|
89
|
+
"file": file,
|
90
|
+
} | issue
|
91
|
+
)
|
92
|
+
for issue in self.issues[file]
|
93
|
+
]
|
94
|
+
self.total_issues = issue_id
|
95
|
+
|
96
|
+
def save(self, file_name: str = ""):
|
97
|
+
file_name = file_name or JSON_REPORT_FILE_NAME
|
98
|
+
with open(file_name, "w") as f:
|
99
|
+
json.dump(asdict(self), f, indent=4)
|
100
|
+
logging.info(f"Report saved to {mc.utils.file_link(file_name)}")
|
101
|
+
|
102
|
+
@staticmethod
|
103
|
+
def load(file_name: str | Path = ""):
|
104
|
+
with open(file_name or JSON_REPORT_FILE_NAME, "r") as f:
|
105
|
+
data = json.load(f)
|
106
|
+
data.pop("total_issues", None)
|
107
|
+
return Report(**data)
|
108
|
+
|
109
|
+
def render(
|
110
|
+
self,
|
111
|
+
config: ProjectConfig = None,
|
112
|
+
report_format: Format = Format.MARKDOWN,
|
113
|
+
) -> str:
|
114
|
+
config = config or ProjectConfig.load()
|
115
|
+
template = getattr(config, f"report_template_{report_format}")
|
116
|
+
return mc.prompt(
|
117
|
+
template,
|
118
|
+
report=self,
|
119
|
+
ui=mc.ui,
|
120
|
+
Fore=Fore,
|
121
|
+
Style=Style,
|
122
|
+
Back=Back,
|
123
|
+
file_link=file_link,
|
124
|
+
textwrap=textwrap,
|
125
|
+
block_wrap_lr=block_wrap_lr,
|
126
|
+
max_line_len=max_line_len,
|
127
|
+
HTML_TEXT_ICON=HTML_TEXT_ICON,
|
128
|
+
**config.prompt_vars
|
129
|
+
)
|
130
|
+
|
131
|
+
def to_cli(self, report_format=Format.CLI):
|
132
|
+
output = self.render(report_format=report_format)
|
133
|
+
print("")
|
134
|
+
print(output)
|