feat: generate repos using templates (#1)
All checks were successful
build / trigger-build-image (push) Successful in 16s

The feature allows choosing templates when creating repos for individuals and groups.

Reviewed-on: #1
Reviewed-by: 张泊明518370910136 <bomingzh@sjtu.edu.cn>
Co-authored-by: Min Zhengjie <minzhengjie@sjtu.edu.cn>
Co-committed-by: Min Zhengjie <minzhengjie@sjtu.edu.cn>
This commit is contained in:
闵政杰523370910252 2025-06-18 14:22:55 +08:00 committed by 张泊明518370910136
parent 0f39e660d0
commit 011b9c26b0
3 changed files with 67 additions and 29 deletions

View File

@ -50,13 +50,17 @@ def add_all_canvas_students_to_teams(team_names: List[str]) -> None:
"create-personal-repos", "create-personal-repos",
help="create personal repos on gitea for all canvas students", help="create personal repos on gitea for all canvas students",
) )
def create_personal_repos_for_all_canvas_students(suffix: str = Option("")) -> None: def create_personal_repos_for_all_canvas_students(
tea.pot.create_personal_repos_for_all_canvas_students(suffix) suffix: str = Option(""), template: str = Option("", help="generate from template")
) -> None:
tea.pot.create_personal_repos_for_all_canvas_students(suffix, template)
@app.command("create-teams", help="create teams on gitea by canvas groups") @app.command("create-teams", help="create teams on gitea by canvas groups")
def create_teams_and_repos_by_canvas_groups(group_prefix: str) -> None: def create_teams_and_repos_by_canvas_groups(
tea.pot.create_teams_and_repos_by_canvas_groups(group_prefix) group_prefix: str, template: str = Option("", help="generate from template")
) -> None:
tea.pot.create_teams_and_repos_by_canvas_groups(group_prefix, template)
@app.command("get-public-keys", help="list all public keys on gitea") @app.command("get-public-keys", help="list all public keys on gitea")

View File

@ -96,15 +96,16 @@ class Teapot:
return self.gitea.add_canvas_students_to_teams(self.canvas.students, team_names) return self.gitea.add_canvas_students_to_teams(self.canvas.students, team_names)
def create_personal_repos_for_all_canvas_students( def create_personal_repos_for_all_canvas_students(
self, suffix: str = "" self, suffix: str = "", template: str = ""
) -> List[str]: ) -> List[str]:
return self.gitea.create_personal_repos_for_canvas_students( return self.gitea.create_personal_repos_for_canvas_students(
self.canvas.students, self.canvas.students,
lambda user: default_repo_name_convertor(user) + suffix, lambda user: default_repo_name_convertor(user) + suffix,
template,
) )
def create_teams_and_repos_by_canvas_groups( def create_teams_and_repos_by_canvas_groups(
self, group_prefix: str = "" self, group_prefix: str = "", template: str = ""
) -> List[str]: ) -> List[str]:
def convertor(name: str) -> Optional[str]: def convertor(name: str) -> Optional[str]:
if group_prefix and not name.startswith(group_prefix): if group_prefix and not name.startswith(group_prefix):
@ -114,7 +115,7 @@ class Teapot:
return f"{team_name}{number:02}" return f"{team_name}{number:02}"
return self.gitea.create_teams_and_repos_by_canvas_groups( return self.gitea.create_teams_and_repos_by_canvas_groups(
self.canvas.students, self.canvas.groups, convertor, convertor self.canvas.students, self.canvas.groups, convertor, convertor, template
) )
def get_public_key_of_all_canvas_students(self) -> Dict[str, List[str]]: def get_public_key_of_all_canvas_students(self) -> Dict[str, List[str]]:

View File

@ -116,6 +116,7 @@ class Gitea:
repo_name_convertor: Callable[ repo_name_convertor: Callable[
[User], Optional[str] [User], Optional[str]
] = default_repo_name_convertor, ] = default_repo_name_convertor,
template: str = "",
) -> List[str]: ) -> List[str]:
repo_names = [] repo_names = []
for student in students: for student in students:
@ -123,17 +124,32 @@ class Gitea:
if repo_name is None: if repo_name is None:
continue continue
repo_names.append(repo_name) repo_names.append(repo_name)
body = {
"auto_init": False,
"default_branch": settings.default_branch,
"name": repo_name,
"private": True,
"template": False,
"trust_model": "default",
}
try: try:
try: try:
self.organization_api.create_org_repo(self.org_name, body=body) if template == "":
body = {
"auto_init": False,
"default_branch": settings.default_branch,
"name": repo_name,
"private": True,
"template": False,
"trust_model": "default",
}
self.organization_api.create_org_repo(self.org_name, body=body)
else:
body = {
"default_branch": settings.default_branch,
"git_content": True,
"git_hooks": True,
"labels": True,
"name": repo_name,
"owner": self.org_name,
"private": True,
"protected_branch": True,
}
self.repository_api.generate_repo(
self.org_name, template, body=body
)
logger.info( logger.info(
f"Personal repo {self.org_name}/{repo_name} for {student} created" f"Personal repo {self.org_name}/{repo_name} for {student} created"
) )
@ -158,6 +174,7 @@ class Gitea:
groups: PaginatedList, groups: PaginatedList,
team_name_convertor: Callable[[str], Optional[str]] = lambda name: name, team_name_convertor: Callable[[str], Optional[str]] = lambda name: name,
repo_name_convertor: Callable[[str], Optional[str]] = lambda name: name, repo_name_convertor: Callable[[str], Optional[str]] = lambda name: name,
template: str = "",
permission: PermissionEnum = PermissionEnum.write, permission: PermissionEnum = PermissionEnum.write,
) -> List[str]: ) -> List[str]:
repo_names = [] repo_names = []
@ -190,21 +207,37 @@ class Gitea:
], ],
}, },
) )
logger.info(f"{self.org_name}/{team_name} created") logger.info(f"Team {team_name} created")
if first(repos, lambda repo: repo.name == repo_name) is None: if first(repos, lambda repo: repo.name == repo_name) is None:
repo_names.append(repo_name) repo_names.append(repo_name)
self.organization_api.create_org_repo( if template == "":
self.org_name, self.organization_api.create_org_repo(
body={ self.org_name,
"auto_init": False, body={
"default_branch": settings.default_branch, "auto_init": False,
"name": repo_name, "default_branch": settings.default_branch,
"private": True, "name": repo_name,
"template": False, "private": True,
"trust_model": "default", "template": False,
}, "trust_model": "default",
) },
logger.info(f"Team {team_name} created") )
else:
self.repository_api.generate_repo(
self.org_name,
template,
body={
"default_branch": settings.default_branch,
"git_content": True,
"git_hooks": True,
"labels": True,
"name": repo_name,
"owner": self.org_name,
"private": True,
"protected_branch": True,
},
)
logger.info(f"{self.org_name}/{team_name} created")
try: try:
self.organization_api.org_add_team_repository( self.organization_api.org_add_team_repository(
team.id, self.org_name, repo_name team.id, self.org_name, repo_name