File: troubleshooting_git.md

package info (click to toggle)
gitlab 17.6.5-19
  • links: PTS, VCS
  • area: main
  • in suites: sid
  • size: 629,368 kB
  • sloc: ruby: 1,915,304; javascript: 557,307; sql: 60,639; xml: 6,509; sh: 4,567; makefile: 1,239; python: 406
file content (453 lines) | stat: -rw-r--r-- 15,203 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
---
stage: Create
group: Source Code
info: "To determine the technical writer assigned to the Stage/Group associated with this page, see https://handbook.gitlab.com/handbook/product/ux/technical-writing/#assignments"
description: "Debugging tips for fixing problems in Git."
---

# Troubleshooting Git

Sometimes things don't work the way they should or as you might expect when
you're using Git. Here are some tips on troubleshooting and resolving issues
with Git.

## Debugging

When troubleshooting problems with Git, try these debugging techniques.

### Use a custom SSH key for a Git command

```shell
GIT_SSH_COMMAND="ssh -i ~/.ssh/gitlabadmin" git <command>
```

### Debug problems with cloning

For Git over SSH:

```shell
GIT_SSH_COMMAND="ssh -vvv" git clone <git@url>
```

For Git over HTTPS:

```shell
GIT_TRACE_PACKET=1 GIT_TRACE=2 GIT_CURL_VERBOSE=1 git clone <url>
```

### Debug Git with traces

