wotc 0.1.14 → 0.1.15

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
  SHA256:
3
- metadata.gz: ed9562cc855d2546a7f44dc89286abef0cd0b1320251d3a0f781e12e4476d9cf
4
- data.tar.gz: 1bf4ae7ed62a749c4d6bf955108948ee7e4471637ce2417b44b0b6b75bdaec53
3
+ metadata.gz: 5e1dc3eee513b938983d7d4068e6886e885f46741067ed4b46ec2a39c3766f09
4
+ data.tar.gz: 17408d0f062dd9a0a771afcc763af24d031cc08d59f79ae30f827cd03333f3a5
5
5
  SHA512:
6
- metadata.gz: bd2cdd17396ce2735c27ae91e0a3dcc812ed2d11e628ddc57cb341375d63143c727d907b42814559958fde4ae871e5fa4bc42414fa6bc49ecd75f1ca618d2135
7
- data.tar.gz: d98300fb6842e2509256f5ee685c21a301dbfecdc3d5d8f0315a0942fd944db0407c8771344d22c39ddb9ea4a5c6125aac9abaa05753014f4ab6a8d5da417165
6
+ metadata.gz: 6d448a43e5cc6bf75f4d54d9be6e4e8e6e44b45459a8155d1856efb93b26efaa1c68804040a7bdb811d0401b16ef60c8735a044d368e8f10de437cd5014f58e4
7
+ data.tar.gz: 4aff0246f7f5b6b5d8faca647238b0d86f0448ff71142b4844c448b63c50674d4aa79ce1d54ebc9e701198556dd7ddc7d955b59e9de6b2b16a9511f1d8b6f9a8
@@ -0,0 +1,18 @@
1
+ name: Test
2
+
3
+ on:
4
+ push:
5
+ branches: [master]
6
+ pull_request:
7
+
8
+ jobs:
9
+ rspec:
10
+ runs-on: ubuntu-latest
11
+ steps:
12
+ - uses: actions/checkout@v4
13
+ - uses: ruby/setup-ruby@v1
14
+ with:
15
+ # Matches the consuming backend's Ruby.
16
+ ruby-version: '3.0.4'
17
+ bundler-cache: true
18
+ - run: bundle exec rspec
data/.gitignore CHANGED
@@ -6,3 +6,4 @@
6
6
  /pkg/
7
7
  /spec/reports/
8
8
  /tmp/
9
+ Gemfile.lock
data/.ruby-version ADDED
@@ -0,0 +1 @@
1
+ 3.0.4
data/CHANGELOG.md CHANGED
@@ -0,0 +1,33 @@
1
+ # Changelog
2
+
3
+ ## 0.1.15 (unreleased)
4
+
5
+ - Every 4xx and 5xx from wotc.com now raises. Named statuses get their own
6
+ class (403 → `WOTC::Forbidden`, 422 → `WOTC::UnprocessableEntity`,
7
+ 429 → `WOTC::TooManyRequests`); anything unnamed raises `WOTC::ClientError`
8
+ or `WOTC::ServerError`. Previously a 403 — and any status without a `case`
9
+ arm — passed through as if the request had succeeded, which is how a 403
10
+ came to look like a revoked token (WS-50887). All new classes subclass
11
+ `WOTC::Error`, so existing rescues still catch them.
12
+ - New: `WOTC::Client#token_state` → `:valid` / `:revoked` / `:unknown`.
13
+ Only a 401 means `:revoked`; a 403, a 5xx, a timeout or an unreadable body
14
+ is `:unknown` and must not be treated as revocation. `token_valid?` is kept
15
+ for compatibility and now delegates to `token_state`, collapsing `:revoked`
16
+ and `:unknown` into the same `false`.
17
+ - `WOTC::MissingRequiredArgument` now subclasses `StandardError` and takes a
18
+ plain message; it previously inherited `Error#initialize(response)` and
19
+ crashed at the raise site.
20
+ - Auth header set via the `request :authorization` middleware instead of the
21
+ deprecated `Connection#authorization` (silences the per-request warning;
22
+ faraday `>= 1.8` now required). Dropped an unused `require 'base64'` that
23
+ triggered the Ruby 3.4 default-gem warning.
24
+
25
+ ## 0.1.14 (2026-03-16)
26
+
27
+ - Error middleware handles `Faraday::Response` correctly. Before this, every
28
+ raise from the middleware crashed with `NoMethodError` on `Faraday::Env`,
29
+ so no typed `WOTC::*` error had ever reached a caller.
30
+
31
+ ## 0.1.13 and earlier
32
+
33
+ - Untracked.
@@ -9,23 +9,31 @@ module FaradayMiddleWare
9
9
  def call(env)
10
10
  response = @app.call(env)
11
11
  response.on_complete do |_env|
