gitlab-labkit 1.9.1 → 1.10.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/.copier-answers.yml +1 -1
- data/CODEOWNERS +1 -1
- data/lib/labkit/rspec/README.md +0 -9
- data/lib/labkit/rspec/matchers/user_experience_matchers.rb +53 -0
- data/lib/labkit/user_experience_sli/README.md +20 -0
- data/lib/labkit/user_experience_sli/experience.rb +22 -0
- data/lib/labkit/user_experience_sli/null.rb +1 -0
- data/lib/labkit/user_experience_sli.rb +15 -3
- data/scripts/prepare-dev-env.sh +1 -0
- metadata +1 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: ce9130ded76934b6e21e82724c7371548b9e790e451179a7e70cd14f545969d7
|
|
4
|
+
data.tar.gz: 1463999f63f123911a57a45d6943fb68e25daa07338cc2afd49f9592cb71ffb0
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: df940f5abe8e939c2bb84440ed9ad340dc2e4a359dddc330d752f778e1d9c7c5aa2a6d19ee233081a7fc0cfd512e7cf5e54ad44fd419d11b2d0f85030ad6fd56
|
|
7
|
+
data.tar.gz: eee7205f950d1c9bf59060d25d0e5e7a196dadc98b521064813014129e022b2e3c9a5adfad68332b4ba1e2b9f75cbe6a6e8625cc228daa9d2976edbc05a31c25
|
data/.copier-answers.yml
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
# See the project for instructions on how to update the project
|
|
4
4
|
#
|
|
5
5
|
# Changes here will be overwritten by Copier; NEVER EDIT MANUALLY
|
|
6
|
-
_commit: v1.
|
|
6
|
+
_commit: v1.45.0
|
|
7
7
|
_src_path: https://gitlab.com/gitlab-com/gl-infra/common-template-copier.git
|
|
8
8
|
ee_licensed: false
|
|
9
9
|
golang: false
|
data/CODEOWNERS
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
# CODEOWNERS is used to lookup assignees for
|
|
2
2
|
# Renovate Bot dependency change Merge Requests.
|
|
3
3
|
# https://docs.renovatebot.com/configuration-options/#assigneesfromcodeowners
|
|
4
|
-
* @reprazent @andrewn @mkaeppler @ayufan @hmerscher @d.barrett @splattael
|
|
4
|
+
* @reprazent @andrewn @mkaeppler @ayufan @hmerscher @d.barrett @splattael @e_forbes @M_Alvarez
|
data/lib/labkit/rspec/README.md
CHANGED
|
@@ -74,15 +74,6 @@ expect { subject }.to complete_user_experience('rails_request', error: true, suc
|
|
|
74
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
|
-
|
|
86
77
|
## Example Usage
|
|
87
78
|
|
|
88
79
|
### In your spec_helper.rb or rails_helper.rb:
|
|
@@ -203,6 +203,59 @@ RSpec::Matchers.define :complete_user_experience do |user_experience_id, error:
|
|
|
203
203
|
end
|
|
204
204
|
end
|
|
205
205
|
|
|
206
|
+
# Matcher for verifying UserExperience observed metrics instrumentation.
|
|
207
|
+
#
|
|
208
|
+
# Usage:
|
|
209
|
+
# expect { subject }.to observed_user_experience('rails_request')
|
|
210
|
+
#
|
|
211
|
+
# This matcher verifies that the following metrics are incremented with specific labels:
|
|
212
|
+
# - gitlab_user_experience_checkpoint_total (with checkpoint=start)
|
|
213
|
+
# - gitlab_user_experience_checkpoint_total (with checkpoint=end)
|
|
214
|
+
# - gitlab_user_experience_total (with error=false)
|
|
215
|
+
# - gitlab_user_experience_apdex_total (with success=true)
|
|
216
|
+
#
|
|
217
|
+
# Parameters:
|
|
218
|
+
# - user_experience_id: Required. The ID of the user experience (e.g., 'rails_request')
|
|
219
|
+
# - error: Optional. The expected error flag for gitlab_user_experience_total (false by default)
|
|
220
|
+
# - success: Optional. The expected success flag for gitlab_user_experience_apdex_total (true by default)
|
|
221
|
+
RSpec::Matchers.define :observed_user_experience do |user_experience_id, error: false, success: true|
|
|
222
|
+
include Labkit::RSpec::Matchers::UserExperience
|
|
223
|
+
|
|
224
|
+
description { "observe user experience '#{user_experience_id}'" }
|
|
225
|
+
supports_block_expectations
|
|
226
|
+
|
|
227
|
+
match do |actual|
|
|
228
|
+
labels = attributes(user_experience_id)
|
|
229
|
+
|
|
230
|
+
start_before = checkpoint_counter&.get(labels.merge(checkpoint: "start")).to_i
|
|
231
|
+
end_before = checkpoint_counter&.get(labels.merge(checkpoint: "end")).to_i
|
|
232
|
+
total_before = total_counter&.get(labels.merge(error: error)).to_i
|
|
233
|
+
apdex_before = apdex_counter&.get(labels.merge(success: success)).to_i
|
|
234
|
+
|
|
235
|
+
actual.call
|
|
236
|
+
|
|
237
|
+
start_after = checkpoint_counter&.get(labels.merge(checkpoint: "start")).to_i
|
|
238
|
+
end_after = checkpoint_counter&.get(labels.merge(checkpoint: "end")).to_i
|
|
239
|
+
total_after = total_counter&.get(labels.merge(error: error)).to_i
|
|
240
|
+
apdex_after = apdex_counter&.get(labels.merge(success: success)).to_i
|
|
241
|
+
|
|
242
|
+
@start_change = start_after - start_before
|
|
243
|
+
@end_change = end_after - end_before
|
|
244
|
+
@total_change = total_after - total_before
|
|
245
|
+
@apdex_change = apdex_after - apdex_before
|
|
246
|
+
|
|
247
|
+
@start_change == 1 && @end_change == 1 && @total_change == 1 && @apdex_change == (error ? 0 : 1)
|
|
248
|
+
end
|
|
249
|
+
|
|
250
|
+
failure_message do
|
|
251
|
+
"Failed to observe user experience '#{user_experience_id}':\n" \
|
|
252
|
+
"expected checkpoint='start' counter to increase by 1, but increased by #{@start_change}\n" \
|
|
253
|
+
"expected checkpoint='end' counter to increase by 1, but increased by #{@end_change}\n" \
|
|
254
|
+
"expected total='error: #{error}' counter to increase by 1, but increased by #{@total_change}\n" \
|
|
255
|
+
"expected apdex='success: #{success}' counter to increase by #{error ? 0 : 1}, but increased by #{@apdex_change}"
|
|
256
|
+
end
|
|
257
|
+
end
|
|
258
|
+
|
|
206
259
|
# Backward compatibility matchers for CoveredExperience
|
|
207
260
|
RSpec::Matchers.alias_matcher :start_covered_experience, :start_user_experience
|
|
208
261
|
RSpec::Matchers.alias_matcher :checkpoint_covered_experience, :checkpoint_user_experience
|
|
@@ -161,6 +161,26 @@ experience.checkpoint
|
|
|
161
161
|
experience.complete
|
|
162
162
|
```
|
|
163
163
|
|
|
164
|
+
#### Observing a Past Experience
|
|
165
|
+
|
|
166
|
+
When an action already happened and you want to record its duration retroactively, use `observed`. It fires the start and end metrics without registering in the active context:
|
|
167
|
+
|
|
168
|
+
```ruby
|
|
169
|
+
Labkit::UserExperienceSli.observed('merge_request_creation', start_time: start_time_of_past_action)
|
|
170
|
+
```
|
|
171
|
+
|
|
172
|
+
You can also signal that an error occurred during the action:
|
|
173
|
+
|
|
174
|
+
```ruby
|
|
175
|
+
Labkit::UserExperienceSli.observed('merge_request_creation', start_time: start_time_of_past_action, error: true)
|
|
176
|
+
```
|
|
177
|
+
|
|
178
|
+
Extra labels are forwarded to both the start and end log events:
|
|
179
|
+
|
|
180
|
+
```ruby
|
|
181
|
+
Labkit::UserExperienceSli.observed('merge_request_creation', start_time: start_time_of_past_action, worker: 'MyWorker')
|
|
182
|
+
```
|
|
183
|
+
|
|
164
184
|
#### Resuming Experiences
|
|
165
185
|
|
|
166
186
|
You can resume a user experience SLI that was previously started and stored in the context. This is useful for distributed operations or when work spans multiple processes.
|
|
@@ -135,6 +135,28 @@ module Labkit
|
|
|
135
135
|
self
|
|
136
136
|
end
|
|
137
137
|
|
|
138
|
+
# Records a past User Experience by its duration.
|
|
139
|
+
#
|
|
140
|
+
# @param start_time [Time] The time when the experience started.
|
|
141
|
+
# @param error [Boolean] Whether the experience ended in an error.
|
|
142
|
+
# @param extra [Hash] Additional data to include in the log events.
|
|
143
|
+
# @return [self]
|
|
144
|
+
def observed(start_time:, error: false, **extra)
|
|
145
|
+
@start_time = start_time.utc
|
|
146
|
+
@end_time = Time.now.utc
|
|
147
|
+
error!("observed_error") if error
|
|
148
|
+
|
|
149
|
+
checkpoint_counter.increment(checkpoint: "start", **base_labels)
|
|
150
|
+
log_event("start", **extra)
|
|
151
|
+
|
|
152
|
+
checkpoint_counter.increment(checkpoint: "end", **base_labels)
|
|
153
|
+
total_counter.increment(error: has_error?, **base_labels)
|
|
154
|
+
apdex_counter.increment(success: apdex_success?, **base_labels) unless has_error?
|
|
155
|
+
log_event("end", **extra)
|
|
156
|
+
|
|
157
|
+
self
|
|
158
|
+
end
|
|
159
|
+
|
|
138
160
|
# Marks the experience as failed with an error
|
|
139
161
|
#
|
|
140
162
|
# @param error [StandardError, String] The error that caused the experience to fail.
|
|
@@ -77,7 +77,7 @@ module Labkit
|
|
|
77
77
|
reset_configuration
|
|
78
78
|
end
|
|
79
79
|
|
|
80
|
-
# Retrieves a
|
|
80
|
+
# Retrieves a user experience using the experience_id.
|
|
81
81
|
# It retrieves from the current context when available,
|
|
82
82
|
# otherwise it instantiates a new experience with the definition
|
|
83
83
|
# from the registry.
|
|
@@ -88,7 +88,7 @@ module Labkit
|
|
|
88
88
|
find_current(experience_id) || raise_or_null(experience_id)
|
|
89
89
|
end
|
|
90
90
|
|
|
91
|
-
# Starts a
|
|
91
|
+
# Starts a user experience using the experience_id.
|
|
92
92
|
#
|
|
93
93
|
# @param experience_id [String, Symbol] The ID of the experience to start.
|
|
94
94
|
# @param extra [Hash] Additional data to include in the log event.
|
|
@@ -97,7 +97,19 @@ module Labkit
|
|
|
97
97
|
get(experience_id).start(**extra, &)
|
|
98
98
|
end
|
|
99
99
|
|
|
100
|
-
#
|
|
100
|
+
# Records a past user experience by its duration atomically.
|
|
101
|
+
#
|
|
102
|
+
# @param experience_id [String, Symbol] The ID of the experience.
|
|
103
|
+
# @param start_time [Time] The time when the experience started.
|
|
104
|
+
# @param extra [Hash] Additional data to include in the log events.
|
|
105
|
+
# @return [Experience, Null] The observed experience or a Null object if not found (in production/staging).
|
|
106
|
+
def observed(experience_id, start_time:, **extra)
|
|
107
|
+
definition = registry[experience_id]
|
|
108
|
+
experience = definition ? Experience.new(definition) : raise_or_null(experience_id)
|
|
109
|
+
experience.observed(start_time: start_time, **extra)
|
|
110
|
+
end
|
|
111
|
+
|
|
112
|
+
# Resumes a user experience using the experience_id.
|
|
101
113
|
#
|
|
102
114
|
# @param experience_id [String, Symbol] The ID of the experience to resume.
|
|
103
115
|
# @return [Experience, Null] The started experience or a Null object if not found (in production/staging).
|
data/scripts/prepare-dev-env.sh
CHANGED