You're looking at it

Homepage: https://roundabout-host.com

By using this site, you agree to have cookies stored on your device, strictly for functional purposes, such as storing your session and preferences.

Dismiss

 misc_utils.py

View raw Download
text/plain • 4.17 kiB
Python script, ASCII text executable
        
            
1
"""
2
This module provides some more general utilities useful in various parts
3
of the application.
4
5
Roundabout - git hosting for everyone <https://roundabout-host.com>
6
Copyright (C) 2023-2025 Roundabout developers <root@roundabout-host.com>
7
8
This program is free software: you can redistribute it and/or modify
9
it under the terms of the GNU Affero General Public License as published by
10
the Free Software Foundation, either version 3 of the License, or
11
(at your option) any later version.
12
13
This program is distributed in the hope that it will be useful,
14
but WITHOUT ANY WARRANTY; without even the implied warranty of
15
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16
GNU Affero General Public License for more details.
17
18
You should have received a copy of the GNU Affero General Public License
19
along with this program. If not, see <http://www.gnu.org/licenses/>.
20
"""
21
22
from common import *
23
24
__all__ = ["git_command", "only_chars", "get_permission_level", "get_visibility", "get_favourite", "human_size",
25
"guess_mime", "convert_to_html", "js_to_bool", "get_commit_identity"]
26
27
import subprocess
28
import os
29
import magic
30
31
def only_chars(string, chars):
32
chars = set(chars)
33
all_chars = set(string)
34
return all_chars.issubset(chars)
35
36
37
def get_permission_level(logged_in, username, repository):
38
from models import User, Repo, RepoAccess
39
user = User.query.filter_by(username=logged_in).first()
40
repo = Repo.query.filter_by(route=f"/{username}/{repository}").first()
41
42
if user and repo:
43
permission = RepoAccess.query.filter_by(user=user, repo=repo).first()
44
if permission:
45
return permission.access_level
46
47
return None
48
49
50
def get_visibility(username, repository):
51
from models import Repo
52
repo = Repo.query.filter_by(route=f"/{username}/{repository}").first()
53
54
if repo:
55
return repo.visibility
56
57
return None
58
59
60
def get_favourite(logged_in, username, repository):
61
from models import RepoFavourite
62
relationship = RepoFavourite.query.filter_by(user_username=logged_in,
63
repo_route=f"/{username}/{repository}").first()
64
return relationship
65
66
67
def human_size(value, decimals=2, scale=1024,
68
units=("B", "kiB", "MiB", "GiB", "TiB", "PiB", "EiB", "ZiB", "YiB", "RiB", "QiB")):
69
for unit in units:
70
if value < scale:
71
break
72
value /= scale
73
if int(value) == value:
74
# do not return decimals if the value is already round
75
return int(value), unit
76
return round(value * 10 ** decimals) / 10 ** decimals, unit
77
78
79
def guess_mime(path):
80
if os.path.isdir(path):
81
mimetype = "inode/directory"
82
elif magic.from_file(path, mime=True):
83
mimetype = magic.from_file(path, mime=True)
84
else:
85
mimetype = "application/octet-stream"
86
return mimetype
87
88
89
def convert_to_html(path):
90
with open(path, "r") as f:
91
contents = f.read()
92
return contents
93
94
95
def js_to_bool(js):
96
return js.lower() == "true" if isinstance(js, str) else bool(js)
97
98
99
def get_commit_identity(identity, pusher, repo):
100
from models import User, RepoAccess
101
email = identity.rpartition("<")[2].rpartition(">")[0].strip()
102
# If the email is not valid, attribute the commit to the pusher.
103
if not email:
104
return pusher
105
email_users = User.query.filter_by(email=email).all()
106
# If no user has the email, attribute the commit to the pusher.
107
if not email_users:
108
return pusher
109
110
# If only one user has the email, attribute the commit to them.
111
if len(email_users) == 1:
112
return email_users[0]
113
114
# If it's ambiguous, attribute the commit to an user with a higher permission level.
115
for user in email_users:
116
if repo.owner == user:
117
return user
118
119
for user in email_users:
120
relationship = RepoAccess.query.filter_by(user=user, repo=repo).first()
121
if relationship.permission_level == 2:
122
return user
123
124
for user in email_users:
125
relationship = RepoAccess.query.filter_by(user=user, repo=repo).first()
126
if relationship.permission_level == 1:
127
return user
128
129
# If no user has a higher permission level, attribute the commit to the pusher :(
130
return pusher
131
132