Skip to content
Snippets Groups Projects
Commit fbb3fd13 authored by Stan Hu's avatar Stan Hu
Browse files

Add backtrace to Gitaly performance bar

This adds the backtrace to a table to show exactly where the Gitaly call
was made to make it easier to understand where the call originated.

This change also collapses the details in the same row to improve the
usability when there is a backtrace.
parent b0c0f81d
No related branches found
No related tags found
No related merge requests found
<script>
import GlModal from '~/vue_shared/components/gl_modal.vue';
import Icon from '~/vue_shared/components/icon.vue';
 
export default {
components: {
GlModal,
Icon,
},
props: {
currentRequest: {
Loading
Loading
@@ -57,9 +59,31 @@ export default {
<template v-if="detailsList.length">
<tr v-for="(item, index) in detailsList" :key="index">
<td>
<strong>{{ item.duration }}ms</strong>
<span>{{ item.duration }}ms</span>
</td>
<td>
<div class="js-toggle-container">
<div
v-for="(key, keyIndex) in keys"
:key="key"
class="break-word"
:class="{ 'mb-3 bold': keyIndex == 0 }"
>
{{ item[key] }}
<button
v-if="keyIndex == 0 && item.backtrace"
class="text-expander js-toggle-button"
type="button"
:aria-label="__('Toggle backtrace')"
>
<icon :size="12" name="ellipsis_h" />
</button>
</div>
<pre v-if="item.backtrace" class="backtrace-row js-toggle-content mt-2">{{
item.backtrace
}}</pre>
</div>
</td>
<td v-for="key in keys" :key="key" class="break-word">{{ item[key] }}</td>
</tr>
</template>
<template v-else>
Loading
Loading
Loading
Loading
@@ -79,8 +79,12 @@
table {
color: $black;
 
strong {
color: $black;
td {
vertical-align: top;
}
.backtrace-row {
display: none;
}
}
 
Loading
Loading
---
title: Add backtrace to Gitaly performance bar
merge_request: 27345
author:
type: other
Loading
Loading
@@ -165,7 +165,10 @@ module Gitlab
current_transaction_labels.merge(gitaly_service: service.to_s, rpc: rpc.to_s),
duration)
 
add_call_details(feature: "#{service}##{rpc}", duration: duration, request: request_hash, rpc: rpc)
if peek_enabled?
add_call_details(feature: "#{service}##{rpc}", duration: duration, request: request_hash, rpc: rpc,
backtrace: Gitlab::Profiler.clean_backtrace(caller))
end
end
 
def self.query_time
Loading
Loading
@@ -350,15 +353,17 @@ module Gitlab
Gitlab::SafeRequestStore["gitaly_call_permitted"] = 0
end
 
def self.add_call_details(details)
return unless Gitlab::SafeRequestStore[:peek_enabled]
def self.peek_enabled?
Gitlab::SafeRequestStore[:peek_enabled]
end
 
def self.add_call_details(details)
Gitlab::SafeRequestStore['gitaly_call_details'] ||= []
Gitlab::SafeRequestStore['gitaly_call_details'] << details
end
 
def self.list_call_details
return [] unless Gitlab::SafeRequestStore[:peek_enabled]
return [] unless peek_enabled?
 
Gitlab::SafeRequestStore['gitaly_call_details'] || []
end
Loading
Loading
Loading
Loading
@@ -16,7 +16,11 @@ module Gitlab
ee/lib/gitlab/middleware/
lib/gitlab/performance_bar/
lib/gitlab/request_profiler/
lib/gitlab/query_limiting/
lib/gitlab/tracing/
lib/gitlab/profiler.rb
lib/gitlab/correlation_id.rb
lib/gitlab/webpack/dev_server_middleware.rb
].freeze
 
# Takes a URL to profile (can be a fully-qualified URL, or an absolute path)
Loading
Loading
Loading
Loading
@@ -9559,6 +9559,9 @@ msgstr ""
msgid "Toggle Sidebar"
msgstr ""
 
msgid "Toggle backtrace"
msgstr ""
msgid "Toggle comments for this file"
msgstr ""
 
Loading
Loading
Loading
Loading
@@ -27,8 +27,8 @@ describe('detailedMetric', () => {
 
describe('when the current request has details', () => {
const requestDetails = [
{ duration: '100', feature: 'find_commit', request: 'abcdef' },
{ duration: '23', feature: 'rebase_in_progress', request: '' },
{ duration: '100', feature: 'find_commit', request: 'abcdef', backtrace: ['hello', 'world'] },
{ duration: '23', feature: 'rebase_in_progress', request: '', backtrace: ['world', 'hello'] },
];
 
beforeEach(() => {
Loading
Loading
@@ -54,9 +54,11 @@ describe('detailedMetric', () => {
});
 
it('adds a modal with a table of the details', () => {
vm.$el.querySelectorAll('.performance-bar-modal td strong').forEach((duration, index) => {
expect(duration.innerText).toContain(requestDetails[index].duration);
});
vm.$el
.querySelectorAll('.performance-bar-modal td:nth-child(1)')
.forEach((duration, index) => {
expect(duration.innerText).toContain(requestDetails[index].duration);
});
 
vm.$el
.querySelectorAll('.performance-bar-modal td:nth-child(2)')
Loading
Loading
@@ -65,10 +67,16 @@ describe('detailedMetric', () => {
});
 
vm.$el
.querySelectorAll('.performance-bar-modal td:nth-child(3)')
.querySelectorAll('.performance-bar-modal td:nth-child(2)')
.forEach((request, index) => {
expect(request.innerText).toEqual(requestDetails[index].request);
expect(request.innerText).toContain(requestDetails[index].request);
});
expect(vm.$el.querySelector('.text-expander.js-toggle-button')).not.toBeNull();
vm.$el.querySelectorAll('.performance-bar-modal td:nth-child(2)').forEach(request => {
expect(request.innerText).toContain('world');
});
});
 
it('displays the metric name', () => {
Loading
Loading
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment