airev 1.1.1__py3-none-any.whl → 1.2.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.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: airev
3
- Version: 1.1.1
3
+ Version: 1.2.0
4
4
  Summary: CLI tool for AI-powered code review with context backtracking
5
5
  Author-email: Tarcisio <tarcisiojunior@gmail.com>
6
6
  License: MIT
@@ -1,5 +1,5 @@
1
- code_reviewer/__init__.py,sha256=WTWWyMXe2oPQMDyLwbxqYUFRu04K8iqu6C9hpCTfxjU,82
2
- code_reviewer/cli.py,sha256=DvVF0o9-hrdUt4D0eWskznDO_Du_1A7LR7GeP8Osujw,6734
1
+ code_reviewer/__init__.py,sha256=39ZhaBH3qjYCSKVmeSRsf21d_-DPx9UOMUCaCnqVRCw,82
2
+ code_reviewer/cli.py,sha256=WaWoN5FFPhOtKoM1LTawCvdT6jb1eVEJyS_G69mYICA,6686
3
3
  code_reviewer/context_builder.py,sha256=XJGsJpc5YOP3jhldpMFnrJ-hLc4uf9O6_efxZa3sbsc,8790
4
4
  code_reviewer/diff_parser.py,sha256=07EO0kJFYuS6GRgDUHH0czYJBKcL8CxLR-jLdq6PShs,6896
5
5
  code_reviewer/models.py,sha256=SUSudQx623zS15yUKd84qOI6zqO-736lu7gjbHSsYwY,4263
@@ -16,13 +16,13 @@ code_reviewer/runners/__init__.py,sha256=cLxawmzHwhymN2xSC7nUWEOpHHvvSklzZOqjy2Q
16
16
  code_reviewer/runners/base.py,sha256=xikp7yI4IcOX86uNA7CUWTCL_oNuHSF9WIs6OP6rnx0,1491
17
17
  code_reviewer/runners/copilot.py,sha256=GpBYO-Splmo66EaUBfCmU8Et-NRB0w2gn7XEtIq9THw,2433
18
18
  code_reviewer/runners/gemini.py,sha256=dadONQIEb0d_y8V3KgYX65JH8IMYmNAP2jC22r0cWXY,2142
19
- code_reviewer/updater/__init__.py,sha256=VLmFh-6RU5XgdiC5MuUdprGMs1KqTKmSSgiC75ctx5w,342
20
- code_reviewer/updater/http_client.py,sha256=B0ZyZdn2kWeKteWn8P-BWT-uYBWtmeD0p-scbz1bAd0,1754
19
+ code_reviewer/updater/__init__.py,sha256=L4irTnOGif85M55jerbjczIr2SxXj74i_vfvWzvfPQo,374
20
+ code_reviewer/updater/http_client.py,sha256=g4PnuY5KKbsA0EqLtHhOK4sxg_6P0drzd1HKxWKJxZw,1746
21
21
  code_reviewer/updater/notifier.py,sha256=o4crwJOnCOSnzqk5gMt0MkYP3xm-yEXIGSnix988YzA,992
22
- code_reviewer/updater/upgrade.py,sha256=NHMLw0p71qUhXGSxoyeKi3eNT1-DGi3eKEiYMqBZJkw,2404
23
- code_reviewer/updater/version_check.py,sha256=j9B8sM6NZwZe01CuRzQjBgqXIZAkShaht0EBOhuMxOo,4432
24
- airev-1.1.1.dist-info/METADATA,sha256=LRW5h-qfxZMleREoJMV4k9h9lB_uXRIZcOEtroaqkD0,6258
25
- airev-1.1.1.dist-info/WHEEL,sha256=wUyA8OaulRlbfwMtmQsvNngGrxQHAvkKcvRmdizlJi0,92
26
- airev-1.1.1.dist-info/entry_points.txt,sha256=LDd8UajxUO4QUs63xt6z635doU7E1XzBPFQZeMrlShU,49
27
- airev-1.1.1.dist-info/top_level.txt,sha256=VqPHk5LmBEOeRJOUhXq1lkW5UiT48zW7a9h7NDy9N0E,14
28
- airev-1.1.1.dist-info/RECORD,,
22
+ code_reviewer/updater/upgrade.py,sha256=xoAfpomMJA_K9t6myeXC6tLEBnKwAgxR9OD8tcJ4YXE,5842
23
+ code_reviewer/updater/version_check.py,sha256=2Zv35s5oeR0dHAGODPwO70dyshECaCzrQx7vEZAXYJM,4917
24
+ airev-1.2.0.dist-info/METADATA,sha256=IVqJfD0FVZFSrjWLHgbSywdE4mdR4a0UHQpynHGr5B8,6258
25
+ airev-1.2.0.dist-info/WHEEL,sha256=wUyA8OaulRlbfwMtmQsvNngGrxQHAvkKcvRmdizlJi0,92
26
+ airev-1.2.0.dist-info/entry_points.txt,sha256=LDd8UajxUO4QUs63xt6z635doU7E1XzBPFQZeMrlShU,49
27
+ airev-1.2.0.dist-info/top_level.txt,sha256=VqPHk5LmBEOeRJOUhXq1lkW5UiT48zW7a9h7NDy9N0E,14
28
+ airev-1.2.0.dist-info/RECORD,,
code_reviewer/__init__.py CHANGED
@@ -1,3 +1,3 @@
1
1
  """Code Reviewer - CLI para revisão de código com IA."""
