hatt 0.0.1 → 0.0.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Gemfile +2 -1
- data/Gemfile.lock +76 -74
- data/README.md +167 -0
- data/README.rdoc +99 -52
- data/Readme.md +167 -0
- data/bin/hatt +0 -4
- data/hatt.gemspec +58 -54
- data/lib/hatt/configuration.rb +1 -1
- data/lib/hatt/http.rb +9 -6
- metadata +24 -8
- data/lib/hatt/hattmixin.rb +0 -21
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 8ec241d7bb22baf345d1380532c613ba88ee6e99
|
4
|
+
data.tar.gz: 3f322224a43da43dcf3ec9eba8de6d3931f621bc
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: e3b146cbe7bcbbca8de97ad68c9da85a3eb1caad4a1b5dfe6c6d1070743e3643a2984455642067a71a545c0327dc9bc00102bc5dc983a0a178ca89b8322199ca
|
7
|
+
data.tar.gz: d6c9e9e406a432cb17d3d61353a894b571bca3bb0ec4b9794dff4be16ce4c35c5249e2da8b6d6eccc5b33c506f04876ea5c3a3ca5c666685a871fba2d7d0b975
|
data/Gemfile
CHANGED
data/Gemfile.lock
CHANGED
@@ -1,120 +1,121 @@
|
|
1
1
|
GEM
|
2
2
|
remote: http://rubygems.org/
|
3
3
|
specs:
|
4
|
-
activesupport (5.
|
4
|
+
activesupport (5.2.0)
|
5
5
|
concurrent-ruby (~> 1.0, >= 1.0.2)
|
6
|
-
i18n (
|
6
|
+
i18n (>= 0.7, < 2)
|
7
7
|
minitest (~> 5.1)
|
8
8
|
tzinfo (~> 1.1)
|
9
|
-
addressable (2.
|
10
|
-
|
11
|
-
|
12
|
-
awesome_print (1.7.0)
|
9
|
+
addressable (2.4.0)
|
10
|
+
ast (2.4.0)
|
11
|
+
awesome_print (1.8.0)
|
13
12
|
builder (3.2.3)
|
14
|
-
coderay (1.1.
|
13
|
+
coderay (1.1.2)
|
15
14
|
concurrent-ruby (1.0.5)
|
16
|
-
debase (0.2.
|
17
|
-
debase-ruby_core_source
|
18
|
-
debase-ruby_core_source (0.
|
15
|
+
debase (0.2.2)
|
16
|
+
debase-ruby_core_source (>= 0.10.2)
|
17
|
+
debase-ruby_core_source (0.10.3)
|
19
18
|
descendants_tracker (0.0.4)
|
20
19
|
thread_safe (~> 0.3, >= 0.3.1)
|
21
20
|
diff-lcs (1.3)
|
22
|
-
docile (1.1
|
23
|
-
ethon (0.
|
21
|
+
docile (1.3.1)
|
22
|
+
ethon (0.11.0)
|
24
23
|
ffi (>= 1.3.0)
|
25
24
|
faraday (0.9.2)
|
26
25
|
multipart-post (>= 1.2, < 3)
|
27
|
-
ffi (1.9.
|
28
|
-
git (1.
|
29
|
-
github_api (0.
|
30
|
-
addressable (~> 2.
|
31
|
-
descendants_tracker (~> 0.0.
|
26
|
+
ffi (1.9.25)
|
27
|
+
git (1.4.0)
|
28
|
+
github_api (0.16.0)
|
29
|
+
addressable (~> 2.4.0)
|
30
|
+
descendants_tracker (~> 0.0.4)
|
32
31
|
faraday (~> 0.8, < 0.10)
|
33
|
-
hashie (>=
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
32
|
+
hashie (>= 3.4)
|
33
|
+
mime-types (>= 1.16, < 3.0)
|
34
|
+
oauth2 (~> 1.0)
|
35
|
+
hashie (3.5.7)
|
36
|
+
highline (2.0.0)
|
37
|
+
i18n (1.0.1)
|
38
|
+
concurrent-ruby (~> 1.0)
|
39
|
+
jaro_winkler (1.5.1)
|
40
|
+
jeweler (2.3.9)
|
41
41
|
builder
|
42
|
-
bundler
|
42
|
+
bundler
|
43
43
|
git (>= 1.2.5)
|
44
|
-
github_api (~> 0.
|
44
|
+
github_api (~> 0.16.0)
|
45
45
|
highline (>= 1.6.15)
|
46
46
|
nokogiri (>= 1.5.10)
|
47
|
-
psych
|
47
|
+
psych
|
48
48
|
rake
|
49
49
|
rdoc
|
50
50
|
semver2
|
51
51
|
json (2.1.0)
|
52
52
|
jwt (1.5.6)
|
53
|
-
method_source (0.
|
54
|
-
|
55
|
-
|
56
|
-
|
53
|
+
method_source (0.9.0)
|
54
|
+
mime-types (2.99.3)
|
55
|
+
mini_portile2 (2.3.0)
|
56
|
+
minitest (5.11.3)
|
57
|
+
multi_json (1.13.1)
|
57
58
|
multi_xml (0.6.0)
|
58
59
|
multipart-post (2.0.0)
|
59
|
-
nokogiri (1.
|
60
|
-
mini_portile2 (~> 2.
|
61
|
-
oauth2 (1.
|
62
|
-
faraday (>= 0.8, < 0.
|
60
|
+
nokogiri (1.8.4)
|
61
|
+
mini_portile2 (~> 2.3.0)
|
62
|
+
oauth2 (1.4.0)
|
63
|
+
faraday (>= 0.8, < 0.13)
|
63
64
|
jwt (~> 1.0)
|
64
65
|
multi_json (~> 1.3)
|
65
66
|
multi_xml (~> 0.5)
|
66
67
|
rack (>= 1.2, < 3)
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
68
|
+
parallel (1.12.1)
|
69
|
+
parser (2.5.1.0)
|
70
|
+
ast (~> 2.4.0)
|
71
|
+
powerpack (0.1.2)
|
72
|
+
pry (0.11.3)
|
71
73
|
coderay (~> 1.1.0)
|
72
|
-
method_source (~> 0.
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
rspec-
|
83
|
-
|
84
|
-
rspec-
|
85
|
-
rspec-
|
86
|
-
rspec-support (~> 3.5.0)
|
87
|
-
rspec-expectations (3.5.0)
|
74
|
+
method_source (~> 0.9.0)
|
75
|
+
psych (3.0.2)
|
76
|
+
rack (2.0.5)
|
77
|
+
rainbow (3.0.0)
|
78
|
+
rake (12.3.1)
|
79
|
+
rdoc (6.0.4)
|
80
|
+
rdoc2md (0.1.1)
|
81
|
+
rspec (3.7.0)
|
82
|
+
rspec-core (~> 3.7.0)
|
83
|
+
rspec-expectations (~> 3.7.0)
|
84
|
+
rspec-mocks (~> 3.7.0)
|
85
|
+
rspec-core (3.7.1)
|
86
|
+
rspec-support (~> 3.7.0)
|
87
|
+
rspec-expectations (3.7.0)
|
88
88
|
diff-lcs (>= 1.2.0, < 2.0)
|
89
|
-
rspec-support (~> 3.
|
90
|
-
rspec-mocks (3.
|
89
|
+
rspec-support (~> 3.7.0)
|
90
|
+
rspec-mocks (3.7.0)
|
91
91
|
diff-lcs (>= 1.2.0, < 2.0)
|
92
|
-
rspec-support (~> 3.
|
93
|
-
rspec-support (3.
|
94
|
-
rubocop (0.
|
95
|
-
|
92
|
+
rspec-support (~> 3.7.0)
|
93
|
+
rspec-support (3.7.1)
|
94
|
+
rubocop (0.57.2)
|
95
|
+
jaro_winkler (~> 1.5.1)
|
96
|
+
parallel (~> 1.10)
|
97
|
+
parser (>= 2.5)
|
96
98
|
powerpack (~> 0.1)
|
97
|
-
rainbow (>=
|
99
|
+
rainbow (>= 2.2.2, < 4.0)
|
98
100
|
ruby-progressbar (~> 1.7)
|
99
101
|
unicode-display_width (~> 1.0, >= 1.0.1)
|
100
|
-
ruby-debug-ide (0.6.
|
102
|
+
ruby-debug-ide (0.6.1)
|
101
103
|
rake (>= 0.8.1)
|
102
|
-
ruby-progressbar (1.
|
104
|
+
ruby-progressbar (1.9.0)
|
103
105
|
semver2 (3.4.2)
|
104
|
-
simplecov (0.
|
105
|
-
docile (~> 1.1
|
106
|
+
simplecov (0.16.1)
|
107
|
+
docile (~> 1.1)
|
106
108
|
json (>= 1.8, < 3)
|
107
109
|
simplecov-html (~> 0.10.0)
|
108
|
-
simplecov-html (0.10.
|
109
|
-
slop (3.6.0)
|
110
|
+
simplecov-html (0.10.2)
|
110
111
|
tcfg (0.2.2)
|
111
112
|
activesupport
|
112
113
|
thread_safe (0.3.6)
|
113
|
-
typhoeus (1.
|
114
|
+
typhoeus (1.3.0)
|
114
115
|
ethon (>= 0.9.0)
|
115
|
-
tzinfo (1.2.
|
116
|
+
tzinfo (1.2.5)
|
116
117
|
thread_safe (~> 0.1)
|
117
|
-
unicode-display_width (1.
|
118
|
+
unicode-display_width (1.4.0)
|
118
119
|
|
119
120
|
PLATFORMS
|
120
121
|
ruby
|
@@ -124,9 +125,10 @@ DEPENDENCIES
|
|
124
125
|
awesome_print
|
125
126
|
debase
|
126
127
|
faraday
|
127
|
-
jeweler
|
128
|
+
jeweler (~> 2)
|
128
129
|
multi_json
|
129
130
|
pry
|
131
|
+
rdoc2md
|
130
132
|
rspec
|
131
133
|
rubocop
|
132
134
|
ruby-debug-ide
|
@@ -135,4 +137,4 @@ DEPENDENCIES
|
|
135
137
|
typhoeus
|
136
138
|
|
137
139
|
BUNDLED WITH
|
138
|
-
1.
|
140
|
+
1.16.2
|
data/README.md
ADDED
@@ -0,0 +1,167 @@
|
|
1
|
+
# HATT (HTTP API Testing Tool)
|
2
|
+
|
3
|
+
HATT is a tool, and a pattern, for testing HTTP APIs (RESTful or otherwise). It can be used to
|
4
|
+
construct fully automated tests, and also provides support for simple manual testing.
|
5
|
+
|
6
|
+
HATT is a Ruby tool and gem. It leverages the full power of Ruby. That said, HATT should be usable by those
|
7
|
+
with little familiarity of Ruby, but some knowledge of scripting languages in general. HATT works with standard
|
8
|
+
Ruby testing frameworks like RSpec and MiniTest.
|
9
|
+
|
10
|
+
## Basic testing features
|
11
|
+
|
12
|
+
* Easily configure and interact with one or more HTTP services (RESTful services).
|
13
|
+
* "Point" tests and requests at various deployment environments (eg, QA, Staging, Production)
|
14
|
+
* Using RSpec or MiniTest or any other testing framework, construct fully automated tests.
|
15
|
+
* Easily define a "DSL", or domain-specific-language for interacting with your API in your
|
16
|
+
own terms. This allows for writing self-documenting, easy to understand tests.
|
17
|
+
* Easily integrates into popular Continuos Integration tools like Jenkins. This means
|
18
|
+
your tests can run on a central server where all team members can access them.
|
19
|
+
|
20
|
+
|
21
|
+
## Short Example
|
22
|
+
|
23
|
+
The code for this entire example lives at [https://github.com/rschultheis/hatt_example].
|
24
|
+
Looking through that project shows examples of using nearly every hatt feature,
|
25
|
+
and examples of many kinds of tests and assertions against APIs.
|
26
|
+
|
27
|
+
This example is based on a free API: OpenWeatherMap. While the API is free, one must sign-up for an API key here:
|
28
|
+
[http://openweathermap.org/appid]. Keep your API key handy you will need it soon...
|
29
|
+
|
30
|
+
### Configure HATT, and setup a simple DSL method
|
31
|
+
|
32
|
+
#### install hatt
|
33
|
+
|
34
|
+
gem install hatt
|
35
|
+
|
36
|
+
#### make a project directory
|
37
|
+
|
38
|
+
mkdir open_weather_map_api_test_suite
|
39
|
+
cd open_weather_map_api_test_suite
|
40
|
+
|
41
|
+
#### Make a file called 'hatt.yml' with these contents:
|
42
|
+
|
43
|
+
hatt_services:
|
44
|
+
# shothand of owm for "open weather map api"
|
45
|
+
owm:
|
46
|
+
url: http://api.openweathermap.org
|
47
|
+
|
48
|
+
#### Put our API key into hatt.secret.yml
|
49
|
+
|
50
|
+
We need a special place to put our API key. For that make a file called hatt.secret.yml. This is a file that is generally not to be checked into source control, it should be used for configuring any secrets (like API keys or passwords). Put this one line into the file:
|
51
|
+
|
52
|
+
owm_app_id: <your api key here>
|
53
|
+
|
54
|
+
#### make the hattdsl directory:
|
55
|
+
|
56
|
+
mkdir hattdsl
|
57
|
+
|
58
|
+
#### add method for checking weather to hattdsl/open_weather_map_hattdsl.rb
|
59
|
+
|
60
|
+
def weather_for city
|
61
|
+
owm.get "/data/2.5/weather?q=#{URI.encode(city)}&APPID=#{appid}"
|
62
|
+
end
|
63
|
+
|
64
|
+
def appid
|
65
|
+
hatt_configuration['owm_app_id']
|
66
|
+
end
|
67
|
+
|
68
|
+
#### Call it from the cmd line:
|
69
|
+
|
70
|
+
hatt -v weather_for "Pleasantville, NY"
|
71
|
+
|
72
|
+
And that returns something like this:
|
73
|
+
|
74
|
+
... <detailed logging showing full request / response>
|
75
|
+
D: [06/14/17 17:07:53][hatt] - HATT method 'weather_for' returned:
|
76
|
+
{"coord"=>{"lon"=>-73.79, "lat"=>41.13}, "weather"=>[{"id"=>800, "main"=>"Clear", "description"=>"clear sky", "icon"=>"01d"}], "base"=>"stations", "main"=>{"temp"=>299.68, "pressure"=>1014, "humidity"=>39, "temp_min"=>296.15, "temp_max"=>303.15}, "visibility"=>16093, "wind"=>{"speed"=>4.1, "deg"=>190}, "clouds"=>{"all"=>1}, "dt"=>1497480900, "sys"=>{"type"=>1, "id"=>1980, "message"=>0.0057, "country"=>"US", "sunrise"=>1497432119, "sunset"=>1497486575}, "id"=>5131757, "name"=>"Pleasantville", "cod"=>200}
|
77
|
+
|
78
|
+
|
79
|
+
So, at this point we are able to call the API, and see the full details of the request and response. We can manually
|
80
|
+
test a lot at this point. But HATT can do more....
|
81
|
+
|
82
|
+
|
83
|
+
### Make a ruby script, that uses the hattdsl:
|
84
|
+
|
85
|
+
#### Make a file called temperatures.rb with this in it:
|
86
|
+
|
87
|
+
[
|
88
|
+
'New York, NY',
|
89
|
+
'Toronto, Canada',
|
90
|
+
'Paris, France',
|
91
|
+
'Tokyo, Japan',
|
92
|
+
'Sydney, Australia',
|
93
|
+
].each do |city|
|
94
|
+
weather = weather_for city
|
95
|
+
kelvin = weather['main']['temp']
|
96
|
+
celcius = (kelvin - 273.15).round
|
97
|
+
puts "#{city}: #{celcius} celcius"
|
98
|
+
end
|
99
|
+
|
100
|
+
#### And then run the hatt script like so:
|
101
|
+
|
102
|
+
hatt -q -f temperatures.rb
|
103
|
+
|
104
|
+
And get this nice output (-q supresses all the detailed request/response logging, leaving only the puts in the script):
|
105
|
+
|
106
|
+
New York, NY: 18 celcius
|
107
|
+
Toronto, Canada: 7 celcius
|
108
|
+
Paris, France: 18 celcius
|
109
|
+
Tokyo, Japan: 16 celcius
|
110
|
+
Sydney, Australia: 14 celcius
|
111
|
+
|
112
|
+
|
113
|
+
### Make an automated test
|
114
|
+
|
115
|
+
Using the included Hatt::Mixin and Hatt::SingletonMixin module, testing an api becomes easy. Lets setup a simple RSpec example here.
|
116
|
+
|
117
|
+
#### Install rspec:
|
118
|
+
|
119
|
+
gem install rspec
|
120
|
+
|
121
|
+
#### Create the spec folder:
|
122
|
+
|
123
|
+
mkdir spec
|
124
|
+
|
125
|
+
#### Setup spec/spec_helper.rb with these contents to :
|
126
|
+
|
127
|
+
require 'hatt'
|
128
|
+
|
129
|
+
RSpec.configure do |config|
|
130
|
+
|
131
|
+
config.include Hatt::SingletonMixin
|
132
|
+
|
133
|
+
config.before(:all) do
|
134
|
+
hatt_initialize
|
135
|
+
end
|
136
|
+
end
|
137
|
+
|
138
|
+
#### Setup spec/weather_spec.rb with contents like:
|
139
|
+
|
140
|
+
require 'spec_helper'
|
141
|
+
describe "getting weather reports" do
|
142
|
+
it "should know the weather for New York City" do
|
143
|
+
response = weather_for 'New York, NY'
|
144
|
+
expected_items = ['temp', 'temp_min', 'temp_max', 'humidity', 'pressure']
|
145
|
+
# the actual assertions here
|
146
|
+
expect(response['main'].keys).to include(*expected_items)
|
147
|
+
# the temp is in kelvin, so it looks kinda wierd
|
148
|
+
expect(response['main']['temp']).to be_between(100, 400)
|
149
|
+
end
|
150
|
+
end
|
151
|
+
|
152
|
+
#### Run it:
|
153
|
+
|
154
|
+
rspec
|
155
|
+
|
156
|
+
And get back:
|
157
|
+
|
158
|
+
... <detailed logging showing all request response details> ...
|
159
|
+
|
160
|
+
1 example, 0 failures
|
161
|
+
|
162
|
+
|
163
|
+
|
164
|
+
And THAT is the basic way to use HATT to test an API.
|
165
|
+
|
166
|
+
For more information, and more detailed examples of how to do nearly anything using HATT, see the example
|
167
|
+
project: [https://github.com/rschultheis/hatt_example]
|
data/README.rdoc
CHANGED
@@ -1,62 +1,88 @@
|
|
1
|
-
|
2
|
-
=======
|
3
|
-
Do cool stuff with HTTP JSON APIs. Designed for the real world of developing systems based on service-oriented-architecture.
|
1
|
+
= HATT (HTTP API Testing Tool)
|
4
2
|
|
5
|
-
|
6
|
-
|
7
|
-
Hatt is primarily designed to be used by software teams that build HTTP JSON services.
|
8
|
-
Hatt makes it easy to:
|
9
|
-
* Define "macro" methods that accomplish high level goals through service calls.
|
10
|
-
* Call services or macro methods from the command line, adhoc scripts, or programtically within any Ruby program.
|
11
|
-
* Test services using RSpec or other testing frameworks
|
12
|
-
* "Point" at different environments (eg. QA, Staging, Production)
|
3
|
+
HATT is a tool, and a pattern, for testing HTTP APIs (RESTful or otherwise). It can be used to
|
4
|
+
construct fully automated tests, and also provides support for simple manual testing.
|
13
5
|
|
14
|
-
|
15
|
-
|
6
|
+
HATT is a Ruby tool and gem. It leverages the full power of Ruby. That said, HATT should be usable by those
|
7
|
+
with little familiarity of Ruby, but some knowledge of scripting languages in general. HATT works with standard
|
8
|
+
Ruby testing frameworks like RSpec and MiniTest.
|
16
9
|
|
17
|
-
|
10
|
+
== Basic testing features
|
18
11
|
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
12
|
+
* Easily configure and interact with one or more HTTP services (RESTful services).
|
13
|
+
* "Point" tests and requests at various deployment environments (eg, QA, Staging, Production)
|
14
|
+
* Using RSpec or MiniTest or any other testing framework, construct fully automated tests.
|
15
|
+
* Easily define a "DSL", or domain-specific-language for interacting with your API in your
|
16
|
+
own terms. This allows for writing self-documenting, easy to understand tests.
|
17
|
+
* Easily integrates into popular Continuos Integration tools like Jenkins. This means
|
18
|
+
your tests can run on a central server where all team members can access them.
|
23
19
|
|
24
|
-
The OpenWeatherMap is a good candidate for a simple API
|
25
|
-
which is accessible without needing any authentication key:
|
26
|
-
[http://api.openweathermap.org/]
|
27
20
|
|
21
|
+
== Short Example
|
28
22
|
|
29
|
-
|
23
|
+
The code for this entire example lives at [https://github.com/rschultheis/hatt_example].
|
24
|
+
Looking through that project shows examples of using nearly every hatt feature,
|
25
|
+
and examples of many kinds of tests and assertions against APIs.
|
30
26
|
|
31
|
-
|
32
|
-
|
27
|
+
This example is based on a free API: OpenWeatherMap. While the API is free, one must sign-up for an API key here:
|
28
|
+
[http://openweathermap.org/appid]. Keep your API key handy you will need it soon...
|
33
29
|
|
34
|
-
|
30
|
+
=== Configure HATT, and setup a simple DSL method
|
35
31
|
|
36
|
-
|
37
|
-
owm:
|
38
|
-
hostname: api.openweathermap.org
|
32
|
+
==== install hatt
|
39
33
|
|
40
|
-
|
34
|
+
gem install hatt
|
41
35
|
|
42
|
-
|
43
|
-
|
36
|
+
==== make a project directory
|
37
|
+
|
38
|
+
mkdir open_weather_map_api_test_suite
|
39
|
+
cd open_weather_map_api_test_suite
|
40
|
+
|
41
|
+
==== Make a file called 'hatt.yml' with these contents:
|
42
|
+
|
43
|
+
hatt_services:
|
44
|
+
# shothand of owm for "open weather map api"
|
45
|
+
owm:
|
46
|
+
url: http://api.openweathermap.org
|
47
|
+
|
48
|
+
==== Put our API key into hatt.secret.yml
|
49
|
+
|
50
|
+
We need a special place to put our API key. For that make a file called hatt.secret.yml. This is a file that is generally not to be checked into source control, it should be used for configuring any secrets (like API keys or passwords). Put this one line into the file:
|
51
|
+
|
52
|
+
owm_app_id: <your api key here>
|
53
|
+
|
54
|
+
==== make the hattdsl directory:
|
55
|
+
|
56
|
+
mkdir hattdsl
|
57
|
+
|
58
|
+
==== add method for checking weather to hattdsl/open_weather_map_hattdsl.rb
|
44
59
|
|
45
|
-
### add method for checking weather to owm_hatts/weather.rb
|
46
60
|
def weather_for city
|
47
|
-
owm.get "/data/2.5/weather?q=#{URI.encode(city)}"
|
61
|
+
owm.get "/data/2.5/weather?q=#{URI.encode(city)}&APPID=#{appid}"
|
62
|
+
end
|
63
|
+
|
64
|
+
def appid
|
65
|
+
hatt_configuration['owm_app_id']
|
48
66
|
end
|
49
67
|
|
50
|
-
|
51
|
-
|
68
|
+
==== Call it from the cmd line:
|
69
|
+
|
70
|
+
hatt -v weather_for "Pleasantville, NY"
|
52
71
|
|
53
72
|
And that returns something like this:
|
54
|
-
{"coord"=>{"lon"=>-73.79169, "lat"=>41.13436}, "sys"=>{"country"=>"United States of America", "sunrise"=>1366883974, "sunset"=>1366933583}, "weather"=>[{"id"=>501, "main"=>"Rain", "description"=>"moderate rain", "icon"=>"10d"}], "base"=>"global stations", "main"=>{"temp"=>290.46, "humidity"=>26, "pressure"=>1020, "temp_min"=>289.15, "temp_max"=>292.59}, "wind"=>{"speed"=>2.06, "gust"=>4.11, "deg"=>265}, "rain"=>{"1h"=>2.32}, "clouds"=>{"all"=>0}, "dt"=>1366926419, "id"=>5131757, "name"=>"Pleasantville", "cod"=>200}
|
55
73
|
|
56
|
-
|
74
|
+
... <detailed logging showing full request / response>
|
75
|
+
D: [06/14/17 17:07:53][hatt] - HATT method 'weather_for' returned:
|
76
|
+
{"coord"=>{"lon"=>-73.79, "lat"=>41.13}, "weather"=>[{"id"=>800, "main"=>"Clear", "description"=>"clear sky", "icon"=>"01d"}], "base"=>"stations", "main"=>{"temp"=>299.68, "pressure"=>1014, "humidity"=>39, "temp_min"=>296.15, "temp_max"=>303.15}, "visibility"=>16093, "wind"=>{"speed"=>4.1, "deg"=>190}, "clouds"=>{"all"=>1}, "dt"=>1497480900, "sys"=>{"type"=>1, "id"=>1980, "message"=>0.0057, "country"=>"US", "sunrise"=>1497432119, "sunset"=>1497486575}, "id"=>5131757, "name"=>"Pleasantville", "cod"=>200}
|
77
|
+
|
78
|
+
|
79
|
+
So, at this point we are able to call the API, and see the full details of the request and response. We can manually
|
80
|
+
test a lot at this point. But HATT can do more....
|
81
|
+
|
57
82
|
|
58
|
-
|
59
|
-
|
83
|
+
=== Make a ruby script, that uses the hattdsl:
|
84
|
+
|
85
|
+
==== Make a file called temperatures.rb with this in it:
|
60
86
|
|
61
87
|
[
|
62
88
|
'New York, NY',
|
@@ -71,50 +97,71 @@ Make a file called temperatures.rb with this in it:
|
|
71
97
|
puts "#{city}: #{celcius} celcius"
|
72
98
|
end
|
73
99
|
|
74
|
-
And then run the hatt script like so:
|
100
|
+
==== And then run the hatt script like so:
|
75
101
|
|
76
|
-
hatt -f temperatures.rb
|
102
|
+
hatt -q -f temperatures.rb
|
77
103
|
|
78
|
-
And get this nice output:
|
104
|
+
And get this nice output (-q supresses all the detailed request/response logging, leaving only the puts in the script):
|
79
105
|
|
80
|
-
I: [04/25/13 17:59:22][hatt] - Running data script 'temperatures.rb'
|
81
106
|
New York, NY: 18 celcius
|
82
107
|
Toronto, Canada: 7 celcius
|
83
108
|
Paris, France: 18 celcius
|
84
109
|
Tokyo, Japan: 16 celcius
|
85
110
|
Sydney, Australia: 14 celcius
|
86
111
|
|
87
|
-
|
88
|
-
|
112
|
+
|
113
|
+
=== Make an automated test
|
114
|
+
|
115
|
+
Using the included Hatt::Mixin and Hatt::SingletonMixin module, testing an api becomes easy. Lets setup a simple RSpec example here.
|
116
|
+
|
117
|
+
==== Install rspec:
|
118
|
+
|
119
|
+
gem install rspec
|
120
|
+
|
121
|
+
==== Create the spec folder:
|
89
122
|
|
90
123
|
mkdir spec
|
91
124
|
|
92
|
-
Setup spec/spec_helper.rb with contents
|
125
|
+
==== Setup spec/spec_helper.rb with these contents to :
|
93
126
|
|
94
|
-
require 'hatt
|
127
|
+
require 'hatt'
|
95
128
|
|
96
129
|
RSpec.configure do |config|
|
97
|
-
|
130
|
+
|
131
|
+
config.include Hatt::SingletonMixin
|
132
|
+
|
133
|
+
config.before(:all) do
|
134
|
+
hatt_initialize
|
135
|
+
end
|
98
136
|
end
|
99
137
|
|
100
|
-
Setup spec/weather_spec.rb with contents like:
|
138
|
+
==== Setup spec/weather_spec.rb with contents like:
|
101
139
|
|
102
140
|
require 'spec_helper'
|
103
141
|
describe "getting weather reports" do
|
104
142
|
it "should know the weather for New York City" do
|
105
143
|
response = weather_for 'New York, NY'
|
106
144
|
expected_items = ['temp', 'temp_min', 'temp_max', 'humidity', 'pressure']
|
107
|
-
|
145
|
+
# the actual assertions here
|
146
|
+
expect(response['main'].keys).to include(*expected_items)
|
147
|
+
# the temp is in kelvin, so it looks kinda wierd
|
148
|
+
expect(response['main']['temp']).to be_between(100, 400)
|
108
149
|
end
|
109
150
|
end
|
110
151
|
|
111
|
-
Run it:
|
152
|
+
==== Run it:
|
112
153
|
|
113
|
-
gem install rspec
|
114
154
|
rspec
|
115
155
|
|
116
156
|
And get back:
|
117
157
|
|
158
|
+
... <detailed logging showing all request response details> ...
|
159
|
+
|
118
160
|
1 example, 0 failures
|
119
161
|
|
120
162
|
|
163
|
+
|
164
|
+
And THAT is the basic way to use HATT to test an API.
|
165
|
+
|
166
|
+
For more information, and more detailed examples of how to do nearly anything using HATT, see the example
|
167
|
+
project: [https://github.com/rschultheis/hatt_example]
|
data/Readme.md
ADDED
@@ -0,0 +1,167 @@
|
|
1
|
+
# HATT (HTTP API Testing Tool)
|
2
|
+
|
3
|
+
HATT is a tool, and a pattern, for testing HTTP APIs (RESTful or otherwise). It can be used to
|
4
|
+
construct fully automated tests, and also provides support for simple manual testing.
|
5
|
+
|
6
|
+
HATT is a Ruby tool and gem. It leverages the full power of Ruby. That said, HATT should be usable by those
|
7
|
+
with little familiarity of Ruby, but some knowledge of scripting languages in general. HATT works with standard
|
8
|
+
Ruby testing frameworks like RSpec and MiniTest.
|
9
|
+
|
10
|
+
## Basic testing features
|
11
|
+
|
12
|
+
* Easily configure and interact with one or more HTTP services (RESTful services).
|
13
|
+
* "Point" tests and requests at various deployment environments (eg, QA, Staging, Production)
|
14
|
+
* Using RSpec or MiniTest or any other testing framework, construct fully automated tests.
|
15
|
+
* Easily define a "DSL", or domain-specific-language for interacting with your API in your
|
16
|
+
own terms. This allows for writing self-documenting, easy to understand tests.
|
17
|
+
* Easily integrates into popular Continuos Integration tools like Jenkins. This means
|
18
|
+
your tests can run on a central server where all team members can access them.
|
19
|
+
|
20
|
+
|
21
|
+
## Short Example
|
22
|
+
|
23
|
+
The code for this entire example lives at [https://github.com/rschultheis/hatt_example].
|
24
|
+
Looking through that project shows examples of using nearly every hatt feature,
|
25
|
+
and examples of many kinds of tests and assertions against APIs.
|
26
|
+
|
27
|
+
This example is based on a free API: OpenWeatherMap. While the API is free, one must sign-up for an API key here:
|
28
|
+
[http://openweathermap.org/appid]. Keep your API key handy you will need it soon...
|
29
|
+
|
30
|
+
### Configure HATT, and setup a simple DSL method
|
31
|
+
|
32
|
+
#### install hatt
|
33
|
+
|
34
|
+
gem install hatt
|
35
|
+
|
36
|
+
#### make a project directory
|
37
|
+
|
38
|
+
mkdir open_weather_map_api_test_suite
|
39
|
+
cd open_weather_map_api_test_suite
|
40
|
+
|
41
|
+
#### Make a file called 'hatt.yml' with these contents:
|
42
|
+
|
43
|
+
hatt_services:
|
44
|
+
# shothand of owm for "open weather map api"
|
45
|
+
owm:
|
46
|
+
url: http://api.openweathermap.org
|
47
|
+
|
48
|
+
#### Put our API key into hatt.secret.yml
|
49
|
+
|
50
|
+
We need a special place to put our API key. For that make a file called hatt.secret.yml. This is a file that is generally not to be checked into source control, it should be used for configuring any secrets (like API keys or passwords). Put this one line into the file:
|
51
|
+
|
52
|
+
owm_app_id: <your api key here>
|
53
|
+
|
54
|
+
#### make the hattdsl directory:
|
55
|
+
|
56
|
+
mkdir hattdsl
|
57
|
+
|
58
|
+
#### add method for checking weather to hattdsl/open_weather_map_hattdsl.rb
|
59
|
+
|
60
|
+
def weather_for city
|
61
|
+
owm.get "/data/2.5/weather?q=#{URI.encode(city)}&APPID=#{appid}"
|
62
|
+
end
|
63
|
+
|
64
|
+
def appid
|
65
|
+
hatt_configuration['owm_app_id']
|
66
|
+
end
|
67
|
+
|
68
|
+
#### Call it from the cmd line:
|
69
|
+
|
70
|
+
hatt -v weather_for "Pleasantville, NY"
|
71
|
+
|
72
|
+
And that returns something like this:
|
73
|
+
|
74
|
+
... <detailed logging showing full request / response>
|
75
|
+
D: [06/14/17 17:07:53][hatt] - HATT method 'weather_for' returned:
|
76
|
+
{"coord"=>{"lon"=>-73.79, "lat"=>41.13}, "weather"=>[{"id"=>800, "main"=>"Clear", "description"=>"clear sky", "icon"=>"01d"}], "base"=>"stations", "main"=>{"temp"=>299.68, "pressure"=>1014, "humidity"=>39, "temp_min"=>296.15, "temp_max"=>303.15}, "visibility"=>16093, "wind"=>{"speed"=>4.1, "deg"=>190}, "clouds"=>{"all"=>1}, "dt"=>1497480900, "sys"=>{"type"=>1, "id"=>1980, "message"=>0.0057, "country"=>"US", "sunrise"=>1497432119, "sunset"=>1497486575}, "id"=>5131757, "name"=>"Pleasantville", "cod"=>200}
|
77
|
+
|
78
|
+
|
79
|
+
So, at this point we are able to call the API, and see the full details of the request and response. We can manually
|
80
|
+
test a lot at this point. But HATT can do more....
|
81
|
+
|
82
|
+
|
83
|
+
### Make a ruby script, that uses the hattdsl:
|
84
|
+
|
85
|
+
#### Make a file called temperatures.rb with this in it:
|
86
|
+
|
87
|
+
[
|
88
|
+
'New York, NY',
|
89
|
+
'Toronto, Canada',
|
90
|
+
'Paris, France',
|
91
|
+
'Tokyo, Japan',
|
92
|
+
'Sydney, Australia',
|
93
|
+
].each do |city|
|
94
|
+
weather = weather_for city
|
95
|
+
kelvin = weather['main']['temp']
|
96
|
+
celcius = (kelvin - 273.15).round
|
97
|
+
puts "#{city}: #{celcius} celcius"
|
98
|
+
end
|
99
|
+
|
100
|
+
#### And then run the hatt script like so:
|
101
|
+
|
102
|
+
hatt -q -f temperatures.rb
|
103
|
+
|
104
|
+
And get this nice output (-q supresses all the detailed request/response logging, leaving only the puts in the script):
|
105
|
+
|
106
|
+
New York, NY: 18 celcius
|
107
|
+
Toronto, Canada: 7 celcius
|
108
|
+
Paris, France: 18 celcius
|
109
|
+
Tokyo, Japan: 16 celcius
|
110
|
+
Sydney, Australia: 14 celcius
|
111
|
+
|
112
|
+
|
113
|
+
### Make an automated test
|
114
|
+
|
115
|
+
Using the included Hatt::Mixin and Hatt::SingletonMixin module, testing an api becomes easy. Lets setup a simple RSpec example here.
|
116
|
+
|
117
|
+
#### Install rspec:
|
118
|
+
|
119
|
+
gem install rspec
|
120
|
+
|
121
|
+
#### Create the spec folder:
|
122
|
+
|
123
|
+
mkdir spec
|
124
|
+
|
125
|
+
#### Setup spec/spec_helper.rb with these contents to :
|
126
|
+
|
127
|
+
require 'hatt'
|
128
|
+
|
129
|
+
RSpec.configure do |config|
|
130
|
+
|
131
|
+
config.include Hatt::SingletonMixin
|
132
|
+
|
133
|
+
config.before(:all) do
|
134
|
+
hatt_initialize
|
135
|
+
end
|
136
|
+
end
|
137
|
+
|
138
|
+
#### Setup spec/weather_spec.rb with contents like:
|
139
|
+
|
140
|
+
require 'spec_helper'
|
141
|
+
describe "getting weather reports" do
|
142
|
+
it "should know the weather for New York City" do
|
143
|
+
response = weather_for 'New York, NY'
|
144
|
+
expected_items = ['temp', 'temp_min', 'temp_max', 'humidity', 'pressure']
|
145
|
+
# the actual assertions here
|
146
|
+
expect(response['main'].keys).to include(*expected_items)
|
147
|
+
# the temp is in kelvin, so it looks kinda wierd
|
148
|
+
expect(response['main']['temp']).to be_between(100, 400)
|
149
|
+
end
|
150
|
+
end
|
151
|
+
|
152
|
+
#### Run it:
|
153
|
+
|
154
|
+
rspec
|
155
|
+
|
156
|
+
And get back:
|
157
|
+
|
158
|
+
... <detailed logging showing all request response details> ...
|
159
|
+
|
160
|
+
1 example, 0 failures
|
161
|
+
|
162
|
+
|
163
|
+
|
164
|
+
And THAT is the basic way to use HATT to test an API.
|
165
|
+
|
166
|
+
For more information, and more detailed examples of how to do nearly anything using HATT, see the example
|
167
|
+
project: [https://github.com/rschultheis/hatt_example]
|
data/bin/hatt
CHANGED
@@ -47,12 +47,8 @@ def parse_cmd_line
|
|
47
47
|
ENV['HATT_ENVIRONMENT'] = e
|
48
48
|
end
|
49
49
|
|
50
|
-
opts.on('-n', '--no-authenticate',
|
51
|
-
'Do not authenticate') { options[:authenticate] = false }
|
52
|
-
|
53
50
|
opts.on('-l', '--list', 'Print each available hatt dsl method') do
|
54
51
|
options[:list_hatt_methods] = true
|
55
|
-
options[:authenticate] = false # no point in authenticating for --list
|
56
52
|
end
|
57
53
|
|
58
54
|
opts.on('-r', '--pry-repl', 'Launch an interactice repl with full access to hatt services and dsl') do
|
data/hatt.gemspec
CHANGED
@@ -2,27 +2,29 @@
|
|
2
2
|
# DO NOT EDIT THIS FILE DIRECTLY
|
3
3
|
# Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
|
4
4
|
# -*- encoding: utf-8 -*-
|
5
|
-
# stub: hatt 0.0.
|
5
|
+
# stub: hatt 0.0.2 ruby lib
|
6
6
|
|
7
7
|
Gem::Specification.new do |s|
|
8
|
-
s.name = "hatt"
|
9
|
-
s.version = "0.0.
|
8
|
+
s.name = "hatt".freeze
|
9
|
+
s.version = "0.0.2"
|
10
10
|
|
11
|
-
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
12
|
-
s.require_paths = ["lib"]
|
13
|
-
s.authors = ["Robert Schultheis"]
|
14
|
-
s.date = "
|
15
|
-
s.description = "convention based approach to interfacing with an HTTP JSON API."
|
16
|
-
s.email = "robert.schultheis@gmail.com"
|
17
|
-
s.executables = ["hatt"]
|
11
|
+
s.required_rubygems_version = Gem::Requirement.new(">= 0".freeze) if s.respond_to? :required_rubygems_version=
|
12
|
+
s.require_paths = ["lib".freeze]
|
13
|
+
s.authors = ["Robert Schultheis".freeze]
|
14
|
+
s.date = "2018-07-05"
|
15
|
+
s.description = "convention based approach to interfacing with an HTTP JSON API.".freeze
|
16
|
+
s.email = "robert.schultheis@gmail.com".freeze
|
17
|
+
s.executables = ["hatt".freeze]
|
18
18
|
s.extra_rdoc_files = [
|
19
19
|
"LICENSE.txt",
|
20
|
+
"README.md",
|
20
21
|
"README.rdoc"
|
21
22
|
]
|
22
23
|
s.files = [
|
23
24
|
"Gemfile",
|
24
25
|
"Gemfile.lock",
|
25
26
|
"LICENSE.txt",
|
27
|
+
"Readme.md",
|
26
28
|
"bin/hatt",
|
27
29
|
"hatt.gemspec",
|
28
30
|
"lib/hatt.rb",
|
@@ -31,64 +33,66 @@ Gem::Specification.new do |s|
|
|
31
33
|
"lib/hatt/blankslateproxy.rb",
|
32
34
|
"lib/hatt/configuration.rb",
|
33
35
|
"lib/hatt/dsl.rb",
|
34
|
-
"lib/hatt/hattmixin.rb",
|
35
36
|
"lib/hatt/http.rb",
|
36
37
|
"lib/hatt/json_helpers.rb",
|
37
38
|
"lib/hatt/log.rb",
|
38
39
|
"lib/hatt/mixin.rb",
|
39
40
|
"lib/hatt/singleton_mixin.rb"
|
40
41
|
]
|
41
|
-
s.homepage = "http://github.com/rschultheis/hatt"
|
42
|
-
s.licenses = ["MIT"]
|
43
|
-
s.rubygems_version = "2.
|
44
|
-
s.summary = "Make calls to HTTP JSON APIs with ease and confidence"
|
42
|
+
s.homepage = "http://github.com/rschultheis/hatt".freeze
|
43
|
+
s.licenses = ["MIT".freeze]
|
44
|
+
s.rubygems_version = "2.6.14.1".freeze
|
45
|
+
s.summary = "Make calls to HTTP JSON APIs with ease and confidence".freeze
|
45
46
|
|
46
47
|
if s.respond_to? :specification_version then
|
47
48
|
s.specification_version = 4
|
48
49
|
|
49
50
|
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
50
|
-
s.add_runtime_dependency(%q<activesupport
|
51
|
-
s.add_runtime_dependency(%q<faraday
|
52
|
-
s.add_runtime_dependency(%q<multi_json
|
53
|
-
s.add_runtime_dependency(%q<tcfg
|
54
|
-
s.add_runtime_dependency(%q<typhoeus
|
55
|
-
s.add_runtime_dependency(%q<pry
|
56
|
-
s.add_runtime_dependency(%q<awesome_print
|
57
|
-
s.add_development_dependency(%q<debase
|
58
|
-
s.add_development_dependency(%q<jeweler
|
59
|
-
s.add_development_dependency(%q<rspec
|
60
|
-
s.add_development_dependency(%q<rubocop
|
61
|
-
s.add_development_dependency(%q<ruby-debug-ide
|
62
|
-
s.add_development_dependency(%q<simplecov
|
51
|
+
s.add_runtime_dependency(%q<activesupport>.freeze, [">= 0"])
|
52
|
+
s.add_runtime_dependency(%q<faraday>.freeze, [">= 0"])
|
53
|
+
s.add_runtime_dependency(%q<multi_json>.freeze, [">= 0"])
|
54
|
+
s.add_runtime_dependency(%q<tcfg>.freeze, ["~> 0.2.2"])
|
55
|
+
s.add_runtime_dependency(%q<typhoeus>.freeze, [">= 0"])
|
56
|
+
s.add_runtime_dependency(%q<pry>.freeze, [">= 0"])
|
57
|
+
s.add_runtime_dependency(%q<awesome_print>.freeze, [">= 0"])
|
58
|
+
s.add_development_dependency(%q<debase>.freeze, [">= 0"])
|
59
|
+
s.add_development_dependency(%q<jeweler>.freeze, ["~> 2"])
|
60
|
+
s.add_development_dependency(%q<rspec>.freeze, [">= 0"])
|
61
|
+
s.add_development_dependency(%q<rubocop>.freeze, [">= 0"])
|
62
|
+
s.add_development_dependency(%q<ruby-debug-ide>.freeze, [">= 0"])
|
63
|
+
s.add_development_dependency(%q<simplecov>.freeze, [">= 0"])
|
64
|
+
s.add_development_dependency(%q<rdoc2md>.freeze, [">= 0"])
|
63
65
|
else
|
64
|
-
s.add_dependency(%q<activesupport
|
65
|
-
s.add_dependency(%q<faraday
|
66
|
-
s.add_dependency(%q<multi_json
|
67
|
-
s.add_dependency(%q<tcfg
|
68
|
-
s.add_dependency(%q<typhoeus
|
69
|
-
s.add_dependency(%q<pry
|
70
|
-
s.add_dependency(%q<awesome_print
|
71
|
-
s.add_dependency(%q<debase
|
72
|
-
s.add_dependency(%q<jeweler
|
73
|
-
s.add_dependency(%q<rspec
|
74
|
-
s.add_dependency(%q<rubocop
|
75
|
-
s.add_dependency(%q<ruby-debug-ide
|
76
|
-
s.add_dependency(%q<simplecov
|
66
|
+
s.add_dependency(%q<activesupport>.freeze, [">= 0"])
|
67
|
+
s.add_dependency(%q<faraday>.freeze, [">= 0"])
|
68
|
+
s.add_dependency(%q<multi_json>.freeze, [">= 0"])
|
69
|
+
s.add_dependency(%q<tcfg>.freeze, ["~> 0.2.2"])
|
70
|
+
s.add_dependency(%q<typhoeus>.freeze, [">= 0"])
|
71
|
+
s.add_dependency(%q<pry>.freeze, [">= 0"])
|
72
|
+
s.add_dependency(%q<awesome_print>.freeze, [">= 0"])
|
73
|
+
s.add_dependency(%q<debase>.freeze, [">= 0"])
|
74
|
+
s.add_dependency(%q<jeweler>.freeze, ["~> 2"])
|
75
|
+
s.add_dependency(%q<rspec>.freeze, [">= 0"])
|
76
|
+
s.add_dependency(%q<rubocop>.freeze, [">= 0"])
|
77
|
+
s.add_dependency(%q<ruby-debug-ide>.freeze, [">= 0"])
|
78
|
+
s.add_dependency(%q<simplecov>.freeze, [">= 0"])
|
79
|
+
s.add_dependency(%q<rdoc2md>.freeze, [">= 0"])
|
77
80
|
end
|
78
81
|
else
|
79
|
-
s.add_dependency(%q<activesupport
|
80
|
-
s.add_dependency(%q<faraday
|
81
|
-
s.add_dependency(%q<multi_json
|
82
|
-
s.add_dependency(%q<tcfg
|
83
|
-
s.add_dependency(%q<typhoeus
|
84
|
-
s.add_dependency(%q<pry
|
85
|
-
s.add_dependency(%q<awesome_print
|
86
|
-
s.add_dependency(%q<debase
|
87
|
-
s.add_dependency(%q<jeweler
|
88
|
-
s.add_dependency(%q<rspec
|
89
|
-
s.add_dependency(%q<rubocop
|
90
|
-
s.add_dependency(%q<ruby-debug-ide
|
91
|
-
s.add_dependency(%q<simplecov
|
82
|
+
s.add_dependency(%q<activesupport>.freeze, [">= 0"])
|
83
|
+
s.add_dependency(%q<faraday>.freeze, [">= 0"])
|
84
|
+
s.add_dependency(%q<multi_json>.freeze, [">= 0"])
|
85
|
+
s.add_dependency(%q<tcfg>.freeze, ["~> 0.2.2"])
|
86
|
+
s.add_dependency(%q<typhoeus>.freeze, [">= 0"])
|
87
|
+
s.add_dependency(%q<pry>.freeze, [">= 0"])
|
88
|
+
s.add_dependency(%q<awesome_print>.freeze, [">= 0"])
|
89
|
+
s.add_dependency(%q<debase>.freeze, [">= 0"])
|
90
|
+
s.add_dependency(%q<jeweler>.freeze, ["~> 2"])
|
91
|
+
s.add_dependency(%q<rspec>.freeze, [">= 0"])
|
92
|
+
s.add_dependency(%q<rubocop>.freeze, [">= 0"])
|
93
|
+
s.add_dependency(%q<ruby-debug-ide>.freeze, [">= 0"])
|
94
|
+
s.add_dependency(%q<simplecov>.freeze, [">= 0"])
|
95
|
+
s.add_dependency(%q<rdoc2md>.freeze, [">= 0"])
|
92
96
|
end
|
93
97
|
end
|
94
98
|
|
data/lib/hatt/configuration.rb
CHANGED
data/lib/hatt/http.rb
CHANGED
@@ -97,7 +97,7 @@ module Hatt
|
|
97
97
|
end
|
98
98
|
|
99
99
|
|
100
|
-
log_request(method, parsed_uri, query_hash,
|
100
|
+
log_request(method, parsed_uri, query_hash, req_headers, body)
|
101
101
|
|
102
102
|
# doing it this way avoids problem with OPTIONS method: https://github.com/lostisland/faraday/issues/305
|
103
103
|
response = nil
|
@@ -204,15 +204,18 @@ module Hatt
|
|
204
204
|
end
|
205
205
|
|
206
206
|
def log_response(response, response_obj)
|
207
|
+
log_messages = [
|
208
|
+
'Response Details:',
|
209
|
+
@log_headers ? ['Response Headers:',
|
210
|
+
response.headers.map { |k, v| "#{k}: #{v.inspect}" }] : nil
|
211
|
+
]
|
207
212
|
if response.headers['content-type'] =~ /json/
|
208
|
-
|
209
|
-
'Response Details:',
|
210
|
-
@log_headers ? ['Response Headers:',
|
211
|
-
response.headers.map { |k, v| "#{k}: #{v.inspect}" }] : nil,
|
213
|
+
log_messages += [
|
212
214
|
@log_bodies ? ['Response Body:', jsonify(response_obj)] : nil,
|
213
215
|
''
|
214
|
-
]
|
216
|
+
]
|
215
217
|
end
|
218
|
+
logger.debug log_messages.flatten.compact.join("\n")
|
216
219
|
end
|
217
220
|
|
218
221
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: hatt
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Robert Schultheis
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2018-07-05 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activesupport
|
@@ -126,16 +126,16 @@ dependencies:
|
|
126
126
|
name: jeweler
|
127
127
|
requirement: !ruby/object:Gem::Requirement
|
128
128
|
requirements:
|
129
|
-
- - "
|
129
|
+
- - "~>"
|
130
130
|
- !ruby/object:Gem::Version
|
131
|
-
version: '
|
131
|
+
version: '2'
|
132
132
|
type: :development
|
133
133
|
prerelease: false
|
134
134
|
version_requirements: !ruby/object:Gem::Requirement
|
135
135
|
requirements:
|
136
|
-
- - "
|
136
|
+
- - "~>"
|
137
137
|
- !ruby/object:Gem::Version
|
138
|
-
version: '
|
138
|
+
version: '2'
|
139
139
|
- !ruby/object:Gem::Dependency
|
140
140
|
name: rspec
|
141
141
|
requirement: !ruby/object:Gem::Requirement
|
@@ -192,6 +192,20 @@ dependencies:
|
|
192
192
|
- - ">="
|
193
193
|
- !ruby/object:Gem::Version
|
194
194
|
version: '0'
|
195
|
+
- !ruby/object:Gem::Dependency
|
196
|
+
name: rdoc2md
|
197
|
+
requirement: !ruby/object:Gem::Requirement
|
198
|
+
requirements:
|
199
|
+
- - ">="
|
200
|
+
- !ruby/object:Gem::Version
|
201
|
+
version: '0'
|
202
|
+
type: :development
|
203
|
+
prerelease: false
|
204
|
+
version_requirements: !ruby/object:Gem::Requirement
|
205
|
+
requirements:
|
206
|
+
- - ">="
|
207
|
+
- !ruby/object:Gem::Version
|
208
|
+
version: '0'
|
195
209
|
description: convention based approach to interfacing with an HTTP JSON API.
|
196
210
|
email: robert.schultheis@gmail.com
|
197
211
|
executables:
|
@@ -199,12 +213,15 @@ executables:
|
|
199
213
|
extensions: []
|
200
214
|
extra_rdoc_files:
|
201
215
|
- LICENSE.txt
|
216
|
+
- README.md
|
202
217
|
- README.rdoc
|
203
218
|
files:
|
204
219
|
- Gemfile
|
205
220
|
- Gemfile.lock
|
206
221
|
- LICENSE.txt
|
222
|
+
- README.md
|
207
223
|
- README.rdoc
|
224
|
+
- Readme.md
|
208
225
|
- bin/hatt
|
209
226
|
- hatt.gemspec
|
210
227
|
- lib/hatt.rb
|
@@ -213,7 +230,6 @@ files:
|
|
213
230
|
- lib/hatt/blankslateproxy.rb
|
214
231
|
- lib/hatt/configuration.rb
|
215
232
|
- lib/hatt/dsl.rb
|
216
|
-
- lib/hatt/hattmixin.rb
|
217
233
|
- lib/hatt/http.rb
|
218
234
|
- lib/hatt/json_helpers.rb
|
219
235
|
- lib/hatt/log.rb
|
@@ -239,7 +255,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
239
255
|
version: '0'
|
240
256
|
requirements: []
|
241
257
|
rubyforge_project:
|
242
|
-
rubygems_version: 2.
|
258
|
+
rubygems_version: 2.6.14.1
|
243
259
|
signing_key:
|
244
260
|
specification_version: 4
|
245
261
|
summary: Make calls to HTTP JSON APIs with ease and confidence
|
data/lib/hatt/hattmixin.rb
DELETED
@@ -1,21 +0,0 @@
|
|
1
|
-
require_relative 'configuration'
|
2
|
-
require_relative 'api_clients'
|
3
|
-
require_relative 'dsl'
|
4
|
-
|
5
|
-
module Hatt
|
6
|
-
module HattMixin
|
7
|
-
include Hatt::Configuration
|
8
|
-
include Hatt::DSL
|
9
|
-
include Hatt::ApiClients
|
10
|
-
|
11
|
-
def initialize(*opts)
|
12
|
-
hatt_initialize
|
13
|
-
super(*opts)
|
14
|
-
end
|
15
|
-
|
16
|
-
def hatt_initialize
|
17
|
-
hatt_build_client_methods
|
18
|
-
load_hatts_using_configuration
|
19
|
-
end
|
20
|
-
end
|
21
|
-
end
|