sql-jarvis 2.0.9 → 2.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (46) hide show
  1. checksums.yaml +4 -4
  2. data/app/assets/javascripts/blazer/main.js +4 -3
  3. data/app/helpers/blazer/base_helper.rb +1 -1
  4. data/app/views/blazer/_nav.html.haml +12 -0
  5. data/app/views/blazer/{_variables.html.erb → _variables.html.haml} +35 -57
  6. data/app/views/blazer/check_mailer/failing_checks.html.haml +6 -0
  7. data/app/views/blazer/check_mailer/state_change.html.haml +31 -0
  8. data/app/views/blazer/checks/_form.html.haml +51 -0
  9. data/app/views/blazer/checks/edit.html.haml +2 -0
  10. data/app/views/blazer/checks/index.html.haml +48 -0
  11. data/app/views/blazer/checks/new.html.haml +2 -0
  12. data/app/views/blazer/dashboards/_form.html.haml +64 -0
  13. data/app/views/blazer/dashboards/edit.html.haml +2 -0
  14. data/app/views/blazer/dashboards/new.html.haml +2 -0
  15. data/app/views/blazer/dashboards/show.html.haml +33 -0
  16. data/app/views/blazer/queries/{_form.html.erb → _form.html.haml} +54 -81
  17. data/app/views/blazer/queries/_tips.html.haml +92 -0
  18. data/app/views/blazer/queries/docs.html.haml +115 -0
  19. data/app/views/blazer/queries/edit.html.haml +2 -0
  20. data/app/views/blazer/queries/{home.html.erb → home.html.haml} +38 -58
  21. data/app/views/blazer/queries/new.html.haml +2 -0
  22. data/app/views/blazer/queries/run.html.haml +153 -0
  23. data/app/views/blazer/queries/schema.html.haml +43 -0
  24. data/app/views/blazer/queries/show.html.haml +50 -0
  25. data/app/views/layouts/blazer/application.html.haml +19 -0
  26. data/lib/blazer/version.rb +1 -1
  27. metadata +38 -24
  28. data/app/views/blazer/_nav.html.erb +0 -15
  29. data/app/views/blazer/check_mailer/failing_checks.html.erb +0 -6
  30. data/app/views/blazer/check_mailer/state_change.html.erb +0 -47
  31. data/app/views/blazer/checks/_form.html.erb +0 -79
  32. data/app/views/blazer/checks/edit.html.erb +0 -3
  33. data/app/views/blazer/checks/index.html.erb +0 -69
  34. data/app/views/blazer/checks/new.html.erb +0 -3
  35. data/app/views/blazer/dashboards/_form.html.erb +0 -76
  36. data/app/views/blazer/dashboards/edit.html.erb +0 -3
  37. data/app/views/blazer/dashboards/new.html.erb +0 -3
  38. data/app/views/blazer/dashboards/show.html.erb +0 -51
  39. data/app/views/blazer/queries/_tips.html.erb +0 -69
  40. data/app/views/blazer/queries/docs.html.erb +0 -131
  41. data/app/views/blazer/queries/edit.html.erb +0 -2
  42. data/app/views/blazer/queries/new.html.erb +0 -2
  43. data/app/views/blazer/queries/run.html.erb +0 -202
  44. data/app/views/blazer/queries/schema.html.erb +0 -58
  45. data/app/views/blazer/queries/show.html.erb +0 -76
  46. data/app/views/layouts/blazer/application.html.erb +0 -25