2
2
 
3
- __version__ = "1.1.1"
3
+ __version__ = "1.2.0"
code_reviewer/cli.py CHANGED
@@ -1,4 +1,4 @@
1
- """CLI Entry Point - Comando principal do code-reviewer."""
1
+ """CLI Entry Point - Comando principal do airev."""
2
2
 
3
3
  import sys
4
4
  import time
@@ -88,13 +88,13 @@ def review(
88
88
 
89
89
  Exemplos:
90
90
 
91
- code-reviewer review --base main
91
+ airev review --base main
92
92
 
93
- code-reviewer review --base develop --runner copilot
93
+ airev review --base develop --runner copilot
94
94
 
95
- code-reviewer review --base main --json-output
95
+ airev review --base main --json-output
96
96
 
97
- code-reviewer review --base main --no-progress
97
+ airev review --base main --no-progress
98
98
  """
99
99
  workdir = workdir or Path.cwd()
100
100
  start_time = time.perf_counter()
@@ -232,7 +232,7 @@ def runners():
232
232
 
233
233
  @main.command()
234
234
  def upgrade():
235
- """Atualiza o code-reviewer para a versão mais recente."""
235
+ """Atualiza o airev para a versão mais recente."""
236
236
  from rich.console import Console
237
237
 
238
238
  console = Console()
@@ -1,11 +1,12 @@
1
1
  """Módulo de auto-update para verificação e atualização de versões."""
2
2
 
3
- from .version_check import check_for_update, UpdateInfo
3
+ from .version_check import check_for_update, clear_cache, UpdateInfo
4
4
  from .notifier import notify_update
5
5
  from .upgrade import detect_installer, run_upgrade
6
6
 
7
7
  __all__ = [
8
8
  "check_for_update",
9
+ "clear_cache",
9
10
  "UpdateInfo",
10
11
  "notify_update",
11
12
  "detect_installer",
@@ -30,7 +30,7 @@ class UrllibClient:
30
30
  try:
31
31
  request = urllib.request.Request(
32
32
  url,
33
- headers={"Accept": "application/json", "User-Agent": "code-reviewer"},
33
+ headers={"Accept": "application/json", "User-Agent": "airev"},
34
34
  )
35
35
  with urllib.request.urlopen(request, timeout=timeout) as response:
36
36
  data = response.read().decode("utf-8")
@@ -1,5 +1,6 @@
1
1
  """Funcionalidades de upgrade do pacote."""
2
2
 
3
+ import json
3
4
  import subprocess
4
5
  import sys
5
6
  from pathlib import Path
@@ -7,7 +8,7 @@ from pathlib import Path
7
8
  from rich.console import Console
8
9
 
9
10
  from .. import __version__
10
- from .version_check import check_for_update
11
+ from .version_check import check_for_update, clear_cache
11
12
 
12
13
 
13
14
  def detect_installer() -> str:
@@ -25,6 +26,78 @@ def detect_installer() -> str:
25
26
  return "pip"
26
27
 
27
28
 
29
+ def get_installed_version(installer: str) -> str | None:
30
+ """Obtém a versão real instalada do airev consultando o instalador.
31
+
32
+ Args:
33
+ installer: "pipx" ou "pip"
34
+
35
+ Returns:
36
+ String com a versão instalada ou None se não conseguir obter
37
+ """
38
+ try:
39
+ if installer == "pipx":
40
+ # Tenta usar pipx list --json
41
+ result = subprocess.run(
42
+ ["pipx", "list", "--json"],
43
+ capture_output=True,
44
+ text=True,
45
+ check=False,
46
+ )
47
+ if result.returncode == 0:
48
+ data = json.loads(result.stdout)
49
+ venvs = data.get("venvs", {})
50
+ if "airev" in venvs:
51
+ metadata = venvs["airev"].get("metadata", {})
52
+ return metadata.get("main_package", {}).get("package_version")
53
+ # Fallback: tenta sem --json (versões antigas do pipx)
54
+ return _get_version_from_pipx_list_text()
55
+ else:
56
+ # pip show airev
57
+ result = subprocess.run(
58
+ [sys.executable, "-m", "pip", "show", "airev"],
59
+ capture_output=True,
60
+ text=True,
61
+ check=False,
62
+ )
63
+ if result.returncode == 0:
64
+ for line in result.stdout.splitlines():
65
+ if line.startswith("Version:"):
66
+ return line.split(":", 1)[1].strip()
67
+ except (subprocess.SubprocessError, json.JSONDecodeError, KeyError):
68
+ pass
69
+ return None
70
+
71
+
72
+ def _get_version_from_pipx_list_text() -> str | None:
73
+ """Fallback para obter versão do pipx list sem --json.
74
+
75
+ Returns:
76
+ String com a versão ou None se não encontrar
77
+ """
78
+ try:
79
+ result = subprocess.run(
80
+ ["pipx", "list"],
81
+ capture_output=True,
82
+ text=True,
83
+ check=False,
84
+ )
85
+ if result.returncode == 0:
86
+ # Procura por linha como "airev 1.0.0" ou "package airev 1.0.0"
87
+ for line in result.stdout.splitlines():
88
+ if "airev" in line.lower():
89
+ parts = line.split()
90
+ for i, part in enumerate(parts):
91
+ if "airev" in part.lower() and i + 1 < len(parts):
92
+ version = parts[i + 1].strip(",")
93
+ # Verifica se parece uma versão
94
+ if version and version[0].isdigit():
95
+ return version
96
+ except subprocess.SubprocessError:
97
+ pass
98
+ return None
99
+
100
+
28
101
  def run_upgrade(console: Console | None = None) -> bool:
29
102
  """Executa upgrade do pacote.
30
103
 
@@ -32,7 +105,7 @@ def run_upgrade(console: Console | None = None) -> bool:
32
105
  console: Console Rich para output (opcional)
33
106
 
34
107
  Returns:
35
- True se upgrade foi executado, False se já está atualizado ou falhou
108
+ True se upgrade foi executado com sucesso, False caso contrário
36
109
  """
37
110
  if console is None:
38
111
  console = Console()
@@ -42,14 +115,20 @@ def run_upgrade(console: Console | None = None) -> bool:
42
115
  update_info = check_for_update()
43
116
 
44
117
  if update_info is None:
118
+ # Limpa cache mesmo quando não há atualização (garante consistência)
119
+ clear_cache()
45
120
  console.print(
46
121
  f"[green]✓[/] Você já está na versão mais recente ([cyan]{__version__}[/])"
47
122
  )
48
123
  return False
49
124
 
50
125
  installer = detect_installer()
126
+
127
+ # Obtém versão antes do upgrade para comparação
128
+ version_before = get_installed_version(installer) or __version__
129
+
51
130
  console.print(
52
- f"[yellow]→[/] Atualizando de {update_info.current_version} "
131
+ f"[yellow]→[/] Atualizando de {version_before} "
53
132
  f"para {update_info.latest_version}..."
54
133
  )
55
134
 
@@ -67,21 +146,37 @@ def run_upgrade(console: Console | None = None) -> bool:
67
146
  check=False,
68
147
  )
69
148
 
149
+ # Sempre limpa o cache após tentativa de upgrade
150
+ clear_cache()
151
+
70
152
  if result.returncode == 0:
71
- console.print(
72
- f"[green]✓[/] Atualizado para versão {update_info.latest_version}"
73
- )
74
- return True
153
+ # Verifica se a versão realmente mudou
154
+ version_after = get_installed_version(installer)
155
+
156
+ if version_after and version_after != version_before:
157
+ console.print(
158
+ f"[green]✓[/] Atualizado de {version_before} para {version_after}"
159
+ )
160
+ return True
161
+ else:
162
+ # Comando executou mas versão não mudou
163
+ console.print(
164
+ f"[green]✓[/] Você já está na versão mais recente "
165
+ f"([cyan]{version_after or version_before}[/])"
166
+ )
167
+ return False
75
168
  else:
76
169
  console.print(f"[red]✗[/] Falha ao atualizar: {result.stderr.strip()}")
77
170
  console.print(f"[dim]Tente manualmente: {' '.join(cmd)}[/]")
78
171
  return False
79
172
 
80
173
  except FileNotFoundError:
174
+ clear_cache()
81
175
  console.print(f"[red]✗[/] Comando '{cmd[0]}' não encontrado")
82
176
  if installer == "pipx":
83
177
  console.print("[dim]Tente: pip install --upgrade airev[/]")
84
178
  return False
85
179
  except Exception as e:
180
+ clear_cache()
86
181
  console.print(f"[red]✗[/] Erro inesperado: {e}")
87
182
  return False
@@ -110,6 +110,24 @@ def _write_cache(latest_version: str) -> None:
110
110
  pass
111
111
 
112
112
 
113
+ def clear_cache() -> bool:
114
+ """Remove o arquivo de cache de verificação de versão.
115
+
116
+ Deve ser chamada após upgrade para garantir que a próxima
117
+ verificação consulte o PyPI novamente.
118
+
119
+ Returns:
120
+ True se o cache foi removido ou não existia, False se falhou
121
+ """
122
+ try:
123
+ if CACHE_FILE.exists():
124
+ CACHE_FILE.unlink()
125
+ return True
126
+ except OSError:
127
+ # Falha ao remover cache - ignora silenciosamente
128
+ return False
129
+
130
+
113
131
  def get_latest_version(timeout: float = DEFAULT_TIMEOUT) -> str | None:
114
132
  """Consulta PyPI para obter a versão mais recente.
115
133
 
File without changes