pgdexter 0.3.0 → 0.3.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +6 -0
- data/README.md +9 -9
- data/lib/dexter/csv_log_parser.rb +6 -2
- data/lib/dexter/indexer.rb +9 -5
- data/lib/dexter/log_parser.rb +18 -2
- data/lib/dexter/processor.rb +1 -1
- data/lib/dexter/version.rb +1 -1
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 78c0747c456e498798accd4e4881a8041d246e07
|
4
|
+
data.tar.gz: c4c9cffe3e04d07675c36abf0532db3634e356ea
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: df826f95f34809bd94cb7450cc43d4bd6beed81606e6e7079842dd4a05e983d4041bf956645c09a290cf8fa37140917da1a12fe332d6268969da5310f688e148
|
7
|
+
data.tar.gz: f7015b408e7864bfe7e4e136cbb60acbe837cbbe640ec4f43dfb2d9631f2d4cb2b4c86826cb58051d68941bdfa6fd6625029babe7c1609e084db1a4f92a23652
|
data/CHANGELOG.md
CHANGED
data/README.md
CHANGED
@@ -130,7 +130,7 @@ Specify the format
|
|
130
130
|
dexter --input-format csv
|
131
131
|
```
|
132
132
|
|
133
|
-
When
|
133
|
+
When streaming logs, specify the time to wait between processing queries
|
134
134
|
|
135
135
|
```sh
|
136
136
|
dexter --interval 60 # seconds
|
@@ -150,6 +150,14 @@ Homebrew on Mac
|
|
150
150
|
tail -F -n +1 /usr/local/var/postgres/server.log | dexter dbname
|
151
151
|
```
|
152
152
|
|
153
|
+
## Analyze
|
154
|
+
|
155
|
+
For best results, make sure your tables have been recently analyzed so statistics are up-to-date. You can ask Dexter to analyze tables it comes across that haven’t been analyzed in the past hour with:
|
156
|
+
|
157
|
+
```sh
|
158
|
+
dexter --analyze
|
159
|
+
```
|
160
|
+
|
153
161
|
## Tables
|
154
162
|
|
155
163
|
You can exclude large or write-heavy tables from indexing with:
|
@@ -172,14 +180,6 @@ See how Dexter is processing queries with:
|
|
172
180
|
dexter --log-sql --log-level debug2
|
173
181
|
```
|
174
182
|
|
175
|
-
## Analyze
|
176
|
-
|
177
|
-
For best results, make sure your tables have been recently analyzed so statistics are up-to-date. You can ask Dexter to analyze tables it comes across that haven’t been analyzed in the past hour with:
|
178
|
-
|
179
|
-
```sh
|
180
|
-
dexter --analyze
|
181
|
-
```
|
182
|
-
|
183
183
|
## Hosted Postgres
|
184
184
|
|
185
185
|
Some hosted providers like Amazon RDS and Heroku do not support the HypoPG extension, which Dexter needs to run. See [how to use Dexter](guides/Hosted-Postgres.md) in these cases.
|
@@ -3,11 +3,15 @@ require "csv"
|
|
3
3
|
module Dexter
|
4
4
|
class CsvLogParser < LogParser
|
5
5
|
def perform
|
6
|
-
CSV.
|
6
|
+
CSV.new(@logfile).each do |row|
|
7
7
|
if (m = REGEX.match(row[13]))
|
8
|
-
|
8
|
+
active_line = m[3]
|
9
|
+
add_parameters(active_line, row[14]) if row[14]
|
10
|
+
process_entry(active_line, m[1].to_f)
|
9
11
|
end
|
10
12
|
end
|
13
|
+
rescue CSV::MalformedCSVError => e
|
14
|
+
abort "ERROR: #{e.message}"
|
11
15
|
end
|
12
16
|
end
|
13
17
|
end
|
data/lib/dexter/indexer.rb
CHANGED
@@ -130,18 +130,22 @@ module Dexter
|
|
130
130
|
|
131
131
|
def calculate_plan(queries)
|
132
132
|
queries.each do |query|
|
133
|
+
if @log_explain
|
134
|
+
puts "Explaining query"
|
135
|
+
puts
|
136
|
+
end
|
133
137
|
begin
|
134
138
|
query.plans << plan(query.statement)
|
135
139
|
if @log_explain
|
136
|
-
log "Explaining query"
|
137
|
-
puts
|
138
140
|
# Pass format to prevent ANALYZE
|
139
141
|
puts execute("EXPLAIN (FORMAT TEXT) #{safe_statement(query.statement)}").map { |r| r["QUERY PLAN"] }.join("\n")
|
140
|
-
puts
|
141
142
|
end
|
142
|
-
rescue PG::Error
|
143
|
-
|
143
|
+
rescue PG::Error => e
|
144
|
+
if @log_explain
|
145
|
+
log e.message
|
146
|
+
end
|
144
147
|
end
|
148
|
+
puts if @log_explain
|
145
149
|
end
|
146
150
|
end
|
147
151
|
|
data/lib/dexter/log_parser.rb
CHANGED
@@ -1,7 +1,8 @@
|
|
1
1
|
module Dexter
|
2
2
|
class LogParser
|
3
|
-
REGEX = /duration: (\d+\.\d+) ms (statement|execute <unnamed
|
3
|
+
REGEX = /duration: (\d+\.\d+) ms (statement|execute <unnamed>): (.+)/
|
4
4
|
LINE_SEPERATOR = ": ".freeze
|
5
|
+
DETAIL_LINE = "DETAIL: ".freeze
|
5
6
|
|
6
7
|
def initialize(logfile, collector)
|
7
8
|
@logfile = logfile
|
@@ -14,7 +15,9 @@ module Dexter
|
|
14
15
|
|
15
16
|
@logfile.each_line do |line|
|
16
17
|
if active_line
|
17
|
-
if line.include?(
|
18
|
+
if line.include?(DETAIL_LINE)
|
19
|
+
add_parameters(active_line, line.chomp.split(DETAIL_LINE)[1])
|
20
|
+
elsif line.include?(LINE_SEPERATOR)
|
18
21
|
process_entry(active_line, duration)
|
19
22
|
active_line = nil
|
20
23
|
else
|
@@ -35,5 +38,18 @@ module Dexter
|
|
35
38
|
def process_entry(query, duration)
|
36
39
|
@collector.add(query, duration)
|
37
40
|
end
|
41
|
+
|
42
|
+
def add_parameters(active_line, details)
|
43
|
+
if details.start_with?("parameters: ")
|
44
|
+
params = Hash[details[12..-1].split(", ").map { |s| s.split(" = ", 2) }]
|
45
|
+
|
46
|
+
# make sure parsing was successful
|
47
|
+
unless params.values.include?(nil)
|
48
|
+
params.each do |k, v|
|
49
|
+
active_line.sub!(k, v)
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
38
54
|
end
|
39
55
|
end
|
data/lib/dexter/processor.rb
CHANGED
data/lib/dexter/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: pgdexter
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.3.
|
4
|
+
version: 0.3.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Andrew Kane
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2017-12-
|
11
|
+
date: 2017-12-29 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: slop
|