cmogstored 1.8.1 - use default system stack size
[cmogstored.git] / test / mgmt-iostat.rb
blob947f9b072d02b67d9e02e7fcb771f37b5246a61f
1 #!/usr/bin/env ruby
2 # -*- encoding: binary -*-
3 # Copyright (C) 2012-2020 all contributors <cmogstored-public@yhbt.net>
4 # License: GPL-3.0+ <https://www.gnu.org/licenses/gpl-3.0.txt>
5 require 'test/test_helper'
6 require 'timeout'
8 class TestMgmtIostat < Test::Unit::TestCase
9   TEST_PATH = File.dirname(__FILE__) + ":#{ENV['PATH']}"
10   RUBY = ENV["RUBY"] || "ruby"
12   def iostat_mock
13     "#{RUBY} #{File.dirname(__FILE__)}/iostat-mock.rb"
14   end
16   def setup
17     @iostat_pid = Tempfile.new('testt-iostat-pid')
18     @tmpdir = Dir.mktmpdir('cmogstored-mgmt-iostat-test')
19     @host = TEST_HOST
20     srv = TCPServer.new(@host, 0)
21     @port = srv.addr[1]
22     srv.close
23     cmd = [ "cmogstored", "--docroot=#@tmpdir", "--mgmtlisten=#@host:#@port",
24             "--maxconns=500" ]
25     vg = ENV["VALGRIND"] and cmd = vg.split(/\s+/).concat(cmd)
26     @cmd = cmd
27     @pid = nil
28     @to_close = []
29   end
31   def teardown
32     @to_close.each { |io| io.close unless io.closed? }
33     if @pid
34       Process.kill(:QUIT, @pid) rescue nil
35       _, status = Process.waitpid2(@pid)
36       assert status.success?, status.inspect
37     end
38     FileUtils.rm_rf(@tmpdir)
39   end
41   def __test_iostat_dies(workers = false)
42     Dir.mkdir "#@tmpdir/dev666"
43     err = Tempfile.new('err')
44     @pid = fork do
45       ENV["PATH"] = TEST_PATH
46       ENV["MOG_IOSTAT_CMD"] = "#{iostat_mock} #{@iostat_pid.path} slow"
47       $stderr.reopen(err.path, 'a')
48       @cmd << workers if workers
49       exec(*@cmd)
50     end
51     iostat_pid = nil
52     Timeout.timeout(30) do
53       begin
54         iostat_pid = @iostat_pid.read.to_i
55       end while iostat_pid == 0 && sleep(0.05)
56       Process.kill(:TERM, iostat_pid)
57     end
59     expect = %r{iostat done \(pid=#{iostat_pid}, status=\d}
60     Timeout.timeout(30) do
61       loop do
62         stderr = File.read(err.path)
63         break if stderr =~ expect
64         sleep 0.05
65       end
66     end
67   ensure
68     err.close!
69   end
71   def test_iostat_dies
72     __test_iostat_dies
73   end
75   def test_iostat_dies_with_workers
76     __test_iostat_dies("--worker-processes=1")
77   end
79   def test_iostat_fast
80     Dir.mkdir "#@tmpdir/dev666"
81     @pid = fork do
82       ENV["PATH"] = TEST_PATH
83       ENV["MOG_IOSTAT_CMD"] = "#{iostat_mock} #{@iostat_pid.path} fast"
84       exec(*@cmd)
85     end
87     og = get_client
88     og.write "watch\n"
89     threads = []
90     nr = RUBY_PLATFORM =~ /linux/ ? 400 : 10
91     nr.times do
92       threads << Thread.new do
93         c = get_client
94         assert_equal 6, c.write("watch\n")
95         100.times { assert_kind_of(String, c.gets) }
96         c
97       end
98     end
100     sleep 1
101     threads.each { |th| th.value.close }
102     assert og.readpartial(16384)
103     sleep 1
104     assert og.read_nonblock(512)
105     sleep 1
106     assert og.read_nonblock(512)
107     iostat_pid = @iostat_pid.read.to_i
108     if iostat_pid > 0
109       Process.kill(:TERM, iostat_pid)
110     end
111   end
113   def test_iostat_bursty1
114     iostat_edge_case("bursty1")
115   end
117   def test_iostat_bursty2
118     iostat_edge_case("bursty2")
119   end
121   def test_iostat_slow
122     iostat_edge_case("slow")
123   end
125   def iostat_edge_case(type)
126     Dir.mkdir "#@tmpdir/dev666"
127     @pid = fork do
128       ENV["PATH"] = TEST_PATH
129       ENV["MOG_IOSTAT_CMD"] = "#{iostat_mock} #{@iostat_pid.path} #{type}"
130       exec(*@cmd)
131     end
133     og = get_client
134     og.write "watch\n"
135     5.times do
136       assert_match(/\n$/, x = og.gets)
137       p(x) if $DEBUG
138     end
139     og.close
140   end