Skip to content

Commit 56710f1

Browse files
authored
Merge branch 'master' into 99-создать-методы-для-работы-get_assignee_story-в-обёртке
2 parents 4ea23ad + 74da71d commit 56710f1

File tree

7 files changed

+254
-145
lines changed

7 files changed

+254
-145
lines changed
Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,41 @@
11
version: '3'
22

33
services:
4+
db:
5+
image: postgres:13
6+
container_name: forgejo_db
7+
environment:
8+
POSTGRES_USER: forgejo
9+
POSTGRES_PASSWORD: forgejo
10+
POSTGRES_DB: forgejo
11+
volumes:
12+
- ./postgres-data:/var/lib/postgresql/data
13+
restart: unless-stopped
14+
networks:
15+
- forgejo_network
16+
417
forgejo:
518
image: codeberg.org/forgejo/forgejo:1.18
619
container_name: forgejo
720
environment:
821
- USER_UID=1000
922
- USER_GID=1000
23+
- FORGEJO__database__DB_TYPE=postgres
24+
- FORGEJO__database__HOST=db:5432
25+
- FORGEJO__database__NAME=forgejo
26+
- FORGEJO__database__USER=forgejo
27+
- FORGEJO__database__PASSWD=forgejo
1028
volumes:
1129
- ./forgejo-data:/data
1230
ports:
1331
- "3000:3000"
1432
- "2222:22"
15-
restart: unless-stopped
33+
depends_on:
34+
- db
35+
restart: unless-stopped
36+
networks:
37+
- forgejo_network
38+
39+
networks:
40+
forgejo_network:
41+
driver: bridge

ForgejoRepoAPI.py

Lines changed: 40 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -299,8 +299,32 @@ def get_comments(self, repo, obj) -> list[Comment]:
299299

300300
return result
301301

302-
def get_invites(self, repo: Repository) -> list[Invite]:
303-
return []
302+
def get_invites(self, repo: Repository, users: list[User] = None) -> list[Invite]:
303+
if users is None:
304+
return []
305+
306+
try:
307+
collaborators = self.client.repository.repo_list_collaborators(
308+
owner=repo.owner.login, repo=repo.name
309+
)
310+
collab_logins = {c.login for c in collaborators}
311+
312+
invites = []
313+
for user in users:
314+
if user.login not in collab_logins:
315+
invites.append(
316+
Invite(
317+
_id=0,
318+
invitee=user,
319+
created_at=None,
320+
html_url=user.html_url,
321+
)
322+
)
323+
return invites
324+
325+
except Exception as e:
326+
logging.error(f"Failed to simulate invites for Forgejo repo {repo.name}: {e}")
327+
return []
304328

305329
def get_rate_limiting(self) -> tuple[int, int]:
306330
return sys.maxsize, sys.maxsize
@@ -355,3 +379,17 @@ def get_base_url(self) -> str:
355379
print(
356380
f"Branch: {branch.name}, Last Commit: {branch.last_commit._id if branch.last_commit else 'None'}"
357381
)
382+
383+
# Получение приглашений
384+
test_users = [
385+
User(login="user1", username="User One", email="", html_url="", node_id="",
386+
type="", bio="", site_admin=False, _id=""),
387+
User(login="user2", username="User Two", email="", html_url="", node_id="",
388+
type="", bio="", site_admin=False, _id=""),
389+
]
390+
391+
invites = api.get_invites(repo, users=test_users)
392+
print(f"Total Invites: {len(invites)}")
393+
394+
for invite in invites:
395+
print(f"Invitee: {invite.invitee.username}, URL: {invite.html_url}")

GitHubRepoAPI.py

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,6 @@ def _client_validation(client: Github) -> Github:
3030
logging.error(
3131
'Github: Connect: user could not be authenticated please try again.'
3232
)
33-
exit(1)
3433
else:
3534
return client
3635

git_logger.py

Lines changed: 26 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -10,9 +10,12 @@
1010
TIMEZONE = 'Europe/Moscow'
1111

1212

13-
def login(source, token, base_url):
14-
client = RepositoryFactory.create_api(source, token, base_url)
15-
return client
13+
def login(token, base_url):
14+
try:
15+
client = RepositoryFactory.create_api(token, base_url)
16+
return client
17+
except Exception:
18+
return None
1619

1720

1821
def get_tokens_from_file(tokens_path: str) -> list[str]:
@@ -30,50 +33,36 @@ def get_repos_from_file(repos_path: str) -> list[str]:
3033