Git includes a complete set of [traces for debugging Git commands](https://git-scm.com/book/en/v2/Git-Internals-Environment-Variables#_debugging), for example:

- `GIT_TRACE_PERFORMANCE=1`: enables tracing of performance data, showing how long each particular `git` invocation takes.
- `GIT_TRACE_SETUP=1`: enables tracing of what `git` is discovering about the repository and environment it's interacting with.
- `GIT_TRACE_PACKET=1`: enables packet-level tracing for network operations.
- `GIT_CURL_VERBOSE=1`: enables `curl`'s verbose output, which [may include credentials](https://curl.se/docs/manpage.html#-v).

## Broken pipe errors on `git push`

'Broken pipe' errors can occur when attempting to push to a remote repository.
When pushing you usually see:

```plaintext
Write failed: Broken pipe
fatal: The remote end hung up unexpectedly
```

To fix this issue, here are some possible solutions.

### Increase the POST buffer size in Git

When you attempt to push large repositories with Git over HTTPS, you might get an error message like:

```shell
fatal: pack has bad object at offset XXXXXXXXX: inflate returned -5
```

To resolve this issue:

- Increase the
  [http.postBuffer](https://git-scm.com/docs/git-config#Documentation/git-config.txt-httppostBuffer)
  value in your local Git configuration. The default value is 1 MB. For example, if `git clone`
  fails when cloning a 500 MB repository, execute the following:

  1. Open a terminal or command prompt.
  1. Increase the `http.postBuffer` value:

      ```shell
      # Set the http.postBuffer size in bytes
      git config http.postBuffer 524288000
      ```

If the local configuration doesn't resolve the issue, you may need to modify the server configuration.
This should be done cautiously and only if you have server access.

- Increase the `http.postBuffer` on the server side:

  1. Open a terminal or command prompt.
  1. Modify the GitLab instance's
    [`gitlab.rb`](https://gitlab.com/gitlab-org/omnibus-gitlab/-/blob/13.5.1+ee.0/files/gitlab-config-template/gitlab.rb.template#L1435-1455) file:

      ```ruby
      gitaly['configuration'] = {
        # ...
        git: {
          # ...
          config: [
            # Set the http.postBuffer size, in bytes
            {key: "http.postBuffer", value: "524288000"},
          ],
        },
      }
      ```

  1. Apply the configuration change:

      ```shell
      sudo gitlab-ctl reconfigure
      ```

### Stream 0 was not closed cleanly

If you see this error, it may be caused by a slow internet connection:

```plaintext
RPC failed; curl 92 HTTP/2 stream 0 was not closed cleanly: INTERNAL_ERROR (err 2)
```

If you use Git over HTTP instead of SSH, try one of these fixes:

- Increase the POST buffer size in the Git configuration with `git config http.postBuffer 52428800`.
- Switch to the `HTTP/1.1` protocol with `git config http.version HTTP/1.1`.

If neither approach fixes the error, you may need a different internet service provider.

### Check your SSH configuration

**If pushing over SSH**, first check your SSH configuration as 'Broken pipe'
errors can sometimes be caused by underlying issues with SSH (such as
authentication). Make sure that SSH is correctly configured by following the
instructions in the [SSH troubleshooting](../../user/ssh_troubleshooting.md#password-prompt-with-git-clone) documentation.

If you're a GitLab administrator with server access, you can also prevent
session timeouts by configuring SSH `keep-alive` on the client or the server.

NOTE:
Configuring both the client and the server is unnecessary.

**To configure SSH on the client side**:

- On UNIX, edit `~/.ssh/config` (create the file if it doesn't exist) and
  add or edit:

  ```plaintext
  Host your-gitlab-instance-url.com
    ServerAliveInterval 60
    ServerAliveCountMax 5
  ```

- On Windows, if you are using PuTTY, go to your session properties, then
  go to "Connection" and under "Sending of null packets to keep
  session active", set `Seconds between keepalives (0 to turn off)` to `60`.

**To configure SSH on the server side**, edit `/etc/ssh/sshd_config` and add:

```plaintext
ClientAliveInterval 60
ClientAliveCountMax 5
```

### Running a `git repack`

**If 'pack-objects' type errors are also being displayed**, you can try to
run a `git repack` before attempting to push to the remote repository again:

```shell
git repack
git push
```

### Upgrade your Git client

In case you're running an older version of Git (< 2.9), consider upgrading
to >= 2.9 (see [Broken pipe when pushing to Git repository](https://stackoverflow.com/questions/19120120/broken-pipe-when-pushing-to-git-repository/36971469#36971469)).

## `ssh_exchange_identification` error

Users may experience the following error when attempting to push or pull
using Git over SSH:

```plaintext
Please make sure you have the correct access rights
and the repository exists.
...
ssh_exchange_identification: read: Connection reset by peer
fatal: Could not read from remote repository.
```

or

```plaintext
ssh_exchange_identification: Connection closed by remote host
fatal: The remote end hung up unexpectedly
```

or

```plaintext
kex_exchange_identification: Connection closed by remote host
Connection closed by x.x.x.x port 22
```

This error usually indicates that SSH daemon's `MaxStartups` value is throttling
SSH connections. This setting specifies the maximum number of concurrent, unauthenticated
connections to the SSH daemon. This affects users with proper authentication
credentials (SSH keys) because every connection is 'unauthenticated' in the
beginning. The [default value](https://man.openbsd.org/sshd_config#MaxStartups) is `10`.

This can be verified by examining the host's [`sshd`](https://en.wikibooks.org/wiki/OpenSSH/Logging_and_Troubleshooting#Server_Logs)
logs. For systems in the Debian family, refer to `/var/log/auth.log`, and for RHEL derivatives,
check `/var/log/secure` for the following errors:

```plaintext
sshd[17242]: error: beginning MaxStartups throttling
sshd[17242]: drop connection #1 from [CLIENT_IP]:52114 on [CLIENT_IP]:22 past MaxStartups
```

The absence of this error suggests that the SSH daemon is not limiting connections,
indicating that the underlying issue may be network-related.

### Increase the number of unauthenticated concurrent SSH connections

Increase `MaxStartups` on the GitLab server
by adding or modifying the value in `/etc/ssh/sshd_config`:

```plaintext
MaxStartups 100:30:200
```

`100:30:200` means up to 100 SSH sessions are allowed without restriction,
after which 30% of connections are dropped until reaching an absolute maximum of 200.

After you modify the value of `MaxStartups`, check for any errors in the configuration.

```shell
sudo sshd -t -f /etc/ssh/sshd_config
```

If the configuration check runs without errors, it should be safe to restart the
SSH daemon for the change to take effect.

```shell
# Debian/Ubuntu
sudo systemctl restart ssh

# CentOS/RHEL
sudo service sshd restart
```

## Timeout during `git push` / `git pull`

If pulling/pushing from/to your repository ends up taking more than 50 seconds,
a timeout is issued. It contains a log of the number of operations performed
and their respective timings, like the example below:

```plaintext
remote: Running checks for branch: master
remote: Scanning for LFS objects... (153ms)
remote: Calculating new repository size... (cancelled after 729ms)
```

This could be used to further investigate what operation is performing poorly
and provide GitLab with more information on how to improve the service.

### Error: Operation timed out

If you encounter an error like this when using Git, it usually indicates a network issue:

```shell
ssh: connect to host gitlab.com port 22: Operation timed out
fatal: Could not read from remote repository
```

To help identify the underlying issue:

- Connect through a different network (for example, switch from Wi-Fi to cellular data) to rule out
  local network or firewall issues.
- Run this bash command to gather `traceroute` and `ping` information: `mtr -T -P 22 <gitlab_server>.com`.
  To learn about MTR and how to read its output, see the Cloudflare article
  [What is My Traceroute (MTR)?](https://www.cloudflare.com/en-gb/learning/network-layer/what-is-mtr/).

## Error: transfer closed with outstanding read data remaining

Sometimes, when cloning old or large repositories, the following error is shown when running `git clone` over HTTP:

```plaintext
error: RPC failed; curl 18 transfer closed with outstanding read data remaining
fatal: The remote end hung up unexpectedly
fatal: early EOF
fatal: index-pack failed
```

This problem is common in Git itself, due to its inability to handle large files or large quantities of files.
[Git LFS](https://about.gitlab.com/blog/2017/01/30/getting-started-with-git-lfs-tutorial/) was created to work around this problem; however, even it has limitations. It's usually due to one of these reasons:

- The number of files in the repository.
- The number of revisions in the history.
- The existence of large files in the repository.

If this error occurs when cloning a large repository, you can
[decrease the cloning depth](../../user/project/repository/monorepos/index.md#shallow-cloning) to a value of `1`. For example:

This approach doesn't resolve the underlying cause, but you can successfully clone the repository.
To decrease the cloning depth to `1`, run:

  ```shell
  variables:
    GIT_DEPTH: 1
  ```

## Password expired error on Git fetch with SSH for LDAP user

If `git fetch` returns this `HTTP 403 Forbidden` error on a self-managed instance of
GitLab, the password expiration date (`users.password_expires_at`) for this user in the
GitLab database is a date in the past:

```plaintext
Your password expired. Please access GitLab from a web browser to update your password.
```

Requests made with a SSO account and where `password_expires_at` is not `null`
return this error:

```plaintext
"403 Forbidden - Your password expired. Please access GitLab from a web browser to update your password."
```

To resolve this issue, you can update the password expiration by either:

- Using the [GitLab Rails console](../../administration/operations/rails_console.md)
  to check and update the user data:

  ```ruby
  user = User.find_by_username('<USERNAME>')
  user.password_expired?
  user.password_expires_at
  user.update!(password_expires_at: nil)
  ```

- Using `gitlab-psql`:

  ```sql
  # gitlab-psql
  UPDATE users SET password_expires_at = null WHERE username='<USERNAME>';
  ```

The bug was reported [in this issue](https://gitlab.com/gitlab-org/gitlab/-/issues/332455).

## Error on Git fetch: "HTTP Basic: Access Denied"

If you receive an `HTTP Basic: Access denied` error when using Git over HTTP(S),
refer to the [two-factor authentication troubleshooting guide](../../user/profile/account/two_factor_authentication_troubleshooting.md).

## `401` errors logged during successful `git clone`

When cloning a repository with HTTP, the
[`production_json.log`](../../administration/logs/index.md#production_jsonlog) file
may show an initial status of `401` (unauthorized), quickly followed by a `200`.

```json
{
   "method":"GET",
   "path":"/group/project.git/info/refs",
   "format":"*/*",
   "controller":"Repositories::GitHttpController",
   "action":"info_refs",
   "status":401,
   "time":"2023-04-18T22:55:15.371Z",
   "remote_ip":"x.x.x.x",
   "ua":"git/2.39.2",
   "correlation_id":"01GYB98MBM28T981DJDGAD98WZ",
   "duration_s":0.03585
}
{
   "method":"GET",
   "path":"/group/project.git/info/refs",
   "format":"*/*",
   "controller":"Repositories::GitHttpController",
   "action":"info_refs",
   "status":200,
   "time":"2023-04-18T22:55:15.714Z",
   "remote_ip":"x.x.x.x",
   "user_id":1,
   "username":"root",
   "ua":"git/2.39.2",
   "correlation_id":"01GYB98MJ0CA3G9K8WDH7HWMQX",
   "duration_s":0.17111
}
```

You should expect this initial `401` log entry for each Git operation performed over HTTP,
due to how [HTTP Basic authentication](https://en.wikipedia.org/wiki/Basic_access_authentication) works.

When the Git client initiates a clone, the initial request sent to GitLab does not provide
any authentication details. GitLab returns a `401 Unauthorized` result for that request.
A few milliseconds later, the Git client sends a follow-up request containing authentication
details. This second request should succeed, and result in a `200 OK` log entry.

If a `401` log entry lacks a corresponding `200` log entry, the Git client is likely using either:

- An incorrect password.
- An expired or revoked token.

If not rectified, you could encounter
[`403` (Forbidden) errors](#403-error-when-performing-git-operations-over-http)
instead.

## `403` error when performing Git operations over HTTP

When performing Git operations over HTTP, a `403` (Forbidden) error indicates that
your IP address has been blocked by the failed-authentication ban:

```plaintext
fatal: unable to access 'https://gitlab.com/group/project.git/': The requested URL returned error: 403
```

The `403` can be seen in the [`production_json.log`](../../administration/logs/index.md#production_jsonlog):

```json
{
   "method":"GET",
   "path":"/group/project.git/info/refs",
   "format":"*/*",
   "controller":"Repositories::GitHttpController",
   "action":"info_refs",
   "status":403,
   "time":"2023-04-19T22:14:25.894Z",
   "remote_ip":"x.x.x.x",
   "user_id":1,
   "username":"root",
   "ua":"git/2.39.2",
   "correlation_id":"01GYDSAKAN2SPZPAMJNRWW5H8S",
   "duration_s":0.00875
}
```

If your IP address has been blocked, a corresponding log entry exists in the
[`auth_json.log`](../../administration/logs/index.md#auth_jsonlog):

```json
{
    "severity":"ERROR",
    "time":"2023-04-19T22:14:25.893Z",
    "correlation_id":"01GYDSAKAN2SPZPAMJNRWW5H8S",
    "message":"Rack_Attack",
    "env":"blocklist",
    "remote_ip":"x.x.x.x",
    "request_method":"GET",
    "path":"/group/project.git/info/refs?service=git-upload-pack"}
```

The failed authentication ban limits differ depending if you are using a
[self-managed instance](../../security/rate_limits.md#failed-authentication-ban-for-git-and-container-registry)
or [GitLab.com](../../user/gitlab_com/index.md#ip-blocks).