toast 1.0.8 → 1.0.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 +4 -4
- data/README.md +1 -1
- data/lib/toast.rb +12 -3
- data/lib/toast/config_dsl/base.rb +15 -3
- data/lib/toast/errors.rb +3 -0
- data/lib/toast/rack_app.rb +10 -9
- data/lib/toast/request_helpers.rb +13 -9
- data/lib/toast/version.rb +1 -1
- metadata +2 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA1:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 013c0b6f57e6509f8555a3bb9a4886e1abaf3f33
|
|
4
|
+
data.tar.gz: 317ecb00aeaff9b9c7e3faf0271119e956d96075
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: f14236d4f0d9d5bb2f4959c36e759bf2d51b1509dbd31b1b4c2560fa31c2a8cbe90c335e73b533fecc7c95bf8588cedcef1681f858ff4694b9ce1f6e45a9b3ee
|
|
7
|
+
data.tar.gz: 8cdb9770f943e081eb7e9d099de3214cb7ab167dc25558162ae0300beb05cfabd29b0508c891cdd3a8d0aa3a9a94b827bf0769b05a4392256d586d477aad16fa
|
data/README.md
CHANGED
|
@@ -20,7 +20,7 @@ Other features are:
|
|
|
20
20
|
* attribute selection per request
|
|
21
21
|
* processing of URI parameters
|
|
22
22
|
|
|
23
|
-
See the [User Manual](https://
|
|
23
|
+
See the [User Manual](https://robert-annies.github.io/toast) for a detailed description.
|
|
24
24
|
|
|
25
25
|
Releases
|
|
26
26
|
========
|
data/lib/toast.rb
CHANGED
|
@@ -15,7 +15,7 @@ module Toast
|
|
|
15
15
|
# path tree to resolve the requested model
|
|
16
16
|
@@path_tree = {}
|
|
17
17
|
|
|
18
|
-
cattr_accessor :expositions, :settings, :path_tree
|
|
18
|
+
cattr_accessor :expositions, :settings, :path_tree, :request
|
|
19
19
|
|
|
20
20
|
class ConfigError < StandardError
|
|
21
21
|
end
|
|
@@ -59,7 +59,7 @@ module Toast
|
|
|
59
59
|
|
|
60
60
|
def self.info str
|
|
61
61
|
if Rails.const_defined?('Server') # only on console server
|
|
62
|
-
puts Toast::Sym+' Toast: '+str
|
|
62
|
+
puts Toast::Sym+' Toast: '+str
|
|
63
63
|
end
|
|
64
64
|
end
|
|
65
65
|
|
|
@@ -82,7 +82,7 @@ module Toast
|
|
|
82
82
|
# base_uri must be passed to be prepended in URIs
|
|
83
83
|
def self.represent instance, base_uri = ''
|
|
84
84
|
|
|
85
|
-
# using RequestHelper#represent_one method with a mocked up object
|
|
85
|
+
# using RequestHelper#represent_one method with a mocked up object :-/
|
|
86
86
|
obj = Object.new
|
|
87
87
|
class << obj
|
|
88
88
|
include Toast::RequestHelpers
|
|
@@ -91,4 +91,13 @@ module Toast
|
|
|
91
91
|
obj.base_uri = base_uri
|
|
92
92
|
obj.represent_one(instance, obj.get_config(instance.class) )
|
|
93
93
|
end
|
|
94
|
+
|
|
95
|
+
def self.base_uri
|
|
96
|
+
raise Toast::NotInRequestContext unless request
|
|
97
|
+
|
|
98
|
+
port = ":#{request.port}" unless request.port.in?([80,443])
|
|
99
|
+
# remove recource path part form full path (namespace remains)
|
|
100
|
+
path = request.path.sub(request.path_parameters[:toast_path],'')
|
|
101
|
+
(request.protocol + request.host + port.to_s + path).chomp('/')
|
|
102
|
+
end
|
|
94
103
|
end
|
|
@@ -20,11 +20,14 @@ class Toast::ConfigDSL::Base
|
|
|
20
20
|
raise_config_error 'Block expected.'
|
|
21
21
|
end
|
|
22
22
|
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
|
|
23
26
|
# register base path with 'under' prefix
|
|
24
|
-
to_path_tree = lambda do |path|
|
|
27
|
+
to_path_tree = lambda do |path|
|
|
25
28
|
if path.empty?
|
|
26
29
|
{ model_class.to_s.underscore.pluralize => model_class }
|
|
27
|
-
else
|
|
30
|
+
else
|
|
28
31
|
{ path.first => to_path_tree.call(path[1..-1]) }
|
|
29
32
|
end
|
|
30
33
|
end
|
|
@@ -34,6 +37,15 @@ class Toast::ConfigDSL::Base
|
|
|
34
37
|
raise_config_error "multiple definitions of endpoint URI segment `.../#{key}/...'"
|
|
35
38
|
end
|
|
36
39
|
|
|
40
|
+
# externd model_class with toast_uri accessor
|
|
41
|
+
model_class.send(:define_method, :toast_full_uri) do
|
|
42
|
+
Toast.base_uri + '/' + self.toast_local_uri
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
model_class.send(:define_method, :toast_local_uri) do
|
|
46
|
+
[path, self.class.name.underscore.pluralize, self.id].delete_if(&:blank?).join('/')
|
|
47
|
+
end
|
|
48
|
+
|
|
37
49
|
# base config object
|
|
38
50
|
config_data = OpenStruct.new
|
|
39
51
|
|
|
@@ -43,7 +55,7 @@ class Toast::ConfigDSL::Base
|
|
|
43
55
|
self.model_class = model_class
|
|
44
56
|
self.media_type = as
|
|
45
57
|
self.prefix_path = path
|
|
46
|
-
|
|
58
|
+
|
|
47
59
|
# defaults
|
|
48
60
|
self.readables = []
|
|
49
61
|
self.writables = []
|
data/lib/toast/errors.rb
CHANGED
data/lib/toast/rack_app.rb
CHANGED
|
@@ -6,7 +6,7 @@ require 'toast/plural_assoc_request'
|
|
|
6
6
|
require 'toast/errors'
|
|
7
7
|
|
|
8
8
|
class Toast::RackApp
|
|
9
|
-
# NOTE: the RackApp object is shared in threads of concurrent requests
|
|
9
|
+
# NOTE: the RackApp object is shared in threads of concurrent requests
|
|
10
10
|
# (e.g. when using Puma server, but not in Passenger (single-threded, multi-process)).
|
|
11
11
|
# Anyays, don't use any instance vars (@ variables in #call).
|
|
12
12
|
# It causes chaos
|
|
@@ -16,17 +16,18 @@ class Toast::RackApp
|
|
|
16
16
|
def call(env)
|
|
17
17
|
|
|
18
18
|
request = ActionDispatch::Request.new(env)
|
|
19
|
-
|
|
19
|
+
Toast.request = request
|
|
20
|
+
|
|
20
21
|
Toast.logger.info "[#{Thread.current.object_id}] processing: <#{URI.decode(request.fullpath)}>"
|
|
21
22
|
|
|
22
|
-
# Authentication: respond with 401 on exception or falsy return value:
|
|
23
|
+
# Authentication: respond with 401 on exception or falsy return value:
|
|
23
24
|
begin
|
|
24
25
|
unless (auth = Toast::ConfigDSL::Settings::AuthenticateContext.new.
|
|
25
26
|
instance_exec(request, &Toast.settings.authenticate))
|
|
26
27
|
return response :unauthorized, msg: "authentication failed"
|
|
27
28
|
end
|
|
28
|
-
rescue Toast::Errors::CustomAuthFailure => caf
|
|
29
|
-
return response(caf.response_data[:status] || :unauthorized,
|
|
29
|
+
rescue Toast::Errors::CustomAuthFailure => caf
|
|
30
|
+
return response(caf.response_data[:status] || :unauthorized,
|
|
30
31
|
msg: caf.response_data[:body],
|
|
31
32
|
headers: caf.response_data[:headers])
|
|
32
33
|
rescue => error
|
|
@@ -34,7 +35,7 @@ class Toast::RackApp
|
|
|
34
35
|
end
|
|
35
36
|
|
|
36
37
|
path = request.path_parameters[:toast_path].split('/')
|
|
37
|
-
|
|
38
|
+
|
|
38
39
|
# look up requested model
|
|
39
40
|
model_class = resolve_model(path, Toast.path_tree)
|
|
40
41
|
|
|
@@ -120,15 +121,15 @@ class Toast::RackApp
|
|
|
120
121
|
end
|
|
121
122
|
|
|
122
123
|
private
|
|
123
|
-
# gets the model class from the
|
|
124
|
+
# gets the model class from the
|
|
124
125
|
# it's similar to Hash#dig but stops at a non string
|
|
125
126
|
def resolve_model path, path_tree
|
|
126
|
-
if path_tree[ path.first ].is_a?(Hash)
|
|
127
|
+
if path_tree[ path.first ].is_a?(Hash)
|
|
127
128
|
# dig deeper
|
|
128
129
|
resolve_model(path[1..-1], path_tree[ path.first ])
|
|
129
130
|
else
|
|
130
131
|
path_tree[ path.first ]
|
|
131
132
|
end
|
|
132
|
-
end
|
|
133
|
+
end
|
|
133
134
|
end
|
|
134
135
|
|
|
@@ -8,13 +8,8 @@ module Toast::RequestHelpers
|
|
|
8
8
|
end || raise(Toast::Errors::ConfigNotFound)
|
|
9
9
|
end
|
|
10
10
|
|
|
11
|
-
# this is hard when behind a proxy
|
|
12
|
-
# relies on HTTP_X_FORWARDED* headers
|
|
13
11
|
def base_uri request
|
|
14
|
-
|
|
15
|
-
# remove recource path part form full path (namespace remains)
|
|
16
|
-
path = request.path.sub(request.path_parameters[:toast_path],'')
|
|
17
|
-
(request.protocol + request.host + port.to_s + path).chomp('/')
|
|
12
|
+
Toast.base_uri
|
|
18
13
|
end
|
|
19
14
|
|
|
20
15
|
# split the name and id of the resource from a LinkHeader
|
|
@@ -25,12 +20,21 @@ module Toast::RequestHelpers
|
|
|
25
20
|
def represent_one record, config
|
|
26
21
|
result = {}
|
|
27
22
|
|
|
23
|
+
model_uri = [@base_uri, config.prefix_path, record.class.name.underscore.pluralize].delete_if(&:blank?).join('/')
|
|
24
|
+
|
|
25
|
+
# can we inject model_uri into the recortd, so that virtual attribute methods can use it in their result?
|
|
26
|
+
|
|
27
|
+
# - setting a special property on the record :-/, OK Toast could extend all exposed classes by a special accessor,
|
|
28
|
+
# maybe only if configured.
|
|
29
|
+
# - calling somehow this method in different/extended context (how?)
|
|
30
|
+
# - passing this as parameter, while not requiring all the attribute methods to accept a 2. arg (possible?)
|
|
31
|
+
# - If the result is a String it can return a templated String like "{{ toast_uri }}", OK for single
|
|
32
|
+
# strings, but for mebedded Hashes with Strings no, too expensive.
|
|
33
|
+
|
|
28
34
|
(config.readables + config.writables).each do |attr|
|
|
29
35
|
result[attr.to_s] = record.send(attr) if attr_selected?(attr)
|
|
30
36
|
end
|
|
31
37
|
|
|
32
|
-
model_uri = [@base_uri, config.prefix_path, record.class.name.underscore.pluralize].delete_if(&:blank?).join('/')
|
|
33
|
-
|
|
34
38
|
result['self'] = "#{model_uri}/#{record.id}" if attr_selected?('self')
|
|
35
39
|
|
|
36
40
|
# add associations, collections and singles
|
|
@@ -127,7 +131,7 @@ module Toast::RequestHelpers
|
|
|
127
131
|
rescue Toast::Errors::BadRequest
|
|
128
132
|
raise # re-raise
|
|
129
133
|
rescue => error
|
|
130
|
-
raise Toast::Errors::HandlerError.new(error, error.backtrace.first.sub
|
|
134
|
+
raise Toast::Errors::HandlerError.new(error, error.backtrace.first.try(:sub,/:in.*/,''))
|
|
131
135
|
end
|
|
132
136
|
result
|
|
133
137
|
end
|
data/lib/toast/version.rb
CHANGED
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: toast
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 1.0.
|
|
4
|
+
version: 1.0.9
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- robokopp (Robert Annies)
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: bin
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2019-
|
|
11
|
+
date: 2019-03-04 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: rails
|