breathe 0.1.3 → 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: b556ec113d7d5c5f9666a7107c86707b4aa28bec7932eb7607c090631c07250c
4
- data.tar.gz: c5b26bce036fd4324e154b0df6e68e10c94e441691e015bb2bb9cd5ac702dc52
3
+ metadata.gz: 50f00c9264cf4b355d988467f0410baeb78606cdc27ceba2e28a3e5671771f0c
4
+ data.tar.gz: 8d815287afcee0bd8e58281869ae4bbb86df13f37fe15498b03c48d7f591d0a0
5
5
  SHA512:
6
- metadata.gz: f0af79e4598c36081ae9705f8b90bec086a54530a008644e4dbce0f7158094e32744d90f7f6677b232caa90cebd55851afaf31d4fe8bd9813b7d4471aa452ef6
7
- data.tar.gz: 0fefc175a63493210d9c5c81e31b11539e5b08b77ac2e6d626285fdd7552846668cf2a4d670b2f59e742d71e48ffb0c65c6c7b799aaacc085a5887cca01e97f7
6
+ metadata.gz: 1a7dbf1a5cf986f68e924c86ae9a3e17f87bf7ef3ab4e66f2b3edea262b23b132d9de35c5aa3bd0fb8d80bc48889ce4c512b96ee707b5693016b8dc24694b87f
7
+ data.tar.gz: 5ab3b6c5fd7ab573b31804e593f1059ed1bc5a13d20819fe368baf8b9a844ed7a823b251382c46df15bcb535def9483710dbb59abe1dc0fe7ff13a91824e0c76
data/README.md CHANGED
@@ -40,32 +40,7 @@ And use like so
40
40
 
41
41
  ```ruby
42
42
  client.absences.list
43
- #=> [
44
- # {
45
- # "employee"=>{"id"=>123, "email"=>"someone@somewhere.com", "first_name"=>"Jo", "last_name"=>"Bloggs"},
46
- # "approved_by"=>{"id"=>123, "first_name"=>"Jo", "last_name"=>"Bloggs"},
47
- # "leave_reason"=>nil,
48
- # "deducted"=>"4.0",
49
- # "work_units"=>"4.0",
50
- # "id"=>456,
51
- # "start_date"=>"2015-06-18",
52
- # "half_start"=>false,
53
- # "half_start_am_pm"=>nil,
54
- # "end_date"=>"2015-06-23",
55
- # "half_end"=>false,
56
- # "half_end_am_pm"=>nil,
57
- # "cancelled"=>true,
58
- # "notes"=>"",
59
- # "type"=>"Holiday",
60
- # "created_at"=>"2015-05-20T15:53:36+01:00",
61
- # "updated_at"=>"2015-06-11T13:58:27+01:00"
62
- # },
63
- # ...
64
- #]
65
- client.absences.list.next_page
66
- # 2
67
- client.absences.list.per_page
68
- # 100
43
+ #=> [...]
69
44
  ```
70
45
 
71
46
  You can also pass in arguments like so:
@@ -75,6 +50,27 @@ client.absences(per_page: 12, start_date: Date.today)
75
50
  #=> [...]
