cgitize 7.0.0__tar.gz → 8.0.0__tar.gz

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.
Files changed (68) hide show
  1. {cgitize-7.0.0 → cgitize-8.0.0}/.github/workflows/ci.yml +6 -6
  2. {cgitize-7.0.0 → cgitize-8.0.0}/.github/workflows/maintenance.yml +3 -6
  3. {cgitize-7.0.0 → cgitize-8.0.0}/DEVELOPMENT.md +3 -3
  4. {cgitize-7.0.0 → cgitize-8.0.0}/PKG-INFO +1 -1
  5. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/bitbucket.py +2 -2
  6. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/config.py +5 -10
  7. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/repo.py +25 -7
  8. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/utils.py +9 -5
  9. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize.egg-info/PKG-INFO +1 -1
  10. {cgitize-7.0.0 → cgitize-8.0.0}/docker/README.md +2 -2
  11. {cgitize-7.0.0 → cgitize-8.0.0}/docs/api.md +6 -4
  12. {cgitize-7.0.0 → cgitize-8.0.0}/docs/auth.md +3 -5
  13. {cgitize-7.0.0 → cgitize-8.0.0}/examples/cgitize.toml +16 -16
  14. {cgitize-7.0.0 → cgitize-8.0.0}/requirements.txt +4 -4
  15. {cgitize-7.0.0 → cgitize-8.0.0}/test/integration/example/test.sh +48 -3
  16. {cgitize-7.0.0 → cgitize-8.0.0}/test/set_credentials.sh +3 -1
  17. {cgitize-7.0.0 → cgitize-8.0.0}/test/unit/test_bitbucket.py +16 -1
  18. {cgitize-7.0.0 → cgitize-8.0.0}/.dockerignore +0 -0
  19. {cgitize-7.0.0 → cgitize-8.0.0}/.gitattributes +0 -0
  20. {cgitize-7.0.0 → cgitize-8.0.0}/.github/dependabot.yml +0 -0
  21. {cgitize-7.0.0 → cgitize-8.0.0}/.gitignore +0 -0
  22. {cgitize-7.0.0 → cgitize-8.0.0}/.pylintrc +0 -0
  23. {cgitize-7.0.0 → cgitize-8.0.0}/.python-version +0 -0
  24. {cgitize-7.0.0 → cgitize-8.0.0}/LICENSE.txt +0 -0
  25. {cgitize-7.0.0 → cgitize-8.0.0}/Makefile +0 -0
  26. {cgitize-7.0.0 → cgitize-8.0.0}/README.md +0 -0
  27. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/__init__.py +0 -0
  28. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/cgit.py +0 -0
  29. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/git.py +0 -0
  30. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/github.py +0 -0
  31. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/gitlab.py +0 -0
  32. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/header.py +0 -0
  33. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/main.py +0 -0
  34. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize/version.py +0 -0
  35. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize.egg-info/SOURCES.txt +0 -0
  36. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize.egg-info/dependency_links.txt +0 -0
  37. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize.egg-info/entry_points.txt +0 -0
  38. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize.egg-info/requires.txt +0 -0
  39. {cgitize-7.0.0 → cgitize-8.0.0}/cgitize.egg-info/top_level.txt +0 -0
  40. {cgitize-7.0.0 → cgitize-8.0.0}/docker/Dockerfile +0 -0
  41. {cgitize-7.0.0 → cgitize-8.0.0}/docker/cgitize.sh +0 -0
  42. {cgitize-7.0.0 → cgitize-8.0.0}/docker/frontend/Dockerfile +0 -0
  43. {cgitize-7.0.0 → cgitize-8.0.0}/docker/frontend/cmd.sh +0 -0
  44. {cgitize-7.0.0 → cgitize-8.0.0}/docker/frontend/etc/cgit/common +0 -0
  45. {cgitize-7.0.0 → cgitize-8.0.0}/docker/frontend/etc/cgitrc +0 -0
  46. {cgitize-7.0.0 → cgitize-8.0.0}/docker/frontend/etc/nginx/conf.d/default.conf +0 -0
  47. {cgitize-7.0.0 → cgitize-8.0.0}/docker/frontend/usr/lib/cgit/filters/about-formatting.sh +0 -0
  48. {cgitize-7.0.0 → cgitize-8.0.0}/docker/frontend/usr/lib/cgit/filters/html-converters/.gitattributes +0 -0
  49. {cgitize-7.0.0 → cgitize-8.0.0}/docker/frontend/usr/lib/cgit/filters/html-converters/md2html +0 -0
  50. {cgitize-7.0.0 → cgitize-8.0.0}/docker/get_output_dir.py +0 -0
  51. {cgitize-7.0.0 → cgitize-8.0.0}/docker/in_cron.sh +0 -0
  52. {cgitize-7.0.0 → cgitize-8.0.0}/docker-compose.yml +0 -0
  53. {cgitize-7.0.0 → cgitize-8.0.0}/examples/docker/cgitize.toml +0 -0
  54. {cgitize-7.0.0 → cgitize-8.0.0}/prelude.mk +0 -0
  55. {cgitize-7.0.0 → cgitize-8.0.0}/pyproject.toml +0 -0
  56. {cgitize-7.0.0 → cgitize-8.0.0}/setup.cfg +0 -0
  57. {cgitize-7.0.0 → cgitize-8.0.0}/test/__init__.py +0 -0
  58. {cgitize-7.0.0 → cgitize-8.0.0}/test/integration/docker/.dockerignore +0 -0
  59. {cgitize-7.0.0 → cgitize-8.0.0}/test/integration/docker/cgitize/.gitignore +0 -0
  60. {cgitize-7.0.0 → cgitize-8.0.0}/test/integration/docker/cgitize/etc/cgitize.toml +0 -0
  61. {cgitize-7.0.0 → cgitize-8.0.0}/test/integration/docker/docker-compose.yml +0 -0
  62. {cgitize-7.0.0 → cgitize-8.0.0}/test/integration/docker/git_server/Dockerfile +0 -0
  63. {cgitize-7.0.0 → cgitize-8.0.0}/test/integration/docker/git_server/setup_repo.sh +0 -0
  64. {cgitize-7.0.0 → cgitize-8.0.0}/test/integration/docker/test.sh +0 -0
  65. {cgitize-7.0.0 → cgitize-8.0.0}/test/integration/local/test.sh +0 -0
  66. {cgitize-7.0.0 → cgitize-8.0.0}/test/unit/__init__.py +0 -0
  67. {cgitize-7.0.0 → cgitize-8.0.0}/test/unit/test_github.py +0 -0
  68. {cgitize-7.0.0 → cgitize-8.0.0}/test/unit/test_gitlab.py +0 -0
