gitlab-labkit 0.42.1 → 1.0.0
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.
- checksums.yaml +4 -4
- data/.gitlab-ci-asdf-versions.yml +1 -1
- data/.pre-commit-config.yaml +1 -1
- data/.tool-versions +1 -1
- data/README.md +1 -1
- data/config/{covered_experiences → user_experience_slis}/schema.json +5 -5
- data/gitlab-labkit.gemspec +2 -2
- data/lib/gitlab-labkit.rb +2 -1
- data/lib/labkit/fields.rb +20 -7
- data/lib/labkit/middleware/rack.rb +3 -3
- data/lib/labkit/middleware/sidekiq/client.rb +1 -1
- data/lib/labkit/middleware/sidekiq/server.rb +1 -1
- data/lib/labkit/middleware/sidekiq/{covered_experience → user_experience_sli}/client.rb +4 -4
- data/lib/labkit/middleware/sidekiq/{covered_experience → user_experience_sli}/server.rb +4 -4
- data/lib/labkit/middleware/sidekiq/user_experience_sli.rb +17 -0
- data/lib/labkit/middleware/sidekiq.rb +2 -1
- data/lib/labkit/rspec/README.md +36 -27
- data/lib/labkit/rspec/matchers/{covered_experience_matchers.rb → user_experience_matchers.rb} +53 -47
- data/lib/labkit/rspec/matchers.rb +1 -1
- data/lib/labkit/{covered_experience → user_experience_sli}/README.md +28 -28
- data/lib/labkit/{covered_experience → user_experience_sli}/current.rb +7 -7
- data/lib/labkit/user_experience_sli/error.rb +9 -0
- data/lib/labkit/{covered_experience → user_experience_sli}/experience.rb +26 -26
- data/lib/labkit/{covered_experience → user_experience_sli}/null.rb +2 -2
- data/lib/labkit/{covered_experience → user_experience_sli}/registry.rb +13 -13
- data/lib/labkit/{covered_experience.rb → user_experience_sli.rb} +16 -11
- metadata +18 -18
- data/lib/labkit/covered_experience/error.rb +0 -9
- data/lib/labkit/middleware/sidekiq/covered_experience.rb +0 -14
- /data/config/{covered_experiences → user_experience_slis}/testing_sample.yml +0 -0
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 848c7a3b2a208349e041ead5190bb2f665190100e9c4868b3391f040674834b7
|
|
4
|
+
data.tar.gz: be220cf29fa57499b1101cabda163816fd37f77b09b5b3be93464cd87c6294b6
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: e5e4181d842aa238bc113b4d1486471f71b44e3d04d7f8613583e2ae23eeb33a4c6e275a5fccb18b2db5a962c0e4ff294b2df7a6eb9bd6c08a8aaf88a9146a96
|
|
7
|
+
data.tar.gz: eeab7e40652242988f381b9192a9384a9098a7bd31ad8ef6e8f0b17c5c6f17032a8f2199f9b1fbe543e9d11ba04a30cb5c59a2b96d9bb86df3a30a026924e96f
|
data/.pre-commit-config.yaml
CHANGED
|
@@ -25,7 +25,7 @@ repos:
|
|
|
25
25
|
# Documentation available at
|
|
26
26
|
# https://gitlab.com/gitlab-com/gl-infra/common-ci-tasks/-/blob/main/docs/pre-commit.md
|
|
27
27
|
- repo: https://gitlab.com/gitlab-com/gl-infra/common-ci-tasks
|
|
28
|
-
rev:
|
|
28
|
+
rev: v3.0 # renovate:managed
|
|
29
29
|
|
|
30
30
|
hooks:
|
|
31
31
|
- id: shellcheck # Run shellcheck for changed Shell files
|
data/.tool-versions
CHANGED
data/README.md
CHANGED
|
@@ -20,7 +20,7 @@ LabKit-Ruby provides functionality in a number of areas:
|
|
|
20
20
|
|
|
21
21
|
1. `Labkit::Context` used for providing context information to log messages.
|
|
22
22
|
1. `Labkit::Correlation` for accessing the correlation id. (Generated and propagated by `Labkit::Context`)
|
|
23
|
-
1. `Labkit::
|
|
23
|
+
1. `Labkit::UserExperienceSli` for tracking User Experience SLIs. More on the [README](./lib/labkit/user_experience_sli/README.md).
|
|
24
24
|
1. `Labkit::FIPS` for checking for FIPS mode and using FIPS-compliant algorithms.
|
|
25
25
|
1. `Labkit::Logging` for sanitizing log messages.
|
|
26
26
|
1. `Labkit::Metrics` for metrics. More on the [README](./lib/labkit/metrics/README.md).
|
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "http://json-schema.org/draft-06/schema#",
|
|
3
|
-
"$id": "https://gitlab.com/gitlab-org/ruby/gems/labkit-ruby/-/raw/master/config/
|
|
4
|
-
"title": "
|
|
5
|
-
"description": "Schema for GitLab
|
|
3
|
+
"$id": "https://gitlab.com/gitlab-org/ruby/gems/labkit-ruby/-/raw/master/config/user_experience_slis/schema.json",
|
|
4
|
+
"title": "User Experience SLI Definition",
|
|
5
|
+
"description": "Schema for GitLab User Experience SLI files",
|
|
6
6
|
"type": "object",
|
|
7
7
|
"properties": {
|
|
8
8
|
"description": {
|
|
9
9
|
"type": "string",
|
|
10
10
|
"minLength": 1,
|
|
11
|
-
"description": "Human-readable description of the
|
|
11
|
+
"description": "Human-readable description of the user experience"
|
|
12
12
|
},
|
|
13
13
|
"feature_category": {
|
|
14
14
|
"type": "string",
|
|
@@ -23,7 +23,7 @@
|
|
|
23
23
|
"async_fast",
|
|
24
24
|
"async_slow"
|
|
25
25
|
],
|
|
26
|
-
"description": "Urgency level for this
|
|
26
|
+
"description": "Urgency level for this user experience"
|
|
27
27
|
}
|
|
28
28
|
},
|
|
29
29
|
"required": [
|
data/gitlab-labkit.gemspec
CHANGED
|
@@ -22,7 +22,7 @@ Gem::Specification.new do |spec|
|
|
|
22
22
|
# Please maintain alphabetical order for dependencies
|
|
23
23
|
spec.add_runtime_dependency "actionpack", ">= 5.0.0", "< 8.1.0"
|
|
24
24
|
spec.add_runtime_dependency "activesupport", ">= 5.0.0", "< 8.1.0"
|
|
25
|
-
spec.add_runtime_dependency "grpc", ">= 1.
|
|
25
|
+
spec.add_runtime_dependency "grpc", ">= 1.75" # Be sure to update the "grpc-tools" dev_dependency too
|
|
26
26
|
spec.add_runtime_dependency "google-protobuf", "~> 3" # Keep the major version to 3 until we update the `grpc` gem
|
|
27
27
|
spec.add_runtime_dependency "jaeger-client", "~> 1.1.0"
|
|
28
28
|
spec.add_runtime_dependency 'json-schema', '~> 5.1'
|
|
@@ -36,7 +36,7 @@ Gem::Specification.new do |spec|
|
|
|
36
36
|
spec.add_development_dependency "faraday", "~> 1.10.3"
|
|
37
37
|
spec.add_development_dependency "gitlab-dangerfiles", "~> 2.11.0"
|
|
38
38
|
spec.add_development_dependency "gitlab-styles", "~> 13.0.2"
|
|
39
|
-
spec.add_development_dependency "grpc-tools", ">= 1.
|
|
39
|
+
spec.add_development_dependency "grpc-tools", ">= 1.75"
|
|
40
40
|
spec.add_development_dependency "httparty", "~> 0.22.0"
|
|
41
41
|
spec.add_development_dependency "httpclient", "~> 2.9.0"
|
|
42
42
|
spec.add_development_dependency "irb", "~> 1.15.2"
|
data/lib/gitlab-labkit.rb
CHANGED
|
@@ -9,7 +9,8 @@ module Labkit
|
|
|
9
9
|
|
|
10
10
|
autoload :Context, "labkit/context"
|
|
11
11
|
autoload :Correlation, "labkit/correlation"
|
|
12
|
-
autoload :CoveredExperience, "labkit/
|
|
12
|
+
autoload :CoveredExperience, "labkit/user_experience_sli" # Backward compatibility alias
|
|
13
|
+
autoload :UserExperienceSli, "labkit/user_experience_sli"
|
|
13
14
|
autoload :FIPS, "labkit/fips"
|
|
14
15
|
autoload :Tracing, "labkit/tracing"
|
|
15
16
|
autoload :Logging, "labkit/logging"
|
data/lib/labkit/fields.rb
CHANGED
|
@@ -18,24 +18,37 @@ module Labkit
|
|
|
18
18
|
# data[Labkit::Fields::GL_USER_ID] = user.id
|
|
19
19
|
# ...
|
|
20
20
|
#
|
|
21
|
+
# Labkit (Go): https://gitlab.com/gitlab-org/labkit/-/tree/master/fields?ref_type=heads
|
|
22
|
+
#
|
|
23
|
+
# For Engineers Looking to add fields:
|
|
24
|
+
#
|
|
25
|
+
# These fields are derived from the Go Labkit variant. Please ensure that you've made the
|
|
26
|
+
# respective changes in that repository prior to including the fields in this package.
|
|
27
|
+
#
|
|
28
|
+
# Please see the handbook page for more information
|
|
29
|
+
# https://handbook.gitlab.com/handbook/engineering/architecture/design-documents/observability_field_standardisation/
|
|
21
30
|
module Fields
|
|
22
31
|
# correlation_id - string
|
|
23
32
|
#
|
|
33
|
+
# correlation_id - string
|
|
24
34
|
# This field is used to correlate
|
|
25
35
|
# the logs emitted by all of our systems.
|
|
26
|
-
#
|
|
27
36
|
# This should be present in all log line
|
|
28
37
|
# emissions.
|
|
29
38
|
CORRELATION_ID = "correlation_id"
|
|
30
39
|
|
|
31
|
-
#
|
|
32
|
-
#
|
|
33
|
-
# [endpoint_id, duration_s, status_code]
|
|
34
|
-
|
|
35
|
-
# gl_user_id - integer
|
|
40
|
+
# GitLabUserID - an integer field that
|
|
41
|
+
# captures the user's numeric ID for logging purposes.
|
|
36
42
|
GL_USER_ID = "gl_user_id"
|
|
37
43
|
|
|
38
|
-
#
|
|
44
|
+
# GitLabUserName - a string field that
|
|
45
|
+
# captures the user's username for logging purposes.
|
|
39
46
|
GL_USER_NAME = "gl_user_name"
|
|
47
|
+
|
|
48
|
+
# New fields being added to this section should have
|
|
49
|
+
# the appropriate doc comments added above. These
|
|
50
|
+
# should clearly indicate what the intended use of the
|
|
51
|
+
# field is and should be replicated across the labkit
|
|
52
|
+
# variations.
|
|
40
53
|
end
|
|
41
54
|
end
|
|
@@ -59,13 +59,13 @@ module Labkit
|
|
|
59
59
|
# 4. Microservices or API-only applications with minimal middleware
|
|
60
60
|
# 5. Background job processors that use Rack but not Rails' full stack
|
|
61
61
|
#
|
|
62
|
-
# By explicitly resetting here, we ensure
|
|
62
|
+
# By explicitly resetting here, we ensure user experiences are properly
|
|
63
63
|
# cleaned up regardless of the application framework or middleware configuration.
|
|
64
64
|
def reset_current_experiences
|
|
65
65
|
# Only reset if the Current class is loaded to avoid unnecessary dependencies
|
|
66
|
-
return unless defined?(Labkit::
|
|
66
|
+
return unless defined?(Labkit::UserExperienceSli::Current)
|
|
67
67
|
|
|
68
|
-
Labkit::
|
|
68
|
+
Labkit::UserExperienceSli::Current.reset
|
|
69
69
|
end
|
|
70
70
|
end
|
|
71
71
|
end
|
|
@@ -13,7 +13,7 @@ module Labkit
|
|
|
13
13
|
@chain ||= ::Sidekiq::Middleware::Chain.new do |chain|
|
|
14
14
|
chain.add Labkit::Middleware::Sidekiq::Context::Client
|
|
15
15
|
chain.add Labkit::Middleware::Sidekiq::Tracing::Client if Labkit::Tracing.enabled?
|
|
16
|
-
chain.add Labkit::Middleware::Sidekiq::
|
|
16
|
+
chain.add Labkit::Middleware::Sidekiq::UserExperienceSli::Client
|
|
17
17
|
end
|
|
18
18
|
end
|
|
19
19
|
|
|
@@ -13,7 +13,7 @@ module Labkit
|
|
|
13
13
|
@chain ||= ::Sidekiq::Middleware::Chain.new do |chain|
|
|
14
14
|
chain.add Labkit::Middleware::Sidekiq::Context::Server
|
|
15
15
|
chain.add Labkit::Middleware::Sidekiq::Tracing::Server if Labkit::Tracing.enabled?
|
|
16
|
-
chain.add Labkit::Middleware::Sidekiq::
|
|
16
|
+
chain.add Labkit::Middleware::Sidekiq::UserExperienceSli::Server
|
|
17
17
|
end
|
|
18
18
|
end
|
|
19
19
|
|
|
@@ -1,22 +1,22 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
|
-
require 'labkit/
|
|
3
|
+
require 'labkit/user_experience_sli/current'
|
|
4
4
|
|
|
5
5
|
module Labkit
|
|
6
6
|
module Middleware
|
|
7
7
|
module Sidekiq
|
|
8
|
-
module
|
|
8
|
+
module UserExperienceSli
|
|
9
9
|
# This middleware for Sidekiq-client wraps scheduling jobs with covered
|
|
10
10
|
# experience context. It retrieves the current experiences and
|
|
11
11
|
# populates the job with them.
|
|
12
12
|
class Client
|
|
13
13
|
def call(worker_class, job, _queue, _redis_pool)
|
|
14
|
-
data = Labkit::
|
|
14
|
+
data = Labkit::UserExperienceSli::Current.active_experiences.inject({}) do |data, (_, xp)|
|
|
15
15
|
xp.checkpoint(checkpoint_action: "sidekiq_job_scheduled", worker: worker_class.to_s)
|
|
16
16
|
data.merge!(xp.to_h)
|
|
17
17
|
end
|
|
18
18
|
|
|
19
|
-
job[Labkit::
|
|
19
|
+
job[Labkit::UserExperienceSli::Current::AGGREGATION_KEY] = data unless data.empty?
|
|
20
20
|
|
|
21
21
|
yield
|
|
22
22
|
end
|
|
@@ -3,20 +3,20 @@
|
|
|
3
3
|
module Labkit
|
|
4
4
|
module Middleware
|
|
5
5
|
module Sidekiq
|
|
6
|
-
module
|
|
6
|
+
module UserExperienceSli
|
|
7
7
|
# This middleware for Sidekiq-server rehydrates the current experiences
|
|
8
8
|
# serialized to the job
|
|
9
9
|
class Server
|
|
10
10
|
def call(_worker_class, job, _queue)
|
|
11
|
-
job[Labkit::
|
|
12
|
-
xp = Labkit::
|
|
11
|
+
job[Labkit::UserExperienceSli::Current::AGGREGATION_KEY]&.each do |experience_id, data|
|
|
12
|
+
xp = Labkit::UserExperienceSli::Current.rehydrate(experience_id, **data)
|
|
13
13
|
xp.checkpoint(checkpoint_action: "sidekiq_job_started", worker: job["class"].to_s)
|
|
14
14
|
end
|
|
15
15
|
|
|
16
16
|
yield
|
|
17
17
|
|
|
18
18
|
ensure
|
|
19
|
-
Labkit::
|
|
19
|
+
Labkit::UserExperienceSli::Current.reset
|
|
20
20
|
end
|
|
21
21
|
end
|
|
22
22
|
end
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Labkit
|
|
4
|
+
module Middleware
|
|
5
|
+
module Sidekiq
|
|
6
|
+
# This module contains all the sidekiq middleware regarding user
|
|
7
|
+
# experience SLIs
|
|
8
|
+
module UserExperienceSli
|
|
9
|
+
autoload :Client, "labkit/middleware/sidekiq/user_experience_sli/client"
|
|
10
|
+
autoload :Server, "labkit/middleware/sidekiq/user_experience_sli/server"
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
# Backward compatibility alias
|
|
14
|
+
CoveredExperience = UserExperienceSli
|
|
15
|
+
end
|
|
16
|
+
end
|
|
17
|
+
end
|
|
@@ -7,7 +7,8 @@ module Labkit
|
|
|
7
7
|
autoload :Client, "labkit/middleware/sidekiq/client"
|
|
8
8
|
autoload :Server, "labkit/middleware/sidekiq/server"
|
|
9
9
|
autoload :Context, "labkit/middleware/sidekiq/context"
|
|
10
|
-
autoload :
|
|
10
|
+
autoload :UserExperienceSli, "labkit/middleware/sidekiq/user_experience_sli"
|
|
11
|
+
autoload :CoveredExperience, "labkit/middleware/sidekiq/user_experience_sli" # Backward compatibility
|
|
11
12
|
autoload :Tracing, "labkit/middleware/sidekiq/tracing"
|
|
12
13
|
end
|
|
13
14
|
end
|
data/lib/labkit/rspec/README.md
CHANGED
|
@@ -19,61 +19,70 @@ This approach ensures that:
|
|
|
19
19
|
|
|
20
20
|
## Available Matchers
|
|
21
21
|
|
|
22
|
-
###
|
|
22
|
+
### User Experience Matchers
|
|
23
23
|
|
|
24
|
-
These matchers help you test that your code properly instruments
|
|
24
|
+
These matchers help you test that your code properly instruments user experience SLIs with the expected metrics.
|
|
25
25
|
|
|
26
|
-
#### `
|
|
26
|
+
#### `start_user_experience`
|
|
27
27
|
|
|
28
|
-
Tests that a
|
|
28
|
+
Tests that a user experience is started (checkpoint=start metric is incremented).
|
|
29
29
|
|
|
30
30
|
```ruby
|
|
31
|
-
expect { subject }.to
|
|
31
|
+
expect { subject }.to start_user_experience('rails_request')
|
|
32
32
|
|
|
33
33
|
# Test that it does NOT start
|
|
34
|
-
expect { subject }.not_to
|
|
34
|
+
expect { subject }.not_to start_user_experience('rails_request')
|
|
35
35
|
```
|
|
36
36
|
|
|
37
|
-
#### `
|
|
37
|
+
#### `checkpoint_user_experience`
|
|
38
38
|
|
|
39
|
-
Tests that a
|
|
39
|
+
Tests that a user experience checkpoint is recorded (checkpoint=intermediate metric is incremented).
|
|
40
40
|
|
|
41
41
|
```ruby
|
|
42
|
-
expect { subject }.to
|
|
42
|
+
expect { subject }.to checkpoint_user_experience('rails_request')
|
|
43
43
|
|
|
44
44
|
# Test that it does NOT checkpoint
|
|
45
|
-
expect { subject }.not_to
|
|
45
|
+
expect { subject }.not_to checkpoint_user_experience('rails_request')
|
|
46
46
|
```
|
|
47
47
|
|
|
48
|
-
#### `
|
|
48
|
+
#### `resume_user_experience`
|
|
49
49
|
|
|
50
|
-
Tests that a
|
|
50
|
+
Tests that a user experience is resumed (checkpoint=intermediate metric is incremented). This is an alias for `checkpoint_user_experience` that provides more semantic meaning when testing code that resumes a user experience previously started.
|
|
51
51
|
|
|
52
52
|
```ruby
|
|
53
|
-
expect { subject }.to
|
|
53
|
+
expect { subject }.to resume_user_experience('rails_request')
|
|
54
54
|
|
|
55
55
|
# Test that it does NOT resume
|
|
56
|
-
expect { subject }.not_to
|
|
56
|
+
expect { subject }.not_to resume_user_experience('rails_request')
|
|
57
57
|
```
|
|
58
58
|
|
|
59
|
-
#### `
|
|
59
|
+
#### `complete_user_experience`
|
|
60
60
|
|
|
61
|
-
Tests that a
|
|
62
|
-
- `
|
|
63
|
-
- `
|
|
64
|
-
- `
|
|
61
|
+
Tests that a user experience is completed with the expected metrics:
|
|
62
|
+
- `gitlab_user_experience_checkpoint_total` (with checkpoint=end)
|
|
63
|
+
- `gitlab_user_experience_total` (with error flag)
|
|
64
|
+
- `gitlab_user_experience_apdex_total` (with success flag)
|
|
65
65
|
|
|
66
66
|
```ruby
|
|
67
67
|
# Test successful completion
|
|
68
|
-
expect { subject }.to
|
|
68
|
+
expect { subject }.to complete_user_experience('rails_request')
|
|
69
69
|
|
|
70
70
|
# Test completion with error
|
|
71
|
-
expect { subject }.to
|
|
71
|
+
expect { subject }.to complete_user_experience('rails_request', error: true, success: false)
|
|
72
72
|
|
|
73
73
|
# Test that it does NOT complete
|
|
74
|
-
expect { subject }.not_to
|
|
74
|
+
expect { subject }.not_to complete_user_experience('rails_request')
|
|
75
75
|
```
|
|
76
76
|
|
|
77
|
+
### Legacy Matchers (Backward Compatibility)
|
|
78
|
+
|
|
79
|
+
For backward compatibility, the following legacy matchers are still available but deprecated. Please migrate to the new `*_user_experience` matchers above.
|
|
80
|
+
|
|
81
|
+
- `start_covered_experience`
|
|
82
|
+
- `checkpoint_covered_experience`
|
|
83
|
+
- `resume_covered_experience`
|
|
84
|
+
- `complete_covered_experience`
|
|
85
|
+
|
|
77
86
|
## Example Usage
|
|
78
87
|
|
|
79
88
|
### In your spec_helper.rb or rails_helper.rb:
|
|
@@ -96,8 +105,8 @@ end
|
|
|
96
105
|
RSpec.describe MyController, type: :controller do
|
|
97
106
|
describe '#index' do
|
|
98
107
|
it 'instruments the request properly' do
|
|
99
|
-
expect { get :index }.to
|
|
100
|
-
.and
|
|
108
|
+
expect { get :index }.to start_user_experience('rails_request')
|
|
109
|
+
.and complete_user_experience('rails_request')
|
|
101
110
|
end
|
|
102
111
|
|
|
103
112
|
context 'when an error occurs' do
|
|
@@ -106,7 +115,7 @@ RSpec.describe MyController, type: :controller do
|
|
|
106
115
|
end
|
|
107
116
|
|
|
108
117
|
it 'records the error in metrics' do
|
|
109
|
-
expect { get :index }.to
|
|
118
|
+
expect { get :index }.to complete_user_experience('rails_request', error: true, success: false)
|
|
110
119
|
end
|
|
111
120
|
end
|
|
112
121
|
end
|
|
@@ -127,6 +136,6 @@ end
|
|
|
127
136
|
|
|
128
137
|
## Requirements
|
|
129
138
|
|
|
130
|
-
- The
|
|
139
|
+
- The user experience SLI must be registered in `Labkit::UserExperienceSli::Registry`
|
|
131
140
|
- Metrics must be properly configured in your test environment
|
|
132
|
-
- The code under test must use Labkit's
|
|
141
|
+
- The code under test must use Labkit's user experience SLI instrumentation
|
data/lib/labkit/rspec/matchers/{covered_experience_matchers.rb → user_experience_matchers.rb}
RENAMED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
|
-
# RSpec matchers for testing Labkit
|
|
3
|
+
# RSpec matchers for testing Labkit UserExperience functionality
|
|
4
4
|
#
|
|
5
5
|
# This file must be explicitly required in your test setup:
|
|
6
6
|
# require 'labkit/rspec/matchers'
|
|
@@ -10,49 +10,49 @@ raise LoadError, "RSpec is not loaded. Please require 'rspec' before requiring '
|
|
|
10
10
|
module Labkit
|
|
11
11
|
module RSpec
|
|
12
12
|
module Matchers
|
|
13
|
-
# Helper module for
|
|
14
|
-
module
|
|
15
|
-
def attributes(
|
|
16
|
-
raise ArgumentError, "
|
|
13
|
+
# Helper module for UserExperience functionality
|
|
14
|
+
module UserExperience
|
|
15
|
+
def attributes(user_experience_id)
|
|
16
|
+
raise ArgumentError, "user_experience_id is required" if user_experience_id.nil?
|
|
17
17
|
|
|
18
|
-
definition = Labkit::
|
|
19
|
-
definition.to_h.slice(:
|
|
18
|
+
definition = Labkit::UserExperienceSli::Registry.new[user_experience_id]
|
|
19
|
+
definition.to_h.slice(:user_experience_id, :feature_category, :urgency)
|
|
20
20
|
end
|
|
21
21
|
|
|
22
22
|
def checkpoint_counter
|
|
23
|
-
Labkit::Metrics::Client.get(:
|
|
23
|
+
Labkit::Metrics::Client.get(:gitlab_user_experience_checkpoint_total)
|
|
24
24
|
end
|
|
25
25
|
|
|
26
26
|
def total_counter
|
|
27
|
-
Labkit::Metrics::Client.get(:
|
|
27
|
+
Labkit::Metrics::Client.get(:gitlab_user_experience_total)
|
|
28
28
|
end
|
|
29
29
|
|
|
30
30
|
def apdex_counter
|
|
31
|
-
Labkit::Metrics::Client.get(:
|
|
31
|
+
Labkit::Metrics::Client.get(:gitlab_user_experience_apdex_total)
|
|
32
32
|
end
|
|
33
33
|
end
|
|
34
34
|
end
|
|
35
35
|
end
|
|
36
36
|
end
|
|
37
37
|
|
|
38
|
-
# Matcher for verifying
|
|
38
|
+
# Matcher for verifying UserExperience start metrics instrumentation.
|
|
39
39
|
#
|
|
40
40
|
# Usage:
|
|
41
|
-
# expect { subject }.to
|
|
41
|
+
# expect { subject }.to start_user_experience('rails_request')
|
|
42
42
|
#
|
|
43
43
|
# This matcher verifies that the following metric is incremented:
|
|
44
|
-
# -
|
|
44
|
+
# - gitlab_user_experience_checkpoint_total (with checkpoint=start)
|
|
45
45
|
#
|
|
46
46
|
# Parameters:
|
|
47
|
-
# -
|
|
48
|
-
RSpec::Matchers.define :
|
|
49
|
-
include Labkit::RSpec::Matchers::
|
|
47
|
+
# - user_experience_id: Required. The ID of the user experience (e.g., 'rails_request')
|
|
48
|
+
RSpec::Matchers.define :start_user_experience do |user_experience_id|
|
|
49
|
+
include Labkit::RSpec::Matchers::UserExperience
|
|
50
50
|
|
|
51
|
-
description { "start
|
|
51
|
+
description { "start user experience '#{user_experience_id}'" }
|
|
52
52
|
supports_block_expectations
|
|
53
53
|
|
|
54
54
|
match do |actual|
|
|
55
|
-
labels = attributes(
|
|
55
|
+
labels = attributes(user_experience_id)
|
|
56
56
|
|
|
57
57
|
checkpoint_before = checkpoint_counter&.get(labels.merge(checkpoint: "start")).to_i
|
|
58
58
|
|
|
@@ -66,29 +66,29 @@ RSpec::Matchers.define :start_covered_experience do |covered_experience_id|
|
|
|
66
66
|
end
|
|
67
67
|
|
|
68
68
|
failure_message do
|
|
69
|
-
"Failed to checkpoint
|
|
69
|
+
"Failed to checkpoint user experience '#{user_experience_id}':\n" \
|
|
70
70
|
"expected checkpoint='start' counter to increase by 1, but increased by #{@checkpoint_change}"
|
|
71
71
|
end
|
|
72
72
|
end
|
|
73
73
|
|
|
74
|
-
# Matcher for verifying
|
|
74
|
+
# Matcher for verifying UserExperience checkpoint metrics instrumentation.
|
|
75
75
|
#
|
|
76
76
|
# Usage:
|
|
77
|
-
# expect { subject }.to
|
|
77
|
+
# expect { subject }.to checkpoint_user_experience('rails_request')
|
|
78
78
|
#
|
|
79
79
|
# This matcher verifies that the following metric is incremented:
|
|
80
|
-
# -
|
|
80
|
+
# - gitlab_user_experience_checkpoint_total (with checkpoint=intermediate)
|
|
81
81
|
#
|
|
82
82
|
# Parameters:
|
|
83
|
-
# -
|
|
84
|
-
RSpec::Matchers.define :
|
|
85
|
-
include Labkit::RSpec::Matchers::
|
|
83
|
+
# - user_experience_id: Required. The ID of the user experience (e.g., 'rails_request')
|
|
84
|
+
RSpec::Matchers.define :checkpoint_user_experience do |user_experience_id, by: 1|
|
|
85
|
+
include Labkit::RSpec::Matchers::UserExperience
|
|
86
86
|
|
|
87
|
-
description { "checkpoint
|
|
87
|
+
description { "checkpoint user experience '#{user_experience_id}'" }
|
|
88
88
|
supports_block_expectations
|
|
89
89
|
|
|
90
90
|
match do |actual|
|
|
91
|
-
labels = attributes(
|
|
91
|
+
labels = attributes(user_experience_id)
|
|
92
92
|
|
|
93
93
|
checkpoint_before = checkpoint_counter&.get(labels.merge(checkpoint: "intermediate")).to_i
|
|
94
94
|
|
|
@@ -104,12 +104,12 @@ RSpec::Matchers.define :checkpoint_covered_experience do |covered_experience_id,
|
|
|
104
104
|
end
|
|
105
105
|
|
|
106
106
|
failure_message do
|
|
107
|
-
"Failed to checkpoint
|
|
107
|
+
"Failed to checkpoint user experience '#{user_experience_id}':\n" \
|
|
108
108
|
"expected checkpoint='intermediate' counter to increase by at least #{by}, but increased by #{@checkpoint_change}"
|
|
109
109
|
end
|
|
110
110
|
|
|
111
111
|
match_when_negated do |actual|
|
|
112
|
-
labels = attributes(
|
|
112
|
+
labels = attributes(user_experience_id)
|
|
113
113
|
|
|
114
114
|
checkpoint_before = checkpoint_counter&.get(labels.merge(checkpoint: "intermediate")).to_i
|
|
115
115
|
|
|
@@ -122,36 +122,36 @@ RSpec::Matchers.define :checkpoint_covered_experience do |covered_experience_id,
|
|
|
122
122
|
end
|
|
123
123
|
|
|
124
124
|
failure_message_when_negated do
|
|
125
|
-
"Expected
|
|
125
|
+
"Expected user experience '#{user_experience_id}' NOT to checkpoint:\n" \
|
|
126
126
|
"expected checkpoint='intermediate' counter not to increase, but increased by #{@checkpoint_change}"
|
|
127
127
|
end
|
|
128
128
|
end
|
|
129
129
|
|
|
130
|
-
# Alias for
|
|
131
|
-
RSpec::Matchers.alias_matcher :
|
|
130
|
+
# Alias for checkpoint_user_experience matcher
|
|
131
|
+
RSpec::Matchers.alias_matcher :resume_user_experience, :checkpoint_user_experience
|
|
132
132
|
|
|
133
|
-
# Matcher for verifying
|
|
133
|
+
# Matcher for verifying UserExperience completion metrics instrumentation.
|
|
134
134
|
#
|
|
135
135
|
# Usage:
|
|
136
|
-
# expect { subject }.to
|
|
136
|
+
# expect { subject }.to complete_user_experience('rails_request')
|
|
137
137
|
#
|
|
138
138
|
# This matcher verifies that the following metrics are incremented with specific labels:
|
|
139
|
-
# -
|
|
140
|
-
# -
|
|
141
|
-
# -
|
|
139
|
+
# - gitlab_user_experience_checkpoint_total (with checkpoint=end)
|
|
140
|
+
# - gitlab_user_experience_total (with error=false)
|
|
141
|
+
# - gitlab_user_experience_apdex_total (with success=true)
|
|
142
142
|
#
|
|
143
143
|
# Parameters:
|
|
144
|
-
# -
|
|
145
|
-
# - error: Optional. The expected error flag for
|
|
146
|
-
# - success: Optional. The expected success flag for
|
|
147
|
-
RSpec::Matchers.define :
|
|
148
|
-
include Labkit::RSpec::Matchers::
|
|
144
|
+
# - user_experience_id: Required. The ID of the user experience (e.g., 'rails_request')
|
|
145
|
+
# - error: Optional. The expected error flag for gitlab_user_experience_total (false by default)
|
|
146
|
+
# - success: Optional. The expected success flag for gitlab_user_experience_apdex_total (true by default)
|
|
147
|
+
RSpec::Matchers.define :complete_user_experience do |user_experience_id, error: false, success: true|
|
|
148
|
+
include Labkit::RSpec::Matchers::UserExperience
|
|
149
149
|
|
|
150
|
-
description { "complete
|
|
150
|
+
description { "complete user experience '#{user_experience_id}'" }
|
|
151
151
|
supports_block_expectations
|
|
152
152
|
|
|
153
153
|
match do |actual|
|
|
154
|
-
labels = attributes(
|
|
154
|
+
labels = attributes(user_experience_id)
|
|
155
155
|
|
|
156
156
|
checkpoint_before = checkpoint_counter&.get(labels.merge(checkpoint: "end")).to_i
|
|
157
157
|
total_before = total_counter&.get(labels.merge(error: error)).to_i
|
|
@@ -170,14 +170,14 @@ RSpec::Matchers.define :complete_covered_experience do |covered_experience_id, e
|
|
|
170
170
|
end
|
|
171
171
|
|
|
172
172
|
failure_message do
|
|
173
|
-
"Failed to complete
|
|
173
|
+
"Failed to complete user experience '#{user_experience_id}':\n" \
|
|
174
174
|
"expected checkpoint='end' counter to increase by 1, but increased by #{@checkpoint_change}\n" \
|
|
175
175
|
"expected total='error: #{error}' counter to increase by 1, but increased by #{@total_change}\n" \
|
|
176
176
|
"expected apdex='success: #{success}' counter to increase by 1, but increased by #{@apdex_change}"
|
|
177
177
|
end
|
|
178
178
|
|
|
179
179
|
match_when_negated do |actual|
|
|
180
|
-
labels = attributes(
|
|
180
|
+
labels = attributes(user_experience_id)
|
|
181
181
|
|
|
182
182
|
checkpoint_before = checkpoint_counter&.get(labels.merge(checkpoint: "end")).to_i
|
|
183
183
|
total_before = total_counter&.get(labels.merge(error: error)).to_i
|
|
@@ -196,9 +196,15 @@ RSpec::Matchers.define :complete_covered_experience do |covered_experience_id, e
|
|
|
196
196
|
end
|
|
197
197
|
|
|
198
198
|
failure_message_when_negated do
|
|
199
|
-
"Failed
|
|
199
|
+
"Failed user experience '#{user_experience_id}' NOT to complete:\n" \
|
|
200
200
|
"expected checkpoint='end' counter to increase by 0, but increased by #{@checkpoint_change}\n" \
|
|
201
201
|
"expected total='error: #{error}' counter to increase by 0, but increased by #{@total_change}\n" \
|
|
202
202
|
"expected apdex='success: #{success}' counter to increase by 0, but increased by #{@apdex_change}"
|
|
203
203
|
end
|
|
204
204
|
end
|
|
205
|
+
|
|
206
|
+
# Backward compatibility matchers for CoveredExperience
|
|
207
|
+
RSpec::Matchers.alias_matcher :start_covered_experience, :start_user_experience
|
|
208
|
+
RSpec::Matchers.alias_matcher :checkpoint_covered_experience, :checkpoint_user_experience
|
|
209
|
+
RSpec::Matchers.alias_matcher :resume_covered_experience, :checkpoint_user_experience
|
|
210
|
+
RSpec::Matchers.alias_matcher :complete_covered_experience, :complete_user_experience
|