pg_reports 0.5.4 → 0.6.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 (50) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +69 -0
  3. data/README.md +123 -370
  4. data/app/controllers/pg_reports/dashboard_controller.rb +21 -21
  5. data/app/views/layouts/pg_reports/application.html.erb +135 -69
  6. data/app/views/pg_reports/dashboard/_show_modals.html.erb +22 -22
  7. data/app/views/pg_reports/dashboard/_show_scripts.html.erb +105 -55
  8. data/app/views/pg_reports/dashboard/_show_styles.html.erb +49 -11
  9. data/app/views/pg_reports/dashboard/index.html.erb +123 -114
  10. data/app/views/pg_reports/dashboard/show.html.erb +30 -26
  11. data/config/locales/en.yml +597 -0
  12. data/config/locales/ru.yml +562 -0
  13. data/config/locales/uk.yml +607 -0
  14. data/lib/pg_reports/compatibility.rb +63 -0
  15. data/lib/pg_reports/configuration.rb +2 -0
  16. data/lib/pg_reports/dashboard/reports_registry.rb +112 -5
  17. data/lib/pg_reports/definitions/indexes/fk_without_indexes.yml +30 -0
  18. data/lib/pg_reports/definitions/indexes/index_correlation.yml +31 -0
  19. data/lib/pg_reports/definitions/indexes/inefficient_indexes.yml +45 -0
  20. data/lib/pg_reports/definitions/queries/temp_file_queries.yml +39 -0
  21. data/lib/pg_reports/definitions/schema_analysis/always_null_columns.yml +31 -0
  22. data/lib/pg_reports/definitions/schema_analysis/unused_columns.yml +32 -0
  23. data/lib/pg_reports/definitions/system/wraparound_risk.yml +31 -0
  24. data/lib/pg_reports/definitions/tables/tables_without_pk.yml +28 -0
  25. data/lib/pg_reports/definitions/tables/unused_tables.yml +30 -0
  26. data/lib/pg_reports/definitions/tables/update_hotspots.yml +32 -0
  27. data/lib/pg_reports/engine.rb +6 -0
  28. data/lib/pg_reports/module_generator.rb +2 -1
  29. data/lib/pg_reports/modules/indexes.rb +3 -0
  30. data/lib/pg_reports/modules/queries.rb +1 -0
  31. data/lib/pg_reports/modules/schema_analysis.rb +261 -2
  32. data/lib/pg_reports/modules/system.rb +27 -0
  33. data/lib/pg_reports/modules/tables.rb +1 -0
  34. data/lib/pg_reports/query_monitor.rb +64 -36
  35. data/lib/pg_reports/report_definition.rb +20 -24
  36. data/lib/pg_reports/sql/indexes/fk_without_indexes.sql +23 -0
  37. data/lib/pg_reports/sql/indexes/index_correlation.sql +27 -0
  38. data/lib/pg_reports/sql/indexes/inefficient_indexes.sql +22 -0
  39. data/lib/pg_reports/sql/queries/temp_file_queries.sql +16 -0
  40. data/lib/pg_reports/sql/schema_analysis/always_null_columns.sql +25 -0
  41. data/lib/pg_reports/sql/schema_analysis/unused_columns.sql +36 -0
  42. data/lib/pg_reports/sql/system/checkpoint_stats.sql +20 -0
  43. data/lib/pg_reports/sql/system/checkpoint_stats_legacy.sql +19 -0
  44. data/lib/pg_reports/sql/system/wraparound_risk.sql +21 -0
  45. data/lib/pg_reports/sql/tables/tables_without_pk.sql +20 -0
  46. data/lib/pg_reports/sql/tables/unused_tables.sql +19 -0
  47. data/lib/pg_reports/sql/tables/update_hotspots.sql +26 -0
  48. data/lib/pg_reports/version.rb +1 -1
  49. data/lib/pg_reports.rb +5 -0
  50. metadata +24 -1
@@ -2,7 +2,7 @@
2
2
 
3
3
  <div class="report-page">
4
4
  <nav class="breadcrumb">
5
- <%= link_to "Dashboard", root_path %>
5
+ <%= link_to t("pg_reports.ui.navigation.dashboard"), root_path %>
6
6
  <span>/</span>
7
7
  <span><%= @categories[@category][:name] %></span>
8
8
  <span>/</span>
@@ -17,36 +17,40 @@
17
17
 
18
18
  <div class="report-actions">
19
19
  <button class="btn btn-primary" onclick="runReport('<%= @category %>', '<%= @report_key %>', this)">
20
- Run Report
20
+ <%= t("pg_reports.ui.actions.run_report") %>
21
21
  </button>
22
22
 
23
- <!-- Download dropdown -->
23
+ <!-- Export dropdown -->
24
24
  <div class="dropdown" id="download-dropdown" style="display: none;">
25
25
  <button class="btn btn-secondary" onclick="toggleDropdown()">
26
- Download
26
+ <%= t("pg_reports.ui.actions.export") %>
27
27
  </button>
28
28
  <div class="dropdown-menu" id="dropdown-menu">
29
- <a href="#" onclick="downloadReport('txt'); return false;">📄 Text (.txt)</a>
30
- <a href="#" onclick="downloadReport('csv'); return false;">📊 CSV (.csv)</a>
31
- <a href="#" onclick="downloadReport('json'); return false;">📋 JSON (.json)</a>
29
+ <a href="#" onclick="downloadReport('txt'); return false;"><%= t("pg_reports.ui.actions.download_text") %></a>
30
+ <a href="#" onclick="downloadReport('csv'); return false;"><%= t("pg_reports.ui.actions.download_csv") %></a>
31
+ <a href="#" onclick="downloadReport('json'); return false;"><%= t("pg_reports.ui.actions.download_json") %></a>
32
+ <% if @documentation && @documentation[:ai_prompt].present? %>
33
+ <div class="dropdown-divider"></div>
34
+ <a href="#" id="ai-prompt-btn" onclick="copyAiPrompt(this); return false;"><span class="ai-icon">AI</span> <%= t("pg_reports.ui.actions.copy_ai_prompt") %></a>
35
+ <% end %>
32
36
  </div>
33
37
  </div>
34
38
 
35
39
  <% if PgReports.config.telegram_configured? %>
36
40
  <button class="btn btn-telegram" onclick="sendToTelegram('<%= @category %>', '<%= @report_key %>', this)" id="telegram-btn" style="display: none;">
37
- 📨 Telegram
41
+ <%= t("pg_reports.ui.actions.send_telegram") %>
38
42
  </button>
39
43
  <% end %>
40
- <button class="btn btn-icon" onclick="showIdeSettingsModal()" title="IDE Settings">
44
+ <button class="btn btn-icon" onclick="showIdeSettingsModal()" title="<%= t("pg_reports.ui.actions.ide_settings_button_title") %>">
41
45
  ⚙️
42
46
  </button>
43
- <%= link_to "← Back", root_path, class: "btn btn-secondary" %>
47
+ <%= link_to t("pg_reports.ui.navigation.back"), root_path, class: "btn btn-secondary" %>
44
48
  </div>
45
49
  </div>
46
50
 
47
51
  <% if @error %>
48
52
  <div class="error-message">
49
- <strong>Error:</strong> <%= @error %>
53
+ <strong><%= t("pg_reports.ui.errors.error_prefix") %></strong> <%= @error %>
50
54
  </div>
51
55
  <% end %>
52
56
 
@@ -56,26 +60,26 @@
56
60
  <details class="documentation-section">
57
61
  <summary class="documentation-toggle">
58
62
  <span class="toggle-icon">▶</span>
59
- <span>📖 What does this report show?</span>
63
+ <span><%= t("pg_reports.ui.documentation.toggle_title") %></span>
60
64
  </summary>
61
65
  <div class="documentation-content">
62
66
  <% if @documentation[:what].present? %>
63
67
  <div class="doc-block">
64
- <h4>📋 What</h4>
68
+ <h4><%= t("pg_reports.ui.documentation.what_section") %></h4>
65
69
  <p><%= @documentation[:what] %></p>
66
70
  </div>
67
71
  <% end %>
68
72
 
69
73
  <% if @documentation[:why].present? %>
70
74
  <div class="doc-block">
71
- <h4>❓ Why It Matters</h4>
75
+ <h4><%= t("pg_reports.ui.documentation.why_section") %></h4>
72
76
  <p><%= @documentation[:why] %></p>
73
77
  </div>
74
78
  <% end %>
75
79
 