@@ -27,11 +27,11 @@ jobs:
27
27
  python-version: ['3.9', '3.10', '3.11', '3.12', '3.13', '3.14']
28
28
  name: 'Test / ${{ matrix.python-version }}'
29
29
  env:
30
- CGITIZE_GITHUB_USERNAME: cgitize-test
30
+ CGITIZE_GITHUB_USERNAME: '${{ secrets.CGITIZE_GITHUB_USERNAME }}'
31
31
  CGITIZE_GITHUB_TOKEN: '${{ secrets.CGITIZE_GITHUB_TOKEN }}'
32
- CGITIZE_BITBUCKET_USERNAME: cgitize-test
32
+ CGITIZE_BITBUCKET_EMAIL: '${{ secrets.CGITIZE_BITBUCKET_EMAIL }}'
33
33
  CGITIZE_BITBUCKET_TOKEN: '${{ secrets.CGITIZE_BITBUCKET_TOKEN }}'
34
- CGITIZE_GITLAB_USERNAME: cgitize-test
34
+ CGITIZE_GITLAB_USERNAME: '${{ secrets.CGITIZE_GITLAB_USERNAME }}'
35
35
  CGITIZE_GITLAB_TOKEN: '${{ secrets.CGITIZE_GITLAB_TOKEN }}'
36
36
  steps:
37
37
  - name: Checkout
