Merged in feature/release-command (pull request #15)

feature: release command

Approved-by: Jonathan Teran
This commit is contained in:
JonathanGitFlow
2025-11-03 11:28:39 +00:00
committed by jt
2 changed files with 100 additions and 13 deletions
+32
View File
@@ -1,3 +1,35 @@
## Lunes, 3 de Noviembre de 2025, 08:28
- Autor: [Jonathan Teran Carballo](mailto:jonathan.nerat@gmail.com)
- Rama: `feature/release-command`
### Commits
- **bugfix**: elimino debug print y return en merge_command (cc66c5b)
- git-flow (M)
- **bugfix**: uso distintos target branches para obtener env y type de ramas dev y release (b8ef0b9)
- git-flow (M)
- **docs**: actualizo texto de ayuda de help_command (8bb0965)
- git-flow (M)
- **feature**: agrego comando release (1bdac67)
- git-flow (M)
---
## Domingo, 2 de Noviembre de 2025, 17:37
- Autor: [Jonathan Teran Carballo](mailto:jonathan.nerat@gmail.com)
- Rama: `feature/release-command`
### Commits
- **docs**: actualizo texto de ayuda de help_command (8bb0965)
- git-flow (M)
- **feature**: agrego comando release (1bdac67)
- git-flow (M)
---
## Domingo, 2 de Noviembre de 2025, 15:47
- Autor: [Jonathan Teran Carballo](mailto:jonathan.nerat@gmail.com)
+68 -13
View File
@@ -40,6 +40,8 @@ def main():
merge_command()
elif command == "tag":
tag_command()
elif command == "release":
release_command()
elif command == "help":
help_command()
else:
@@ -83,7 +85,7 @@ COMMIT_TYPES = [
"typo",
"testing",
"ignore",
"WIP"
"wip"
]
DEFAULT_REMOTE = "origin"
@@ -229,7 +231,7 @@ def merge_command():
print_error("No se pueden mergear ramas de tipo 'wip'")
return
target = get_base_branch(branch)
(target, _) = get_branch_env_and_type(branch)
status = Git.status()
remote = Git.flow_config("flow.remote").firstline()
@@ -312,6 +314,33 @@ def parse_url(url: str) -> list[str]:
return [service, repository]
def get_branch_env_and_type(branch: str) -> tuple[str, str]:
components = branch.split("/")
target_branches = Git.flow_config("flow.branches").firstline().split(" ")
if len(components) == 2:
if components[0] not in BRANCH_TYPES:
raise ValueError(f"Branch inválida, el tipo '{components[0]}' no es válido.")
return (target_branches[0], components[0])
elif len(components) == 4:
target_branches = target_branches[1:]
if (
components[0] != "release"
or components[1] not in target_branches
or components[2] not in BRANCH_TYPES
):
raise ValueError(
"Branch release inválido, debe tener el siguiente formato: "
"release/<env>/<type>/<name>, pero es: " + branch
)
return (components[1], components[2])
else:
raise ValueError("Branch inválido: " + branch)
def tag_command():
ensure_initialized()
ci = len(sys.argv) == 3 # ./git-flow tag <BEARER>
@@ -357,16 +386,8 @@ def tag_command():
until_dash = last_version.index("-") if "-" in last_version else None
[major, minor, patch] = map(int, last_version[from_major:until_dash].split("."))
components = merged_branch.split("/")
if len(components) not in [2, 4]:
raise RuntimeError("Branch mergeado es inválido: " + merged_branch)
elif len(components) == 4 and components[0] != "release":
raise RuntimeError("Release branch mergeado es inválido: " + merged_branch)
elif components[-2] not in BRANCH_TYPES:
raise RuntimeError("Tipo de rama mergeado es inválido: " + components[-2])
increment = BRANCH_TYPES_INCREMENT[components[-2]]
(_, merged_branch_type) = get_branch_env_and_type(merged_branch)
increment = BRANCH_TYPES_INCREMENT[merged_branch_type]
if increment == "major":
major = major + 1
@@ -390,6 +411,39 @@ def tag_command():
Git("tag", new_version, commit).exec()
def release_command():
ensure_initialized()
branch = ensure_right_branch()
env_branches = Git.flow_config("flow.branches").firstline().split(" ")
(env, _) = get_branch_env_and_type(branch)
if env == env_branches[-1]:
raise RuntimeError("No se puede hacer release de una rama en el ultimo entorno.")
next_env = env_branches[env_branches.index(env) + 1]
boundary_commits = list(filter(
lambda c: c.startswith("-"), # boundary commits
Git("rev-list", env + "..." + branch, topo_order=True, boundary=True).lines()
))
if not boundary_commits:
raise RuntimeError("No se encontro un commit base para realizar el rebase.")
base = boundary_commits[-1].removeprefix("-")
next_branch = branch.replace(f"/{env}/", f"/{next_env}/") if branch.startswith("release/") else f"release/{next_env}/{branch}"
Git("switch", next_branch, create=True).exec()
commits = int(Git("rev-list", base + ".." + next_branch, count=True).firstline())
if commits > 1 and confirm(f"Desea reemplazar los {commits} commits de la rama por uno solo?"):
Git("reset", base, soft=True).exec()
commit_type = choose("Tipo de commit", COMMIT_TYPES[:-1]) # Solo permitir commits NO wip
Git("commit", m=commit_type + ": " + get_commit_message()).exec()
Git("rebase", base, next_branch, onto=next_env).exec()
def help_command(name: str|None = None):
if name is not None:
print_error(f"Comando inválido: {name}")
@@ -397,7 +451,7 @@ def help_command(name: str|None = None):
script = sys.argv[0]
print(f"""USO:
{script} [help | init | new | commit]
{script} <COMANDO>
COMANDOS:
init inicializa el repositorio por única vez para utilizar git-flow
@@ -405,6 +459,7 @@ COMANDOS:
commit crea un commit siguiendo el formato de Conventional Commit
merge actualiza el changelog y crea un nuevo PR para mergear la rama
tag crea un nuevo tag para el ultimo merge
release crea una nueva rama release para pasar la rama actual al siguiente entorno
help muestra este texto de ayuda""", file=sys.stderr)