3134

3235
class Clients:
33-
def __init__(self, source: str, tokens: list[str], base_url: str | None = None):
34-
self.clients = self._init_clients(source, tokens, base_url)
35-
self.cur_client = None
36+
def __init__(self, tokens: list[str], base_url: str | None = None):
37+
self.clients = []
38+
self.token_map = {}
3639

37-
def _init_clients(self, source: str, tokens: list[str], base_url: str | None) -> list[dict]:
38-
clients = [{"client": login(source, token, base_url), "token": token} for token in tokens]
39-
return clients
40+
for token in tokens:
41+
client = login(token, base_url)
42+
if client:
43+
self.clients.append(client)
44+
self.token_map[client] = token
4045

41-
def get_next_client(self) -> IRepositoryAPI:
46+
if not self.clients:
47+
raise Exception("No valid tokens for either GitHub or Forgejo")
48+
49+
def _get_next_client(self) -> tuple[IRepositoryAPI, str]:
4250
client = None
4351
max_remaining_limit = -1
4452

45-
for client_tmp in self.clients:
46-
remaining_limit, limit = client_tmp["client"].get_rate_limiting()
47-
48-
# можно добавить вывод износа токена
49-
# можно дополнительно проверять на 403 и временно пропускать эти токены,
50-
# либо завести константу "минимальный коэффициент износа" и не трогать "изношенные" токены
51-
52-
if remaining_limit > max_remaining_limit:
53-
client = client_tmp
54-
max_remaining_limit = remaining_limit
55-
53+
for c in self.clients:
54+
remaining, _ = c.get_rate_limiting()
55+
if remaining > max_remaining_limit:
56+
client = c
57+
max_remaining_limit = remaining
5658
sleep(TIMEDELTA)
5759

5860
if client is None:
5961
raise Exception("No git clients available")
62+
return client, self.token_map[client]
6063

61-
self.cur_client = client
62-
return client
63-
64-
65-
def get_next_repo(clients: Clients, repositories):
66-
with open(repositories, 'r') as file:
67-
list_repos = [x for x in file.read().split('\n') if x]
68-
for repo_name in list_repos:
69-
try:
70-
cur_client = clients.get_next_client()
71-
repo = cur_client['client'].get_repository(repo_name)
72-
except Exception as err:
73-
print(f'get_next_repo(): error {err}')
74-
print(f'get_next_repo(): failed to load repository "{repo_name}"')
75-
else:
76-
yield cur_client['client'], repo, cur_client['token']
64+
def get_next_client(self) -> tuple[IRepositoryAPI, str]:
65+
return self._get_next_client()
7766

7867

7968
def get_next_binded_repo(clients: Clients, repositories: list[str]):

interface_wrapper.py

Lines changed: 15 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ class PullRequest:
9494
class Invite:
9595
_id: int
9696
invitee: User
97-
created_at: datetime
97+
created_at: datetime | None
9898
html_url: str
9999

100100

@@ -198,25 +198,26 @@ def get_base_url(self) -> str:
198198
pass
199199

200200

201-
# Фабрика для создания API
202201
class RepositoryFactory:
203202
@staticmethod
204-
def create_api(
205-
source: str, token: str, base_url: str | None = None
206-
) -> IRepositoryAPI:
203+
def create_api(token: str, base_url: str | None = None) -> IRepositoryAPI:
207204
from ForgejoRepoAPI import ForgejoRepoAPI
208205
from GitHubRepoAPI import GitHubRepoAPI
209206

210-
if source == 'github':
207+
errors = []
208+
209+
try:
211210
return GitHubRepoAPI(Github(auth=Auth.Token(token)))
212-
elif source == 'forgejo':
213-
if not isinstance(base_url, str):
214-
raise ValueError(
215-
f"base_url for PyforgejoApi should be str, got {type(base_url)}"
216-
)
217-
return ForgejoRepoAPI(PyforgejoApi(api_key=token, base_url=base_url))
218-
else:
219-
raise ValueError(f"Unsupported source: {source}")
211+
except Exception as e:
212+
errors.append(f"GitHub login failed: {e}")
213+
214+
if base_url:
215+
try:
216+
return ForgejoRepoAPI(PyforgejoApi(api_key=token, base_url=base_url))
217+
except Exception as e:
218+
errors.append(f"Forgejo login failed: {e}")
219+
220+
raise Exception(" / ".join(errors))
220221

221222

222223
# Сервис для расчёта метрик

0 commit comments

Comments
 (0)