@@ -64,11 +64,11 @@ jobs:
64
64
  runs-on: ubuntu-latest
65
65
  name: 'Test / example config'
66
66
  env:
67
- CGITIZE_GITHUB_USERNAME: cgitize-test
67
+ CGITIZE_GITHUB_USERNAME: '${{ secrets.CGITIZE_GITHUB_USERNAME }}'
68
68
  CGITIZE_GITHUB_TOKEN: '${{ secrets.CGITIZE_GITHUB_TOKEN }}'
69
- CGITIZE_BITBUCKET_USERNAME: cgitize-test
69
+ CGITIZE_BITBUCKET_EMAIL: '${{ secrets.CGITIZE_BITBUCKET_EMAIL }}'
70
70
  CGITIZE_BITBUCKET_TOKEN: '${{ secrets.CGITIZE_BITBUCKET_TOKEN }}'
71
- CGITIZE_GITLAB_USERNAME: cgitize-test
71
+ CGITIZE_GITLAB_USERNAME: '${{ secrets.CGITIZE_GITLAB_USERNAME }}'
72
72
  CGITIZE_GITLAB_TOKEN: '${{ secrets.CGITIZE_GITLAB_TOKEN }}'
73
73
  steps:
74
74
  - name: Checkout
@@ -16,8 +16,6 @@ jobs:
16
16
  with:
17
17
  # I think that by default, pushes don't trigger other workflows, and
18
18
  # you need a separate token for that: https://github.com/orgs/community/discussions/37103
19
- #
20
- # Re-using the Jekyll projects token here BTW:
21
19
  token: '${{ secrets.GH_TOKEN }}'
22
20
  - name: Set up ssh-agent
23
21
  uses: webfactory/ssh-agent@v0.10.0
@@ -27,11 +25,10 @@ jobs:
27
25
  uses: actions/setup-python@v6
28
26
  with:
29
27
  python-version-file: .python-version
30
- - name: Run maintenance
31
- id: maintenance
28
+ - name: Configure git
32
29
  run: |
33
30
  # See https://github.com/actions/checkout#push-a-commit-using-the-built-in-token
34
31
  git config user.name "github-actions[bot]"
35
32
  git config user.email "41898282+github-actions[bot]@users.noreply.github.com"
36
-
37
- make maintenance
33
+ - name: Run maintenance
34
+ run: make maintenance
@@ -18,11 +18,11 @@ test.
18
18
  You need to set the following environment variables for the authenticated
19
19
  access tests to work:
20
20
 
21
- * `CGITIZE_BITBUCKET_USERNAME`: `cgitize-test`
21
+ * `CGITIZE_BITBUCKET_EMAIL`
22
22
  * `CGITIZE_BITBUCKET_TOKEN`
23
- * `CGITIZE_GITHUB_USERNAME`: `cgitize-test`
23
+ * `CGITIZE_GITHUB_USERNAME`
24
24
  * `CGITIZE_GITHUB_TOKEN`
25
- * `CGITIZE_GITLAB_USERNAME`: `cgitize-test`
25
+ * `CGITIZE_GITLAB_USERNAME`
26
26
  * `CGITIZE_GITLAB_TOKEN`
27
27
 
28
28
  You can run `. test/set_credentials.sh`; it'll ask you to fill in the secrets.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: cgitize
3
- Version: 7.0.0
3
+ Version: 8.0.0
4
4
  Summary: Self-host your repositories using cgit
5
5
  Author-email: Egor Tensin <egor@tensin.name>
6
6
  License-Expression: MIT
@@ -12,8 +12,8 @@ from cgitize.repo import Repo, Visibility
12
12
 
13
13
 
14
14
  class Bitbucket:
15
- def __init__(self, username=None, password=None):
16
- self._impl = Cloud(username=username, password=password, cloud=True)
15
+ def __init__(self, email=None, token=None):
16
+ self._impl = Cloud(username=email, password=token, cloud=True)
17
17
 
18
18
  def get_repo(self, repo):
19
19
  try:
@@ -5,6 +5,7 @@
5
5
 
6
6
  from abc import ABC, abstractmethod
