process-metrics 0.1.1 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: f6eef8073c3bde206609e197c710ff0a3a7b5bb100b9e7e3081ceb1a3cafad4d
4
- data.tar.gz: 8861bf2052c3cd39bc0e1d75682538efdce0c6bc6bbb444a44a4a12a8bbc23bd
3
+ metadata.gz: 7cec50409b679c3cb38ad2951f012f9ec80ebd932af96a27aa8e443724b6f08b
4
+ data.tar.gz: e93c274723c0a744b9b27d38f20e7ca7c430b33ad804d55f706d3ceda30b95b8
5
5
  SHA512:
6
- metadata.gz: 48118f047e6b37cae47ab65b5486c63009efc60379eeaf984bb0076e0a2890ff3be3e4ee6ded12d32dc3e18b805bb04564c590ad6233bef666b8238e88de76d4
7
- data.tar.gz: 21c7a27dc3494df5a7ae7fa830af1bfe8d7989b388534e0b7b6bac1bd4416168a927e7efcfe13faba5abb369ec6ae51181d039f294b614166096a46ad88797b0
6
+ metadata.gz: c81cee9bea7a96472e8e649f6695fafeff89d6c129c0fbc967f4fecac94a5e52818225992d9cce94e75c43abbed8877c1a5da186f14aae3cc56d085c1651c2f2
7
+ data.tar.gz: 72694d4aa9dd22d9b9f3ec82bd66586119c1fc6be7edb278c5263279004b551c0a1d8b7364ab5877d503828d904aab9f58206d72fbec65b5d59ce518e01a36f3
data/README.md CHANGED
@@ -133,6 +133,18 @@ pp metrics
133
133
  # ... snip ...
