lbspec 0.2.8 → 0.2.9

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: bc6f025cf48f9f28b899219aee4782724b75affe
4
- data.tar.gz: bfaaad1d0182f19d0210f329d0a981a19151dad9
3
+ metadata.gz: 662a6f0ca37d759561d0596c7cc3a48626feb60e
4
+ data.tar.gz: 78286a3b3aa79cc0a819e15ba4e0b69e410b2e36
5
5
  SHA512:
6
- metadata.gz: be891f0b85609b354e73c05fdc87bad1b03fa5e099744a25815d9eb2399e7eef34e083227fd00aa09dcc1178a91e0625475ff4fdfd1c3c5d1b5b61ba59b827bb
7
- data.tar.gz: bef0f7f51636c4978f297957ce1853462c81e8dc33fa80db2be973ba89c4ca8515b12ab5b8c21a8869571f55bb724db5f2bfd3508521625d4a33f48de8077f87
6
+ metadata.gz: e1c1fac74410b25045a7c465c33edc1a9549e95ed3fa33dba38388f9439965694cf56e15dd57f0648d1eb8135e2cf6d6b3ae2e3a0b9b07a65525ab5a581b924d
7
+ data.tar.gz: 87da405d23608e193cdc930e269ff4db39e45f99d71fc3d55206cda1f2e85e4ef94096aea2cda68bca7a492209083b7ba2d86f14431070bb0d9be4f0fe6ee6e0
data/README.md CHANGED
@@ -88,6 +88,27 @@ Lbspec::Util.logger = Logger.new('test.log')
88
88
  ```
89
89
 
90
90
  The default Logger show Logger::ERROR level on STDOUT.
91
+ =======
92
+ ### #haelthcheck
93
+ `#healthcheck` tests if a load balancer healthchecks to target nodes.
94
+
95
+ #### chains
96
+ You can use following chains with `#healthcheck`.
97
+
98
+ - include
99
+ - Tests if healthchecks include string.
100
+ - from
101
+ - Tests if healthchecks are from specific address.
102
+ - interval
103
+ - Tests if healthchecks are at intervals of specific time.
104
+ - port
105
+ - Tests if healthchecks are on specified port on target nodes.
106
+ - icmp
107
+ - Tests if healthchecks are icmp.
108
+ - tcp
109
+ - Tests if healthchecks are tcp.
110
+ - udp
111
+ - Tests if healthchecks are udp.
91
112
 
92
113
  ## Requires
93
114
  * Users need to be able to login with ssh to the target nodes.
@@ -156,6 +177,14 @@ describe 'vhost_c:80/test/' do
156
177
  it { should transfer('node_c').http.from('node_a') }
157
178
  end
158
179
 