7
7
  import os
8
+ from urllib.parse import quote
8
9
 
9
10
  import tomli
10
11
 
@@ -110,7 +111,7 @@ class GitHubSection(ServiceSection):
110
111
 
111
112
  @property
112
113
  def url_auth(self):
113
- return self.token
114
+ return (self.token, None)
114
115
 
115
116
  def _enum_org_repositories(self, cfg, api, org):
116
117
  for repo in api.get_org_repos(org):
@@ -135,12 +136,6 @@ class GitHubSection(ServiceSection):
135
136
  return GitHub(username, token)
136
137
 
137
138
 
138
- def two_part_url_auth(username, password):
139
- if username is None or password is None:
140
- return None
141
- return f'{username}:{password}'
142
-
143
-
144
139
  class BitbucketSection(ServiceSection):
145
140
  @property
146
141
  def token(self):
@@ -148,11 +143,11 @@ class BitbucketSection(ServiceSection):
148
143
 
149
144
  @property
150
145
  def username(self):
151
- return self._get_config_or_env('username', 'CGITIZE_BITBUCKET_USERNAME')
146
+ return self._get_config_or_env('email', 'CGITIZE_BITBUCKET_EMAIL')
152
147
 
153
148
  @property
154
149
  def url_auth(self):
155
- return two_part_url_auth(self.username, self.token)
150
+ return (self.username, self.token)
156
151
 
157
152
  def connect_to_service(self):
158
153
  username = self.username
@@ -175,7 +170,7 @@ class GitLabSection(ServiceSection):
175
170
 
176
171
  @property
177
172
  def url_auth(self):
178
- return two_part_url_auth(self.username, self.token)
173
+ return (self.username, self.token)
179
174
 
180
175
  def connect_to_service(self):
181
176
  username = self.username
@@ -87,8 +87,12 @@ class Repo:
87
87
 
88
88
  https_url = src.clone_url
89
89
  ssh_url = src.ssh_url
90
- clone_url = ssh_url if config.main.clone_via_ssh else https_url
91
- url_auth = None if config.main.clone_via_ssh else config.github.url_auth
90
+
91
+ clone_url = ssh_url
92
+ url_auth = None
93
+ if not config.main.clone_via_ssh:
94
+ clone_url = https_url
95
+ url_auth = config.github.url_auth
92
96
 
