shaf 0.6.0 → 0.7.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +0 -0
- data.tar.gz.sig +0 -0
- data/lib/shaf/extensions.rb +2 -0
- data/lib/shaf/extensions/controller_hooks.rb +47 -0
- data/lib/shaf/extensions/resource_uris.rb +96 -13
- data/lib/shaf/formable/field.rb +3 -3
- data/lib/shaf/formable/form.rb +1 -1
- data/lib/shaf/generator/templates/api/controller.rb.erb +7 -7
- data/lib/shaf/generator/templates/spec/integration_spec.rb.erb +2 -1
- data/lib/shaf/tasks.rb +1 -0
- data/lib/shaf/tasks/routes_task.rb +28 -0
- data/lib/shaf/version.rb +1 -1
- metadata +4 -2
- metadata.gz.sig +0 -0
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 9123190de71ec1df3a8c53c32a8f7e26a72b42bf6255fe2e0613cd0ee5f15837
|
4
|
+
data.tar.gz: 53f39cd9d1283771a638a4f1a53f85e79e9f329b0dacb8f7dd3ce08ed54d8199
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9713237dc988ae3a336016338ad711d59766533a68f88db7bbec9da70ac349906f779abef11cf8e9fb3b3865b652120cc756f8a0bd6558d0a7406405b7122ee6
|
7
|
+
data.tar.gz: 5f80c980f49450f27e1b17b3a13b1d3b724c43c7ae75c297cce54807b1a2a99920159171be152da6dd0fa6d7c239dd0e1e42d4cd08307c3d91f393f730ec5038
|
checksums.yaml.gz.sig
CHANGED
Binary file
|
data.tar.gz.sig
CHANGED
Binary file
|
data/lib/shaf/extensions.rb
CHANGED
@@ -1,4 +1,5 @@
|
|
1
1
|
require 'shaf/extensions/resource_uris'
|
2
|
+
require 'shaf/extensions/controller_hooks'
|
2
3
|
require 'shaf/extensions/current_user'
|
3
4
|
require 'shaf/extensions/authorize'
|
4
5
|
require 'shaf/extensions/symbolic_routes'
|
@@ -7,6 +8,7 @@ module Shaf
|
|
7
8
|
def self.extensions
|
8
9
|
[
|
9
10
|
ResourceUris,
|
11
|
+
ControllerHooks,
|
10
12
|
CurrentUser,
|
11
13
|
Authorize,
|
12
14
|
SymbolicRoutes
|
@@ -0,0 +1,47 @@
|
|
1
|
+
require 'sinatra/base'
|
2
|
+
|
3
|
+
module Shaf
|
4
|
+
module ControllerHooks
|
5
|
+
def before_action(method_name = nil, **options, &block)
|
6
|
+
__action_hook(:before, method_name, block, options)
|
7
|
+
end
|
8
|
+
|
9
|
+
def after_action(method_name = nil, **options, &block)
|
10
|
+
__action_hook(:after, method_name, block, options)
|
11
|
+
end
|
12
|
+
|
13
|
+
private
|
14
|
+
|
15
|
+
def __action_hook(hook, method_name, block, **options)
|
16
|
+
only = Array(options[:only]) if options.key? :only
|
17
|
+
except = Array(options[:except]) if options.key? :except
|
18
|
+
|
19
|
+
path_helpers.each do |helper|
|
20
|
+
next if only && !only.include?(helper)
|
21
|
+
next if except&.include? helper
|
22
|
+
pattern = __path_pattern(helper)
|
23
|
+
|
24
|
+
if method_name
|
25
|
+
send(hook, pattern) { send(method_name) }
|
26
|
+
elsif block
|
27
|
+
send(hook, pattern, &block)
|
28
|
+
else
|
29
|
+
log.warn <<~RUBY
|
30
|
+
#{hook}_action without block (options: #{options}).
|
31
|
+
Specify method or pass a block!
|
32
|
+
RUBY
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
def __path_pattern(path_helper)
|
38
|
+
uri_helper = path_helper.to_s.sub(/path\Z/, 'uri')
|
39
|
+
template_method = "#{uri_helper}_template".to_sym
|
40
|
+
template = send template_method
|
41
|
+
str = template.gsub(%r{:[^/]*}, '\w+')
|
42
|
+
Regexp.new("#{str}/?")
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
Sinatra.register ControllerHooks
|
47
|
+
end
|
@@ -2,14 +2,25 @@ require 'sinatra/base'
|
|
2
2
|
|
3
3
|
module Shaf
|
4
4
|
module ResourceUris
|
5
|
+
class UriHelperMethodAlreadyExistError < Error
|
6
|
+
def initialize(resource_name, method_name)
|
7
|
+
super(
|
8
|
+
"resource uri #{resource_name} can't be registered. " \
|
9
|
+
"Method :#{method_name} already exist!"
|
10
|
+
)
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
5
14
|
def resource_uris_for(*args)
|
6
|
-
CreateUriMethods.new(*args).call
|
15
|
+
result = CreateUriMethods.new(*args).call
|
16
|
+
UriHelperMethods.add_path_helpers(self, result)
|
7
17
|
|
8
18
|
include UriHelper unless self < UriHelper
|
9
19
|
end
|
10
20
|
|
11
21
|
def register_uri(name, uri)
|
12
|
-
MethodBuilder.new(name, uri).call
|
22
|
+
result = MethodBuilder.new(name, uri).call
|
23
|
+
UriHelperMethods.add_path_helpers(self, result)
|
13
24
|
|
14
25
|
include UriHelper unless self < UriHelper
|
15
26
|
end
|
@@ -18,12 +29,39 @@ module Shaf
|
|
18
29
|
Sinatra.register ResourceUris
|
19
30
|
|
20
31
|
module UriHelperMethods
|
21
|
-
|
22
|
-
|
32
|
+
class << self
|
33
|
+
def register(name, &block)
|
34
|
+
define_method(name, &block)
|
35
|
+
end
|
36
|
+
|
37
|
+
def eval_method(str)
|
38
|
+
class_eval str
|
39
|
+
end
|
40
|
+
|
41
|
+
def add_path_helpers(clazz, methods)
|
42
|
+
@path_helpers ||= {}
|
43
|
+
@path_helpers[clazz] ||= []
|
44
|
+
@path_helpers[clazz].concat Array(methods)
|
45
|
+
end
|
46
|
+
|
47
|
+
def path_helpers_for(clazz = nil)
|
48
|
+
@path_helpers ||= {}
|
49
|
+
return @path_helpers unless clazz
|
50
|
+
return [] unless @path_helpers.key?(clazz)
|
51
|
+
@path_helpers[clazz] ||= []
|
52
|
+
end
|
53
|
+
|
54
|
+
# For cleaning up after tests
|
55
|
+
def remove_all
|
56
|
+
helpers = instance_methods - [:path_helpers]
|
57
|
+
remove_method(*helpers)
|
58
|
+
@path_helpers = {}
|
59
|
+
end
|
23
60
|
end
|
24
61
|
|
25
|
-
def
|
26
|
-
|
62
|
+
def path_helpers
|
63
|
+
clazz = is_a?(Class) ? self : self.class
|
64
|
+
UriHelperMethods.path_helpers_for clazz
|
27
65
|
end
|
28
66
|
end
|
29
67
|
|
@@ -46,13 +84,13 @@ module Shaf
|
|
46
84
|
# This class register uri helper methods like:
|
47
85
|
# books_uri => /books
|
48
86
|
# book_uri(book) => /books/5
|
49
|
-
# new_book_uri => /
|
87
|
+
# new_book_uri => /book/form
|
50
88
|
# edit_book_uri(book) => /books/5/edit
|
51
89
|
#
|
52
90
|
# And uri template methods:
|
53
91
|
# books_uri_template => /books
|
54
92
|
# book_uri_template => /books/:id
|
55
|
-
# new_book_uri_template => /
|
93
|
+
# new_book_uri_template => /book/form
|
56
94
|
# edit_book_uri_template => /books/:id/edit
|
57
95
|
#
|
58
96
|
class CreateUriMethods
|
@@ -61,6 +99,7 @@ module Shaf
|
|
61
99
|
@name = name.to_s
|
62
100
|
@base = base&.sub(%r(/\Z), '') || ''
|
63
101
|
@plural_name = plural_name&.to_s || Utils::pluralize(name.to_s)
|
102
|
+
@added_path_methods = []
|
64
103
|
end
|
65
104
|
|
66
105
|
def call
|
@@ -72,6 +111,7 @@ module Shaf
|
|
72
111
|
end
|
73
112
|
register_new_resource_uri
|
74
113
|
register_edit_resource_uri
|
114
|
+
@added_path_methods
|
75
115
|
end
|
76
116
|
|
77
117
|
private
|
@@ -95,11 +135,12 @@ module Shaf
|
|
95
135
|
resource_template_uri = "#{base}/#{plural_name}/:id"
|
96
136
|
collection_template_uri = "#{base}/#{plural_name}"
|
97
137
|
|
98
|
-
MethodBuilder.new(name, resource_template_uri, alt_uri: collection_template_uri)
|
138
|
+
builder = MethodBuilder.new(name, resource_template_uri, alt_uri: collection_template_uri)
|
139
|
+
@added_path_methods << builder.call
|
99
140
|
end
|
100
141
|
|
101
142
|
def register_new_resource_uri
|
102
|
-
template_uri = "#{base}/#{
|
143
|
+
template_uri = "#{base}/#{name}/form".freeze
|
103
144
|
register("new_#{name}", template_uri)
|
104
145
|
end
|
105
146
|
|
@@ -109,7 +150,8 @@ module Shaf
|
|
109
150
|
end
|
110
151
|
|
111
152
|
def register(name, template_uri)
|
112
|
-
MethodBuilder.new(name, template_uri)
|
153
|
+
builder = MethodBuilder.new(name, template_uri)
|
154
|
+
@added_path_methods << builder.call
|
113
155
|
end
|
114
156
|
end
|
115
157
|
|
@@ -127,8 +169,8 @@ module Shaf
|
|
127
169
|
|
128
170
|
def call
|
129
171
|
if UriHelper.respond_to? uri_method_name
|
130
|
-
|
131
|
-
|
172
|
+
exception = ResourceUris::UriHelperMethodAlreadyExistError
|
173
|
+
raise exception.new(@name, uri_method_name)
|
132
174
|
end
|
133
175
|
|
134
176
|
if @alt_uri.nil?
|
@@ -144,12 +186,18 @@ module Shaf
|
|
144
186
|
UriHelperMethods.eval_method uri_method_string
|
145
187
|
UriHelperMethods.eval_method path_method_string
|
146
188
|
UriHelperMethods.register(template_method_name, &template_proc)
|
189
|
+
UriHelperMethods.register(legacy_template_method_name, &template_proc)
|
190
|
+
UriHelperMethods.register(path_matcher_name, &path_matcher_proc)
|
191
|
+
path_method_name.to_sym
|
147
192
|
end
|
148
193
|
|
149
194
|
def build_methods_with_optional_arg
|
150
195
|
UriHelperMethods.eval_method uri_method_with_optional_arg_string
|
151
196
|
UriHelperMethods.eval_method path_method_with_optional_arg_string
|
152
197
|
UriHelperMethods.register(template_method_name, &template_proc)
|
198
|
+
UriHelperMethods.register(legacy_template_method_name, &template_proc)
|
199
|
+
UriHelperMethods.register(path_matcher_name, &path_matcher_proc)
|
200
|
+
path_method_name.to_sym
|
153
201
|
end
|
154
202
|
|
155
203
|
def uri_method_name
|
@@ -160,7 +208,15 @@ module Shaf
|
|
160
208
|
"#{@name}_path".freeze
|
161
209
|
end
|
162
210
|
|
211
|
+
def path_matcher_name
|
212
|
+
:"#{path_method_name}?"
|
213
|
+
end
|
214
|
+
|
163
215
|
def template_method_name
|
216
|
+
"#{path_method_name}_template".freeze
|
217
|
+
end
|
218
|
+
|
219
|
+
def legacy_template_method_name
|
164
220
|
"#{uri_method_name}_template".freeze
|
165
221
|
end
|
166
222
|
|
@@ -268,5 +324,32 @@ module Shaf
|
|
268
324
|
->(collection = false) { collection ? alt_uri : uri }
|
269
325
|
end
|
270
326
|
end
|
327
|
+
|
328
|
+
def path_mather_patterns
|
329
|
+
[
|
330
|
+
@uri.gsub(%r{:[^/]*}, '\w+'),
|
331
|
+
@alt_uri&.gsub(%r{:[^/]*}, '\w+')
|
332
|
+
].compact.map { |str| Regexp.new("\\A#{str}\\Z") }
|
333
|
+
end
|
334
|
+
|
335
|
+
def path_matcher_proc
|
336
|
+
patterns = path_mather_patterns
|
337
|
+
|
338
|
+
lambda do |path = nil, collection: false|
|
339
|
+
unless path
|
340
|
+
r = request if respond_to? :request
|
341
|
+
path = r.path_info if r&.respond_to? :path_info
|
342
|
+
|
343
|
+
unless path
|
344
|
+
raise(
|
345
|
+
ArgumentError,
|
346
|
+
"Uri must be given (or #{self} should respond to :request)"
|
347
|
+
)
|
348
|
+
end
|
349
|
+
end
|
350
|
+
pattern = collection ? patterns.last : patterns.first
|
351
|
+
!!(pattern =~ path)
|
352
|
+
end
|
353
|
+
end
|
271
354
|
end
|
272
355
|
end
|
data/lib/shaf/formable/field.rb
CHANGED
@@ -8,13 +8,13 @@ module Shaf
|
|
8
8
|
immutable_reader :name, :type, :value, :label, :required
|
9
9
|
|
10
10
|
HTML_TYPE_MAPPINGS = {
|
11
|
-
|
12
|
-
|
11
|
+
string: 'text',
|
12
|
+
boolean: 'checkbox'
|
13
13
|
}.freeze
|
14
14
|
|
15
15
|
def initialize(name, params = {})
|
16
16
|
@name = name
|
17
|
-
@type = params[:type]
|
17
|
+
@type = params[:type]&.to_sym
|
18
18
|
@label = params[:label]
|
19
19
|
@has_value = params.key? :value
|
20
20
|
@value = params[:value]
|
data/lib/shaf/formable/form.rb
CHANGED
@@ -6,43 +6,43 @@ class <%= controller_class_name %> < BaseController
|
|
6
6
|
|
7
7
|
resource_uris_for :<%= name %>
|
8
8
|
|
9
|
-
get :<%= plural_name %>
|
9
|
+
get :<%= plural_name %>_path do
|
10
10
|
authorize! :read
|
11
11
|
collection = paginate(<%= model_class_name %>.order(:created_at).reverse)
|
12
12
|
respond_with_collection collection, serializer: <%= serializer_class_name %>
|
13
13
|
end
|
14
14
|
|
15
|
-
get :new_<%= name %>
|
15
|
+
get :new_<%= name %>_path do
|
16
16
|
authorize! :read
|
17
17
|
cache_control(:private, http_cache_max_age: :short)
|
18
18
|
respond_with create_form
|
19
19
|
end
|
20
20
|
|
21
|
-
post :<%= plural_name %>
|
21
|
+
post :<%= plural_name %>_path do
|
22
22
|
authorize! :write
|
23
23
|
<%= name %> = <%= model_class_name %>.create(<%= name %>_params)
|
24
24
|
headers({ "Location" => <%= name %>_uri(<%= name %>) })
|
25
25
|
respond_with <%= name %>, status: 201
|
26
26
|
end
|
27
27
|
|
28
|
-
get :<%= name %>
|
28
|
+
get :<%= name %>_path do
|
29
29
|
authorize! :read
|
30
30
|
respond_with <%= name %>
|
31
31
|
end
|
32
32
|
|
33
|
-
get :edit_<%= name %>
|
33
|
+
get :edit_<%= name %>_path do
|
34
34
|
authorize! :read
|
35
35
|
cache_control(:private, http_cache_max_age: :short)
|
36
36
|
respond_with edit_form
|
37
37
|
end
|
38
38
|
|
39
|
-
put :<%= name %>
|
39
|
+
put :<%= name %>_path do
|
40
40
|
authorize! :write
|
41
41
|
<%= name %>.update(<%= name %>_params)
|
42
42
|
respond_with <%= name %>
|
43
43
|
end
|
44
44
|
|
45
|
-
delete :<%= name %>
|
45
|
+
delete :<%= name %>_path do
|
46
46
|
authorize! :write
|
47
47
|
<%= name %>.destroy
|
48
48
|
status 204
|
@@ -30,7 +30,7 @@ describe <%= model_class_name %>, type: :integration do
|
|
30
30
|
<% end -%>
|
31
31
|
end
|
32
32
|
end
|
33
|
-
|
33
|
+
<% if params.size > 0 %>
|
34
34
|
it "can create <%= plural_name %>" do
|
35
35
|
get <%= plural_name %>_uri
|
36
36
|
|
@@ -88,6 +88,7 @@ describe <%= model_class_name %>, type: :integration do
|
|
88
88
|
status.must_equal 200
|
89
89
|
link_rels.must_include(:self)
|
90
90
|
end
|
91
|
+
<% end -%>
|
91
92
|
|
92
93
|
it "<%= plural_name %> can be deleted" do
|
93
94
|
<%= name %> = <%= model_class_name %>.create
|
data/lib/shaf/tasks.rb
CHANGED
@@ -0,0 +1,28 @@
|
|
1
|
+
module Shaf
|
2
|
+
module Tasks
|
3
|
+
class RoutesTask
|
4
|
+
include Rake::DSL
|
5
|
+
|
6
|
+
def initialize(*)
|
7
|
+
desc "List path helpers"
|
8
|
+
task :routes do
|
9
|
+
require 'shaf/utils'
|
10
|
+
require 'config/database'
|
11
|
+
|
12
|
+
extend Shaf::Utils
|
13
|
+
bootstrap
|
14
|
+
|
15
|
+
UriHelperMethods.path_helpers_for.each do |controller, methods|
|
16
|
+
puts "\n#{controller}:"
|
17
|
+
methods.each do |method|
|
18
|
+
template_method = "#{method}_template".to_sym
|
19
|
+
puts sprintf( "%-60s%s" , method, controller.send(template_method))
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
RoutesTask.new
|
27
|
+
end
|
28
|
+
end
|
data/lib/shaf/version.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: shaf
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.7.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Sammy Henningsson
|
@@ -30,7 +30,7 @@ cert_chain:
|
|
30
30
|
ZMhjYR7sRczGJx+GxGU2EaR0bjRsPVlC4ywtFxoOfRG3WaJcpWGEoAoMJX6Z0bRv
|
31
31
|
M40=
|
32
32
|
-----END CERTIFICATE-----
|
33
|
-
date: 2018-11-
|
33
|
+
date: 2018-11-24 00:00:00.000000000 Z
|
34
34
|
dependencies:
|
35
35
|
- !ruby/object:Gem::Dependency
|
36
36
|
name: rake
|
@@ -133,6 +133,7 @@ files:
|
|
133
133
|
- lib/shaf/errors.rb
|
134
134
|
- lib/shaf/extensions.rb
|
135
135
|
- lib/shaf/extensions/authorize.rb
|
136
|
+
- lib/shaf/extensions/controller_hooks.rb
|
136
137
|
- lib/shaf/extensions/current_user.rb
|
137
138
|
- lib/shaf/extensions/resource_uris.rb
|
138
139
|
- lib/shaf/extensions/symbolic_routes.rb
|
@@ -188,6 +189,7 @@ files:
|
|
188
189
|
- lib/shaf/tasks.rb
|
189
190
|
- lib/shaf/tasks/api_doc_task.rb
|
190
191
|
- lib/shaf/tasks/db_task.rb
|
192
|
+
- lib/shaf/tasks/routes_task.rb
|
191
193
|
- lib/shaf/tasks/test_task.rb
|
192
194
|
- lib/shaf/upgrade.rb
|
193
195
|
- lib/shaf/upgrade/manifest.rb
|
metadata.gz.sig
CHANGED
Binary file
|