180
+ describe 'loadbalancer' do
181
+ it { should healthcheck('node_c').include('/test/healthcheck').from('192.168.1.1') }
182
+ end
183
+
184
+ describe 'loadbalancer' do
185
+ it { should healthcheck('node_c').include('/test/healthcheck').interval(5) }
186
+ end
187
+
159
188
  ```
160
189
  ## How it works
161
190
  ### #transfer
@@ -9,27 +9,24 @@ module Lbspec
9
9
 
10
10
  attr_reader :result, :output
11
11
 
12
- def initialize(nodes, port, prove, include_str = nil)
12
+ def initialize(nodes, bpf = nil, prove = nil, include_str = nil,
13
+ term_sec = nil)
13
14
  @nodes = nodes.respond_to?(:each) ? nodes : [nodes]
14
- @port = port ? port : 0
15
- @prove = prove
15
+ @bpf = bpf ? bpf : ''
16
+ @prove = prove ? prove : ''
16
17
  @include_str = include_str
17
- @threads = []
18
- @ssh = []
19
- @nodes_connected = []
20
- @result = false
21
- @output = []
18
+ @term_sec = term_sec ? term_sec : -1
19
+ set_initial_value
22
20
  Util.log.debug("#{self.class} initialized #{inspect}")
23
21
  end
24
22
 
25
23
  def open
26
- @nodes.each do |node|
27
- open_node(node)
28
- end
24
+ @nodes.each { |node| open_node(node) }
29
25
  wait_connected
30
26
  end
31
27
 
32
28
  def close
29
+ sleep 0.5 until capture_done?
33
30
  @threads.each do |t|
34
31
  t.kill
35
32
  end
@@ -38,8 +35,28 @@ module Lbspec
38
35
  end
39
36
  end
40
37
 
38
+ def self.bpf(options = {})
39
+ is_first = true
40
+ filter = ''
41
+
42
+ options.each do |k, v|
43
+ if k && v
44
+ filter << ' and ' unless is_first
45
+ filter << k.to_s.gsub('_', ' ') + ' ' + v.to_s
46
+ is_first = false
47
+ end
48
+ end
49
+ filter
50
+ end
51
+
41
52
  private
42
53
 
54
+ def set_initial_value
55
+ @threads, @ssh, @nodes_connected = [], [], []
56
+ @result = false
57
+ @output = []
58
+ end
59
+
43
60
  def open_node(node)
44
61
  @threads << Thread.new do
45
62
  Net::SSH.start(node, nil, config: true) do |ssh|
@@ -73,18 +90,25 @@ module Lbspec
73
90
 
74
91
  def exec_capture_command(channel, command)
75
92
  whole_data = ''
76
- channel.exec command do |ch, stream, data|
77
- ch.on_data do |c, d|
93
+ @start_sec = Time.now.to_i + 1
94
+ channel.exec command do |ch, _stream , _data|
95
+ ch.on_data do |_c, d|
78
96
  whole_data << d
79
- patterns = [@prove]
80
- patterns << @include_str if @include_str
81
- @result = match_all?(whole_data, patterns)
97
+ @result = match_all?(whole_data)
82
98
  end
99
+ break if capture_done?
83
100
  end
84
101
  whole_data
85
102
  end
86
103
 
87
- def match_all?(string, patterns)
104
+ def capture_done?
105
+ now_sec = Time.now.to_i
106
+ (@term_sec > 0 && now_sec - @start_sec > @term_sec) ? true : @result
107
+ end
108
+
109
+ def match_all?(string)
110
+ patterns = [@prove]
111
+ patterns << @include_str if @include_str
88
112
  num_patterns, num_match = 0, 0
89
113
  patterns.each do |pat|
90
114
  num_patterns += 1
@@ -94,8 +118,7 @@ module Lbspec
94
118
  end
95
119
 
96
120
  def capture_command
97
- port_str = @port > 0 ? "port #{@port}" : ''
98
- "sudo ngrep -W byline #{@prove} #{port_str} | grep -v \"match:\""
121
+ "sudo ngrep -W byline #{@prove} #{@bpf} | grep -v \"match:\""
99
122
  end
100
123
  end
101
124
  end
@@ -0,0 +1,90 @@
1
+ # -*- encoding: utf-8 -*-
2
+ require 'lbspec'
3
+
4
+ RSpec::Matchers.define :healthcheck do |nodes|
5
+ match do |lb|
6
+ @lb = lb
7
+ @nodes = nodes
8
+ bpf = Lbspec::Capture.bpf(port: @port,
9
+ src_host: @from,
10
+ protocol: @protocol)
11
+ capture =
12
+ Lbspec::Capture.new(nodes, bpf, nil, @include_str, @interval)
13
+ capture.open
14
+ @output_capture = capture.output
15
+ capture.close
16
+ capture.result
17
+ end
18
+
19
+ chain :include do |str|
20
+ @include_str = str
21
+ @chain_str = Lbspec::Util.add_string(@chain_str, " including #{str}")
22
+ end
23
+
24
+ chain :from do |from|
25
+ @from = from
26
+ @chain_str = Lbspec::Util.add_string(@chain_str, " from #{from}")
27
+ end
28
+
29
+ chain :interval do |second|
30
+ @interval = second
31
+ @chain_str = Lbspec::Util.add_string(@chain_str,
32
+ " at interval of #{second} sec")
33
+ end
34
+
35
+ chain :port do |port|
36
+ @port = port
37
+ @chain_str = Lbspec::Util.add_string(@chain_str, " port #{port}")
38
+ end
39
+
40
+ chain :icmp do
41
+ @protocol = :icmp
42
+ @chain_str = Lbspec::Util.add_string(@chain_str, ' icmp')
43
+ end
44
+
45
+ chain :tcp do
46
+ @protocol = :tcp
47
+ @chain_str = Lbspec::Util.add_string(@chain_str, ' tcp')
48
+ end
49
+
50
+ chain :udp do
51
+ @protocol = :udp
52
+ @chain_str = Lbspec::Util.add_string(@chain_str, ' udp')
53
+ end
54
+
55
+ chain :options do |options|
56
+ @options = options
57
+ end
58
+
59
+ description do
60
+ "healthcheck #{@nodes}#{@chain_str}."
61
+ end
62
+
63
+ failure_message_for_should do
64
+ result_string
65
+ end
66
+
67
+ failure_message_for_should_not do
68
+ negative = true
69
+ result_string(negative)
70
+ end
71
+
72
+ def result_string(negative = false)
73
+ negation = negative ? '' : ' not'
74
+ result = "expected #{@lb} to healthcheck to"
75
+ result << @nodes.to_s + @chain_str
76
+ result << ", but did#{negation}.\n"
77
+ result << "\ncaptured:\n"
78
+ result << result_capture
79
+ result
80
+ end
81
+
82
+ def result_capture
83
+ result = ''
84
+ @output_capture.each do |o|
85
+ result << o[:node].gsub(/^/, ' ') + "\n"
86
+ result << o[:output].gsub(/^/, ' ') + "\n"
87
+ end
88
+ result
89
+ end
90
+ end
@@ -10,8 +10,9 @@ RSpec::Matchers.define :transfer do |nodes|
10
10
  log.debug("#transfer(#{nodes.inspect}) is called")
11
11
  @vhost = vhost
12
12
  prove = Lbspec::Util.create_prove
13
+ bpf = Lbspec::Capture.bpf(port: @port)
13
14
  capture =
14
- Lbspec::Capture.new(nodes, @port, prove, @include_str)
15
+ Lbspec::Capture.new(nodes, bpf, prove, @include_str)
15
16
  capture.open
16
17
  request =
17
18
  Lbspec::Request.new(vhost, @from,
@@ -1,5 +1,5 @@
1
1
  # -*- encoding: utf-8 -*-
2
2
  # Lbspec is an RSpec plugin for easy Loadbalancer testing.
3
3
  module Lbspec
4
- VERSION = '0.2.8'
4
+ VERSION = '0.2.9'
5
5
  end
data/lib/lbspec.rb CHANGED
@@ -2,6 +2,7 @@
2
2
  require 'lbspec/version'
3
3
  require 'lbspec/transfer'
4
4
  require 'lbspec/respond'
5
+ require 'lbspec/healthcheck'
5
6
  require 'lbspec/request'
6
7
  require 'lbspec/capture'
7
8
  require 'lbspec/util'
@@ -0,0 +1,48 @@
1
+ # -*- encoding: utf-8 -*-
2
+ require 'spec_helper'
3
+ require 'net/ssh'
4
+
5
+ describe '#healthcheck' do
6
+ before(:each) do
7
+ include_str = 'X-Test: 1'
8
+ channel_connected = double('channel_connected')
9
+ channel_connected.stub(:request_pty).and_yield(channel_connected, true)
10
+ channel_connected.stub(:exec).and_yield(channel_connected, nil, nil)
11
+ channel_connected.stub(:on_data)
12
+ .and_yield(nil, include_str)
13
+ .and_yield(nil, include_str)
14
+ ssh_connected = double('ssh_connected')
15
+ ssh_connected.stub(:open_channel).and_yield(channel_connected)
16
+ ssh_connected.stub(:closed?).and_return(false)
17
+ ssh_connected.stub(:close)
18
+ ssh_connected.stub(:exec!).and_return(true)
19
+ Net::SSH.stub(:start).and_yield(ssh_connected).and_return(ssh_connected)
20
+ Kernel.stub(:system).and_return true
21
+ Kernel.stub(:`).and_return(include_str) # `
22
+ end
23
+
24
+ it 'should test loadbalancer healthchecks' do
25
+ 'loadbalancer'.should healthcheck('node_a')
26
+ end
27
+ it 'should test loadbalancer healthchecks include string' do
28
+ 'loadbalancer'.should healthcheck('node_a').include('X-Test')
29
+ end
30
+ it 'should test loadbalancer healthchecks from specified host' do
31
+ 'loadbalancer'.should healthcheck('node_a').from('X-Test')
32
+ end
33
+ it 'should test loadbalancer healthchecks at specified interval' do
34
+ 'loadbalancer'.should healthcheck('node_a').interval(5)
35
+ end
36
+ it 'should test loadbalancer healthchecks specified port' do
37
+ 'loadbalancer'.should healthcheck('node_a').port(80)
38
+ end
39
+ it 'should test loadbalancer healthchecks icmp' do
40
+ 'loadbalancer'.should healthcheck('node_a').icmp
41
+ end
42
+ it 'should test loadbalancer healthchecks tcp' do
43
+ 'loadbalancer'.should healthcheck('node_a').tcp
44
+ end
45
+ it 'should test loadbalancer healthchecks udp' do
46
+ 'loadbalancer'.should healthcheck('node_a').udp
47
+ end
48
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: lbspec
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.8
4
+ version: 0.2.9
5
5
  platform: ruby
