blob: 20bcf3585e140e71aebb8a12f4df74069083a69a (
plain)
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
|
# frozen_string_literal: true
module Gitlab
module Git
module WrapsGitalyErrors
def wrapped_gitaly_errors(&block)
yield block
rescue GRPC::BadStatus => e
# The GRPC::BadStatus is the fundamental error that serves as the basis for all other gRPC error categories,
# including GRPC::InvalidArgument. It is essential to note that rescuing the specific exception class does not
# account for all possible cases. In this regard, a status exception can be directly generated from
# GRPC::BadStatus. Therefore, it is recommended that we capture and rescue the GRPC::BadStatus and assert the
# status code to ensure adequate coverage of error cases.
case e.code
when GRPC::Core::StatusCodes::NOT_FOUND
raise Gitlab::Git::Repository::NoRepository, e
when GRPC::Core::StatusCodes::INVALID_ARGUMENT
raise ArgumentError, e
when GRPC::Core::StatusCodes::DEADLINE_EXCEEDED
raise Gitlab::Git::CommandTimedOut, e
when GRPC::Core::StatusCodes::RESOURCE_EXHAUSTED
handle_resource_exhausted(e)
else
raise Gitlab::Git::CommandError, e
end
end
private
def handle_resource_exhausted(exception)
detail = Gitlab::GitalyClient.decode_detailed_error(exception)
case detail.class.name
when Gitaly::LimitError.name
retry_after = detail&.retry_after&.seconds
raise ResourceExhaustedError.new(
"Upstream Gitaly has been exhausted: #{detail.error_message}. Try again later", retry_after
)
else
raise ResourceExhaustedError, _("Upstream Gitaly has been exhausted. Try again later")
end
end
end
end
end
|