@@ -0,0 +1,92 @@
1
+ %small.text-muted
2
+ %h5
3
+ %i.far.fa-lightbulb
4
+ ProTip!
5
+ \#{link_to 'more...', docs_queries_path, target: :_blank, style: "float: right; font-weight: 200"}
6
+ %ul#proTip.list-unstyled
7
+ %li
8
+ %strong Command + S
9
+ to backup your SQL string.
10
+ %li
11
+ Set column name to
12
+ %strong *_date
13
+ to format DateTime to
14
+ %strong= Time.current.strftime('%Y/%m/%d')
15
+ %li
16
+ Set column name to
17
+ %strong *_time
18
+ to format DateTime to
19
+ %strong= Time.current.strftime('%H:%M')
20
+ - if @data_source.smart_variables.any?
21
+ - @data_source.smart_variables.keys.each do |key|
22
+ %li
23
+ %strong
24
+ %i.fas.fa-caret-square-down
25
+ Use
26
+ %code
27
+ {#{key}}
28
+ to get a dropdown of values.
29
+ %li
30
+ %strong
31
+ %i.fas.fa-caret-square-down
32
+ Use
33
+ %code {start_time}
34
+ and
35
+ %code {end_time}
36
+ for a date range selector.
37
+ %li
38
+ %strong
39
+ %i.fas.fa-caret-square-down
40
+ End a variable name with
41
+ %code _at
42
+ for a date selector.
43
+ %li
44
+ %strong
45
+ %i.fas.fa-chart-line
46
+ Chart:
47
+ 2+ columns - timestamp, numeric(s)
48
+ %li
49
+ %strong
50
+ %i.fas.fa-chart-line
51
+ Chart:
52
+ 3 columns - timestamp, string, numeric
53
+ %li
54
+ %strong
55
+ %i.far.fa-chart-bar
56
+ Chart:
57
+ 2+ columns - string, numeric(s)
58
+ %li
59
+ %strong
60
+ %i.far.fa-chart-bar
61
+ Chart:
62
+ 3 columns - string, string, numeric
63
+ %li
64
+ %strong Scatter Chart:
65
+ 2 columns - both numeric
66
+ %li
67
+ %strong
68
+ %i.fas.fa-chart-pie
69
+ Chart:
70
+ 2 columns - string, numeric - and last column named
71
+ %code pie
72
+ %li
73
+ %strong
74
+ %i.fas.fa-globe-americas
75
+ Chart:
76
+ Named
77
+ %code latitude
78
+ and
79
+ = succeed "," do
80
+ %code longitude
81
+ %code lat
82
+ and
83
+ = succeed "," do
84
+ %code lon
85
+ %code lat
86
+ and
87
+ %code lng
88
+ %ul
89
+ :javascript
90
+ var itemCount = $('ul#proTip li').length;
91
+ var showIndex = Math.floor(Math.random() * Math.floor(itemCount)) + 1;
92
+ $("ul#proTip li:nth-child(" + showIndex + ")").show();
@@ -0,0 +1,115 @@
1
+ - blazer_title "Docs: #{@data_source.name}"
2
+ %h1
3
+ Docs: #{@data_source.name}
4
+ %hr/
5
+ %h2 Smart Variables
6
+ - if @smart_variables.any?
7
+ %p Use these variable names to get a dropdown of values.
8
+ %table.table{:style => "max-width: 500px;"}
9
+ %thead
10
+ %tr
11
+ %th Variable
12
+ %tbody
13
+ - @smart_variables.each do |k, _|
14
+ %tr
15
+ %td
16
+ %code
17
+ {#{k}}
18
+ %p
19
+ Use
20
+ %code {start_time}
21
+ and
22
+ %code {end_time}
23
+ for a date range selector. End a variable name with
24
+ %code _at
25
+ for a date selector.
26
+ - else
27
+ %p
28
+ None set - add them in
29
+ = succeed "." do
30
+ %code config/blazer.yml
31
+ %h2 Linked Columns
32
+ - if @linked_columns.any?
33
+ %p Use these column names to link results to other pages.
34
+ %table.table{:style => "max-width: 500px;"}
35
+ %thead
36
+ %tr
37
+ %th{:style => "width: 20%;"} Name
38
+ %th URL
39
+ %tbody
40
+ - @linked_columns.each do |k, v|
41
+ %tr
42
+ %td= k
43
+ %td= v
44
+ %p Values that match the format of a URL will be linked automatically.
45
+ - else
46
+ %p
47
+ None set - add them in
48
+ = succeed "." do
49
+ %code config/blazer.yml
50
+ %h2 Smart Columns
51
+ - if @smart_columns.any?
52
+ %p Use these column names to show additional data.
53
+ %table.table{:style => "max-width: 500px;"}
54
+ %thead
55
+ %tr
56
+ %th Name
57
+ %tbody
58
+ - @smart_columns.each do |k, _|
59
+ %tr
60
+ %td= k
61
+ - else
62
+ %p
63
+ None set - add them in
64
+ = succeed "." do
65
+ %code config/blazer.yml
66
+ %h2 Charts
67
+ %p Use specific combinations of column types to generate charts.
68
+ %table.table{:style => "max-width: 500px;"}
69
+ %thead
70
+ %tr
71
+ %th{:style => "width: 20%;"} Chart
72
+ %th Column Types
73
+ %tbody
74
+ %tr
75
+ %td Line
76
+ %td 2+ columns - timestamp, numeric(s)
77
+ %tr
78
+ %td Line
79
+ %td 3 columns - timestamp, string, numeric
80
+ %tr
81
+ %td Column
82
+ %td 2+ columns - string, numeric(s)
83
+ %tr
84
+ %td Column
85
+ %td 3 columns - string, string, numeric
86
+ %tr
87
+ %td Scatter
88
+ %td 2 columns - both numeric
89
+ %tr
90
+ %td Pie
91
+ %td
92
+ 2 columns - string, numeric - and last column named
93
+ %code pie
94
+ %tr
95
+ %td Map
96
+ %td
97
+ Named
98
+ %code latitude
99
+ and
100
+ = succeed "," do
101
+ %code longitude
102
+ %code lat
103
+ and
104
+ = succeed "," do
105
+ %code lon
106
+ %code lat
107
+ and
108
+ %code lng
109
+ - if !blazer_maps?
110
+ %br/
111
+ %strong Needs configured
112
+ %p
113
+ Use the column name
114
+ %code target
115
+ to draw a line for goals.
@@ -0,0 +1,2 @@
1
+ - blazer_title "Edit - #{@query.name}"
2
+ = render partial: "form"
@@ -1,60 +1,41 @@
1
- <div id="queries">
2
- <div id="header">
3
- <div class="pull-right" style="line-height: 34px;">
4
- <% if blazer_user %>
5
- <div class='btn-group' style='margin-right: 20px;'>
6
- <%= link_to "All", root_path, class: !params[:filter] ? 'active btn btn-default btn-xs' : 'btn btn-default btn-xs' %>
7
- <% if Blazer.audit %>
8
- <%= link_to "Viewed", root_path(filter: "viewed"), class: params[:filter] == "viewed" ? 'active btn btn-default btn-xs' : 'btn btn-default btn-xs' %>
9
- <% end %>
10
- <%= link_to "Mine", root_path(filter: "mine"), class: params[:filter] == "mine" ? 'active btn btn-default btn-xs' : 'btn btn-default btn-xs' %>
11
- </div>
12
- <% end %>
13
- <div class='btn-group'>
14
- <%= link_to "Checks", checks_path, class: 'btn btn-default' %>
15
- </div>
16
- <div class="btn-group">
17
- <%= link_to "New Query", new_query_path, class: "btn btn-info" %>
18
- <button type="button" class="btn btn-info dropdown-toggle" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
19
- <span class="caret"></span>
20
- <span class="sr-only">Toggle Dropdown</span>
21
- </button>
22
- <ul class="dropdown-menu">
23
- <li><%= link_to "Checks", checks_path %></li>
24
- <li role="separator" class="divider"></li>
25
- <li><%= link_to "New Dashboard", new_dashboard_path %></li>
26
- <li><%= link_to "New Check", new_check_path %></li>
27
- </ul>
28
- </div>
29
- </div>
30
- <input type="text" v-model="searchTerm" placeholder="Start typing a query, dashboard, or person" style="width: 300px; display: inline-block;" v-focus class="search form-control" />
31
- </div>
32
-
33
- <table class="table">
34
- <thead>
35
- <tr>
36
- <th>Name</th>
37
- <th style="width: 20%; text-align: right;">Mastermind</th>
38
- </tr>
39
- </thead>
40
- <tbody class="list" v-cloak>
41
- <tr v-for="query in visibleItems">
42
- <td>
43
- <a :href="itemPath(query)" :class="{ dashboard: query.dashboard }">{{ query.name }}</a>
44
- <span class="vars">{{ query.vars }}</span>
45
- </td>
46
- <td class="creator">{{ query.creator }}</td>
47
- </tr>
48
- </tbody>
49
- </table>
50
-
51
- <p v-if="more" class="text-muted">Loading...</p>
52
- </div>
53
-
54
- <script>
55
- <%= blazer_js_var "dashboards", @dashboards %>
56
- <%= blazer_js_var "queries", @queries %>
57
- <%= blazer_js_var "more", @more %>
1
+ #queries
2
+ #header
3
+ .pull-right{:style => "line-height: 34px;"}
4
+ - if blazer_user
5
+ .btn-group{:style => "margin-right: 20px;"}
6
+ = link_to "All", root_path, class: !params[:filter] ? 'active btn btn-default btn-xs' : 'btn btn-default btn-xs'
7
+ - if Blazer.audit
8
+ = link_to "Viewed", root_path(filter: "viewed"), class: params[:filter] == "viewed" ? 'active btn btn-default btn-xs' : 'btn btn-default btn-xs'
9
+ = link_to "Mine", root_path(filter: "mine"), class: params[:filter] == "mine" ? 'active btn btn-default btn-xs' : 'btn btn-default btn-xs'
10
+ .btn-group
11
+ = link_to "Checks", checks_path, class: 'btn btn-default'
12
+ .btn-group
13
+ = link_to "New Query", new_query_path, class: "btn btn-info"
14
+ %button.btn.btn-info.dropdown-toggle{"aria-expanded" => "false", "aria-haspopup" => "true", "data-toggle" => "dropdown", :type => "button"}
15
+ %span.caret
16
+ %span.sr-only Toggle Dropdown
17
+ %ul.dropdown-menu
18
+ %li= link_to "Checks", checks_path
19
+ %li.divider{:role => "separator"}
20
+ %li= link_to "New Dashboard", new_dashboard_path
21
+ %li= link_to "New Check", new_check_path
22
+ %input.search.form-control{:placeholder => "Start typing a query, dashboard, or person", :style => "width: 300px; display: inline-block;", :type => "text", "v-focus" => "", "v-model" => "searchTerm"}/
23
+ %table.table
24
+ %thead
25
+ %tr
26
+ %th Name
27
+ %th{:style => "width: 20%; text-align: right;"} Mastermind
28
+ %tbody.list{"v-cloak" => ""}
29
+ %tr{"v-for" => "query in visibleItems"}
30
+ %td
31
+ %a{":class" => "{ dashboard: query.dashboard }", ":href" => "itemPath(query)"} {{ query.name }}
32
+ %span.vars {{ query.vars }}
33
+ %td.creator {{ query.creator }}
34
+ %p.text-muted{"v-if" => "more"} Loading...
35
+ :javascript
36
+ #{blazer_js_var "dashboards", @dashboards}
37
+ #{blazer_js_var "queries", @queries}
38
+ #{blazer_js_var "more", @more}
58
39
 
59
40
  var prepareSearch = function (list) {
60
41
  var i, q, searchStr
@@ -158,4 +139,3 @@
158
139
  }
159
140
  }
160
141
  })