6
6
  authors:
7
7
  - OTA Hiroshi
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-04-24 00:00:00.000000000 Z
11
+ date: 2014-05-15 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -144,6 +144,7 @@ files:
144
144
  - lbspec.gemspec
145
145
  - lib/lbspec.rb
146
146
  - lib/lbspec/capture.rb
147
+ - lib/lbspec/healthcheck.rb
147
148
  - lib/lbspec/request.rb
148
149
  - lib/lbspec/respond.rb
149
150
  - lib/lbspec/transfer.rb
@@ -152,6 +153,7 @@ files:
152
153
  - rubocop-todo.yml
153
154
  - sample/lb_spec.rb
154
155
  - sample/spec_helper.rb
156
+ - spec/lbspec_healthcheck_spec.rb
155
157
  - spec/lbspec_respond_spec.rb
156
158
  - spec/lbspec_spec.rb
157
159
  - spec/lbspec_transfer_spec.rb
@@ -177,11 +179,12 @@ required_rubygems_version: !ruby/object:Gem::Requirement
177
179
  version: '0'
178
180
  requirements: []
179
181
  rubyforge_project:
180
- rubygems_version: 2.2.2
182
+ rubygems_version: 2.0.14
181
183
  signing_key:
182
184
  specification_version: 4
183
185
  summary: Easily test your Loadbalancers with RSpec.
184
186
  test_files:
187
+ - spec/lbspec_healthcheck_spec.rb
185
188
  - spec/lbspec_respond_spec.rb
186
189
  - spec/lbspec_spec.rb
187
190
  - spec/lbspec_transfer_spec.rb