93
97
  return Repo(
94
98
  name,
@@ -113,7 +117,7 @@ class Repo:
113
117
  if len(https_urls) != 1:
114
118
  raise RuntimeError(f"no https:// clone URL for repository '{name}'?!")
115
119
  # Bitbucket leaves the username in the URL... Sigh.
116
- https_url = url_remove_auth(https_urls[0]['href'])
120
+ api_auth, https_url = url_remove_auth(https_urls[0]['href'])
117
121
 
118
122
  ssh_urls = [
119
123
  link for link in src.data['links']['clone'] if link['name'] == 'ssh'
@@ -122,8 +126,18 @@ class Repo:
122
126
  raise RuntimeError(f"no ssh:// clone URL for repository '{name}'?!")
123
127
  ssh_url = ssh_urls[0]['href']
124
128
 
125
- clone_url = ssh_url if config.main.clone_via_ssh else https_url
126
- url_auth = None if config.main.clone_via_ssh else config.bitbucket.url_auth
129
+ clone_url = ssh_url
130
+ url_auth = None
131
+ if not config.main.clone_via_ssh:
132
+ clone_url = https_url
133
+ url_auth = config.bitbucket.url_auth
134
+ # Bitbucket, since deprecating app passwords, now requires that
135
+ # users authenticate with their Atlassian email & API token.
136
+ # Unfortunately (sigh...), if you want to clone a repo via HTTPS,
137
+ # you can't use the very same email + token combo in the URL, you
138
+ # have to use your username (double sigh...). Luckily, for some
139
+ # reason, Bitbucket leaves the relevant username in the API response.
140
+ url_auth = api_auth[0], url_auth[1]
127
141
 
128
142
  return Repo(
129
143
  name,
@@ -144,8 +158,12 @@ class Repo:
144
158
 
145
159
  https_url = src.http_url_to_repo
146
160
  ssh_url = src.ssh_url_to_repo
147
- clone_url = ssh_url if config.main.clone_via_ssh else https_url
148
- url_auth = None if config.main.clone_via_ssh else config.gitlab.url_auth
161
+
162
+ clone_url = ssh_url
163
+ url_auth = None
164
+ if not config.main.clone_via_ssh:
165
+ clone_url = https_url
166
+ url_auth = config.gitlab.url_auth
149
167
 
150
168
  return Repo(
151
169
  name,
@@ -9,7 +9,7 @@ import os
9
9
  import stat
10
10
  import subprocess
11
11
  import sys
12
- from urllib.parse import urlsplit, urlunsplit
12
+ from urllib.parse import quote, urlsplit, urlunsplit
13
13
 
14
14
 
15
15
  @contextmanager
@@ -97,11 +97,12 @@ def protected_file(path):
97
97
  os.unlink(path)
98
98
 
99
99
 
100
- def url_replace_auth(url, username, password=None):
100
+ def url_replace_auth(url, auth):
101
+ username, password = auth
101
102
  parts = urlsplit(url)
102
- netloc = username
103
+ netloc = quote(username)
103
104
  if password is not None:
104
- netloc += f':{password}'
105
+ netloc += f':{quote(password)}'
105
106
  netloc += f'@{parts.hostname}'
106
107
  if parts.port is not None:
107
108
  netloc += f':{parts.port}'
@@ -111,6 +112,9 @@ def url_replace_auth(url, username, password=None):
111
112
 
112
113
  def url_remove_auth(url):
113
114
  parts = urlsplit(url)
115
+ auth = parts.username, parts.password
114
116
  netloc = parts.hostname
117
+ if parts.port is not None:
118
+ netloc += f':{parts.port}'
115
119
  parts = parts._replace(netloc=netloc)
116
- return urlunsplit(parts)
120
+ return auth, urlunsplit(parts)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: cgitize
3
- Version: 7.0.0
3
+ Version: 8.0.0
4
4
  Summary: Self-host your repositories using cgit
5
5
  Author-email: Egor Tensin <egor@tensin.name>
6
6
  License-Expression: MIT
@@ -48,13 +48,13 @@ Here's an example docker-compose.yml file:
48
48
  SCHEDULE: '0 */3 * * *'
49
49
  # Set CGITIZE_{GITHUB,BITBUCKET,GITLAB}_{USERNAME,TOKEN} variables
50
50
  # here or in the config file.
51
- image: egortensin/cgitize:6
51
+ image: egortensin/cgitize:8
52
52
  restart: unless-stopped
53
53
  volumes:
54
54
  - ./example.toml:/etc/cgitize/cgitize.toml:ro
55
55
  - /srv/volumes/cgitize:/mnt/cgitize
56
56
  frontend:
57
- image: egortensin/cgitize-frontend:6
57
+ image: egortensin/cgitize-frontend:8
58
58
  ports:
59
59
  - '127.0.0.1:80:80'
60
60
  restart: unless-stopped
@@ -4,10 +4,9 @@ unfortunately, peculiar in their own way.
4
4
  Tokens
5
5
  ------
6
6
 
7
- All of the forges support access tokens, of course (although they're called
8
- "app passwords" on Bitbucket). They can be used to do `git clone https://`
9
- with authentication info in the URL. For GitHub, it's enough to just specify
10
- the token:
7
+ All of the forges support access tokens, of course. They can be used to do
8
+ `git clone https://` with authentication info in the URL. For GitHub, it's
9
+ enough to just specify the token:
11
10
 
12
11
  git clone https://TOKEN@github.com/USER/REPO.git
13
12
 
@@ -16,6 +15,9 @@ token in the URL:
16
15
 
17
16
  git clone https://USER:TOKEN@bitbucket.org/USER/REPO.git
18
17
 
18
+ (For Bitbucket, since they deprecated their "app passwords", you need to
19
+ specify not the username, but rather the Atlassian account email.)
20
+
19
21
  Terminology
20
22
  -----------
21
23
 
@@ -22,11 +22,9 @@ When using HTTPS, there're multiple options to access the private repositories.
22
22
 
23
23
  2. Use OAuth. I thought this was too complicated to implement quickly.
24
24
 
25
- 3. Use per-application passwords. This option is pretty cool. Both GitHub (in
26
- the form of "personal access tokens") and Bitbucket (calls them "app
27
- passwords") support creating one-purpose passwords that are supposed to be
28
- used by a single app only. They allow to bypass the 2FA also. Let's do
29
- this!
25
+ 3. Use application access tokens. This option is pretty cool. Both GitHub
26
+ and Bitbucket support creating read-only tokens. They allow to bypass the
27
+ 2FA also. Let's do this!
30
28
 
31
29
  Passing the access tokens to Git is tricky though. First, simply including
32
30
  them in the clone URL would be incredibly stupid, since that URL is going to be
@@ -7,8 +7,8 @@ output_dir = "/tmp/cgitize"
7
7
  # repository's directory path.
8
8
  clone_url = "https://yourhost.com/git/{repo}"
9
9
 
10
- # Clones via SSH by default.
11
- clone_via_ssh = false
10
+ # Clones via SSH by default (instead of Git-over-HTTPS).
11
+ clone_via_ssh = true
12
12
 
13
13
  # Unless this is specified, cgit is going to derive the owner from the
14
14
  # repository's directory ownership.
@@ -19,8 +19,10 @@ owner = "Your Name"
19
19
 
20
20
  [github]
21
21
  # If some of the repositories hosted on GitHub are private (or if you hit the
22
- # request rate limit), use "access tokens". Set in the config or using the
23
- # CGITIZE_GITHUB_TOKEN environment variable.
22
+ # request rate limit), use a personal access token. Set in the config or using
23
+ # the CGITIZE_GITHUB_TOKEN environment variable.
24
+ # Required scopes:
25
+ # * repo
24
26
  #token = "XXX"
25
27
  # Set the username that owns the token here or using the environment variable
26
28
  # CGITIZE_GITHUB_USERNAME.
@@ -56,21 +58,20 @@ dir = "python"
56
58
  # Bitbucket
57
59
  # =========
58
60
 
59
- # Bitbucket settings are similar to those for GitHub.
60
-
61
61
  [bitbucket]
62
- # Access tokens are called "app passwords" on Bitbucket.
63
- # The environment variable is CGITIZE_BITBUCKET_TOKEN.
62
+ # Atlassian API token (environment variable CGITIZE_BITBUCKET_TOKEN).
63
+ # Required scopes:
64
+ # * read:workspace:bitbucket
65
+ # * read:repository:bitbucket
64
66
  #token = "XXX"
65
- # The environment variable is CGITIZE_BITBUCKET_USERNAME.
66
- #username = "your-username"
67
+ # Atlassian account email address (environment variable CGITIZE_BITBUCKET_EMAIL).
68
+ #email = "your-email"
67
69
 
68
70
  [bitbucket.users.me]
69
71
  name = "cgitize-test-workspace"
70
72
  dir = "bitbucket-dir"
71
73
  #skip = ["repo1", "repo2"]
72
74
 
73
- # The defaults.
74
75
  public = true
75
76
  private = false
76
77
 
@@ -84,12 +85,12 @@ id = "berkeleylab/upc-runtime"
84
85
  # GitLab
85
86
  # ======
86
87
 
87
- # GitLab settings are similar to those for GitHub.
88
-
89
88
  [gitlab]
90
- # The environment variable is CGITIZE_GITLAB_TOKEN.
89
+ # Personal access token (environment variable CGITIZE_GITLAB_TOKEN).
90
+ # Required scopes (for legacy tokens):
91
+ # * read_api
91
92
  #token = "XXX"
92
- # The environment variable is CGITIZE_GITLAB_USERNAME.
93
+ # Gitlab username (environment variable CGITIZE_GITLAB_USERNAME).
93
94
  #username = "your-username"
94
95
 
95
96
  [gitlab.users.me]
@@ -97,7 +98,6 @@ name = "cgitize-test"
97
98
  dir = "gitlab-dir"
98
99
  #skip = ["repo1", "repo2"]
99
100
 
100
- # The defaults.
101
101
  public = true
102
102
  private = false
103
103
 
@@ -1,11 +1,11 @@
1
1
  atlassian-python-api==4.0.7
2
- beautifulsoup4==4.14.3
2
+ beautifulsoup4==4.15.0
3
3
  certifi==2026.5.20
4
4
  cffi==2.0.0
5
5
  charset-normalizer==3.4.7
6
6
  cryptography==48.0.0
7
7
  Deprecated==1.3.1
8
- idna==3.16
8
+ idna==3.18
9
9
  jmespath==1.1.0
10
10
  oauthlib==3.3.1
11
11
  pycparser==3.0
@@ -16,8 +16,8 @@ python-gitlab==6.5.0
16
16
  requests==2.34.2
17
17
  requests-oauthlib==2.0.0
18
18
  requests-toolbelt==1.0.0
19
- soupsieve==2.8.3
19
+ soupsieve==2.8.4
20
20
  tomli==2.4.1
21
21
  typing_extensions==4.15.0
22
22
  urllib3==2.7.0
23
- wrapt==2.2.0
23
+ wrapt==2.2.1
@@ -151,7 +151,48 @@ test_ssh() {
151
151
  goauthentik-dir/authentik \
152
152
  github-dir/public \
153
153
  bitbucket-dir/public \
154
+ gitlab-dir/public
155
+
156
+ verify_no_repos \
157
+ github-dir/private \
158
+ bitbucket-dir/private \
159
+ gitlab-dir/private
160
+
161
+ verify_origin lens 'git@github.com:ekmett/lens.git'
162
+ verify_origin chromiumembedded/cef 'git@bitbucket.org:chromiumembedded/cef.git'
163
+ verify_origin graphviz 'git@gitlab.com:graphviz/graphviz.git'
164
+ verify_origin goauthentik-dir/authentik 'git@github.com:goauthentik/authentik.git'
165
+
166
+ verify_origin github-dir/public 'git@github.com:cgitize-test/public.git'
167
+ verify_origin bitbucket-dir/public 'git@bitbucket.org:cgitize-test-workspace/public.git'
168
+ verify_origin gitlab-dir/public 'git@gitlab.com:cgitize-test/public.git'
169
+
170
+ cleanup
171
+ success
172
+ }
173
+
174
+ test_ssh_private() {
175
+ echo
176
+ echo ======================================================================
177
+ echo "${FUNCNAME[0]}"
178
+ echo ======================================================================
179
+
180
+ setup_ssh
181
+ setup_private_repos
182
+ cgitize
183
+
184
+ verify_repos \
185
+ lens \
186
+ chromiumembedded/cef \
187
+ graphviz \
188
+ wireguard/wintun \
189
+ goauthentik-dir/authentik \
190
+ github-dir/public \
191
+ github-dir/private \
192
+ bitbucket-dir/public \
193
+ bitbucket-dir/private \
154
194
  gitlab-dir/public \
195
+ gitlab-dir/private
155
196
 
156
197
  verify_origin lens 'git@github.com:ekmett/lens.git'
157
198
  verify_origin chromiumembedded/cef 'git@bitbucket.org:chromiumembedded/cef.git'
@@ -159,8 +200,11 @@ test_ssh() {
159
200
  verify_origin goauthentik-dir/authentik 'git@github.com:goauthentik/authentik.git'
160
201
 
161
202
  verify_origin github-dir/public 'git@github.com:cgitize-test/public.git'
203
+ verify_origin github-dir/private 'git@github.com:cgitize-test/private.git'
162
204
  verify_origin bitbucket-dir/public 'git@bitbucket.org:cgitize-test-workspace/public.git'
205
+ verify_origin bitbucket-dir/private 'git@bitbucket.org:cgitize-test-workspace/private.git'
163
206
  verify_origin gitlab-dir/public 'git@gitlab.com:cgitize-test/public.git'
207
+ verify_origin gitlab-dir/private 'git@gitlab.com:cgitize-test/private.git'
164
208
 
165
209
  cleanup
166
210
  success
@@ -195,9 +239,9 @@ test_https() {
195
239
  verify_origin graphviz 'https://gitlab.com/graphviz/graphviz.git'
196
240
  verify_origin goauthentik-dir/authentik 'https://github.com/goauthentik/authentik.git'
197
241
 
198
- verify_origin github-dir/public 'https://github.com/cgitize-test/public.git'
199
- verify_origin bitbucket-dir/public 'https://bitbucket.org/cgitize-test-workspace/public.git'
200
- verify_origin gitlab-dir/public 'https://gitlab.com/cgitize-test/public.git'
242
+ verify_origin github-dir/public 'https://github.com/cgitize-test/public.git'
243
+ verify_origin bitbucket-dir/public 'https://bitbucket.org/cgitize-test-workspace/public.git'
244
+ verify_origin gitlab-dir/public 'https://gitlab.com/cgitize-test/public.git'
201
245
 
202
246
  cleanup
203
247
  success
@@ -259,6 +303,7 @@ test_one_repo() {
259
303
  main() {
260
304
  trap cleanup EXIT
261
305
  test_ssh
306
+ test_ssh_private
262
307
  test_https
263
308
  test_https_private
264
309
  test_one_repo
@@ -1,3 +1,5 @@
1
+ IFS= read -r -s -p 'Bitbucket email: ' CGITIZE_BITBUCKET_EMAIL
2
+ echo
1
3
  IFS= read -r -s -p 'Bitbucket token: ' CGITIZE_BITBUCKET_TOKEN
2
4
  echo
3
5
  IFS= read -r -s -p 'GitHub token: ' CGITIZE_GITHUB_TOKEN
@@ -5,7 +7,7 @@ echo
5
7
  IFS= read -r -s -p 'GitLab token: ' CGITIZE_GITLAB_TOKEN
6
8
  echo
7
9
 
8
- export CGITIZE_BITBUCKET_USERNAME=cgitize-test
10
+ export CGITIZE_BITBUCKET_EMAIL
9
11
  export CGITIZE_BITBUCKET_TOKEN
10
12
  export CGITIZE_GITHUB_USERNAME=cgitize-test
11
13
  export CGITIZE_GITHUB_TOKEN
@@ -13,7 +13,7 @@ from requests.exceptions import HTTPError
13
13
  class BitbucketTests(unittest.TestCase):
14
14
  def setUp(self):
15
15
  self.bitbucket = Cloud(
16
- username=os.environ.get('CGITIZE_BITBUCKET_USERNAME'),
16
+ username=os.environ.get('CGITIZE_BITBUCKET_EMAIL'),
17
17
  password=os.environ.get('CGITIZE_BITBUCKET_TOKEN'),
18
18
  cloud=True,
19
19
  )
@@ -65,6 +65,21 @@ class BitbucketTests(unittest.TestCase):
65
65
  r.get_link('html'), 'https://bitbucket.org/cgitize-test-workspace/private'
66
66
  )
67
67
 
68
+ clone_urls = [
69
+ link for link in r.data['links']['clone'] if link['name'] == 'https'
70
+ ]
71
+ self.assertEqual(len(clone_urls), 1)
72
+ self.assertEqual(
73
+ clone_urls[0]['href'],
74
+ 'https://cgitize-test@bitbucket.org/cgitize-test-workspace/private.git',
75
+ )
76
+
77
+ ssh_urls = [link for link in r.data['links']['clone'] if link['name'] == 'ssh']
78
+ self.assertEqual(len(ssh_urls), 1)
79
+ self.assertEqual(
80
+ ssh_urls[0]['href'], 'git@bitbucket.org:cgitize-test-workspace/private.git'
81
+ )
82
+
68
83
  def test_user(self):
69
84
  w = self.bitbucket.workspaces.get('cgitize-test-workspace')
70
85
  self.assertEqual(
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes