sql-jarvis 2.0.9 → 2.1

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.
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