autoforme 1.0.3 → 1.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG +4 -0
- data/MIT-LICENSE +1 -1
- data/README.rdoc +17 -2
- data/lib/autoforme/framework.rb +22 -2
- data/lib/autoforme/model.rb +16 -5
- data/lib/autoforme/models/sequel.rb +5 -5
- data/lib/autoforme/version.rb +1 -1
- data/spec/associations_spec.rb +5 -5
- data/spec/basic_spec.rb +82 -9
- data/spec/mtm_spec.rb +4 -4
- 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: 728834eb84059f820d99421609b8f274868fa06f
|
4
|
+
data.tar.gz: 497582c00ccd77bcb14f716ae5596d32210ae33e
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: e71852cb6b1b049123b388d944789f8678b392724d299d776cd9ea43dd5ef3f6230d81135e11d6589a0610feb957e2838a1a3fd83181676f146089ec8832b837
|
7
|
+
data.tar.gz: ed0cecfc641fccdd7e1337421c3fdab68d38f4b1cbddbb470744924ffde7e9d35ab5e0c6b8205df8908bea8630a12ce392b9846fadb9f76166e0149495fe16cd
|
data/CHANGELOG
CHANGED
data/MIT-LICENSE
CHANGED
data/README.rdoc
CHANGED
@@ -55,8 +55,8 @@ for Sinatra:
|
|
55
55
|
end
|
56
56
|
|
57
57
|
Let's break down how this works. You setup AutoForme using <tt>AutoForme.for</tt>,
|
58
|
-
which takes 2 arguments, the controller type symbol (currently either :sinatra or :rails),
|
59
|
-
and the controller class (either a Sinatra::Base or ActionController::Base subclass). You
|
58
|
+
which takes 2 arguments, the controller type symbol (currently either :sinatra, :roda, or :rails),
|
59
|
+
and the controller class (either a Sinatra::Base, Roda, or ActionController::Base subclass). You
|
60
60
|
pass <tt>AutoForme.for</tt> a block, which is instance evaled at the framework level. This
|
61
61
|
level sets the defaults.
|
62
62
|
|
@@ -212,6 +212,21 @@ AutoForme's javascript support is contained in the autoforme.js file in the root
|
|
212
212
|
of the distribution. AutoForme's autocompleting support also requires
|
213
213
|
https://github.com/dyve/jquery-autocomplete
|
214
214
|
|
215
|
+
= Reloading Code
|
216
|
+
|
217
|
+
By default, AutoForme stores classes by reference. This can cause issues when using
|
218
|
+
code reloading in development environments. You can call +register_by_name+ to set
|
219
|
+
Autoforme to store classes by name, so that if a class is removed and reloaded (giving
|
220
|
+
a new class reference), it will use the new class instead of the reference to the old
|
221
|
+
class. Example:
|
222
|
+
|
223
|
+
class App < Sinatra::Base
|
224
|
+
AutoForme.for(:sinatra, self) do
|
225
|
+
register_by_name
|
226
|
+
model Artist
|
227
|
+
end
|
228
|
+
end
|
229
|
+
|
215
230
|
= TODO
|
216
231
|
|
217
232
|
* capybara-webkit tests for ajax behavior
|
data/lib/autoforme/framework.rb
CHANGED
@@ -116,10 +116,30 @@ module AutoForme
|
|
116
116
|
handle_proc(association_links, model, type, request)
|
117
117
|
end
|
118
118
|
|
119
|
+
# Set whether to register classes by name instead of by reference
|
120
|
+
def register_by_name(register=true)
|
121
|
+
opts[:register_by_name] = register
|
122
|
+
end
|
123
|
+
|
124
|
+
# Whether to register classes by name instead of by reference
|
125
|
+
def register_by_name?
|
126
|
+
opts[:register_by_name]
|
127
|
+
end
|
128
|
+
|
129
|
+
# Look up the Autoforme::Model class to use for the underlying model class instance.
|
130
|
+
def model_class(model_class)
|
131
|
+
if register_by_name?
|
132
|
+
model_class = model_class.name
|
133
|
+
end
|
134
|
+
@model_classes[model_class]
|
135
|
+
end
|
136
|
+
|
119
137
|
# Add a new model to the existing framework.
|
120
138
|
def model(model_class, &block)
|
121
|
-
|
122
|
-
|
139
|
+
if register_by_name?
|
140
|
+
model_class = model_class.name
|
141
|
+
end
|
142
|
+
model = @model_classes[model_class] = Model.for(self, model_type, model_class, &block)
|
123
143
|
@models[model.link] = model
|
124
144
|
end
|
125
145
|
|
data/lib/autoforme/model.rb
CHANGED
@@ -13,6 +13,9 @@ module AutoForme
|
|
13
13
|
# The default supported actions for models.
|
14
14
|
DEFAULT_SUPPORTED_ACTIONS = [:browse, :new, :show, :edit, :delete, :search, :mtm_edit]
|
15
15
|
|
16
|
+
# Regexp for valid constant names, to prevent code execution.
|
17
|
+
VALID_CONSTANT_NAME_REGEXP = /\A(?:::)?([A-Z]\w*(?:::[A-Z]\w*)*)\z/.freeze
|
18
|
+
|
16
19
|
extend OptsAttributes
|
17
20
|
|
18
21
|
# Create a new instance for the given model type and underlying model class
|
@@ -26,9 +29,6 @@ module AutoForme
|
|
26
29
|
# The AutoForme::Framework class tied to the current model
|
27
30
|
attr_reader :framework
|
28
31
|
|
29
|
-
# The underlying model class for the current model
|
30
|
-
attr_reader :model
|
31
|
-
|
32
32
|
# The options for the given model.
|
33
33
|
attr_reader :opts
|
34
34
|
|
@@ -47,6 +47,17 @@ module AutoForme
|
|
47
47
|
@opts = {}
|
48
48
|
end
|
49
49
|
|
50
|
+
# The underlying model class for the current model
|
51
|
+
def model
|
52
|
+
if @model.is_a?(Class)
|
53
|
+
@model
|
54
|
+
elsif m = VALID_CONSTANT_NAME_REGEXP.match(@model)
|
55
|
+
Object.module_eval("::#{m[1]}", __FILE__, __LINE__)
|
56
|
+
else
|
57
|
+
raise Error, "invalid model for AutoForme::Model, not a class or valid constant name: #{@model.inspect}"
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
50
61
|
# Whether the given type of action is supported for this model.
|
51
62
|
def supported_action?(type, request)
|
52
63
|
v = (handle_proc(supported_actions || framework.supported_actions_for(model, request), request) || DEFAULT_SUPPORTED_ACTIONS).include?(type)
|
@@ -223,7 +234,7 @@ module AutoForme
|
|
223
234
|
|
224
235
|
# The AutoForme::Model instance associated to the given association.
|
225
236
|
def associated_model_class(assoc)
|
226
|
-
framework.
|
237
|
+
framework.model_class(associated_class(assoc))
|
227
238
|
end
|
228
239
|
|
229
240
|
# The column value to display for the given object and column.
|
@@ -283,7 +294,7 @@ module AutoForme
|
|
283
294
|
# Create a new instance of the underlying model, setting
|
284
295
|
# defaults based on the params given.
|
285
296
|
def new(params, request)
|
286
|
-
obj =
|
297
|
+
obj = model.new
|
287
298
|
if params
|
288
299
|
columns_for(:new, request).each do |col|
|
289
300
|
if association?(col)
|
@@ -11,7 +11,7 @@ module AutoForme
|
|
11
11
|
# Make sure the forme plugin is loaded into the model.
|
12
12
|
def initialize(*)
|
13
13
|
super
|
14
|
-
|
14
|
+
model.plugin :forme
|
15
15
|
end
|
16
16
|
|
17
17
|
# The base class for the underlying model, ::Sequel::Model.
|
@@ -21,7 +21,7 @@ module AutoForme
|
|
21
21
|
|
22
22
|
# A completely empty search object, with no defaults.
|
23
23
|
def new_search
|
24
|
-
|
24
|
+
model.call({})
|
25
25
|
end
|
26
26
|
|
27
27
|
# The name of the form param for the given association.
|
@@ -120,7 +120,7 @@ module AutoForme
|
|
120
120
|
# The namespace for form parameter names for this model, needs to match
|
121
121
|
# the ones automatically used by Forme.
|
122
122
|
def params_name
|
123
|
-
|
123
|
+
model.send(:underscore, model.name)
|
124
124
|
end
|
125
125
|
|
126
126
|
# Retrieve underlying model instance with matching primary key
|
@@ -329,7 +329,7 @@ module AutoForme
|
|
329
329
|
private
|
330
330
|
|
331
331
|
def dataset_for(type, request)
|
332
|
-
ds =
|
332
|
+
ds = model.dataset
|
333
333
|
if filter = filter_for
|
334
334
|
ds = filter.call(ds, type, request)
|
335
335
|
end
|
@@ -337,7 +337,7 @@ module AutoForme
|
|
337
337
|
end
|
338
338
|
|
339
339
|
def all_dataset_for(type, request)
|
340
|
-
apply_dataset_options(type, request,
|
340
|
+
apply_dataset_options(type, request, model.dataset)
|
341
341
|
end
|
342
342
|
end
|
343
343
|
end
|
data/lib/autoforme/version.rb
CHANGED
data/spec/associations_spec.rb
CHANGED
@@ -215,7 +215,7 @@ describe AutoForme do
|
|
215
215
|
click_link 'Album'
|
216
216
|
page.all('td').map{|s| s.text}.should == ["Album1b", "A2", "Show", "Edit", "Delete"]
|
217
217
|
|
218
|
-
click_link 'Delete'
|
218
|
+
click_link 'Delete', :match=>:first
|
219
219
|
select 'A2-Album1b'
|
220
220
|
click_button 'Delete'
|
221
221
|
end
|
@@ -293,7 +293,7 @@ describe AutoForme do
|
|
293
293
|
click_link 'Album'
|
294
294
|
page.all('tr td:first-child').map{|s| s.text}.should == %w'Y ZZ X'
|
295
295
|
|
296
|
-
click_link 'Delete'
|
296
|
+
click_link 'Delete', :match=>:first
|
297
297
|
page.all('select option').map{|s| s.text}.should == ['', 'A-Y', 'A-ZZ', 'B-X']
|
298
298
|
select 'B-X'
|
299
299
|
click_button 'Delete'
|
@@ -359,7 +359,7 @@ describe AutoForme do
|
|
359
359
|
click_link 'Album'
|
360
360
|
page.all('tr td:first-child').map{|s| s.text}.should == %w'C D E'
|
361
361
|
|
362
|
-
click_link 'Delete'
|
362
|
+
click_link 'Delete', :match=>:first
|
363
363
|
page.all('select option').map{|s| s.text}.should == ['', 'C', 'D', 'E']
|
364
364
|
select 'C'
|
365
365
|
click_button 'Delete'
|
@@ -410,7 +410,7 @@ describe AutoForme do
|
|
410
410
|
click_link 'Artist'
|
411
411
|
page.current_path.should == '/Artist/browse'
|
412
412
|
|
413
|
-
click_link 'Edit'
|
413
|
+
click_link 'Edit', :match=>:first
|
414
414
|
select 'Artist1'
|
415
415
|
click_button 'Edit'
|
416
416
|
click_link 'Album1'
|
@@ -490,7 +490,7 @@ describe AutoForme do
|
|
490
490
|
click_link 'Artist'
|
491
491
|
page.current_path.should == '/Artist/browse'
|
492
492
|
|
493
|
-
click_link 'Edit'
|
493
|
+
click_link 'Edit', :match=>:first
|
494
494
|
select 'Artist1'
|
495
495
|
click_button 'Edit'
|
496
496
|
click_link 'Show Associations'
|
data/spec/basic_spec.rb
CHANGED
@@ -12,20 +12,20 @@ describe AutoForme do
|
|
12
12
|
it "should have basic functionality working" do
|
13
13
|
app_setup(Artist)
|
14
14
|
visit("/Artist/new")
|
15
|
-
page.
|
15
|
+
page.title.should == 'Artist - New'
|
16
16
|
fill_in 'Name', :with=>'TestArtistNew'
|
17
17
|
click_button 'Create'
|
18
18
|
page.html.should =~ /Created Artist/
|
19
19
|
page.current_path.should == '/Artist/new'
|
20
20
|
|
21
21
|
click_link 'Show'
|
22
|
-
page.
|
22
|
+
page.title.should == 'Artist - Show'
|
23
23
|
select 'TestArtistNew'
|
24
24
|
click_button 'Show'
|
25
25
|
page.html.should =~ /Name.+TestArtistNew/m
|
26
26
|
|
27
27
|
click_link 'Edit'
|
28
|
-
page.
|
28
|
+
page.title.should == 'Artist - Edit'
|
29
29
|
select 'TestArtistNew'
|
30
30
|
click_button 'Edit'
|
31
31
|
fill_in 'Name', :with=>'TestArtistUpdate'
|
@@ -35,7 +35,7 @@ describe AutoForme do
|
|
35
35
|
page.current_path.should =~ %r{/Artist/edit/\d+}
|
36
36
|
|
37
37
|
click_link 'Search'
|
38
|
-
page.
|
38
|
+
page.title.should == 'Artist - Search'
|
39
39
|
fill_in 'Name', :with=>'Upd'
|
40
40
|
click_button 'Search'
|
41
41
|
page.all('th').map{|s| s.text}.should == ['Name', 'Show', 'Edit', 'Delete']
|
@@ -47,12 +47,12 @@ describe AutoForme do
|
|
47
47
|
page.all('td').map{|s| s.text}.should == []
|
48
48
|
|
49
49
|
click_link 'Artist'
|
50
|
-
page.
|
50
|
+
page.title.should == 'Artist - Browse'
|
51
51
|
page.all('td').map{|s| s.text}.should == ["TestArtistUpdate", "Show", "Edit", "Delete"]
|
52
52
|
|
53
53
|
page.all('td').last.find('a').click
|
54
54
|
click_button 'Delete'
|
55
|
-
page.
|
55
|
+
page.title.should == 'Artist - Delete'
|
56
56
|
page.html.should =~ /Deleted Artist/
|
57
57
|
page.current_path.should == '/Artist/delete'
|
58
58
|
|
@@ -274,7 +274,7 @@ describe AutoForme do
|
|
274
274
|
a.should == [:show, :browse]
|
275
275
|
a.clear
|
276
276
|
|
277
|
-
click_link 'Delete'
|
277
|
+
click_link 'Delete', :match=>:first
|
278
278
|
Artist.create(:name=>'A')
|
279
279
|
select 'WENTSITRATSET21'
|
280
280
|
click_button 'Delete'
|
@@ -653,7 +653,7 @@ describe AutoForme do
|
|
653
653
|
click_link 'Artist'
|
654
654
|
page.all('tr td:first-child').map{|s| s.text}.should == %w'2 1'
|
655
655
|
|
656
|
-
click_link 'Delete'
|
656
|
+
click_link 'Delete', :match=>:first
|
657
657
|
page.all('option').map{|s| s.text}.should == ['', '2', '1']
|
658
658
|
select '1'
|
659
659
|
click_button 'Delete'
|
@@ -672,7 +672,7 @@ describe AutoForme do
|
|
672
672
|
it "should display decimals in float format in tables" do
|
673
673
|
app_setup(Artist)
|
674
674
|
visit("/Artist/new")
|
675
|
-
page.
|
675
|
+
page.title.should == 'Artist - New'
|
676
676
|
fill_in 'Num', :with=>'1.01'
|
677
677
|
click_button 'Create'
|
678
678
|
click_link 'Artist'
|
@@ -682,3 +682,76 @@ describe AutoForme do
|
|
682
682
|
page.all('tr td:first-child').map{|s| s.text}.should == %w'1.01'
|
683
683
|
end
|
684
684
|
end
|
685
|
+
|
686
|
+
describe AutoForme do
|
687
|
+
before(:all) do
|
688
|
+
db_setup(:artists=>[[:name, :string]])
|
689
|
+
model_setup(:Artist=>[:artists])
|
690
|
+
end
|
691
|
+
after(:all) do
|
692
|
+
Object.send(:remove_const, :Artist)
|
693
|
+
end
|
694
|
+
|
695
|
+
it "should have basic functionality working when reloading code" do
|
696
|
+
app_setup do
|
697
|
+
register_by_name
|
698
|
+
model Artist
|
699
|
+
end
|
700
|
+
artist_class = Artist
|
701
|
+
Object.send(:remove_const, :Artist)
|
702
|
+
::Artist = Class.new(artist_class) do
|
703
|
+
def name
|
704
|
+
"-#{super}-"
|
705
|
+
end
|
706
|
+
def forme_name
|
707
|
+
"[#{name}]"
|
708
|
+
end
|
709
|
+
end
|
710
|
+
visit("/Artist/new")
|
711
|
+
page.title.should == 'Artist - New'
|
712
|
+
fill_in 'Name', :with=>'TestArtistNew'
|
713
|
+
click_button 'Create'
|
714
|
+
page.html.should =~ /Created Artist/
|
715
|
+
page.current_path.should == '/Artist/new'
|
716
|
+
|
717
|
+
click_link 'Show'
|
718
|
+
page.title.should == 'Artist - Show'
|
719
|
+
select '[-TestArtistNew-]'
|
720
|
+
click_button 'Show'
|
721
|
+
page.html.should =~ /Name.+-TestArtistNew-/m
|
722
|
+
|
723
|
+
click_link 'Edit'
|
724
|
+
page.title.should == 'Artist - Edit'
|
725
|
+
select '[-TestArtistNew-]'
|
726
|
+
click_button 'Edit'
|
727
|
+
fill_in 'Name', :with=>'TestArtistUpdate'
|
728
|
+
click_button 'Update'
|
729
|
+
page.html.should =~ /Updated Artist/
|
730
|
+
page.html.should =~ /Name.+-TestArtistUpdate-/m
|
731
|
+
page.current_path.should =~ %r{/Artist/edit/\d+}
|
732
|
+
|
733
|
+
click_link 'Search'
|
734
|
+
page.title.should == 'Artist - Search'
|
735
|
+
fill_in 'Name', :with=>'Upd'
|
736
|
+
click_button 'Search'
|
737
|
+
page.all('th').map{|s| s.text}.should == ['Name', 'Show', 'Edit', 'Delete']
|
738
|
+
page.all('td').map{|s| s.text}.should == ["-TestArtistUpdate-", "Show", "Edit", "Delete"]
|
739
|
+
|
740
|
+
click_link 'Search'
|
741
|
+
fill_in 'Name', :with=>'Foo'
|
742
|
+
click_button 'Search'
|
743
|
+
page.all('td').map{|s| s.text}.should == []
|
744
|
+
|
745
|
+
click_link 'Artist'
|
746
|
+
page.title.should == 'Artist - Browse'
|
747
|
+
page.all('td').map{|s| s.text}.should == ["-TestArtistUpdate-", "Show", "Edit", "Delete"]
|
748
|
+
|
749
|
+
page.all('td').last.find('a').click
|
750
|
+
click_button 'Delete'
|
751
|
+
page.html.should =~ /Deleted Artist/
|
752
|
+
page.current_path.should == '/Artist/delete'
|
753
|
+
|
754
|
+
click_link 'Artist'
|
755
|
+
page.all('td').map{|s| s.text}.should == []
|
756
|
+
end
|
757
|
+
end
|
data/spec/mtm_spec.rb
CHANGED
@@ -36,7 +36,7 @@ describe AutoForme do
|
|
36
36
|
Album.create(:name=>'Album3')
|
37
37
|
|
38
38
|
visit("/Artist/mtm_edit")
|
39
|
-
page.
|
39
|
+
page.title.should == 'Artist - Many To Many Edit'
|
40
40
|
select("Artist1")
|
41
41
|
click_button "Edit"
|
42
42
|
|
@@ -123,7 +123,7 @@ describe AutoForme do
|
|
123
123
|
click_button 'Add'
|
124
124
|
Artist.first.refresh.albums.map{|x| x.name}.sort.should == %w'Album1 Album2'
|
125
125
|
|
126
|
-
click_button 'Remove'
|
126
|
+
click_button 'Remove', :match=>:first
|
127
127
|
Artist.first.refresh.albums.map{|x| x.name}.should == %w'Album2'
|
128
128
|
|
129
129
|
select 'Album3'
|
@@ -158,7 +158,7 @@ describe AutoForme do
|
|
158
158
|
click_button 'Add'
|
159
159
|
Artist.first.refresh.albums.map{|x| x.name}.sort.should == %w'Album1 Album2'
|
160
160
|
|
161
|
-
click_button 'Remove'
|
161
|
+
click_button 'Remove', :match=>:first
|
162
162
|
Artist.first.refresh.albums.map{|x| x.name}.should == %w'Album2'
|
163
163
|
|
164
164
|
fill_in 'Albums', :with=>a3.id.to_s
|
@@ -351,7 +351,7 @@ describe AutoForme do
|
|
351
351
|
Album.create(:name=>'Album3')
|
352
352
|
|
353
353
|
visit("/Artist/mtm_edit")
|
354
|
-
page.
|
354
|
+
page.title.should == 'Artist - Many To Many Edit'
|
355
355
|
select("Artist1")
|
356
356
|
click_button "Edit"
|
357
357
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: autoforme
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0
|
4
|
+
version: 1.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jeremy Evans
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-
|
11
|
+
date: 2015-03-23 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: forme
|