134
134
  ```
135
135
 
136
+ ### Metrics
137
+
138
+ On some platforms (currently only Linux), additional memory metrics are captured.
139
+
140
+ #### Proportional Set Size
141
+
142
+ The total private memory usage + shared memory usage divided by the number of processes sharing said data.
143
+
144
+ #### Unique Set Size
145
+
146
+ The total private memory usage.
147
+
136
148
  ## Contributing
137
149
 
138
150
  1. Fork it
@@ -0,0 +1,29 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ # Copyright, 2020, by Samuel G. D. Williams. <http://www.codeotaku.com>
5
+ #
6
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
7
+ # of this software and associated documentation files (the "Software"), to deal
8
+ # in the Software without restriction, including without limitation the rights
9
+ # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10
+ # copies of the Software, and to permit persons to whom the Software is
11
+ # furnished to do so, subject to the following conditions:
12
+ #
13
+ # The above copyright notice and this permission notice shall be included in
14
+ # all copies or substantial portions of the Software.
15
+ #
16
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22
+ # THE SOFTWARE.
23
+
24
+ require_relative '../lib/process/metrics/command'
25
+
26
+ begin
27
+ Process::Metrics::Command.call
28
+ rescue Interrupt
29
+ end
@@ -0,0 +1,31 @@
1
+ # Copyright, 2017, by Samuel G. D. Williams. <http://www.codeotaku.com>
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
4
+ # of this software and associated documentation files (the "Software"), to deal
5
+ # in the Software without restriction, including without limitation the rights
6
+ # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7
+ # copies of the Software, and to permit persons to whom the Software is
8
+ # furnished to do so, subject to the following conditions:
9
+ #
10
+ # The above copyright notice and this permission notice shall be included in
11
+ # all copies or substantial portions of the Software.
12
+ #
13
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19
+ # THE SOFTWARE.
20
+
21
+ require_relative 'command/top'
22
+
23
+ module Process
24
+ module Metrics
25
+ module Command
26
+ def self.call(*arguments)
27
+ Top.call(*arguments)
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,177 @@
1
+ # Copyright, 2020, by Samuel G. D. Williams. <http://www.codeotaku.com>
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
4
+ # of this software and associated documentation files (the "Software"), to deal
5
+ # in the Software without restriction, including without limitation the rights
6
+ # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7
+ # copies of the Software, and to permit persons to whom the Software is
8
+ # furnished to do so, subject to the following conditions:
9
+ #
10
+ # The above copyright notice and this permission notice shall be included in
11
+ # all copies or substantial portions of the Software.
12
+ #
13
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19
+ # THE SOFTWARE.
20
+
21
+ require 'samovar'
22
+
23
+ require_relative '../general'
24
+
25
+ require 'console/terminal'
26
+
27
+ module Process
28
+ module Metrics
29
+ module Command
30
+ module Bar
31
+ BLOCK = [
32
+ " ",
33
+ "▏",
34
+ "▎",
35
+ "▍",
36
+ "▌",
37
+ "▋",
38
+ "▊",
39
+ "▉",
40
+ "█",
41
+ ]
42
+
43
+ def self.format(value, width)
44
+ blocks = width * value
45
+ full_blocks = blocks.floor
46
+ partial_block = ((blocks - full_blocks) * BLOCK.size).floor
47
+
48
+ if partial_block.zero?
49
+ BLOCK.last * full_blocks
50
+ else
51
+ "#{BLOCK.last * full_blocks}#{BLOCK[partial_block]}"
52
+ end.ljust(width)
53
+ end
54
+ end
55
+
56
+ class Summary < Samovar::Command
57
+ self.description = "Display a summary of memory usage statistics."
58
+
59
+ options do
60
+ option '--pid <integer>', "Report on a single process id.", type: Integer, required: true
61
+ option '-p/--ppid <integer>', "Report on all children of this process id.", type: Integer, required: true
62
+
63
+ option '--memory-scale <integer>', "Scale maximum memory usage to the specified amount (MiB).", type: Integer, default: 512
64
+ end
65
+
66
+ def terminal
67
+ terminal = Console::Terminal.for($stdout)
68
+
69
+ # terminal[:pid] = terminal.style(:blue)
70
+ terminal[:command] = terminal.style(nil, nil, :bold)
71
+ terminal[:key] = terminal.style(:cyan)
72
+
73
+ terminal[:low] = terminal.style(:green)
74
+ terminal[:medium] = terminal.style(:yellow)
75
+ terminal[:high] = terminal.style(:red)
76
+
77
+ return terminal
78
+ end
79
+
80
+ def format_pcpu(value, terminal)
81
+ if value > 80.0
82
+ intensity = :high
83
+ elsif value > 50.0
84
+ intensity = :medium
85
+ else
86
+ intensity = :low
87
+ end
88
+
89
+ formatted = "%5.1f%% " % value
90
+
91
+ terminal.print(formatted.rjust(10), intensity, "[", Bar.format(value / 100.0, 60), "]", :reset)
92
+ end
93
+
94
+ UNITS = ["KiB", "MiB", "GiB"]
95
+
96
+ def format_size(value, units: UNITS)
97
+ unit = 0
98
+
99
+ while value > 1024.0 && unit < units.size
100
+ value /= 1024.0
101
+ unit += 1
102
+ end
103
+
104
+ return "#{value.round(unit)}#{units[unit]}"
105
+ end
106
+
107
+ def format_memory_usage(value, terminal, scale: @options[:memory_scale])
108
+ if value > (1024.0 * scale * 0.8)
109
+ intensity = :high
110
+ elsif value > (1024.0 * scale * 0.5)
111
+ intensity = :medium
112
+ else
113
+ intensity = :low
114
+ end
115
+
116
+ formatted = (format_size(value) + ' ').rjust(10)
117
+
118
+ terminal.print(formatted, intensity, "[", Bar.format(value / (1024.0 * scale), 60), "]", :reset)
119
+ end
120
+
121
+ def call
122
+ terminal = self.terminal
123
+
124
+ summary = Process::Metrics::General.capture(pid: @options[:pid], ppid: @options[:ppid])
125
+
126
+ format_memory_usage = self.method(:format_memory_usage).curry
127
+ memory_usage = 0
128
+ proportional = true
129
+
130
+ summary.each do |pid, general|
131
+ terminal.print_line(:pid, pid, :reset, " ", :command, general[:command])
132
+
133
+ terminal.print(:key, "Processor Usage: ".rjust(20), :reset)
134
+ format_pcpu(general.pcpu, terminal)
135
+ terminal.print_line
136
+
137
+ if memory = general.memory
138
+ memory_usage += memory.proportional_size
139
+
140
+ terminal.print_line(
141
+ :key, "Memory (PSS): ".rjust(20), :reset,
142
+ format_memory_usage[memory.proportional_size]
143
+ )
144
+
145
+ terminal.print_line(
146
+ :key, "Private (USS): ".rjust(20), :reset,
147
+ format_memory_usage[memory.unique_size]
148
+ )
149
+ else
150
+ memory_usage += general.rsz
151
+ proportional = false
152
+
153
+ terminal.print_line(
154
+ :key, "Memory (RSS): ".rjust(20), :reset,
155
+ format_memory_usage[general.rsz]
156
+ )
157
+ end
158
+ end
159
+
160
+ terminal.print_line("Summary")
161
+
162
+ if proportional
163
+ terminal.print_line(
164
+ :key, "Memory (PSS): ".rjust(20), :reset,
165
+ format_memory_usage[memory_usage]
166
+ )
167
+ else
168
+ terminal.print_line(
169
+ :key, "Memory (RSS): ".rjust(20), :reset,
170
+ format_memory_usage[memory_usage]
171
+ )
172
+ end
173
+ end
174
+ end
175
+ end
176
+ end
177
+ end
@@ -0,0 +1,53 @@
1
+ # Copyright, 2020, by Samuel G. D. Williams. <http://www.codeotaku.com>
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
4
+ # of this software and associated documentation files (the "Software"), to deal
5
+ # in the Software without restriction, including without limitation the rights
6
+ # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7
+ # copies of the Software, and to permit persons to whom the Software is
8
+ # furnished to do so, subject to the following conditions:
9
+ #
10
+ # The above copyright notice and this permission notice shall be included in
11
+ # all copies or substantial portions of the Software.
12
+ #
13
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19
+ # THE SOFTWARE.
20
+
21
+ require 'samovar'
22
+
23
+ require_relative 'summary'
24
+ require_relative '../version'
25
+
26
+ module Process
27
+ module Metrics
28
+ module Command
29
+ class Top < Samovar::Command
30
+ self.description = "Collect memory usage statistics."
31
+
32
+ options do
33
+ option '-h/--help', "Print out help information."
34
+ option '-v/--version', "Print out the application version."
35
+ end
36
+
37
+ nested :command, {
38
+ 'summary' => Summary,
39
+ }, default: 'summary'
40
+
41
+ def call
42
+ if @options[:version]
43
+ puts "#{self.name} v#{VERSION}"
44
+ elsif @options[:help]
45
+ self.print_usage
46
+ else
47
+ @command.call
48
+ end
49
+ end
50
+ end
51
+ end
52
+ end
53
+ end
@@ -49,86 +49,131 @@ module Process
49
49
  pcpu: ->(value){value.to_f},
50
50
  time: self.method(:duration),
51
51
  vsz: ->(value){value.to_i},
52
- rss: ->(value){value.to_i},
52
+ rsz: ->(value){value.to_i},
53
53
  etime: self.method(:duration),
54
54
  command: ->(value){value},
55
55
  }
56
56
 
57
- def self.set(ids)
58
- Set.new(Array(ids))
59
- end
60
-
61
- def self.expand_children(children, hierarchy, pids)
62
- children.each do |pid|
63
- self.expand(pid, hierarchy, pids)
57
+ class General < Struct.new(:pid, :ppid, :pgid, :pcpu, :vsz, :rsz, :time, :etime, :command, :memory)
58
+ def as_json
59
+ {
60
+ pid: self.pid,
61
+ ppid: self.ppid,
62
+ pgid: self.pgid,
63
+ pcpu: self.pcpu,
64
+ vsz: self.vsz,
65
+ rsz: self.rsz,
66
+ time: self.time,
67
+ etime: self.etime,
68
+ command: self.command,
69
+ memory: self.memory&.as_json,
70
+ }
64
71
  end
65
- end
66
-
67
- def self.expand(pid, hierarchy, pids)
68
- unless pids.include?(pid)
69
- pids << pid
70
-
71
- if children = hierarchy.fetch(pid, nil)
72
- self.expand_children(children, hierarchy, pids)
73
- end
74
- end
75
- end
76
-
77
- def self.capture(pid: nil, ppid: nil, ps: PS, fields: FIELDS)
78
- input, output = IO.pipe
79
72
 
80
- arguments = [ps]
81
-
82
- if pid && ppid.nil?
83
- arguments.push("-p", Array(pid).join(','))
84
- else
85
- arguments.push("ax")
73
+ def to_json(*arguments)
74
+ as_json.to_json(*arguments)
86
75
  end
87
76
 
88
- arguments.push("-o", fields.keys.join(','))
89
-
90
- ps_pid = Process.spawn(*arguments, out: output, pgroup: true)
91
-
92
- output.close
77
+ def memory_usage
78
+ if self.memory
79
+ self.memory.proportional_size
80
+ else
81
+ self.rsz
82
+ end
83
+ end
93
84
 
94
- header, *lines = input.readlines.map(&:strip)
85
+ def self.expand_children(children, hierarchy, pids)
86
+ children.each do |pid|
87
+ self.expand(pid, hierarchy, pids)
88
+ end
89
+ end
95
90
 
96
- processes = lines.map do |line|
97
- fields.
98
- zip(line.split(/\s+/, fields.size)).
99
- map{|(key, type), value| [key, type.call(value)]}.
100
- to_h
91
+ def self.expand(pid, hierarchy, pids)
92
+ unless pids.include?(pid)
93
+ pids << pid
94
+
95
+ if children = hierarchy.fetch(pid, nil)
96
+ self.expand_children(children, hierarchy, pids)
97
+ end
98
+ end
101
99
  end
102
100
 
103
- if ppid
104
- pids = Set.new
101
+ def self.build_tree(processes)
105
102
  hierarchy = Hash.new{|h,k| h[k] = []}
106
103
 
107
- processes.each do |process|
108
- unless process[:pid] == ps_pid
109
- hierarchy[process[:ppid]] << process[:pid]
104
+ processes.each_value do |process|
105
+ if ppid = process.ppid
106
+ hierarchy[ppid] << process.pid
110
107
  end
111
108
  end
112
109
 
113
- self.expand_children(Array(pid), hierarchy, pids)
114
- self.expand_children(Array(ppid), hierarchy, pids)
115
-
116
- processes.select! do |process|
117
- pids.include?(process[:pid])
110
+ return hierarchy
111
+ end
112
+
113
+ def self.capture_memory(processes)
114
+ processes.each do |pid, process|
115
+ process.memory = Memory.capture(Array(pid))
118
116
  end
119
117
  end
120
118
 
121
- if Memory.supported?
122
- processes.each do |process|
123
- if pid = process[:pid]
124
- process[:memory] = Memory.capture(Array(process[:pid]))
119
+ def self.capture(pid: nil, ppid: nil, ps: PS, fields: FIELDS)
120
+ input, output = IO.pipe
121
+
122
+ arguments = [ps]
123
+
124
+ if pid && ppid.nil?
125
+ arguments.push("-p", Array(pid).join(','))
126
+ else
127
+ arguments.push("ax")
128
+ end
129
+
130
+ arguments.push("-o", fields.keys.join(','))
131
+
132
+ ps_pid = Process.spawn(*arguments, out: output, pgroup: true)
133
+
134
+ output.close
135
+
136
+ header, *lines = input.readlines.map(&:strip)
137
+
138
+ processes = {}
139
+
140
+ lines.map do |line|
141
+ record = fields.
142
+ zip(line.split(/\s+/, fields.size)).
143
+ map{|(key, type), value| type.call(value)}
144
+
145
+ instance = self.new(*record)
146
+
147
+ processes[instance.pid] = instance
148
+ end
149
+
150
+ if ppid
151
+ pids = Set.new
152
+
153
+ hierarchy = self.build_tree(processes)
154
+
155
+ self.expand_children(Array(pid), hierarchy, pids)
156
+ self.expand_children(Array(ppid), hierarchy, pids)
157
+
158
+ processes.select! do |pid, process|
159
+ if pid != ps_pid
160
+ pids.include?(pid)
161
+ end
125
162
  end
126
163
  end
164
+
165
+ if Memory.supported?
166
+ self.capture_memory(processes)
167
+
168
+ # if pid
169
+ # self.compute_summary(pid, processes)
170
+ # end
171
+ end
172
+
173
+ return processes
174
+ ensure
175
+ Process.wait(ps_pid) if ps_pid
127
176
  end
128
-
129
- return processes
130
- ensure
131
- Process.wait(ps_pid) if ps_pid
132
177
  end
133
178
  end
134
179
  end
@@ -22,28 +22,40 @@
22
22
 
23
23
  module Process
24
24
  module Metrics
25
- module Memory
25
+ class Memory < Struct.new(:map_count, :total_size, :resident_size, :proportional_size, :shared_clean_size, :shared_dirty_size, :private_clean_size, :private_dirty_size, :referenced_size, :anonymous_size, :swap_size, :proportional_swap_size)
26
+
27
+ alias as_json to_h
28
+
29
+ def to_json(*arguments)
30
+ as_json.to_json(*arguments)
31
+ end
32
+
33
+ # The unique set size, the size of completely private (unshared) data.
34
+ def unique_size
35
+ self.private_clean_size + self.private_dirty_size
36
+ end
37
+
26
38
  if File.readable?('/proc/self/smaps')
27
39
  def self.supported?
28
40
  true
29
41
  end
30
42
 
31
43
  MAP = {
32
- "Size" => :total,
33
- "Rss" => :rss,
34
- "Pss" => :pss,
35
- "Shared_Clean" => :shared_clean,
36
- "Shared_Dirty" => :shared_dirty,
37
- "Private_Clean" => :private_clean,
38
- "Private_Dirty" => :private_dirty,
39
- "Referenced" => :referenced,
40
- "Anonymous" => :anonymous,
41
- "Swap" => :swap,
42
- "SwapPss" => :swap_pss,
44
+ "Size" => :total_size,
45
+ "Rss" => :resident_size,
46
+ "Pss" => :proportional_size,
47
+ "Shared_Clean" => :shared_clean_size,
48
+ "Shared_Dirty" => :shared_dirty_size,
49
+ "Private_Clean" => :private_clean_size,
50
+ "Private_Dirty" => :private_dirty_size,
51
+ "Referenced" => :referenced_size,
52
+ "Anonymous" => :anonymous_size,
53
+ "Swap" => :swap_size,
54
+ "SwapPss" => :proportional_swap_size,
43
55
  }
44
56
 
45
57
  def self.capture(pids)
46
- usage = Hash.new{|h,k| h[k] = 0}
58
+ usage = self.new(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0)
47
59
 
48
60
  pids.each do |pid|
49
61
  if lines = File.readlines("/proc/#{pid}/smaps")
@@ -57,13 +69,13 @@ module Process
57
69
  elsif /VmFlags:\s+(?<flags>.*)/ =~ line
58
70
  # It should be possible to extract the number of fibers and each fiber's memory usage.
59
71
  # flags = flags.split(/\s+/)
60
- usage[:maps] += 1
72
+ usage.map_count += 1
61
73
  end
62
74
  end
63
75
  end
64
76
  end
65
77
 
66
- return usage.freeze
78
+ return usage
67
79
  end
68
80
  else
69
81
  def self.supported?
@@ -71,6 +83,7 @@ module Process
71
83
  end
72
84
 
73
85
  def self.capture(pids)
86
+ return self.new
74
87
  end
75
88
  end
76
89
  end
@@ -22,6 +22,6 @@
22
22
 
23
23
  module Process
24
24
  module Metrics
25
- VERSION = "0.1.1"
25
+ VERSION = "0.2.0"
26
26
  end
27
27
  end
@@ -23,6 +23,8 @@ Gem::Specification.new do |spec|
23
23
  spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
24
24
  spec.require_paths = ["lib"]
25
25
 
26
+ spec.add_dependency "console", "~> 1.8"
27
+
26
28
  spec.add_development_dependency "covered"
27
29
  spec.add_development_dependency "bundler"
28
30
  spec.add_development_dependency "rake", "~> 12.0"
metadata CHANGED
@@ -1,15 +1,29 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: process-metrics
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.1
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Samuel Williams
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2019-12-30 00:00:00.000000000 Z
11
+ date: 2020-02-01 00:00:00.000000000 Z
12
12
  dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: console
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '1.8'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '1.8'
13
27
  - !ruby/object:Gem::Dependency
14
28
  name: covered
15
29
  requirement: !ruby/object:Gem::Requirement
@@ -70,8 +84,7 @@ description:
70
84
  email:
71
85
  - samuel.williams@oriontransfer.co.nz
72
86
  executables:
73
- - console
74
- - setup
87
+ - process-metrics
75
88
  extensions: []
76
89
  extra_rdoc_files: []
77
90
  files:
@@ -81,9 +94,11 @@ files:
81
94
  - Gemfile
82
95
  - README.md
83
96
  - Rakefile
84
- - bin/console
85
- - bin/setup
97
+ - bin/process-metrics
86
98
  - lib/process/metrics.rb
99
+ - lib/process/metrics/command.rb
100
+ - lib/process/metrics/command/summary.rb
101
+ - lib/process/metrics/command/top.rb
87
102
  - lib/process/metrics/general.rb
88
103
  - lib/process/metrics/memory.rb
89
104
  - lib/process/metrics/version.rb
@@ -108,7 +123,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
108
123
  - !ruby/object:Gem::Version
109
124
  version: '0'
110
125
  requirements: []
111
- rubygems_version: 3.0.6
126
+ rubygems_version: 3.1.2
112
127
  signing_key:
113
128
  specification_version: 4
114
129
  summary: Provide detailed OS-specific process metrics.
@@ -1,14 +0,0 @@
1
- #!/usr/bin/env ruby
2
-
3
- require "bundler/setup"
4
- require "process/metrics"
5
-
6
- # You can add fixtures and/or initialization code here to make experimenting
7
- # with your gem easier. You can also use a different console, if you like.
8
-
9
- # (If you use this, don't forget to add pry to your Gemfile!)
10
- # require "pry"
11
- # Pry.start
12
-
13
- require "irb"
14
- IRB.start(__FILE__)
data/bin/setup DELETED
@@ -1,8 +0,0 @@
1
- #!/usr/bin/env bash
2
- set -euo pipefail
3
- IFS=$'\n\t'
4
- set -vx
5
-
6
- bundle install
7
-
8
- # Do any other automated setup that you need to do here