76
80
  <% if @documentation[:nuances].present? %>
77
81
  <div class="doc-block">
78
- <h4>⚠️ Nuances</h4>
82
+ <h4><%= t("pg_reports.ui.documentation.nuances_section") %></h4>
79
83
  <ul class="nuances-list">
80
84
  <% @documentation[:nuances].each do |nuance| %>
81
85
  <li><%= nuance %></li>
@@ -86,15 +90,15 @@
86
90
 
87
91
  <% if @thresholds.present? %>
88
92
  <div class="thresholds-block">
89
- <h4>📊 Thresholds</h4>
93
+ <h4><%= t("pg_reports.ui.documentation.thresholds_section") %></h4>
90
94
  <div class="thresholds-grid">
91
95
  <% @thresholds.each do |field, values| %>
92
96
  <div class="threshold-item">
93
97
  <span class="threshold-field"><%= field %></span>
94
- <span class="threshold-warning">⚠️ Warning: <%= values[:warning] %></span>
95
- <span class="threshold-critical">🔴 Critical: <%= values[:critical] %></span>
98
+ <span class="threshold-warning"><%= t("pg_reports.ui.documentation.threshold_warning_label") %> <%= values[:warning] %></span>
99
+ <span class="threshold-critical"><%= t("pg_reports.ui.documentation.threshold_critical_label") %> <%= values[:critical] %></span>
96
100
  <% if values[:inverted] %>
97
- <span class="threshold-note">(lower is worse)</span>
101
+ <span class="threshold-note"><%= t("pg_reports.ui.documentation.threshold_inverted_note") %></span>
98
102
  <% end %>
99
103
  </div>
100
104
  <% end %>
@@ -111,7 +115,7 @@
111
115
  <details class="filter-details">
112
116
  <summary class="filter-toggle">
113
117
  <span class="toggle-icon">▶</span>
114
- <span>🔍 Параметры фильтрации</span>
118
+ <span><%= t("pg_reports.ui.filters.title") %></span>
115
119
  </summary>
116
120
  <div class="filter-content">
117
121
  <div class="filter-grid">
@@ -123,7 +127,7 @@
123
127
  <span class="filter-description"><%= config[:description] %></span>
124
128
  <% end %>
125
129
  <% if config[:is_threshold] && config[:current_config] %>
126
- <span class="filter-current-value">(current: <%= config[:current_config] %>)</span>
130
+ <span class="filter-current-value">(<%= t("pg_reports.ui.filters.current_value") %>: <%= config[:current_config] %>)</span>
127
131
  <% end %>
128
132
  </label>
129
133
  <input
@@ -149,17 +153,17 @@
149
153
  <!-- Saved Records Section -->
150
154
  <div class="saved-records-section" id="saved-records-section" style="display: none;">
151
155
  <div class="saved-records-header">
152
- <span class="saved-records-title">📌 Saved for Comparison</span>
153
- <button class="btn btn-small btn-muted" onclick="clearAllSavedRecords()">Clear All</button>
156
+ <span class="saved-records-title"><%= t("pg_reports.ui.saved.title") %></span>
157
+ <button class="btn btn-small btn-muted" onclick="clearAllSavedRecords()"><%= t("pg_reports.ui.actions.clear_all") %></button>
154
158
  </div>
155
159
  <div class="saved-records-list" id="saved-records-list"></div>
156
160
  </div>
157
161
 
158
162
  <div class="results-container" id="results-container">
159
163
  <div class="results-header">
160
- <span class="results-title">Results</span>
164
+ <span class="results-title"><%= t("pg_reports.ui.results.title") %></span>
161
165
  <div class="results-meta" id="results-meta">
162
- <span>Click "Run Report" to fetch data</span>
166
+ <span><%= t("pg_reports.ui.results.click_run_hint") %></span>
163
167
  </div>
164
168
  </div>
165
169
 
@@ -169,7 +173,7 @@
169
173
 
170
174
  <div id="empty-state" class="empty-state" style="display: none;">
171
175
  <div class="empty-state-icon">✓</div>
172
- <p>No issues found. Everything looks good!</p>
176
+ <p><%= t("pg_reports.ui.results.empty_message") %></p>
173
177
  </div>
174
178
 
175
179
  <div class="top-scroll-wrapper" id="top-scroll-wrapper" style="display: none;">