rails_performance 1.0.5.3 → 1.2.0.alpha1
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/README.md +10 -1
- data/app/controllers/rails_performance/rails_performance_controller.rb +7 -1
- data/app/helpers/rails_performance/application_helper.rb +8 -2
- data/app/views/rails_performance/javascripts/_javascripts.html.erb +1 -0
- data/app/views/rails_performance/javascripts/app.js +13 -0
- data/app/views/rails_performance/javascripts/local-time.es2017-umd.js +1 -0
- data/app/views/rails_performance/rails_performance/_recent_row.html.erb +5 -2
- data/app/views/rails_performance/rails_performance/_trace.html.erb +6 -0
- data/app/views/rails_performance/rails_performance/recent.html.erb +1 -1
- data/app/views/rails_performance/rails_performance/slow.html.erb +39 -0
- data/app/views/rails_performance/shared/_header.html.erb +1 -0
- data/config/routes.rb +1 -0
- data/lib/rails_performance/data_source.rb +3 -3
- data/lib/rails_performance/engine.rb +1 -1
- data/lib/rails_performance/gems/custom_ext.rb +1 -1
- data/lib/rails_performance/reports/response_time_report.rb +2 -2
- data/lib/rails_performance/reports/slow_requests_report.rb +24 -0
- data/lib/rails_performance/reports/throughput_report.rb +2 -2
- data/lib/rails_performance/thread/current_request.rb +1 -1
- data/lib/rails_performance/version.rb +1 -1
- data/lib/rails_performance.rb +11 -0
- metadata +22 -5
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 7b526cdf667201a0ea200a83af542812f0be52724409ce9e2573ca878d2efd06
|
4
|
+
data.tar.gz: 26b5591a60b14647cdd713615e1d3e7163e840d1048466deba94241aab762544
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 0acf1b56c93e1bfb3085fccf239839a96e92a4f92eb55633fbeaca3371a33427bbcbc97091124c864fb2ca8743a338c33fd77c95ece6d85982c9e276bb12bc5f
|
7
|
+
data.tar.gz: b2a8d5c8460c047f0614f6bae5124512e892e21d88f58c45578ce838dfefe16cd8aff3fce1c7838e5061d090e1df88047ea52ec6d8ce38f36346e1ce65d0b82b
|
data/README.md
CHANGED
@@ -14,6 +14,7 @@ This is a **simple and free alternative** to the New Relic APM, Datadog or other
|
|
14
14
|
It allows you to track:
|
15
15
|
|
16
16
|
- real-time monitoring on the Recent tab
|
17
|
+
- monitor slow requests
|
17
18
|
- throughput report (see amount of RPM (requests per minute))
|
18
19
|
- an average response time
|
19
20
|
- the slowest controllers & actions
|
@@ -59,7 +60,12 @@ RailsPerformance.setup do |config|
|
|
59
60
|
|
60
61
|
# configure Recent tab (time window and limit of requests)
|
61
62
|
# config.recent_requests_time_window = 60.minutes
|
62
|
-
# config.recent_requests_limit = nil
|
63
|
+
# config.recent_requests_limit = nil # or 1000
|
64
|
+
|
65
|
+
# configure Slow Requests tab (time window, limit of requests and threshold)
|
66
|
+
# config.slow_requests_time_window = 4.hours # time window for slow requests
|
67
|
+
# config.slow_requests_limit = 500 # number of max rows
|
68
|
+
# config.slow_requests_threshold = 500 # number of ms
|
63
69
|
|
64
70
|
# default path where to mount gem,
|
65
71
|
# alternatively you can mount the RailsPerformance::Engine in your routes.rb
|
@@ -234,6 +240,9 @@ If "schema" how records are stored i Redis is changed, and this is a breacking c
|
|
234
240
|
- https://github.com/D1ceWard
|
235
241
|
- https://github.com/carl-printreleaf
|
236
242
|
|
243
|
+
[<img src="https://opensource-heroes.com/svg/embed/igorkasyanchuk/rails_performance"
|
244
|
+
/>](https://opensource-heroes.com/r/igorkasyanchuk/rails_performance)
|
245
|
+
|
237
246
|
## License
|
238
247
|
|
239
248
|
The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
|
@@ -61,6 +61,12 @@ module RailsPerformance
|
|
61
61
|
end
|
62
62
|
end
|
63
63
|
|
64
|
+
def slow
|
65
|
+
@datasource = RailsPerformance::DataSource.new(**prepare_query, type: :requests)
|
66
|
+
db = @datasource.db
|
67
|
+
@data = RailsPerformance::Reports::SlowRequestsReport.new(db).data
|
68
|
+
end
|
69
|
+
|
64
70
|
def sidekiq
|
65
71
|
@datasource = RailsPerformance::DataSource.new(**prepare_query, type: :sidekiq)
|
66
72
|
db = @datasource.db
|
@@ -107,4 +113,4 @@ module RailsPerformance
|
|
107
113
|
end
|
108
114
|
|
109
115
|
end
|
110
|
-
end
|
116
|
+
end
|
@@ -1,5 +1,7 @@
|
|
1
1
|
module RailsPerformance
|
2
2
|
module ApplicationHelper
|
3
|
+
include LocalTimeHelper
|
4
|
+
|
3
5
|
def round_it(value, limit = 1)
|
4
6
|
return nil unless value
|
5
7
|
return value if value.is_a?(Integer)
|
@@ -49,7 +51,7 @@ module RailsPerformance
|
|
49
51
|
|
50
52
|
def link_to_path(e)
|
51
53
|
if e[:method] == 'GET'
|
52
|
-
link_to(short_path(e[:path]), e[:path], target: '_blank')
|
54
|
+
link_to(short_path(e[:path]), e[:path], target: '_blank', title: short_path(e[:path]))
|
53
55
|
else
|
54
56
|
short_path(e[:path])
|
55
57
|
end
|
@@ -105,7 +107,9 @@ module RailsPerformance
|
|
105
107
|
end
|
106
108
|
|
107
109
|
def format_datetime(e)
|
108
|
-
e.strftime("%Y-%m-%d %H:%M:%S")
|
110
|
+
#e.strftime("%Y-%m-%d %H:%M:%S")
|
111
|
+
# I18n.l(e, format: "%Y-%m-%d %H:%M:%S")
|
112
|
+
local_time(e, "%Y-%m-%d %H:%M:%S")
|
109
113
|
end
|
110
114
|
|
111
115
|
def active?(section)
|
@@ -118,6 +122,8 @@ module RailsPerformance
|
|
118
122
|
"is-active" if controller_name == "rails_performance" && action_name == "requests"
|
119
123
|
when :recent
|
120
124
|
"is-active" if controller_name == "rails_performance" && action_name == "recent"
|
125
|
+
when :slow
|
126
|
+
"is-active" if controller_name == "rails_performance" && action_name == "slow"
|
121
127
|
when :sidekiq
|
122
128
|
"is-active" if controller_name == "rails_performance" && action_name == "sidekiq"
|
123
129
|
when :delayed_job
|
@@ -1,6 +1,7 @@
|
|
1
1
|
<%= insert_js_file 'jquery-3.4.1.min.js' %>
|
2
2
|
<%= insert_js_file 'rails.js' %>
|
3
3
|
<%= insert_js_file 'stupidtable.min.js' %>
|
4
|
+
<%= insert_js_file 'local-time.es2017-umd.js' %>
|
4
5
|
|
5
6
|
<%= javascript_include_tag 'https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.12.1/js/all.min.js' %>
|
6
7
|
<%= javascript_include_tag 'https://code.highcharts.com/highcharts.js' %>
|
@@ -170,6 +170,17 @@ function showRTChart(div, data) {
|
|
170
170
|
const recent = document.getElementById("recent")
|
171
171
|
const autoupdate = document.getElementById("autoupdate")
|
172
172
|
|
173
|
+
if(autoupdate) {
|
174
|
+
// set autoupdate checked from localStorage is missing
|
175
|
+
if (localStorage.getItem("autoupdate") === null) {
|
176
|
+
localStorage.setItem("autoupdate", "true");
|
177
|
+
}
|
178
|
+
autoupdate.checked = localStorage.getItem("autoupdate") === "true";
|
179
|
+
autoupdate.addEventListener('change', () => {
|
180
|
+
localStorage.setItem("autoupdate", autoupdate.checked);
|
181
|
+
});
|
182
|
+
}
|
183
|
+
|
173
184
|
if(recent) {
|
174
185
|
const tbody = recent.querySelector("tbody")
|
175
186
|
|
@@ -192,3 +203,5 @@ if(recent) {
|
|
192
203
|
})
|
193
204
|
}, 3000);
|
194
205
|
}
|
206
|
+
|
207
|
+
LocalTime.start()
|
@@ -0,0 +1 @@
|
|
1
|
+
!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?module.exports=e():"function"==typeof define&&define.amd?define(e):(t="undefined"!=typeof globalThis?globalThis:t||self).LocalTime=e()}(this,(function(){"use strict";var t;t={config:{},run:function(){return this.getController().processElements()},process:function(...t){var e,r,a;for(r=0,a=t.length;r<a;r++)e=t[r],this.getController().processElement(e);return t.length},getController:function(){return null!=this.controller?this.controller:this.controller=new t.Controller}};var e,r,a,n,s,i,o,u,l,c,d,m,h,f,g,y,p,v,b,S,M,T,D,E,w,A,N,O,$,C=t;return C.config.i18n={en:{date:{dayNames:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],abbrDayNames:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],monthNames:["January","February","March","April","May","June","July","August","September","October","November","December"],abbrMonthNames:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"],yesterday:"yesterday",today:"today",tomorrow:"tomorrow",on:"on {date}",formats:{default:"%b %e, %Y",thisYear:"%b %e"}},time:{am:"am",pm:"pm",singular:"a {time}",singularAn:"an {time}",elapsed:"{time} ago",second:"second",seconds:"seconds",minute:"minute",minutes:"minutes",hour:"hour",hours:"hours",formats:{default:"%l:%M%P"}},datetime:{at:"{date} at {time}",formats:{default:"%B %e, %Y at %l:%M%P %Z"}}}},C.config.locale="en",C.config.defaultLocale="en",C.config.timerInterval=6e4,a=!isNaN(Date.parse("2011-01-01T12:00:00-05:00")),C.parseDate=function(t){return t=t.toString(),a||(t=r(t)),new Date(Date.parse(t))},e=/^(\d{4})-(\d{2})-(\d{2})T(\d{2}):(\d{2}):(\d{2})(Z|[-+]?[\d:]+)$/,r=function(t){var r,a,n,s,i,o,u,l,c,d;if(s=t.match(e))return[r,c,o,a,n,i,l,d]=s,"Z"!==d&&(u=d.replace(":","")),`${c}/${o}/${a} ${n}:${i}:${l} GMT${[u]}`},C.elementMatchesSelector=(n=document.documentElement,s=null!=(i=null!=(o=null!=(u=null!=(l=n.matches)?l:n.matchesSelector)?u:n.webkitMatchesSelector)?o:n.mozMatchesSelector)?i:n.msMatchesSelector,function(t,e){if((null!=t?t.nodeType:void 0)===Node.ELEMENT_NODE)return s.call(t,e)}),({config:c}=C),({i18n:m}=c),C.getI18nValue=function(t="",{locale:e}={locale:c.locale}){var r;return null!=(r=d(m[e],t))?r:e!==c.defaultLocale?C.getI18nValue(t,{locale:c.defaultLocale}):void 0},C.translate=function(t,e={},r){var a,n,s;for(a in s=C.getI18nValue(t,r),e)n=e[a],s=s.replace(`{${a}}`,n);return s},d=function(t,e){var r,a,n,s,i;for(i=t,r=0,n=(s=e.split(".")).length;r<n;r++){if(null==i[a=s[r]])return null;i=i[a]}return i},({getI18nValue:h,translate:p}=C),C.strftime=y=function(t,e){var r,a,n,s,i,o,u;return a=t.getDay(),r=t.getDate(),i=t.getMonth(),u=t.getFullYear(),n=t.getHours(),s=t.getMinutes(),o=t.getSeconds(),e.replace(/%(-?)([%aAbBcdeHIlmMpPSwyYZ])/g,(function(e,l,c){switch(c){case"%":return"%";case"a":return h("date.abbrDayNames")[a];case"A":return h("date.dayNames")[a];case"b":return h("date.abbrMonthNames")[i];case"B":return h("date.monthNames")[i];case"c":return t.toString();case"d":return f(r,l);case"e":return r;case"H":return f(n,l);case"I":return f(y(t,"%l"),l);case"l":return 0===n||12===n?12:(n+12)%12;case"m":return f(i+1,l);case"M":return f(s,l);case"p":return p("time."+(n>11?"pm":"am")).toUpperCase();case"P":return p("time."+(n>11?"pm":"am"));case"S":return f(o,l);case"w":return a;case"y":return f(u%100,l);case"Y":return u;case"Z":return g(t)}}))},f=function(t,e){return"-"===e?t:`0${t}`.slice(-2)},g=function(t){var e,r,a,n,s;return(e=null!=(r=(s=t.toString()).match(/\(([\w\s]+)\)$/))?r[1]:void 0)?/\s/.test(e)?e.match(/\b(\w)/g).join(""):e:(e=null!=(a=s.match(/(\w{3,4})\s\d{4}$/))?a[1]:void 0)||(e=null!=(n=s.match(/(UTC[\+\-]\d+)/))?n[1]:void 0)?e:""},C.CalendarDate=class{static fromDate(t){return new this(t.getFullYear(),t.getMonth()+1,t.getDate())}static today(){return this.fromDate(new Date)}constructor(t,e,r){this.date=new Date(Date.UTC(t,e-1)),this.date.setUTCDate(r),this.year=this.date.getUTCFullYear(),this.month=this.date.getUTCMonth()+1,this.day=this.date.getUTCDate(),this.value=this.date.getTime()}equals(t){return(null!=t?t.value:void 0)===this.value}is(t){return this.equals(t)}isToday(){return this.is(this.constructor.today())}occursOnSameYearAs(t){return this.year===(null!=t?t.year:void 0)}occursThisYear(){return this.occursOnSameYearAs(this.constructor.today())}daysSince(t){if(t)return(this.date-t.date)/864e5}daysPassed(){return this.constructor.today().daysSince(this)}},({strftime:b,translate:S,getI18nValue:v}=C),C.RelativeTime=class{constructor(t){this.date=t,this.calendarDate=C.CalendarDate.fromDate(this.date)}toString(){var t,e;return(e=this.toTimeElapsedString())?S("time.elapsed",{time:e}):(t=this.toWeekdayString())?(e=this.toTimeString(),S("datetime.at",{date:t,time:e})):S("date.on",{date:this.toDateString()})}toTimeOrDateString(){return this.calendarDate.isToday()?this.toTimeString():this.toDateString()}toTimeElapsedString(){var t,e,r,a,n;return r=(new Date).getTime()-this.date.getTime(),a=Math.round(r/1e3),e=Math.round(a/60),t=Math.round(e/60),r<0?null:a<10?(n=S("time.second"),S("time.singular",{time:n})):a<45?`${a} ${S("time.seconds")}`:a<90?(n=S("time.minute"),S("time.singular",{time:n})):e<45?`${e} ${S("time.minutes")}`:e<90?(n=S("time.hour"),S("time.singularAn",{time:n})):t<24?`${t} ${S("time.hours")}`:""}toWeekdayString(){switch(this.calendarDate.daysPassed()){case 0:return S("date.today");case 1:return S("date.yesterday");case-1:return S("date.tomorrow");case 2:case 3:case 4:case 5:case 6:return b(this.date,"%A");default:return""}}toDateString(){var t;return t=this.calendarDate.occursThisYear()?v("date.formats.thisYear"):v("date.formats.default"),b(this.date,t)}toTimeString(){return b(this.date,v("time.formats.default"))}},({elementMatchesSelector:M}=C),C.PageObserver=class{constructor(t,e){this.processMutations=this.processMutations.bind(this),this.processInsertion=this.processInsertion.bind(this),this.selector=t,this.callback=e}start(){if(!this.started)return this.observeWithMutationObserver()||this.observeWithMutationEvent(),this.started=!0}observeWithMutationObserver(){if("undefined"!=typeof MutationObserver&&null!==MutationObserver)return new MutationObserver(this.processMutations).observe(document.documentElement,{childList:!0,subtree:!0}),!0}observeWithMutationEvent(){return addEventListener("DOMNodeInserted",this.processInsertion,!1),!0}findSignificantElements(t){var e;return e=[],(null!=t?t.nodeType:void 0)===Node.ELEMENT_NODE&&(M(t,this.selector)&&e.push(t),e.push(...t.querySelectorAll(this.selector))),e}processMutations(t){var e,r,a,n,s,i,o,u;for(e=[],r=0,n=t.length;r<n;r++)if("childList"===(i=t[r]).type)for(a=0,s=(u=i.addedNodes).length;a<s;a++)o=u[a],e.push(...this.findSignificantElements(o));return this.notify(e)}processInsertion(t){var e;return e=this.findSignificantElements(t.target),this.notify(e)}notify(t){if(null!=t?t.length:void 0)return"function"==typeof this.callback?this.callback(t):void 0}},({parseDate:E,strftime:w,getI18nValue:D,config:T}=C),C.Controller=function(){var t,e,r;return t="time[data-local]:not([data-localized])",e=function(t){return t.setAttribute("data-localized","")},r=function(t){return new C.RelativeTime(t)},class{constructor(){this.processElements=this.processElements.bind(this),this.pageObserver=new C.PageObserver(t,this.processElements)}start(){if(!this.started)return this.processElements(),this.startTimer(),this.pageObserver.start(),this.started=!0}startTimer(){var t;if(t=T.timerInterval)return null!=this.timer?this.timer:this.timer=setInterval(this.processElements,t)}processElements(e=document.querySelectorAll(t)){var r,a,n;for(a=0,n=e.length;a<n;a++)r=e[a],this.processElement(r);return e.length}processElement(t){var a,n,s,i,o,u;if(n=t.getAttribute("datetime"),s=t.getAttribute("data-format"),i=t.getAttribute("data-local"),o=E(n),!isNaN(o))return t.hasAttribute("title")||(u=w(o,D("datetime.formats.default")),t.setAttribute("title",u)),t.textContent=a=function(){switch(i){case"time":return e(t),w(o,s);case"date":return e(t),r(o).toDateString();case"time-ago":return r(o).toString();case"time-or-date":return r(o).toTimeOrDateString();case"weekday":return r(o).toWeekdayString();case"weekday-or-date":return r(o).toWeekdayString()||r(o).toDateString()}}(),t.hasAttribute("aria-label")?void 0:t.setAttribute("aria-label",a)}}}.call(window),$=!1,A=function(){return document.attachEvent?"complete"===document.readyState:"loading"!==document.readyState},N=function(t){var e;return null!=(e="function"==typeof requestAnimationFrame?requestAnimationFrame(t):void 0)?e:setTimeout(t,17)},O=function(){return C.getController().start()},C.start=function(){if(!$)return $=!0,"undefined"!=typeof MutationObserver&&null!==MutationObserver||A()?O():N(O)},window.LocalTime===C&&C.start(),C}));
|
@@ -7,7 +7,10 @@
|
|
7
7
|
<% end %>
|
8
8
|
</td>
|
9
9
|
<td><%= format_datetime e[:datetime] %></td>
|
10
|
-
<td
|
10
|
+
<td>
|
11
|
+
<% controller_action_info = e[:controller] + '#' + e[:action]%>
|
12
|
+
<%= link_to truncate(controller_action_info, length: 40), rails_performance.rails_performance_summary_path({controller_eq: e[:controller], action_eq: e[:action]}), remote: true, title: controller_action_info %>
|
13
|
+
</td>
|
11
14
|
<td><%= e[:method] %></td>
|
12
15
|
<td><%= e[:format] %></td>
|
13
16
|
<td><%= link_to_path(e) %></td>
|
@@ -22,4 +25,4 @@
|
|
22
25
|
<% end %>
|
23
26
|
<% end %>
|
24
27
|
</td>
|
25
|
-
</tr>
|
28
|
+
</tr>
|
@@ -19,5 +19,11 @@
|
|
19
19
|
<% end %>
|
20
20
|
</tr>
|
21
21
|
<% end %>
|
22
|
+
|
23
|
+
<% if @data.empty? %>
|
24
|
+
<tr>
|
25
|
+
<td>Nothing to show here. Perphaps details about the requests already expired. Setting "slow_requests_time_window" should be equal to "duration".</td>
|
26
|
+
</td>
|
27
|
+
<% end %>
|
22
28
|
</tbody>
|
23
29
|
</table>
|
@@ -0,0 +1,39 @@
|
|
1
|
+
<title>Slow Requests</title>
|
2
|
+
|
3
|
+
<div class="card">
|
4
|
+
<div class="card-content">
|
5
|
+
<div class="columns">
|
6
|
+
<div class="column">
|
7
|
+
<h2 class="subtitle">Slow Requests (last <%= RailsPerformance.slow_requests_time_window / 60 %> minutes + slower then <%= RailsPerformance.slow_requests_threshold %>ms)<h2>
|
8
|
+
</div>
|
9
|
+
</div>
|
10
|
+
|
11
|
+
<table id="recent" class="table is-fullwidth is-hoverable is-narrow">
|
12
|
+
<thead>
|
13
|
+
<tr>
|
14
|
+
<th data-sort="string"></th>
|
15
|
+
<th data-sort="string">Datetime</th>
|
16
|
+
<th data-sort="string">Controller#action</th>
|
17
|
+
<th data-sort="string">Method</th>
|
18
|
+
<th data-sort="string">Format</th>
|
19
|
+
<th data-sort="string">Path</th>
|
20
|
+
<th data-sort="string">Status</th>
|
21
|
+
<th data-sort="float">Duration</th>
|
22
|
+
<th data-sort="float">Views</th>
|
23
|
+
<th data-sort="float">DB</th>
|
24
|
+
<th></th>
|
25
|
+
</tr>
|
26
|
+
</thead>
|
27
|
+
<tbody>
|
28
|
+
<% if @data.empty? %>
|
29
|
+
<tr>
|
30
|
+
<td colspan="10">Nothing to show here. Try to make a few requests in the main app.</td>
|
31
|
+
</tr>
|
32
|
+
<% end %>
|
33
|
+
<% @data.each do |e| %>
|
34
|
+
<%= render 'recent_row', e: e %>
|
35
|
+
<% end %>
|
36
|
+
</tbody>
|
37
|
+
</table>
|
38
|
+
</div>
|
39
|
+
</div>
|
@@ -18,6 +18,7 @@
|
|
18
18
|
<%= link_to 'Requests Analysis', rails_performance.rails_performance_requests_url, class: "navbar-item #{active?(:requests)}" %>
|
19
19
|
<%= link_to '500 Errors', rails_performance.rails_performance_crashes_url, class: "navbar-item #{active?(:crashes)}" %>
|
20
20
|
<%= link_to 'Recent Requests', rails_performance.rails_performance_recent_url, class: "navbar-item #{active?(:recent)}" %>
|
21
|
+
<%= link_to 'Slow Requests', rails_performance.rails_performance_slow_url, class: "navbar-item #{active?(:slow)}" %>
|
21
22
|
<% if defined?(Sidekiq) %>
|
22
23
|
<%= link_to 'Sidekiq', rails_performance.rails_performance_sidekiq_url, class: "navbar-item #{active?(:sidekiq)}" %>
|
23
24
|
<% end %>
|
data/config/routes.rb
CHANGED
@@ -4,6 +4,7 @@ RailsPerformance::Engine.routes.draw do
|
|
4
4
|
get '/requests' => 'rails_performance#requests', as: :rails_performance_requests
|
5
5
|
get '/crashes' => 'rails_performance#crashes', as: :rails_performance_crashes
|
6
6
|
get '/recent' => 'rails_performance#recent', as: :rails_performance_recent
|
7
|
+
get '/slow' => 'rails_performance#slow', as: :rails_performance_slow
|
7
8
|
|
8
9
|
get '/trace/:id' => 'rails_performance#trace', as: :rails_performance_trace
|
9
10
|
get '/summary' => 'rails_performance#summary', as: :rails_performance_summary
|
@@ -20,8 +20,8 @@ module RailsPerformance
|
|
20
20
|
|
21
21
|
def db
|
22
22
|
result = RailsPerformance::Models::Collection.new
|
23
|
-
(RailsPerformance::Utils.days + 1).
|
24
|
-
RailsPerformance::DataSource.new(q: self.q.merge({ on: e.days.
|
23
|
+
(0..(RailsPerformance::Utils.days + 1)).to_a.reverse.each do |e|
|
24
|
+
RailsPerformance::DataSource.new(q: self.q.merge({ on: (Time.now - e.days).to_date }), type: type).add_to(result)
|
25
25
|
end
|
26
26
|
result
|
27
27
|
end
|
@@ -118,4 +118,4 @@ module RailsPerformance
|
|
118
118
|
end
|
119
119
|
|
120
120
|
end
|
121
|
-
end
|
121
|
+
end
|
@@ -55,7 +55,7 @@ module RailsPerformance
|
|
55
55
|
next unless RailsPerformance.enabled
|
56
56
|
|
57
57
|
ActionView::LogSubscriber.send :prepend, RailsPerformance::Extensions::View
|
58
|
-
ActiveRecord::LogSubscriber.send :prepend, RailsPerformance::Extensions::Db
|
58
|
+
ActiveRecord::LogSubscriber.send :prepend, RailsPerformance::Extensions::Db if defined?(ActiveRecord)
|
59
59
|
|
60
60
|
if defined?(::Rake::Task)
|
61
61
|
require_relative './gems/rake_ext.rb'
|
@@ -10,7 +10,7 @@ module RailsPerformance
|
|
10
10
|
stop = Time.at(60 * (Time.now.to_i / 60))
|
11
11
|
current = stop - RailsPerformance.duration
|
12
12
|
@data = []
|
13
|
-
offset = Time.
|
13
|
+
offset = Time.now.utc_offset
|
14
14
|
|
15
15
|
# puts "current: #{current}"
|
16
16
|
# puts "stop: #{stop}"
|
@@ -34,4 +34,4 @@ module RailsPerformance
|
|
34
34
|
end
|
35
35
|
end
|
36
36
|
end
|
37
|
-
end
|
37
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
module RailsPerformance
|
2
|
+
module Reports
|
3
|
+
class SlowRequestsReport < BaseReport
|
4
|
+
def set_defaults
|
5
|
+
@sort ||= :datetimei
|
6
|
+
end
|
7
|
+
|
8
|
+
def data
|
9
|
+
db.data
|
10
|
+
.collect{|e| e.record_hash}
|
11
|
+
.select{|e| e if e[sort] > RailsPerformance.slow_requests_time_window.ago.to_i}
|
12
|
+
.sort{|a, b| b[sort] <=> a[sort]}
|
13
|
+
.filter{|e| e[:duration] > RailsPerformance.slow_requests_threshold.to_i}
|
14
|
+
.first(limit)
|
15
|
+
end
|
16
|
+
|
17
|
+
private
|
18
|
+
|
19
|
+
def limit
|
20
|
+
RailsPerformance.slow_requests_limit ? RailsPerformance.slow_requests_limit.to_i : 100_000
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -11,7 +11,7 @@ module RailsPerformance
|
|
11
11
|
stop = Time.at(60 * (Time.now.to_i / 60))
|
12
12
|
current = stop - RailsPerformance.duration
|
13
13
|
@data = []
|
14
|
-
offset = Time.
|
14
|
+
offset = Time.now.utc_offset
|
15
15
|
|
16
16
|
# puts "current: #{current}"
|
17
17
|
# puts "stop: #{stop}"
|
@@ -34,4 +34,4 @@ module RailsPerformance
|
|
34
34
|
|
35
35
|
end
|
36
36
|
end
|
37
|
-
end
|
37
|
+
end
|
data/lib/rails_performance.rb
CHANGED
@@ -1,5 +1,6 @@
|
|
1
1
|
require "redis"
|
2
2
|
require "redis-namespace"
|
3
|
+
require "local_time"
|
3
4
|
require_relative "./rails_performance/version.rb"
|
4
5
|
require_relative "rails_performance/rails/query_builder.rb"
|
5
6
|
require_relative "rails_performance/rails/middleware.rb"
|
@@ -19,6 +20,7 @@ require_relative "rails_performance/reports/crash_report.rb"
|
|
19
20
|
require_relative "rails_performance/reports/response_time_report.rb"
|
20
21
|
require_relative "rails_performance/reports/throughput_report.rb"
|
21
22
|
require_relative "rails_performance/reports/recent_requests_report.rb"
|
23
|
+
require_relative "rails_performance/reports/slow_requests_report.rb"
|
22
24
|
require_relative "rails_performance/reports/breakdown_report.rb"
|
23
25
|
require_relative "rails_performance/reports/trace_report.rb"
|
24
26
|
require_relative "rails_performance/extensions/trace.rb"
|
@@ -39,6 +41,15 @@ module RailsPerformance
|
|
39
41
|
mattr_accessor :recent_requests_limit
|
40
42
|
@@recent_requests_limit = nil
|
41
43
|
|
44
|
+
mattr_accessor :slow_requests_time_window
|
45
|
+
@@slow_requests_time_window = 4.hours
|
46
|
+
|
47
|
+
mattr_accessor :slow_requests_limit
|
48
|
+
@@recent_requests_limit = 500
|
49
|
+
|
50
|
+
mattr_accessor :slow_requests_threshold
|
51
|
+
@@slow_requests_threshold = 500
|
52
|
+
|
42
53
|
mattr_accessor :debug
|
43
54
|
@@debug = false
|
44
55
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rails_performance
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0.
|
4
|
+
version: 1.2.0.alpha1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Igor Kasyanchuk
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-06-
|
11
|
+
date: 2023-06-24 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rails
|
@@ -52,6 +52,20 @@ dependencies:
|
|
52
52
|
- - ">="
|
53
53
|
- !ruby/object:Gem::Version
|
54
54
|
version: '0'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: local_time
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - ">="
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
62
|
+
type: :runtime
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - ">="
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '0'
|
55
69
|
- !ruby/object:Gem::Dependency
|
56
70
|
name: sqlite3
|
57
71
|
requirement: !ruby/object:Gem::Requirement
|
@@ -234,6 +248,7 @@ files:
|
|
234
248
|
- app/views/rails_performance/javascripts/_javascripts.html.erb
|
235
249
|
- app/views/rails_performance/javascripts/app.js
|
236
250
|
- app/views/rails_performance/javascripts/jquery-3.4.1.min.js
|
251
|
+
- app/views/rails_performance/javascripts/local-time.es2017-umd.js
|
237
252
|
- app/views/rails_performance/javascripts/navbar.js
|
238
253
|
- app/views/rails_performance/javascripts/panel.js
|
239
254
|
- app/views/rails_performance/javascripts/rails.js
|
@@ -253,6 +268,7 @@ files:
|
|
253
268
|
- app/views/rails_performance/rails_performance/recent.js.erb
|
254
269
|
- app/views/rails_performance/rails_performance/requests.html.erb
|
255
270
|
- app/views/rails_performance/rails_performance/sidekiq.html.erb
|
271
|
+
- app/views/rails_performance/rails_performance/slow.html.erb
|
256
272
|
- app/views/rails_performance/rails_performance/summary.js.erb
|
257
273
|
- app/views/rails_performance/rails_performance/trace.js.erb
|
258
274
|
- app/views/rails_performance/shared/_header.html.erb
|
@@ -292,6 +308,7 @@ files:
|
|
292
308
|
- lib/rails_performance/reports/recent_requests_report.rb
|
293
309
|
- lib/rails_performance/reports/requests_report.rb
|
294
310
|
- lib/rails_performance/reports/response_time_report.rb
|
311
|
+
- lib/rails_performance/reports/slow_requests_report.rb
|
295
312
|
- lib/rails_performance/reports/throughput_report.rb
|
296
313
|
- lib/rails_performance/reports/trace_report.rb
|
297
314
|
- lib/rails_performance/thread/current_request.rb
|
@@ -312,11 +329,11 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
312
329
|
version: '0'
|
313
330
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
314
331
|
requirements:
|
315
|
-
- - "
|
332
|
+
- - ">"
|
316
333
|
- !ruby/object:Gem::Version
|
317
|
-
version:
|
334
|
+
version: 1.3.1
|
318
335
|
requirements: []
|
319
|
-
rubygems_version: 3.4.
|
336
|
+
rubygems_version: 3.4.13
|
320
337
|
signing_key:
|
321
338
|
specification_version: 4
|
322
339
|
summary: Simple Rails Performance tracker. Alternative to the NewRelic, Datadog or
|