itesttool 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/Gemfile ADDED
@@ -0,0 +1,5 @@
1
+ source 'http://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in hoge.gemspec
4
+ gemspec
5
+
data/LICENSE.txt ADDED
@@ -0,0 +1,8 @@
1
+ Copyright (c) 2013 Yohei Kariya
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
4
+
5
+ The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
6
+
7
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
8
+
data/README.md ADDED
@@ -0,0 +1,263 @@
1
+ # itesttool
2
+
3
+ [![Build Status](https://travis-ci.org/bati11/itesttool.png?branch=master)](https://travis-ci.org/bati11/itesttool)
4
+
5
+ WebアプリケーションのEnd-to-Endのテストを自動化するためのツール。
6
+ RSpecにユーティリティを追加して実現してます。
7
+
8
+
9
+ # Install
10
+ cloneしたらBundlerを使って必要なgemをインストールします。
11
+ ~~~~~ {sh}
12
+ $ bundle install --path vendor/bundle
13
+ ~~~~~
14
+ サンプルアプリケーションが起動します。
15
+
16
+ ~~~~~ {sh}
17
+ $ bundle exec ruby sample/app.rb
18
+ ~~~~~
19
+
20
+ 以下のコマンドでサンプルに対するテストを実行します。
21
+
22
+ ~~~~~ {sh}
23
+ $ bundle exec rspec
24
+ ~~~~~
25
+
26
+ テストが通れば準備完了です。
27
+
28
+
29
+ # Usage
30
+ ## GET リクエストを送信する
31
+ GET リクエスト送って、レスポンスコードを確認するには以下のようにします。
32
+ `_given` ブロックでテストの前提条件を書きます。`_given`は、単純にRSpecの`before`の別名です。
33
+ `_when` ブロックでGETリクエストを送ります。
34
+ `_then` ブロック内でres変数を使うことでレスポンスにアクセスできます。
35
+ resは、Net::HTTPResponseオブジェクトです。
36
+
37
+ ~~~~~ {ruby}
38
+ describe 'send GET request' do
39
+ _given {
40
+ headers 'referer' => 'http://local.example.com',
41
+ }
42
+ _when { get 'http://localhost:4567/index' }
43
+ _then {
44
+ res.code.should eq '200'
45
+ }
46
+ end
47
+ ~~~~~
48
+
49
+ ## レスポンスを検証する
50
+ 上の例にもありますが、ステータスコードは`res.code.should eq '200'`と書きます。
51
+ レスポンスボディは`res.body.should eq 'Hello world!'`というように書きます。
52
+
53
+ レスポンスボディが、JSON、XML、HTMLの場合はそれぞれ、JSONPath、XPath、CSSセレクタを用いて要素を検証できます。
54
+ JSONPath、XPathについては、下のサイトを参考にしてください。
55
+ [http://goessner.net/articles/JsonPath/](http://goessner.net/articles/JsonPath/)
56
+
57
+ また、配列に対する検証のために、以下のカスタムマッチャーを定義してます。
58
+ `all`は引数に、matcherを受け取ります。引数で受け取ったmatcherを配列の全要素に適用します。
59
+ `be_one_and`は引数に、matcherを受け取ります。まず配列の要素が1つであることを検証してから引数で受け取ったmatcherを要素に適用します。
60
+ `be_sorted`は配列の要素が、昇順もしくは降順で並んでいるかを検証します。
61
+
62
+ - `all`
63
+ - `be_one_and`
64
+ - `be_sorted`
65
+
66
+
67
+ ### JSON
68
+ JSONPathを用いて、以下のように検証できます。
69
+
70
+ ~~~~~ {ruby}
71
+ res['$.team'].should eq ['ABC']
72
+ res['$.members..name'].should eq ['Ichiro', 'Jiro', 'Saburo']
73
+ res['$.members..age'].should include 32
74
+ res['$.members[::]'].should have(3).items
75
+ res['$.members[::]'].should have_at_most(3).items
76
+ res['$.members[::]'].should have_at_least(1).items
77
+ res['$.members..name'].should all be_kind_of String
78
+ res['$.members..age'].should all be_kind_of Integer
79
+ res['$.members..age'].should all be > 11
80
+ res['$.members..age'].should all be >= 12
81
+ res['$.members..age'].should all be < 33
82
+ res['$.members..age'].should all be <= 32
83
+ res['$.members..age'].should be_sorted :desc
84
+ ~~~~~
85
+
86
+
87
+ 同じ要素を色々検証したい場合は、`select`を使ってブロック内に検証を書くと見やすいかも。
88
+
89
+ ~~~~~ {ruby}
90
+ res.select('$.members..age') do |member_ages|
91
+ member_ages.should all be_kind_of Integer
92
+ member_ages.should all be > 11
93
+ member_ages.should all be >= 12
94
+ member_ages.should all be < 33
95
+ member_ages.should all be <= 32
96
+ member_ages.should be_sorted :desc
97
+ end
98
+ ~~~~~
99
+
100
+ また、JSON schemaによる検証もできます。
101
+ json_schema/hello.js ファイルに以下のようなJSON schemaが記述します。
102
+
103
+ {
104
+ "type": "object",
105
+ "properties": {
106
+ "team": {"type": "string", "required": true},
107
+ "members": {
108
+ "type": "array",
109
+ "items": {
110
+ "type": "object",
111
+ "properties": {
112
+ "name": {"type": "string", "required": true},
113
+ "age": {"type": "integer", "required": true}
114
+ }
115
+ }
116
+ }
117
+ }
118
+ }
119
+
120
+ `_then`ブロックに以下のように記述することで、レスポンスボディが上記のJSON schemaとマッチするかを検証できます。
121
+
122
+ ~~~~~ {ruby}
123
+ res.body.should eq_schema_of 'json_schema/hello.json'
124
+ ~~~~~
125
+
126
+
127
+ ### XML
128
+ XPathを用いて以下のように検証できます。
129
+
130
+ ~~~~~ {ruby}
131
+ res['/root/team/text()'].should eq ['ABC']
132
+ res['/root/members//name/text()'].should eq ['Ichiro', 'Jiro', 'Saburo']
133
+ res['/root/members//age/text()'].should include '32'
134
+ res['/root/members/*'].should have(3).items
135
+ res['/root/members/*'].should have_at_most(3).items
136
+ res['/root/members/*'].should have_at_least(1).items
137
+ res['/root/members//age/text()'].should all be > "11"
138
+ member_ages = res['/root/members//age/text()']
139
+ member_ages.should all be >= "10"
140
+ member_ages.should all be < "33"
141
+ member_ages.should all be <= "32"
142
+ member_ages.should be_sorted :desc
143
+ res['/root/members/member/@order'].should be_sorted :asc
144
+ ~~~~~
145
+
146
+
147
+ ### HTML
148
+ CSSセレクタを用いて以下のように検証できます。
149
+
150
+ ~~~~~ {ruby}
151
+ res['title'].should eq ['Page Title!']
152
+ res['h1#team'].should eq ['ABC']
153
+ res['.member dd.name'].should eq ['Ichiro', 'Jiro', 'Saburo']
154
+ res['.member dd.age'].should include '32'
155
+ res['.member'].should have(3).items
156
+ res['.member'].should have_at_most(3).items
157
+ res['.member'].should have_at_least(1).items
158
+ res['.member dd.age'].should all be > "11"
159
+ member_ages = res['.member dd.age']
160
+ member_ages.should all be >= 10
161
+ member_ages.should all be < 33
162
+ member_ages.should all be <= 32
163
+ member_ages.should be_sorted :desc
164
+ ~~~~~
165
+
166
+
167
+ ## クエリパラメータを設定する
168
+ クエリパラメータを設定する方法は2通りあります。
169
+ 1つ目が、単純にurlの末尾に"?"をつけてクエリパラメータを指定する方法です。
170
+ ~~~~~ {ruby}
171
+ _when { get 'http://localhost:4567/index?night=true', as_text }
172
+ _then {
173
+ res.code.should eq '200'
174
+ }
175
+ ~~~~~
176
+
177
+ 2つ目が、`query`ヘルパー関数を使う方法です。
178
+ ~~~~~ {ruby}
179
+ _when {
180
+ get 'http://localhost:4567/index',
181
+ as_text,
182
+ query('night' => 'true',
183
+ 'times' => 3)
184
+ }
185
+ _then {
186
+ res.code.should eq '200'
187
+ }
188
+ ~~~~~
189
+
190
+
191
+ ## リクエストヘッダを設定する
192
+ リクエストヘッダの設定は、`_given`ブロックで、`headers`ヘルパー関数を呼び出して設定します。
193
+ `headers`関数に、ハッシュを渡して設定します。
194
+ ~~~~~ {ruby}
195
+ _given {
196
+ headers 'referer' => 'http://local.example.com',
197
+ 'user_agent' => 'itesttool'
198
+ }
199
+ _when { get 'http://localhost:4567/index.html', as_html }
200
+ _then {
201
+ res.code.should eq '200'
202
+ }
203
+ ~~~~~
204
+
205
+
206
+ ## POSTリクエストを送信する
207
+ POSTリクエストを送信する場合、`get`の代わりに`post`を使います。
208
+ 第1引数に送信先URL、第2引数にリクエストボディ、第3引数にレスポンスのフォーマット、を指定します。
209
+
210
+ ### formデータ
211
+ リクエストボディに、formデータを設定する場合は、`body_as_form`を使用します。
212
+
213
+ ~~~~~ {ruby}
214
+ _when {
215
+ post 'http://localhost:4567/login',
216
+ body_as_form('nickname' => 'admin',
217
+ 'password' => 'pass'),
218
+ res_is_json
219
+ }
220
+ _then {
221
+ res.code.should eq '200'
222
+ res['$.nickname'].should eq ['admin']
223
+ }
224
+ ~~~~~
225
+
226
+ ### JSON
227
+ リクエストボディに、JSONを設定する場合は、`body_as_json`を使用します。
228
+
229
+ ~~~~~ {ruby}
230
+ _when {
231
+ post 'http://localhost:4567/echo',
232
+ body_as_json('name' => 'Shiro',
233
+ 'age' => 2),
234
+ res_is_json
235
+ }
236
+ _then {
237
+ res.code.should eq '200'
238
+ res.body.should eq '{"name":"Shiro","age":2}'
239
+ }
240
+ ~~~~~
241
+
242
+ 単純に、`body`を使って直接文字列で設定することもできます。
243
+
244
+ ~~~~~ {ruby}
245
+ _when {
246
+ post 'http://localhost:4567/echo',
247
+ body('{"name":"Shiro","age":2}'),
248
+ res_is_json
249
+ }
250
+ _then {
251
+ res.code.should eq '200'
252
+ res.body.should eq '{"name":"Shiro","age":2}'
253
+ }
254
+ ~~~~~
255
+
256
+ ## PUT, DELETEリクエスト
257
+ PUT, DELETEリクエストの場合は、`post`の代わりに`put`,`delete`を使ってください。
258
+ 後は`post`の場合といっしょです。
259
+
260
+
261
+ # License
262
+ The MIT License. See LICENSE.txt
263
+
data/Rakefile ADDED
@@ -0,0 +1,7 @@
1
+ require "bundler/gem_tasks"
2
+ require "rspec/core/rake_task"
3
+
4
+ RSpec::Core::RakeTask.new("spec")
5
+
6
+ task :default => ["spec"]
7
+
@@ -0,0 +1,168 @@
1
+ # coding: utf-8
2
+ require 'rubygems'
3
+ require 'json-schema'
4
+
5
+ def eq_schema_of(schema_file)
6
+ EqSchemaOf.new(schema_file)
7
+ end
8
+
9
+ class EqSchemaOf
10
+ def initialize(schema_file)
11
+ @schema_file = schema_file
12
+ end
13
+ def matches? (body)
14
+ @body = body
15
+ @msg = ""
16
+ begin
17
+ JSON::Validator.validate!(@schema_file, body)
18
+ true
19
+ rescue JSON::Schema::ValidationError
20
+ @msg = $!.message
21
+ false
22
+ end
23
+ end
24
+
25
+ def failure_message_for_should
26
+ <<"MSG"
27
+
28
+ Invalid response body on "#{@schema_file}".
29
+ #{@msg}
30
+
31
+ Body is
32
+ ====================
33
+ #{@body}
34
+
35
+ #{@schema_file} is
36
+ ====================
37
+ #{File.open(@schema_file).read}
38
+
39
+ MSG
40
+ end
41
+
42
+ def failure_message_for_should_not
43
+ "\nValid response body on \"#{@schema_file}\".\n\n"
44
+ end
45
+ end
46
+
47
+
48
+ def be_sorted(order)
49
+ BeSorted.new(order)
50
+ end
51
+
52
+ class BeSorted
53
+ def initialize(order)
54
+ @order = order
55
+ end
56
+ def matches?(list)
57
+ @list = list
58
+ type = list.first.class
59
+ unless list.all?{|x| x.class == type }
60
+ @not_aligned = true
61
+ false
62
+ else
63
+ sorted_list = list.sort
64
+ if @order == :asc
65
+ list == sorted_list
66
+ elsif @order == :desc
67
+ list == sorted_list.reverse
68
+ else
69
+ @order_invalid = true
70
+ false
71
+ end
72
+ end
73
+ end
74
+
75
+ def failure_message_for_should
76
+ if @not_aligned
77
+ "expected #{@list.inspect} type is not available."
78
+ elsif @order_invalid
79
+ "specified order is invalid. valid order in [:asc, :desc]"
80
+ else
81
+ "expected #{@list.inspect} to be sorted #{@order}"
82
+ end
83
+ end
84
+ end
85
+
86
+
87
+ def all(meta)
88
+ All.new(meta)
89
+ end
90
+
91
+ class All
92
+ def initialize(matcher)
93
+ @matcher = matcher
94
+ end
95
+
96
+ def matches?(rows)
97
+ rows.each_with_index do |i, j|
98
+ @elem = j
99
+ unless @matcher.matches? i
100
+ return false
101
+ end
102
+ end
103
+ return true
104
+ end
105
+
106
+ def failure_message_for_should
107
+ "at[#{@elem}] #{@matcher.failure_message_for_should}"
108
+ end
109
+
110
+ end
111
+
112
+
113
+ def be_one_and(meta)
114
+ BeOneAnd.new(meta)
115
+ end
116
+
117
+ class BeOneAnd
118
+ def initialize(matcher)
119
+ @matcher = matcher
120
+ end
121
+
122
+ def matches?(rows)
123
+ @have_error = false
124
+ @have = RSpec::Matchers::BuiltIn::Have.new(1).items
125
+ unless @have.matches? rows then
126
+ @have_error = true
127
+ return false;
128
+ end
129
+ @matcher.matches? rows[0]
130
+ end
131
+
132
+ def failure_message_for_should
133
+ if @have_error
134
+ @have.failure_message_for_should
135
+ else
136
+ @matcher.failure_message_for_should
137
+ end
138
+ end
139
+
140
+ end
141
+
142
+ def include_with(key, values)
143
+ IncludeWith.new(key, values)
144
+ end
145
+
146
+ class IncludeWith
147
+ def initialize(key, values)
148
+ @key = key
149
+ @values = values
150
+ end
151
+ def matches?(rows)
152
+ @rows = rows
153
+ list = rows.map{|x| x[@key]}
154
+ Set[*list] == Set[*@values]
155
+ end
156
+
157
+ def failure_message_for_should
158
+ str = @values.map{|x| "#{@key} => #{x}"}.join(" and ")
159
+ "expected #{@rows.inspect} to include #{str}"
160
+ end
161
+
162
+ private
163
+ def msg_of_type_invalid
164
+ str = @values.map{|x| "#{@key} => #{x}"}.join(" and ")
165
+ "expected not #{@rows.inspect} to include #{str}"
166
+ end
167
+ end
168
+
@@ -0,0 +1,3 @@
1
+ module Itesttool
2
+ VERSION = "0.0.1"
3
+ end
data/lib/itesttool.rb ADDED
@@ -0,0 +1,156 @@
1
+ # coding: utf-8
2
+ require 'rubygems'
3
+ require 'net/http'
4
+ require 'uri'
5
+ require 'json'
6
+ require 'jsonpath'
7
+ require 'nokogiri'
8
+ require "itesttool/version"
9
+ require "itesttool/custom_matchers"
10
+
11
+ def _given(&b) before(:each, &b) end
12
+ def _when(&b) let(:res, &b) end
13
+ def _then(&b) it(&b) end
14
+
15
+ module ItestHelpers
16
+
17
+ def as_text() "text" end
18
+ def as_json() "json" end
19
+ def as_xml() "xml" end
20
+ def as_html() "html" end
21
+
22
+ alias res_is_json as_json
23
+ alias res_is_xml as_xml
24
+ alias res_is_html as_html
25
+
26
+ def headers(h = {})
27
+ @headers = h
28
+ end
29
+
30
+ def query(h = {})
31
+ h.map{ |k, v| URI.encode(k) + "=" + URI.encode(v.to_s) }.join("&")
32
+ end
33
+
34
+ def body(data = "")
35
+ {:body => data}
36
+ end
37
+ def body_as_form(data = {})
38
+ {:form => data}
39
+ end
40
+ def body_as_json(data = {})
41
+ {:json => data}
42
+ end
43
+
44
+ def get(url, res_format="text", query="")
45
+ url_obj = URI.parse(url)
46
+ res = Net::HTTP.start(url_obj.host, url_obj.port) {|http|
47
+ queries = []
48
+ queries.push(query) unless query.empty?
49
+ queries.push(url_obj.query) unless url_obj.query.nil?
50
+ path_with_query =
51
+ if queries.empty?
52
+ url_obj.path
53
+ else
54
+ url_obj.path + "?" + queries.join("&")
55
+ end
56
+ request = Net::HTTP::Get.new(path_with_query)
57
+ add_headers(request)
58
+ http.request(request)
59
+ }
60
+ decorate_response(res, "GET", url, res_format)
61
+ end
62
+
63
+ def post(url, data, res_format)
64
+ url_obj = URI.parse(url)
65
+ res = Net::HTTP.start(url_obj.host, url_obj.port) {|http|
66
+ request = Net::HTTP::Post.new(url_obj.path)
67
+ setup(request, data)
68
+ http.request(request)
69
+ }
70
+ decorate_response(res, "POST", url, res_format)
71
+ end
72
+
73
+ def put(url, data, res_format)
74
+ url_obj = URI.parse(url)
75
+ res = Net::HTTP.start(url_obj.host, url_obj.port) {|http|
76
+ request = Net::HTTP::Put.new(url_obj.path)
77
+ setup(request, data)
78
+ http.request(request)
79
+ }
80
+ decorate_response(res, "PUT", url, res_format)
81
+ end
82
+
83
+ def delete(url, data, res_format)
84
+ url_obj = URI.parse(url)
85
+ res = Net::HTTP.start(url_obj.host, url_obj.port) {|http|
86
+ request = Net::HTTP::DELETE.new(url_obj.path)
87
+ setup(request, data)
88
+ http.request(request)
89
+ }
90
+ decorate_response(res, "DELETE", url, res_format)
91
+ end
92
+
93
+ private
94
+ def setup(request, data)
95
+ set_body(request, data)
96
+ add_headers(request)
97
+ end
98
+
99
+ def add_headers(request)
100
+ if @headers then @headers.each{|k, v| request.add_field k, v} end
101
+ end
102
+
103
+ def set_body(request, data)
104
+ if data.include? :form
105
+ set_form_data(request, data[:form])
106
+ elsif data.include? :json
107
+ request.body = JSON.generate(data[:json])
108
+ else
109
+ request.body = data[:body]
110
+ end
111
+ end
112
+
113
+ def set_form_data(request, params, sep = '&')
114
+ request.body = params.map {|k, v| encode_kvpair(k, v) }.flatten.join(sep)
115
+ request.content_type = 'application/x-www-form-urlencoded'
116
+ end
117
+
118
+ def encode_kvpair(k, vs)
119
+ Array(vs).map {|v| "#{URI::encode(k.to_s)}=#{URI::encode(v.to_s)}" }
120
+ end
121
+
122
+ def decorate_response(res, method, url, res_format)
123
+ class << res
124
+ attr_accessor :url, :res_format, :method
125
+ def [](path)
126
+ select(path)
127
+ end
128
+ def select(path, &block)
129
+ result =
130
+ if res_format && res_format == "xml"
131
+ Nokogiri::XML(body).xpath(path).map{|x| x.text}
132
+ elsif res_format && res_format == "html"
133
+ Nokogiri::HTML(body).css(path).map{|x| x.text}
134
+ elsif res_format && res_format == "json"
135
+ JsonPath.on(body, path)
136
+ end
137
+ block.call(result) unless block.nil?
138
+ result
139
+ end
140
+ def to_s
141
+ method + " " + url
142
+ end
143
+ end
144
+ res.url = url
145
+ res.res_format = res_format
146
+ res.method = method
147
+ res
148
+ end
149
+
150
+ module_function :get, :post, :add_headers, :decorate_response
151
+ end
152
+
153
+ RSpec.configure do |c|
154
+ c.include ItestHelpers
155
+ end
156
+
metadata ADDED
@@ -0,0 +1,187 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: itesttool
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - bati11
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2014-01-26 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: rspec
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ~>
20
+ - !ruby/object:Gem::Version
21
+ version: '2.14'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ~>
28
+ - !ruby/object:Gem::Version
29
+ version: '2.14'
30
+ - !ruby/object:Gem::Dependency
31
+ name: json-schema
32
+ requirement: !ruby/object:Gem::Requirement
33
+ none: false
34
+ requirements:
35
+ - - ~>
36
+ - !ruby/object:Gem::Version
37
+ version: '2.2'
38
+ type: :runtime
39
+ prerelease: false
40
+ version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ~>
44
+ - !ruby/object:Gem::Version
45
+ version: '2.2'
46
+ - !ruby/object:Gem::Dependency
47
+ name: json
48
+ requirement: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - '='
52
+ - !ruby/object:Gem::Version
53
+ version: 1.8.1
54
+ type: :runtime
55
+ prerelease: false
56
+ version_requirements: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - '='
60
+ - !ruby/object:Gem::Version
61
+ version: 1.8.1
62
+ - !ruby/object:Gem::Dependency
63
+ name: jsonpath
64
+ requirement: !ruby/object:Gem::Requirement
65
+ none: false
66
+ requirements:
67
+ - - ~>
68
+ - !ruby/object:Gem::Version
69
+ version: 0.5.5
70
+ type: :runtime
71
+ prerelease: false
72
+ version_requirements: !ruby/object:Gem::Requirement
73
+ none: false
74
+ requirements:
75
+ - - ~>
76
+ - !ruby/object:Gem::Version
77
+ version: 0.5.5
78
+ - !ruby/object:Gem::Dependency
79
+ name: nokogiri
80
+ requirement: !ruby/object:Gem::Requirement
81
+ none: false
82
+ requirements:
83
+ - - ~>
84
+ - !ruby/object:Gem::Version
85
+ version: 1.6.1
86
+ type: :runtime
87
+ prerelease: false
88
+ version_requirements: !ruby/object:Gem::Requirement
89
+ none: false
90
+ requirements:
91
+ - - ~>
92
+ - !ruby/object:Gem::Version
93
+ version: 1.6.1
94
+ - !ruby/object:Gem::Dependency
95
+ name: sinatra
96
+ requirement: !ruby/object:Gem::Requirement
97
+ none: false
98
+ requirements:
99
+ - - ~>
100
+ - !ruby/object:Gem::Version
101
+ version: '1.4'
102
+ type: :development
103
+ prerelease: false
104
+ version_requirements: !ruby/object:Gem::Requirement
105
+ none: false
106
+ requirements:
107
+ - - ~>
108
+ - !ruby/object:Gem::Version
109
+ version: '1.4'
110
+ - !ruby/object:Gem::Dependency
111
+ name: bundler
112
+ requirement: !ruby/object:Gem::Requirement
113
+ none: false
114
+ requirements:
115
+ - - ~>
116
+ - !ruby/object:Gem::Version
117
+ version: '1.3'
118
+ type: :development
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ none: false
122
+ requirements:
123
+ - - ~>
124
+ - !ruby/object:Gem::Version
125
+ version: '1.3'
126
+ - !ruby/object:Gem::Dependency
127
+ name: rake
128
+ requirement: !ruby/object:Gem::Requirement
129
+ none: false
130
+ requirements:
131
+ - - ! '>='
132
+ - !ruby/object:Gem::Version
133
+ version: '0'
134
+ type: :development
135
+ prerelease: false
136
+ version_requirements: !ruby/object:Gem::Requirement
137
+ none: false
138
+ requirements:
139
+ - - ! '>='
140
+ - !ruby/object:Gem::Version
141
+ version: '0'
142
+ description: End-to-End Test tool for web api.
143
+ email:
144
+ - mail.bati11@gmail.com
145
+ executables: []
146
+ extensions: []
147
+ extra_rdoc_files: []
148
+ files:
149
+ - lib/itesttool.rb
150
+ - lib/itesttool/version.rb
151
+ - lib/itesttool/custom_matchers.rb
152
+ - Rakefile
153
+ - Gemfile
154
+ - README.md
155
+ - LICENSE.txt
156
+ homepage: ''
157
+ licenses:
158
+ - MIT
159
+ post_install_message:
160
+ rdoc_options: []
161
+ require_paths:
162
+ - lib
163
+ required_ruby_version: !ruby/object:Gem::Requirement
164
+ none: false
165
+ requirements:
166
+ - - ! '>='
167
+ - !ruby/object:Gem::Version
168
+ version: '0'
169
+ segments:
170
+ - 0
171
+ hash: 242860858589185526
172
+ required_rubygems_version: !ruby/object:Gem::Requirement
173
+ none: false
174
+ requirements:
175
+ - - ! '>='
176
+ - !ruby/object:Gem::Version
177
+ version: '0'
178
+ segments:
179
+ - 0
180
+ hash: 242860858589185526
181
+ requirements: []
182
+ rubyforge_project:
183
+ rubygems_version: 1.8.23
184
+ signing_key:
185
+ specification_version: 3
186
+ summary: End-to-End Test tool for web api.
187
+ test_files: []