perfmonger 0.10.1 → 0.12.0
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 +5 -5
- data/.gitignore +3 -0
- data/.travis.yml +9 -8
- data/HOWTO.md +0 -1
- data/NEWS +47 -3
- data/README.md +77 -27
- data/Rakefile +20 -9
- data/core/Makefile +10 -18
- data/core/build.sh +2 -2
- data/core/perfmonger-player.go +90 -40
- data/core/perfmonger-plot-formatter.go +18 -4
- data/core/perfmonger-recorder.go +22 -2
- data/core/perfmonger-summarizer.go +20 -14
- data/core/perfmonger-viewer.go +164 -0
- data/core/subsystem/Makefile +4 -0
- data/core/subsystem/perfmonger_linux.go +95 -0
- data/core/subsystem/perfmonger_linux_test.go +40 -0
- data/core/subsystem/stat.go +70 -0
- data/core/subsystem/stat_test.go +9 -0
- data/core/subsystem/usage.go +223 -66
- data/core/subsystem/usage_test.go +62 -32
- data/{bin → exe}/perfmonger +0 -0
- data/lib/perfmonger/command/fingerprint.rb +26 -1
- data/lib/perfmonger/command/live.rb +19 -0
- data/lib/perfmonger/command/play.rb +16 -0
- data/lib/perfmonger/command/plot.rb +25 -9
- data/lib/perfmonger/command/record.rb +1 -1
- data/lib/perfmonger/command/record_option.rb +16 -0
- data/lib/perfmonger/command/server.rb +1 -1
- data/lib/perfmonger/version.rb +1 -1
- data/misc/werker-box/Dockerfile +34 -0
- data/misc/werker-box/build-push.sh +7 -0
- data/perfmonger.gemspec +2 -1
- data/spec/data/busy100.pgr.played +3 -3
- data/spec/fingerprint_spec.rb +1 -1
- data/spec/live_spec.rb +2 -3
- data/spec/perfmonger_spec.rb +1 -1
- data/spec/play_spec.rb +1 -1
- data/spec/plot_spec.rb +16 -1
- data/spec/record_spec.rb +10 -1
- data/spec/spec_helper.rb +28 -3
- data/spec/stat_spec.rb +2 -2
- data/spec/summary_spec.rb +1 -1
- data/wercker.yml +29 -16
- metadata +28 -10
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: d54380ef057091f9d6829d3a792c0c4a91789b56077ff7a59b4a1bf063ec883e
|
4
|
+
data.tar.gz: c01127d30de0978a88bf1481357d3e20cde8193dd16e6bde9e0f2030d6423710
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 8ae9ded1f5d4c5157902ccfa23a12910866834480f7b82e1464f4c2d5e767cbf2d5752118f1aa666f445d2f61a0e5cfbc7198c3ad9cf098539c0cd96a25b12f3
|
7
|
+
data.tar.gz: 3c507d05cec5b3b28e49367379846009b1848ac75d23227d22a019203190b9adeaf201a25805b3746d518d221a46399580d49899f6205f236980c70b3b73a7e5
|
data/.gitignore
CHANGED
data/.travis.yml
CHANGED
@@ -1,24 +1,25 @@
|
|
1
|
-
|
2
1
|
language: ruby
|
3
2
|
install:
|
4
3
|
- sudo apt-get update
|
5
4
|
- sudo apt-get install gnuplot
|
6
5
|
- gnuplot -e "set terminal" < /dev/null 2>&1
|
7
6
|
- bundle install
|
8
|
-
- go_version="1.
|
7
|
+
- go_version="1.14.1"
|
9
8
|
- wget http://golang.org/dl/go${go_version}.linux-amd64.tar.gz
|
10
9
|
- sudo tar -C /usr/local -xzf go${go_version}.linux-amd64.tar.gz
|
11
10
|
- export PATH=$PATH:/usr/local/go/bin
|
12
11
|
- export GOPATH="$HOME/go"
|
13
12
|
- export PATH="$PATH:$GOPATH/bin"
|
14
13
|
- mkdir -p "$HOME/go/{src,pkg,bin}"
|
15
|
-
- go get -u golang.org/x/crypto/ssh/terminal
|
16
|
-
- go get -u github.com/hayamiz/perfmonger/core/subsystem
|
17
14
|
rvm:
|
18
|
-
-
|
19
|
-
- 2.
|
20
|
-
- 2.
|
21
|
-
- 2.
|
15
|
+
- 2.4.9
|
16
|
+
- 2.5.7
|
17
|
+
- 2.6.5
|
18
|
+
- 2.7.0
|
22
19
|
script:
|
20
|
+
- rake go_get
|
23
21
|
- rake spec
|
24
22
|
- rake test_core
|
23
|
+
notifications:
|
24
|
+
slack:
|
25
|
+
secure: fH8tRyxWHL60OV6QuJlzig9lCLbjfpHx8E6D2EzgQz7+/wqAxtoTUyiN7mbpEJa4hyQeZfpmMpDTnl2tHD6eI8yqjAsY4Q+jt21tCKyrKMegq9Pypd4eMP4o+DupT2mXm0K3cZ2Kgb+yP8AuJPoTy20j3kpmnDFWdqRnhgpBLC8=
|
data/HOWTO.md
CHANGED
data/NEWS
CHANGED
@@ -1,5 +1,49 @@
|
|
1
|
-
##
|
2
|
-
|
1
|
+
## 20XX-XX-XX: PerfMonger 0.13.0
|
2
|
+
|
3
|
+
## 2021-05-10: PerfMonger 0.12.0
|
4
|
+
* New features
|
5
|
+
* [record] subcommand:
|
6
|
+
* Add memory usage collection
|
7
|
+
|
8
|
+
## 2021-02-10: PerfMonger 0.11.3
|
9
|
+
* Bug fixes
|
10
|
+
* [plot] subcommand:
|
11
|
+
* Fall back to available gnuplot terminal
|
12
|
+
* Changes
|
13
|
+
* [plot] subcommand:
|
14
|
+
* Added --with-gnuplot option for specifying gnuplot binary
|
15
|
+
|
16
|
+
## 2020-03-31: PerfMonger 0.11.2
|
17
|
+
* Bug fixes
|
18
|
+
* [plot] subcommand:
|
19
|
+
* Remove temporary directory correctly
|
20
|
+
* Changes
|
21
|
+
* CI environment
|
22
|
+
* Changed golang version to 1.14
|
23
|
+
* Dropped support of ruby older than 2.4
|
24
|
+
* Added ruby 2.6 and 2.7
|
25
|
+
|
26
|
+
## 2018-05-15: PerfMonger 0.11.1
|
27
|
+
* Bug fixes
|
28
|
+
* [record] subcommand:
|
29
|
+
* Fixed session detection mechanism (did not worked for execution under sudo)
|
30
|
+
|
31
|
+
## 2018-05-15: PerfMonger 0.11.0
|
32
|
+
* New features
|
33
|
+
* [play] subcommand:
|
34
|
+
* Add --color, --pretty option for pretty JSON output
|
35
|
+
* [live] subcommand:
|
36
|
+
* Add --color, --pretty option for pretty JSON output
|
37
|
+
* [fingerprint] subcommand:
|
38
|
+
* Collect additional info: numactl, ec2-metadata
|
39
|
+
* Bug fixes
|
40
|
+
* [plot] subcommand:
|
41
|
+
* Correctly filter out disk usages by --disk-only option
|
42
|
+
* Changes
|
43
|
+
* Dropped support of i386
|
44
|
+
* Use go-projson for JSON output
|
45
|
+
* [plot] subcommand:
|
46
|
+
* Stacked graphs layout in allcpu.pdf
|
3
47
|
|
4
48
|
## 2017-06-19: PerfMonger 0.10.0
|
5
49
|
* New features
|
@@ -199,4 +243,4 @@ PerfMonger is available on yum repository from this release.
|
|
199
243
|
## 2011-12-09: PerfMonger 0.1.0 released
|
200
244
|
|
201
245
|
* New features
|
202
|
-
* I/O performance monitoring
|
246
|
+
* I/O performance monitoring
|
data/README.md
CHANGED
@@ -5,31 +5,97 @@
|
|
5
5
|
|
6
6
|
[](https://app.wercker.com/project/bykey/44c3ade6a2406d337df6d93097a52fdf)
|
7
7
|
|
8
|
-
PerfMonger is
|
9
|
-
|
8
|
+
PerfMonger is a system performance monitor which enables high-resolution and holistic performance measurement with the programmer friendly interface.
|
9
|
+
|
10
|
+
* High-resolution: sub-second level monitoring is possible!
|
11
|
+
* Holistic performance measurement: monitoring CPU, Disk I/O, Network all at once.
|
12
|
+
* Programmer friendly: PerfMonger speaks monitoring results in JSON format, which makes later performance analysis much easier (ex. [jq](https://github.com/stedolan/jq)).
|
10
13
|
|
11
14
|
**CAUTION: PerfMonger is still in early stage, so there may be a drastic change in the future. Do not use it for critical jobs**
|
12
15
|
|
13
16
|
## Target platform
|
14
17
|
|
15
18
|
* GNU/Linux
|
19
|
+
* Mac OS X (experimental support)
|
16
20
|
|
17
|
-
##
|
18
|
-
|
19
|
-
* Ruby 1.9.3 or later
|
20
|
-
* gnuplot 4.6.0 or later (optional)
|
21
|
-
|
22
|
-
Note: You need Cutter unit testing framework for building/running tests.
|
23
|
-
|
24
|
-
## How to install
|
21
|
+
## How to installation
|
25
22
|
|
26
23
|
gem install perfmonger
|
27
24
|
|
25
|
+
You need gnuplot 4.6.0 or later build with cairo terminals for plotting measurement data with `perfmonger plot` command.
|
26
|
+
|
28
27
|
### Build from source
|
29
28
|
|
29
|
+
You need Ruby 2.2 or later, and Go 1.8 or later to build perfmonger.
|
30
|
+
|
31
|
+
bundle
|
30
32
|
rake build
|
31
33
|
|
32
|
-
##
|
34
|
+
## Getting started
|
35
|
+
|
36
|
+
Basic usage of PerfMonger is:
|
37
|
+
|
38
|
+
* Run `perfmonger record` to record performance information logs
|
39
|
+
* Run `perfmonger play` to show performance information logs in JSON format
|
40
|
+
|
41
|
+
`perfmonger play` repatedly prints records of system performance including CPU
|
42
|
+
usages, disk usages, and network usages. One line includes only one record, so
|
43
|
+
you can easily process output records with `jq`, or any scripting languages like
|
44
|
+
Ruby, Python, and etc.
|
45
|
+
|
46
|
+
Pretty-printed structure of a record is as follows:
|
47
|
+
|
48
|
+
```
|
49
|
+
{"time": 1500043743.504, # timestamp in unix epoch time
|
50
|
+
"cpu": { # CPU usages
|
51
|
+
"num_core": 2, # the number of cores
|
52
|
+
"all": { # aggregated CPU usage (max = num_core * 100%)
|
53
|
+
"usr": 50.0,
|
54
|
+
"sys": 50.0,
|
55
|
+
"idle": 100.0,
|
56
|
+
...
|
57
|
+
},
|
58
|
+
"cores": [ # Usage of each CPU core
|
59
|
+
{
|
60
|
+
"usr": 25.0,
|
61
|
+
"sys": 25.0,
|
62
|
+
"idle": 50.0,
|
63
|
+
...
|
64
|
+
},
|
65
|
+
{
|
66
|
+
"usr": 25.0,
|
67
|
+
"sys": 25.0,
|
68
|
+
"idle": 50.0,
|
69
|
+
...
|
70
|
+
}
|
71
|
+
]
|
72
|
+
},
|
73
|
+
"disk": { # Disk usages
|
74
|
+
"devices": ["sda"], # List of disk devices
|
75
|
+
"sda": { # Usage of device 'sda'
|
76
|
+
"riops": 10.0, # The number of read I/O per second
|
77
|
+
"wiops": 20.0, # The number of write I/O per second
|
78
|
+
"rkbyteps": 80.0, # Read transfer rate in KB/s
|
79
|
+
"wkbyteps": 160.0, # Write transfer rate in KB/s
|
80
|
+
...
|
81
|
+
}
|
82
|
+
"total": { # Aggregated usage of all devices
|
83
|
+
"riops": 10.0,
|
84
|
+
"wiops": 20.0,
|
85
|
+
"rkbyteps": 80.0,
|
86
|
+
"wkbyteps": 160.0,
|
87
|
+
...
|
88
|
+
}
|
89
|
+
}
|
90
|
+
}
|
91
|
+
```
|
92
|
+
|
93
|
+
|
94
|
+
## Typical use cases
|
95
|
+
|
96
|
+
### `perfmonger live`: live performance monitoring
|
97
|
+
|
98
|
+
$ perfmonger live
|
33
99
|
|
34
100
|
### Monitor IO performance of /dev/sda for each 0.1 second
|
35
101
|
|
@@ -42,19 +108,3 @@ Note: You need Cutter unit testing framework for building/running tests.
|
|
42
108
|
### Monitor CPU usage and IO performance of /dev/sda, sdb for each 0.1 second
|
43
109
|
|
44
110
|
$ perfmonger record -i 0.1 -d sda -d sdb
|
45
|
-
|
46
|
-
### Plot CPU and IOPS
|
47
|
-
|
48
|
-
$ perfmonger record -i 0.1 -C -d sda > /tmp/perfmonger.log & sleep 10; pkill perfmonger
|
49
|
-
$ perfmonger plot -o /path/to/output_dir/ -Tpng /tmp/perfmonger.log
|
50
|
-
$ display /path/to/output_dir/read-iops.png
|
51
|
-
$ display /path/to/output_dir/cpu.png
|
52
|
-
|
53
|
-

|
54
|
-

|
55
|
-
|
56
|
-
## Special Thanks
|
57
|
-
|
58
|
-
Large portion of PerfMonger comes from
|
59
|
-
[SYSSTAT](http://sebastien.godard.pagesperso-orange.fr/) codebase. Thanks for
|
60
|
-
their great work.
|
data/Rakefile
CHANGED
@@ -7,7 +7,7 @@ task :default => [:spec, :test_core]
|
|
7
7
|
desc "Run all specs in spec directory"
|
8
8
|
RSpec::Core::RakeTask.new(:spec)
|
9
9
|
|
10
|
-
task :spec => [:
|
10
|
+
task :spec => [:cross_build_core]
|
11
11
|
|
12
12
|
desc "Cross build core recorder/player"
|
13
13
|
task :cross_build_core do
|
@@ -18,20 +18,31 @@ task :cross_build_core do
|
|
18
18
|
end
|
19
19
|
end
|
20
20
|
|
21
|
-
desc "Self build core recorder/player"
|
22
|
-
task :self_build_core do
|
23
|
-
Dir.chdir("./core") do
|
24
|
-
sh "./build.sh -"
|
25
|
-
end
|
26
|
-
end
|
27
|
-
|
28
21
|
task :build => :cross_build_core
|
29
22
|
|
23
|
+
desc "Install Golang libraries"
|
24
|
+
task :go_get do
|
25
|
+
sh "go get -u github.com/hayamiz/go-projson"
|
26
|
+
sh "go get -u github.com/hayamiz/perfmonger/core/subsystem"
|
27
|
+
sh "go get -u golang.org/x/crypto/ssh/terminal"
|
28
|
+
sh "go get -u github.com/mattn/go-isatty"
|
29
|
+
sh "go get -u github.com/nsf/termbox-go"
|
30
|
+
sh "go get -u github.com/jroimartin/gocui"
|
31
|
+
end
|
32
|
+
|
30
33
|
desc "Run tests of core recorder/player"
|
31
|
-
task :test_core do
|
34
|
+
task :test_core => [:cross_build_core] do
|
32
35
|
Dir.chdir("./core/subsystem") do
|
33
36
|
sh "go test -v -cover"
|
37
|
+
|
38
|
+
# running static analysis
|
39
|
+
sh "go vet *.go"
|
34
40
|
end
|
41
|
+
|
42
|
+
Dir.chdir("./core") do
|
43
|
+
sh "go vet *.go"
|
44
|
+
end
|
45
|
+
|
35
46
|
end
|
36
47
|
|
37
48
|
desc "Removed generated files"
|
data/core/Makefile
CHANGED
@@ -9,22 +9,6 @@ GO_SRC := utils.go
|
|
9
9
|
all: build
|
10
10
|
|
11
11
|
|
12
|
-
../lib/exec/perfmonger-recorder_linux_386: perfmonger-recorder.go $(GO_DEPS)
|
13
|
-
go build -o $@ perfmonger-recorder.go $(GO_SRC)
|
14
|
-
|
15
|
-
|
16
|
-
../lib/exec/perfmonger-player_linux_386: perfmonger-player.go $(GO_DEPS)
|
17
|
-
go build -o $@ perfmonger-player.go $(GO_SRC)
|
18
|
-
|
19
|
-
|
20
|
-
../lib/exec/perfmonger-summarizer_linux_386: perfmonger-summarizer.go $(GO_DEPS)
|
21
|
-
go build -o $@ perfmonger-summarizer.go $(GO_SRC)
|
22
|
-
|
23
|
-
|
24
|
-
../lib/exec/perfmonger-plot-formatter_linux_386: perfmonger-plot-formatter.go $(GO_DEPS)
|
25
|
-
go build -o $@ perfmonger-plot-formatter.go $(GO_SRC)
|
26
|
-
|
27
|
-
|
28
12
|
../lib/exec/perfmonger-recorder_linux_amd64: perfmonger-recorder.go $(GO_DEPS)
|
29
13
|
go build -o $@ perfmonger-recorder.go $(GO_SRC)
|
30
14
|
|
@@ -33,6 +17,10 @@ all: build
|
|
33
17
|
go build -o $@ perfmonger-player.go $(GO_SRC)
|
34
18
|
|
35
19
|
|
20
|
+
../lib/exec/perfmonger-viewer_linux_amd64: perfmonger-viewer.go $(GO_DEPS)
|
21
|
+
go build -o $@ perfmonger-viewer.go $(GO_SRC)
|
22
|
+
|
23
|
+
|
36
24
|
../lib/exec/perfmonger-summarizer_linux_amd64: perfmonger-summarizer.go $(GO_DEPS)
|
37
25
|
go build -o $@ perfmonger-summarizer.go $(GO_SRC)
|
38
26
|
|
@@ -49,6 +37,10 @@ all: build
|
|
49
37
|
go build -o $@ perfmonger-player.go $(GO_SRC)
|
50
38
|
|
51
39
|
|
40
|
+
../lib/exec/perfmonger-viewer_darwin_amd64: perfmonger-viewer.go $(GO_DEPS)
|
41
|
+
go build -o $@ perfmonger-viewer.go $(GO_SRC)
|
42
|
+
|
43
|
+
|
52
44
|
../lib/exec/perfmonger-summarizer_darwin_amd64: perfmonger-summarizer.go $(GO_DEPS)
|
53
45
|
go build -o $@ perfmonger-summarizer.go $(GO_SRC)
|
54
46
|
|
@@ -57,8 +49,8 @@ all: build
|
|
57
49
|
go build -o $@ perfmonger-plot-formatter.go $(GO_SRC)
|
58
50
|
|
59
51
|
|
60
|
-
build: ../lib/exec/perfmonger-
|
52
|
+
build: ../lib/exec/perfmonger-recorder_linux_amd64 ../lib/exec/perfmonger-player_linux_amd64 ../lib/exec/perfmonger-viewer_linux_amd64 ../lib/exec/perfmonger-summarizer_linux_amd64 ../lib/exec/perfmonger-plot-formatter_linux_amd64 ../lib/exec/perfmonger-recorder_darwin_amd64 ../lib/exec/perfmonger-player_darwin_amd64 ../lib/exec/perfmonger-viewer_darwin_amd64 ../lib/exec/perfmonger-summarizer_darwin_amd64 ../lib/exec/perfmonger-plot-formatter_darwin_amd64
|
61
53
|
|
62
54
|
clean:
|
63
|
-
rm -f ../lib/exec/perfmonger-
|
55
|
+
rm -f ../lib/exec/perfmonger-recorder_linux_amd64 ../lib/exec/perfmonger-player_linux_amd64 ../lib/exec/perfmonger-viewer_linux_amd64 ../lib/exec/perfmonger-summarizer_linux_amd64 ../lib/exec/perfmonger-plot-formatter_linux_amd64 ../lib/exec/perfmonger-recorder_darwin_amd64 ../lib/exec/perfmonger-player_darwin_amd64 ../lib/exec/perfmonger-viewer_darwin_amd64 ../lib/exec/perfmonger-summarizer_darwin_amd64 ../lib/exec/perfmonger-plot-formatter_darwin_amd64
|
64
56
|
|
data/core/build.sh
CHANGED
@@ -28,7 +28,7 @@ if [[ $1 = "-" ]]; then
|
|
28
28
|
TARGET=("${os} ${arch}")
|
29
29
|
else
|
30
30
|
# cross build
|
31
|
-
TARGET=("linux
|
31
|
+
TARGET=("linux amd64" "darwin amd64")
|
32
32
|
fi
|
33
33
|
|
34
34
|
set -e
|
@@ -57,7 +57,7 @@ for idx in $(seq 0 $((${#TARGET[@]}-1))); do
|
|
57
57
|
export var_GOOS=$1
|
58
58
|
export var_GOARCH=$2
|
59
59
|
|
60
|
-
for subcmd in recorder player summarizer plot-formatter; do
|
60
|
+
for subcmd in recorder player viewer summarizer plot-formatter; do
|
61
61
|
TARGETS+=(../lib/exec/perfmonger-${subcmd}_${var_GOOS}_${var_GOARCH})
|
62
62
|
|
63
63
|
cat <<EOF >> $makefile
|
data/core/perfmonger-player.go
CHANGED
@@ -4,39 +4,38 @@ package main
|
|
4
4
|
|
5
5
|
import (
|
6
6
|
"bufio"
|
7
|
-
"bytes"
|
8
7
|
"encoding/gob"
|
8
|
+
"flag"
|
9
9
|
"fmt"
|
10
10
|
"io"
|
11
11
|
"os"
|
12
12
|
|
13
|
+
projson "github.com/hayamiz/go-projson"
|
13
14
|
ss "github.com/hayamiz/perfmonger/core/subsystem"
|
14
15
|
)
|
15
16
|
|
16
|
-
|
17
|
+
type PlayerOption struct {
|
18
|
+
logfile string
|
19
|
+
color bool
|
20
|
+
pretty bool
|
21
|
+
}
|
22
|
+
|
23
|
+
var option PlayerOption
|
24
|
+
var init_rec ss.StatRecord
|
25
|
+
|
26
|
+
func showCpuStat(printer *projson.JsonPrinter, prev_rec *ss.StatRecord, cur_rec *ss.StatRecord) error {
|
17
27
|
cusage, err := ss.GetCpuUsage(prev_rec.Cpu, cur_rec.Cpu)
|
18
28
|
if err != nil {
|
19
29
|
return err
|
20
30
|
}
|
21
|
-
|
22
|
-
|
31
|
+
|
32
|
+
printer.PutKey("cpu")
|
33
|
+
cusage.WriteJsonTo(printer)
|
23
34
|
|
24
35
|
return nil
|
25
36
|
}
|
26
37
|
|
27
|
-
func showInterruptStat(
|
28
|
-
// intr_usage, err := ss.GetInterruptUsage(
|
29
|
-
// prev_rec.Time, prev_rec.Interrupt,
|
30
|
-
// cur_rec.Time, cur_rec.Interrupt)
|
31
|
-
// if err != nil {
|
32
|
-
// return err
|
33
|
-
// }
|
34
|
-
//
|
35
|
-
// buffer.WriteString(`,"intr":`)
|
36
|
-
// intr_usage.WriteJsonTo(buffer)
|
37
|
-
//
|
38
|
-
// return nil
|
39
|
-
|
38
|
+
func showInterruptStat(printer *projson.JsonPrinter, prev_rec *ss.StatRecord, cur_rec *ss.StatRecord) error {
|
40
39
|
intr_usage, err := ss.GetInterruptUsage(
|
41
40
|
prev_rec.Time, prev_rec.Interrupt,
|
42
41
|
cur_rec.Time, cur_rec.Interrupt)
|
@@ -44,13 +43,13 @@ func showInterruptStat(buffer *bytes.Buffer, prev_rec *ss.StatRecord, cur_rec *s
|
|
44
43
|
return err
|
45
44
|
}
|
46
45
|
|
47
|
-
|
48
|
-
intr_usage.WriteJsonTo(
|
46
|
+
printer.PutKey("intr")
|
47
|
+
intr_usage.WriteJsonTo(printer)
|
49
48
|
|
50
49
|
return nil
|
51
50
|
}
|
52
51
|
|
53
|
-
func showDiskStat(
|
52
|
+
func showDiskStat(printer *projson.JsonPrinter, prev_rec *ss.StatRecord, cur_rec *ss.StatRecord) error {
|
54
53
|
dusage, err := ss.GetDiskUsage(
|
55
54
|
prev_rec.Time, prev_rec.Disk,
|
56
55
|
cur_rec.Time, cur_rec.Disk)
|
@@ -58,13 +57,14 @@ func showDiskStat(buffer *bytes.Buffer, prev_rec *ss.StatRecord, cur_rec *ss.Sta
|
|
58
57
|
return err
|
59
58
|
}
|
60
59
|
|
61
|
-
|
62
|
-
|
60
|
+
printer.PutKey("disk")
|
61
|
+
|
62
|
+
dusage.WriteJsonTo(printer)
|
63
63
|
|
64
64
|
return nil
|
65
65
|
}
|
66
66
|
|
67
|
-
func showNetStat(
|
67
|
+
func showNetStat(printer *projson.JsonPrinter, prev_rec *ss.StatRecord, cur_rec *ss.StatRecord) error {
|
68
68
|
dusage, err := ss.GetNetUsage(
|
69
69
|
prev_rec.Time, prev_rec.Net,
|
70
70
|
cur_rec.Time, cur_rec.Net,
|
@@ -73,52 +73,96 @@ func showNetStat(buffer *bytes.Buffer, prev_rec *ss.StatRecord, cur_rec *ss.Stat
|
|
73
73
|
return err
|
74
74
|
}
|
75
75
|
|
76
|
-
|
77
|
-
|
76
|
+
printer.PutKey("net")
|
77
|
+
|
78
|
+
dusage.WriteJsonTo(printer)
|
79
|
+
|
80
|
+
return nil
|
81
|
+
}
|
82
|
+
|
83
|
+
func showMemStat(printer *projson.JsonPrinter, cur_rec *ss.StatRecord) error {
|
84
|
+
musage, err := ss.GetMemUsage(cur_rec.Mem)
|
85
|
+
if err != nil {
|
86
|
+
return err
|
87
|
+
}
|
88
|
+
|
89
|
+
printer.PutKey("mem")
|
90
|
+
|
91
|
+
musage.WriteJsonTo(printer)
|
78
92
|
|
79
93
|
return nil
|
80
94
|
}
|
81
95
|
|
82
|
-
func showStat(
|
83
|
-
|
96
|
+
func showStat(printer *projson.JsonPrinter, prev_rec *ss.StatRecord, cur_rec *ss.StatRecord) error {
|
97
|
+
printer.Reset()
|
98
|
+
if option.pretty {
|
99
|
+
printer.SetStyle(projson.SmartStyle)
|
100
|
+
}
|
101
|
+
if option.color {
|
102
|
+
printer.SetColor(true)
|
103
|
+
}
|
104
|
+
printer.BeginObject()
|
105
|
+
printer.PutKey("time")
|
106
|
+
printer.PutFloatFmt(float64(cur_rec.Time.UnixNano())/1e9, "%.3f")
|
107
|
+
printer.PutKey("elapsed_time")
|
108
|
+
printer.PutFloatFmt((float64(cur_rec.Time.UnixNano())-float64(init_rec.Time.UnixNano()))/1e9,
|
109
|
+
"%.3f")
|
110
|
+
|
84
111
|
if cur_rec.Cpu != nil {
|
85
|
-
err := showCpuStat(
|
112
|
+
err := showCpuStat(printer, prev_rec, cur_rec)
|
86
113
|
if err != nil {
|
87
114
|
return err
|
88
115
|
}
|
89
116
|
}
|
90
117
|
if cur_rec.Interrupt != nil {
|
91
|
-
err := showInterruptStat(
|
118
|
+
err := showInterruptStat(printer, prev_rec, cur_rec)
|
92
119
|
if err != nil {
|
93
120
|
return err
|
94
121
|
}
|
95
122
|
}
|
96
123
|
if cur_rec.Disk != nil {
|
97
|
-
err := showDiskStat(
|
124
|
+
err := showDiskStat(printer, prev_rec, cur_rec)
|
98
125
|
if err != nil {
|
99
126
|
return err
|
100
127
|
}
|
101
128
|
}
|
102
129
|
if cur_rec.Net != nil {
|
103
|
-
err := showNetStat(
|
130
|
+
err := showNetStat(printer, prev_rec, cur_rec)
|
131
|
+
if err != nil {
|
132
|
+
return err
|
133
|
+
}
|
134
|
+
}
|
135
|
+
if cur_rec.Mem != nil {
|
136
|
+
err := showMemStat(printer, cur_rec)
|
104
137
|
if err != nil {
|
105
138
|
return err
|
106
139
|
}
|
107
140
|
}
|
108
|
-
|
141
|
+
|
142
|
+
printer.FinishObject()
|
109
143
|
|
110
144
|
return nil
|
111
145
|
}
|
112
146
|
|
147
|
+
func parseArgs() {
|
148
|
+
flag.BoolVar(&option.color, "color", false, "Use colored JSON output")
|
149
|
+
flag.BoolVar(&option.pretty, "pretty", false, "Use human readable JSON output")
|
150
|
+
|
151
|
+
flag.Parse()
|
152
|
+
|
153
|
+
option.logfile = flag.Arg(0)
|
154
|
+
}
|
155
|
+
|
113
156
|
func main() {
|
114
|
-
args := os.Args
|
115
157
|
var in *os.File
|
116
158
|
var out *bufio.Writer
|
117
159
|
|
118
|
-
|
160
|
+
parseArgs()
|
161
|
+
|
162
|
+
if option.logfile == "" {
|
119
163
|
in = os.Stdin
|
120
164
|
} else {
|
121
|
-
f, err := os.Open(
|
165
|
+
f, err := os.Open(option.logfile)
|
122
166
|
if err != nil {
|
123
167
|
panic(err)
|
124
168
|
}
|
@@ -159,9 +203,10 @@ func main() {
|
|
159
203
|
} else if err != nil {
|
160
204
|
panic(err)
|
161
205
|
}
|
206
|
+
init_rec = records[curr]
|
162
207
|
curr ^= 1
|
163
208
|
|
164
|
-
|
209
|
+
printer := projson.NewPrinter()
|
165
210
|
for {
|
166
211
|
prev_rec := &records[curr^1]
|
167
212
|
cur_rec := &records[curr]
|
@@ -173,21 +218,26 @@ func main() {
|
|
173
218
|
panic(err)
|
174
219
|
}
|
175
220
|
|
176
|
-
err = showStat(
|
221
|
+
err = showStat(printer, prev_rec, cur_rec)
|
177
222
|
if err != nil {
|
178
|
-
|
223
|
+
printer.Reset()
|
179
224
|
fmt.Fprintln(os.Stderr, "skip by err")
|
180
225
|
continue
|
181
226
|
}
|
182
227
|
|
183
|
-
|
228
|
+
if str, err := printer.String(); err != nil {
|
229
|
+
fmt.Println("error", err)
|
230
|
+
fmt.Println(str)
|
231
|
+
} else {
|
232
|
+
_, err = out.WriteString(str + "\n")
|
233
|
+
}
|
184
234
|
err = out.Flush()
|
185
235
|
if err != nil {
|
186
236
|
// stdout is closed
|
187
237
|
break
|
188
238
|
}
|
189
239
|
|
190
|
-
|
240
|
+
printer.Reset()
|
191
241
|
|
192
242
|
curr ^= 1
|
193
243
|
}
|