12
- case response.status.to_i
13
- when 400
14
- raise WOTC::BadRequest.new(response)
15
- when 401
16
- raise WOTC::Unauthorized.new(response)
17
- when 404
18
- raise WOTC::NotFound.new(response)
19
- when 500
20
- raise WOTC::InternalServerError.new(response)
21
- when 502
22
- raise WOTC::BadGateway.new(response)
23
- when 503
24
- raise WOTC::ServiceUnavailable.new(response)
25
- when 504
26
- raise WOTC::GatewayTimeout.new(response)
27
- end
12
+ error = error_class(response.status.to_i)
13
+ raise error.new(response) if error
14
+ end
15
+ end
16
+
17
+ private
18
+
19
+ # Every 4xx and 5xx raises. The named statuses get their own class; anything
20
+ # else falls back to ClientError or ServerError, so a status we have not
21
+ # thought about can never be mistaken for a successful response.
22
+ def error_class(status)
23
+ case status
24
+ when 400 then WOTC::BadRequest
25
+ when 401 then WOTC::Unauthorized
26
+ when 403 then WOTC::Forbidden
27
+ when 404 then WOTC::NotFound
28
+ when 422 then WOTC::UnprocessableEntity
29
+ when 429 then WOTC::TooManyRequests
30
+ when 500 then WOTC::InternalServerError
31
+ when 502 then WOTC::BadGateway
32
+ when 503 then WOTC::ServiceUnavailable
33
+ when 504 then WOTC::GatewayTimeout
34
+ when 400..499 then WOTC::ClientError
35
+ when 500..599 then WOTC::ServerError
28
36
  end
29
37
  end
30
38
  end
31
- end
39
+ end
@@ -3,14 +3,30 @@ module WOTC
3
3
  # Defines methods related to utils
4
4
  module Utils
5
5
 
6
- # Trigger an api call to verify access_token is valid.
6
+ # Ask wotc.com whether our access token is still accepted.
7
+ #
8
+ # Returns :valid, :revoked or :unknown.
9
+ #
10
+ # Only a 401 means revoked. A 403, a 5xx, a timeout or a body we cannot
11
+ # read means we could not tell, and callers must not treat that as
12
+ # revocation.
13
+ def token_state
14
+ body = get('user').body
15
+ return :valid if body.is_a?(Hash) && !body['id'].nil?
16
+
17
+ :unknown
18
+ rescue WOTC::Unauthorized
19
+ :revoked
20
+ rescue StandardError
21
+ :unknown
22
+ end
23
+
24
+ # Kept for compatibility. Prefer #token_state: this collapses "revoked"
25
+ # and "could not tell" into the same false.
7
26
  def token_valid?
8
- user = get('user').body
9
- return true if user&.fetch("id")
10
- rescue => e
11
- return false
27
+ token_state == :valid
12
28
  end
13
-
29
+
14
30
  # Pre-qualify an application of WOTC status
15
31
  def wotc_calculator(options={})
16
32
  result = post('wotc/calculator', options)
@@ -18,4 +34,4 @@ module WOTC
18
34
  end
19
35
  end
20
36
  end
21
- end
37
+ end
@@ -17,7 +17,9 @@ module WOTC
17
17
  }.merge(connection_options)
18
18
 
19
19
  Faraday::Connection.new(options) do |conn|
20
- conn.authorization :Bearer, access_token
20
+ # Faraday 1.8+ middleware form; Connection#authorization is deprecated
21
+ # and removed in Faraday 2.0.
22
+ conn.request :authorization, :Bearer, access_token
21
23
  # https://github.com/lostisland/faraday/issues/417#issuecomment-223413386
22
24
  conn.options[:timeout] = timeout
23
25
  conn.options[:open_timeout] = open_timeout
data/lib/wotc/error.rb CHANGED
@@ -6,8 +6,10 @@ module WOTC
6
6
  def initialize(response)
7
7
  @response = response.dup
8
8
  env = response.env
9
- # Use hash-style access for :method to avoid calling Kernel#method
10
- @http_method = env[:method].to_s.upcase.presence || "UNKNOWN"
9
+ # Use hash-style access for :method to avoid calling Kernel#method.
10
+ # Plain Ruby only: this gem does not depend on ActiveSupport.
11
+ http_method = env[:method].to_s.upcase
12
+ @http_method = http_method.empty? ? "UNKNOWN" : http_method
11
13
  @url = env.url.to_s
12
14
  @status = response.status
13
15
  @body = response.body
@@ -42,27 +44,47 @@ module WOTC
42
44
  end
43
45
  end
44
46
 
47
+ # Any 4xx we do not name below. Our request was not accepted.
48
+ class ClientError < Error; end
49
+
50
+ # Any 5xx we do not name below. wotc.com could not answer. Retryable.
51
+ class ServerError < Error; end
52
+
45
53
  # Raised when wotc.com returns the HTTP status code 400