161
- </script>
@@ -0,0 +1,2 @@
1
+ - blazer_title "New Query"
2
+ = render partial: "form"
@@ -0,0 +1,153 @@
1
+ - if @error
2
+ .alert.alert-danger= @error.first(200)
3
+ - elsif !@success
4
+ - if @only_chart
5
+ %p.text-muted Select variables
6
+ - else
7
+ .alert.alert-info Can’t preview queries with variables...yet!
8
+ - else
9
+ - unless @only_chart
10
+ - if @cached_at || @just_cached
11
+ %p.text-muted{style: "float: right;"}
12
+ - if @cached_at
13
+ Cached #{time_ago_in_words(@cached_at, include_seconds: true)} ago
14
+ - elsif !params[:data_source]
15
+ Cached just now
16
+ - if @data_source.cache_mode == "slow"
17
+ (over #{"%g" % @data_source.cache_slow_threshold}s)
18
+ - if @query && !params[:data_source]
19
+ = link_to "Refresh", refresh_query_path(@query, variable_params), method: :post
20
+ - if @forecast_error
21
+ .alert.alert-danger= @forecast_error
22
+ - if @rows.any?
23
+ - values = @rows.first
24
+ - chart_id = SecureRandom.hex
25
+ - column_types = @result.column_types
26
+ - chart_type = @result.chart_type
27
+ - chart_options = {id: chart_id}
28
+ - if ["line", "line2"].include?(chart_type)
29
+ - chart_options.merge!(min: nil)
30
+ - if chart_type == "scatter"
31
+ - chart_options.merge!(library: {tooltips: {intersect: false}})
32
+ - elsif ["bar", "bar2"].include?(chart_type)
33
+ - chart_options.merge!(library: {tooltips: {intersect: false, axis: 'x'}})
34
+ - elsif chart_type != "pie"
35
+ - if column_types.size == 2 || @forecast
36
+ - chart_options.merge!(library: {tooltips: {intersect: false, axis: 'x'}})
37
+ - else
38
+ - chart_options.merge!(library: {tooltips: {intersect: false}})
39
+ - series_library = {}
40
+ - target_index = @columns.index { |k| k.downcase == "target" }
41
+ - if target_index
42
+ - series_library[target_index - 1] = {pointStyle: "line", hitRadius: 5, borderColor: "#109618", pointBackgroundColor: "#109618", backgroundColor: "#109618"}
43
+ - if @forecast
44
+ - color = "#54a3ee"
45
+ - series_library[1] = {borderDash: [8], borderColor: color, pointBackgroundColor: color, backgroundColor: color, pointHoverBackgroundColor: color}
46
+ - if blazer_maps? && @markers.any?
47
+ #map{style: "height: #{@only_chart ? 300 : 500}px;"}
48
+ :javascript
49
+ L.mapbox.accessToken = '#{Blazer.mapbox_access_token}';
50
+ var map = L.mapbox.map('map', 'ankane.ioo8nki0');
51
+ #{blazer_js_var "markers", @markers}
52
+ var featureLayer = L.mapbox.featureLayer().addTo(map);
53
+ var geojson = [];
54
+ for (var i = 0; i < markers.length; i++) {
55
+ var marker = markers[i];
56
+ geojson.push({
57
+ type: 'Feature',
58
+ geometry: {
59
+ type: 'Point',
60
+ coordinates: [
61
+ marker.longitude,
62
+ marker.latitude
63
+ ]
64
+ },
65
+ properties: {
66
+ description: marker.title,
67
+ 'marker-color': '#f86767',
68
+ 'marker-size': 'medium'
69
+ }
70
+ });
71
+ }
72
+ featureLayer.setGeoJSON(geojson);
73
+ map.fitBounds(featureLayer.getBounds());
74
+ - elsif chart_type == "line"
75
+ - chart_data = @columns[1..-1].each_with_index.map{ |k, i| {name: blazer_series_name(k), data: @rows.map{ |r| [r[0], r[i + 1]] }, library: series_library[i]} }
76
+ = line_chart chart_data, chart_options
77
+ - elsif chart_type == "line2"
78
+ = line_chart @rows.group_by { |r| v = r[1]; (@boom[@columns[1]] || {})[v.to_s] || v }.each_with_index.map { |(name, v), i| {name: blazer_series_name(name), data: v.map { |v2| [v2[0], v2[2]] }, library: series_library[i]} }, chart_options
79
+ - elsif chart_type == "pie"
80
+ = pie_chart @rows.map { |r| [(@boom[@columns[0]] || {})[r[0].to_s] || r[0], r[1]] }, chart_options
81
+ - elsif chart_type == "bar"
82
+ = column_chart (values.size - 1).times.map { |i| name = @columns[i + 1]; {name: blazer_series_name(name), data: @rows.first(20).map { |r| [(@boom[@columns[0]] || {})[r[0].to_s] || r[0], r[i + 1]] } } }, chart_options
83
+ - elsif chart_type == "bar2"
84
+ - first_20 = @rows.group_by { |r| r[0] }.values.first(20).flatten(1)
85
+ - labels = first_20.map { |r| r[0] }.uniq
86
+ - series = first_20.map { |r| r[1] }.uniq
87
+ - labels.each do |l|
88
+ - series.each do |s|
89
+ - first_20 << [l, s, 0] unless first_20.find { |r| r[0] == l && r[1] == s }
90
+ = column_chart first_20.group_by { |r| v = r[1]; (@boom[@columns[1]] || {})[v.to_s] || v }.each_with_index.map { |(name, v), i| {name: blazer_series_name(name), data: v.sort_by { |r2| labels.index(r2[0]) }.map { |v2| v3 = v2[0]; [(@boom[@columns[0]] || {})[v3.to_s] || v3, v2[2]] }} }, chart_options
91
+ - elsif chart_type == "scatter"
92
+ = scatter_chart @rows, xtitle: @columns[0], ytitle: @columns[1], **chart_options
93
+ - elsif @only_chart
94
+ - if @rows.size == 1 && @rows.first.size == 1
95
+ - v = @rows.first.first
96
+ - if v.is_a?(String) && v == ""
97
+ .text-muted empty string
98
+ - else
99
+ %p{style: "font-size: 160px;"}= blazer_format_value(@columns.first, v)
100
+ - else
101
+ - @no_chart = true
102
+ - unless @only_chart && !@no_chart
103
+ - header_width = 100 / @columns.size.to_f
104
+ .results-container
105
+ - if @columns == ["QUERY PLAN"]
106
+ %pre
107
+ %code= @rows.map { |r| r[0] }.join("\n")
108
+ - elsif @columns == ["PLAN"] && @data_source.adapter == "druid"
109
+ %pre
110
+ %code= @rows[0][0]
111
+ - else
112
+ %p.text-muted{style: "margin-bottom: 10px; margin-top: 15px"}
113
+ = pluralize(@rows.size, "row")
114
+ - @checks.select(&:state).each do |check|
115
+ ·
116
+ %small{:class => "check-state #{check.state.parameterize.gsub("-", "_")}"}= link_to check.state.upcase, edit_check_path(check)
117
+ - if check.try(:message)
118
+ · #{check.message}
119
+ - if @query && @result.forecastable? && !params[:forecast]
120
+ ·
121
+ \#{link_to "Forecast", query_path(@query, {forecast: "t"}.merge(variable_params))}
122
+ %span.pull-right
123
+ - if @rows.size > 0
124
+ = link_to 'Copy to clipboard', '#results-table', class: 'click2CopyTable btn btn-xs btn-info'
125
+ .scroll-content
126
+ %table#results-table.table.results-table
127
+ %thead
128
+ %tr
129
+ - @columns.each_with_index do |key, i|
130
+ - type = @column_types[i]
131
+ - summany_popup = type.in?(['float', 'int']) && !key.end_with?('id')
132
+ %th{"data-popup" => summany_popup, "data-sort" => type, style: "width: #{header_width}%;"}
133
+ %div{style: "min-width: #{@min_width_types.include?(i) ? 180 : 60}px;"}
134
+ = key
135
+ %tbody
136
+ - @rows.each do |row|
137
+ %tr
138
+ - row.each_with_index do |v, i|
139
+ - k = @columns[i]
140
+ %td
141
+ - if v.is_a?(Time)
142
+ - v = blazer_time_value(@data_source, k, v)
143
+ - unless v.nil?
144
+ - if v.is_a?(String) && v == ""
145
+ .text-muted empty string
146
+ - elsif @linked_columns[k]
147
+ = link_to blazer_format_value(k, v), @linked_columns[k].gsub("{value}", u(v.to_s)), target: "_blank"
148
+ - else
149
+ = blazer_format_value(k, v)
150
+ - if v2 = (@boom[k] || {})[v.nil? ? v : v.to_s]
151
+ .text-muted= v2
152
+ - else
153
+ %p.text-muted.text-center{style: "margin-top: 15px"} No rows