76
51
  ```
77
52
 
53
+ ### Pagination
54
+
55
+ You can also paginate through the data like so:
56
+
57
+ ```ruby
58
+ client.absences.list.next_page
59
+ #=> [...]
60
+ client.absences.list.previous_page
61
+ #=> [...]
62
+ client.absences.list.last_page
63
+ #=> [...]
64
+ client.absences.list.first_pages
65
+ #=> [..]
66
+ ```
67
+
68
+ If you don't want to paginate at all, you can initialize the client with the `auto_paginate` argument set to `true` like so:
69
+
70
+ ```ruby
71
+ client = Breathe::Client.new(api_key: YOUR_API_KEY, auto_paginate: true)
72
+ ```
73
+
78
74
  Only the absences endpoint is currently supported. PRs are accepted for more endpoints!
79
75
 
80
76
  ## Development
data/breathe.gemspec CHANGED
@@ -34,5 +34,5 @@ Gem::Specification.new do |spec|
34
34
  spec.add_development_dependency "pry", "~> 0.12.2"
35
35
  spec.add_development_dependency "webmock", "~> 3.7.6"
36
36
 
37
- spec.add_dependency "faraday", "~> 0.17.0"
37
+ spec.add_dependency "sawyer", "~> 0.8.2"
38
38
  end
data/lib/breathe.rb CHANGED
@@ -1,4 +1,4 @@
1
- require "faraday"
1
+ require "sawyer"
2
2
 
3
3
  require "breathe/version"
4
4
  require "breathe/client"
@@ -9,5 +9,6 @@ require "breathe/absences"
9
9
  module Breathe
10
10
  class Error < StandardError; end
11
11
  class AuthenticationError < StandardError; end
12
+ class UnknownError < StandardError; end
12
13
  # Your code goes here...
13
14
  end
@@ -7,8 +7,11 @@ module Breathe
7
7
  end
8
8
 
9
9
  def list(args = {})
10
- response = client.get("absences", args)
11
- Response.new(response, "absences")
10
+ client.response(
11
+ method: :get,
12
+ path: "absences",
13
+ args: args
14
+ )
12
15
  end
13
16
  end
14
17
  end
@@ -1,43 +1,49 @@
1
1
  module Breathe
2
2
  class Client
3
+ attr_reader :api_key, :last_response
4
+
3
5
  BASE_URL = "https://api.breathehr.com/v1/"
4
6
 
5
- def initialize(api_key:)
7
+ def initialize(api_key:, auto_paginate: false)
6
8
  @api_key = api_key
9
+ @auto_paginate = auto_paginate
7
10
  end
8
11
 
9
12
  def absences
10
- @_absences ||= Absences.new(self)
13
+ @absences ||= Absences.new(self)
14
+ end
15
+
16
+ def response(method:, path:, args:)
17
+ response = request(method: method, path: path, options: {query: args})
18
+ parsed_response = Response.new(response: response, type: path)
19
+
20
+ if parsed_response.success?
21
+ @auto_paginate ? auto_paginated_response(parsed_response) : parsed_response
22
+ end
11
23
  end
12
24
 
13
- def get(url, url_opts = {})
14
- request(:get, url, url_opts)
25
+ def agent
26
+ Sawyer::Agent.new(BASE_URL, links_parser: Sawyer::LinkParsers::Simple.new) do |http|
27
+ http.headers["Content-Type"] = "application/json"
28
+ http.headers["X-Api-Key"] = api_key
29
+ end
30
+ end
31
+
32
+ def request(method:, path:, data: {}, options: {})
33
+ @last_response = agent.call(method, path, data, options)
34
+ @last_response
15
35
  end
16
36
 
17
37
  private
18
38
 
19
- attr_reader :api_key, :environment
39
+ def auto_paginated_response(parsed_response)
40
+ while (next_page = parsed_response.next_page)
41
+ break if next_page.nil?
20
42
 
21
- def connection
22
- Faraday.new(url: BASE_URL) do |faraday|
23
- faraday.use Faraday::Response::RaiseError
24
- faraday.adapter Faraday.default_adapter
43
+ parsed_response.concat(next_page)
25
44
  end
26
- end
27
45
 
28
- def request(method, url, url_opts = {})
29
- connection.send(method) do |req|
30
- req.url BASE_URL + url, url_opts
31
- req.headers["Content-Type"] = "application/json"
32
- req.headers["X-Api-Key"] = api_key
33
- end
34
- rescue Faraday::ClientError => e
35
- case e.message
36
- when /401/
37
- raise Breathe::AuthenticationError, "The BreatheHR API returned a 401 error - are you sure you've set the correct API key?"
38
- else
39
- raise e
40
- end
46
+ parsed_response
41
47
  end
42
48
  end
43
49
  end
@@ -1,53 +1,63 @@
1
1
  module Breathe
2
2
  class Response
3
3
  extend Forwardable
4
- attr_reader :data, :type, :response
4
+ attr_reader :response, :type
5
5
 
6
6
  delegate [:each, :find, :select, :count, :[]] => :body
7
7
 
8
- def initialize(response, type)
8
+ def initialize(response:, type:)
9
9
  @response = response
10
- @data = JSON.parse(response.body)
11
10
  @type = type
12
11
  end
13
12
 
13
+ def concat(response)
14
+ @response = response.response
15
+ body.concat(response.body)
16
+ end
17
+
18
+ def body
19
+ @body ||= response.data[type]
20
+ end
21
+
14
22
  def total
15
23
  response.headers["total"].to_i
16
24
  end
17
25
 
18
26
  def per_page
19
- response.headers.per_page
27
+ response.headers["per-page"].to_i
20
28
  end
21
29
 
22
- def next_page
23
- link_headers["next"].to_i unless link_headers.nil?
30
+ def first_page
31
+ get_page(:first)
24
32
  end
25
33
 
26
- def last_page
27
- link_headers["last"].to_i unless link_headers.nil?
34
+ def next_page
35
+ get_page(:next)
28
36
  end
29
37
 
30
- private
38
+ def previous_page
39
+ get_page(:prev)
40
+ end
31
41
 
32
- def body
33
- data[type]
42
+ def last_page
43
+ get_page(:last)
34
44
  end
35
45
 
36
- def link_headers
37
- @link_headers ||= begin
38
- return nil if response.headers["link"].nil?
46
+ def success?
47
+ return true if /^2+/.match?(response.status.to_s)
39
48
 
40
- parse_link_headers(response.headers["link"])
49
+ case response.status
50
+ when 401
51
+ raise Breathe::AuthenticationError, "The BreatheHR API returned a 401 error - are you sure you've set the correct API key?"
52
+ else
53
+ raise Breathe::UnknownError, "The BreatheHR API returned an unknown error"
41
54
  end
42
55
  end
43
56
 
44
- def parse_link_headers(header)
45
- header.split(",").map { |header|
46
- v, k = header.split(";")
47
- k = k.match("rel=\"(.+)\"")[1]
48
- v = v.match("page=([0-9]+)")[1]
49
- [k, v]
50
- }.to_h
57
+ private
58
+
59
+ def get_page(rel_type)
60
+ self.class.new(response: response.rels[rel_type].get, type: type) if response.rels[rel_type]
51
61
  end
52
62
  end
53
63
  end
@@ -1,3 +1,3 @@
1
1
  module Breathe
2
- VERSION = "0.1.3"
2
+ VERSION = "0.2.0"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: breathe
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.3
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Stuart Harrison
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2019-11-08 00:00:00.000000000 Z
11
+ date: 2019-11-16 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -123,19 +123,19 @@ dependencies:
123
123
  - !ruby/object:Gem::Version
124
124
  version: 3.7.6
125
125
  - !ruby/object:Gem::Dependency
126
- name: faraday
126
+ name: sawyer
127
127
  requirement: !ruby/object:Gem::Requirement
128
128
  requirements:
129
129
  - - "~>"
130
130
  - !ruby/object:Gem::Version
131
- version: 0.17.0
131
+ version: 0.8.2
132
132
  type: :runtime
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: 0.17.0
138
+ version: 0.8.2
139
139
  description:
140
140
  email:
141
141
  - pezholio@gmail.com