46
- class BadRequest < Error; end
54
+ class BadRequest < ClientError; end
55
+
56
+ # Raised when wotc.com returns the HTTP status code 401. This is the only
57
+ # status that means our access token was rejected.
58
+ class Unauthorized < ClientError; end
47
59
 
48
- # Raised when wotc.com returns the HTTP status code 401
49
- class Unauthorized < Error; end
60
+ # Raised when wotc.com returns the HTTP status code 403. Distinct from 401:
61
+ # the token authenticated, the action was refused, often because the resource
62
+ # does not exist or does not belong to this account.
63
+ class Forbidden < ClientError; end
50
64
 
51
65
  # Raised when wotc.com returns the HTTP status code 404
52
- class NotFound < Error; end
66
+ class NotFound < ClientError; end
67
+
68
+ # Raised when wotc.com returns the HTTP status code 422
69
+ class UnprocessableEntity < ClientError; end
70
+
71
+ # Raised when wotc.com returns the HTTP status code 429
72
+ class TooManyRequests < ClientError; end
53
73
 
54
74
  # Raised when wotc.com returns the HTTP status code 500
55
- class InternalServerError < Error; end
75
+ class InternalServerError < ServerError; end
56
76
 
57
77
  # Raised when wotc.com returns the HTTP status code 502
58
- class BadGateway < Error; end
78
+ class BadGateway < ServerError; end
59
79
 
60
80
  # Raised when wotc.com returns the HTTP status code 503
61
- class ServiceUnavailable < Error; end
81
+ class ServiceUnavailable < ServerError; end
62
82
 
63
83
  # Raised when wotc.com returns the HTTP status code 504
64
- class GatewayTimeout < Error; end
84
+ class GatewayTimeout < ServerError; end
65
85
 
66
- # Raised when client fails to provide required parameters.
67
- class MissingRequiredArgument < Error; end
86
+ # Raised when client code fails to provide required parameters — before any
87
+ # HTTP request exists. Unlike every class above it carries a plain message,
88
+ # not a Faraday::Response, so it cannot inherit Error#initialize.
89
+ class MissingRequiredArgument < StandardError; end
68
90
  end
data/lib/wotc/request.rb CHANGED
@@ -1,5 +1,3 @@
1
- require 'base64'
2
-
3
1
  module WOTC
4
2
  # Defines HTTP request methods
5
3
  module Request
data/lib/wotc/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module WOTC
2
- VERSION = '0.1.14'
2
+ VERSION = '0.1.15'
3
3
  end
data/wotc.gemspec CHANGED
@@ -40,7 +40,8 @@ Gem::Specification.new do |spec|
40
40
  spec.add_development_dependency "rspec", ">= 3.9.0"
41
41
  spec.add_development_dependency "pry"
42
42
  spec.add_development_dependency "webmock"
43
- spec.add_runtime_dependency 'faraday'
43
+ # >= 1.8 for the unified `request :authorization` middleware.
44
+ spec.add_runtime_dependency 'faraday', '>= 1.8'
44
45
  spec.add_runtime_dependency 'faraday_middleware'
45
46
  spec.add_runtime_dependency 'addressable'
46
47
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: wotc
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.14
4
+ version: 0.1.15
5
5
  platform: ruby
6
6
  authors:
7
7
  - workstream.us
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2026-03-16 00:00:00.000000000 Z
11
+ date: 2026-07-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -86,14 +86,14 @@ dependencies:
86
86
  requirements:
87
87
  - - ">="
88
88
  - !ruby/object:Gem::Version
89
- version: '0'
89
+ version: '1.8'
90
90
  type: :runtime
91
91
  prerelease: false
92
92
  version_requirements: !ruby/object:Gem::Requirement
93
93
  requirements:
94
94
  - - ">="
95
95
  - !ruby/object:Gem::Version
96
- version: '0'
96
+ version: '1.8'
97
97
  - !ruby/object:Gem::Dependency
98
98
  name: faraday_middleware
99
99
  requirement: !ruby/object:Gem::Requirement
@@ -129,8 +129,10 @@ executables: []
129
129
  extensions: []
130
130
  extra_rdoc_files: []
131
131
  files:
132
+ - ".github/workflows/test.yml"
132
133
  - ".gitignore"
133
134
  - ".rakeTasks"
135
+ - ".ruby-version"
134
136
  - ".travis.yml"
135
137
  - CHANGELOG.md
136
138
  - CODE_OF_CONDUCT.md
@@ -183,7 +185,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
183
185
  - !ruby/object:Gem::Version
184
186
  version: '0'
185
187
  requirements: []
186
- rubygems_version: 3.5.20
188
+ rubygems_version: 3.2.33
187
189
  signing_key:
188
190
  specification_version: 4
189
191
  summary: Ruby wrapper for wotc.com APIs