active_scaffold 3.1.20 → 3.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (95) hide show
  1. data/app/assets/javascripts/jquery/active_scaffold.js +4 -1
  2. data/app/assets/javascripts/prototype/active_scaffold.js +4 -1
  3. data/app/assets/stylesheets/{active_scaffold.scss~ → active_scaffold.css.scss} +5 -2
  4. data/app/assets/stylesheets/{active_scaffold_colors.scss → active_scaffold_colors.css.scss} +4 -0
  5. data/app/assets/stylesheets/active_scaffold_extensions.css.erb +2 -0
  6. data/app/assets/stylesheets/active_scaffold_images.css.scss +43 -0
  7. data/lib/active_scaffold/actions/core.rb +1 -0
  8. data/lib/active_scaffold/actions/nested.rb +0 -1
  9. data/lib/active_scaffold/extensions/action_view_rendering.rb +1 -1
  10. data/lib/active_scaffold/helpers/form_column_helpers.rb +1 -0
  11. data/lib/active_scaffold/version.rb +2 -2
  12. data/test/mock_app/.gitignore +2 -0
  13. metadata +86 -164
  14. data/app/assets/javascripts/active_scaffold.js.erb~ +0 -16
  15. data/app/assets/javascripts/jquery/active_scaffold.js~ +0 -1053
  16. data/app/assets/javascripts/jquery/draggable_lists.js~ +0 -27
  17. data/app/assets/javascripts/prototype/active_scaffold.js~ +0 -1037
  18. data/app/assets/stylesheets/active_scaffold.css.erb +0 -11
  19. data/app/assets/stylesheets/active_scaffold.css.erb~ +0 -11
  20. data/app/assets/stylesheets/active_scaffold.css.scss.erb~ +0 -1120
  21. data/app/assets/stylesheets/active_scaffold.css.scss~ +0 -11
  22. data/app/assets/stylesheets/active_scaffold.css~ +0 -11
  23. data/app/assets/stylesheets/active_scaffold_colors.css +0 -244
  24. data/app/assets/stylesheets/active_scaffold_colors.css.scss~ +0 -481
  25. data/app/assets/stylesheets/active_scaffold_default.css.erb +0 -47
  26. data/app/assets/stylesheets/active_scaffold_default.css.erb~ +0 -57
  27. data/app/assets/stylesheets/active_scaffold_default.css.scss~ +0 -1092
  28. data/app/assets/stylesheets/active_scaffold_default.css~ +0 -923
  29. data/app/assets/stylesheets/active_scaffold_layout.css~ +0 -922
  30. data/app/assets/stylesheets/blue-theme.css~ +0 -1150
  31. data/config/locales/es.yml~ +0 -120
  32. data/frontends/default/views/_action_group.html.erb~ +0 -24
  33. data/frontends/default/views/_base_form.html.erb~ +0 -42
  34. data/frontends/default/views/_form.html.erb~ +0 -26
  35. data/frontends/default/views/_form_association.html.erb~ +0 -19
  36. data/frontends/default/views/_form_association_footer.html.erb~ +0 -48
  37. data/frontends/default/views/_horizontal_subform.html.erb~ +0 -32
  38. data/frontends/default/views/_horizontal_subform_header.html.erb~ +0 -11
  39. data/frontends/default/views/_horizontal_subform_record.html.erb~ +0 -38
  40. data/frontends/default/views/_list_actions.html.erb~ +0 -15
  41. data/frontends/default/views/_list_inline_adapter.html.erb~ +0 -10
  42. data/frontends/default/views/_list_messages.html.erb~ +0 -30
  43. data/frontends/default/views/_list_pagination.html.erb~ +0 -11
  44. data/frontends/default/views/_list_pagination_links.html.erb~ +0 -0
  45. data/frontends/default/views/_list_with_header.html.erb~ +0 -36
  46. data/frontends/default/views/_render_field.js.erb~ +0 -23
  47. data/frontends/default/views/_row.html.erb~ +0 -6
  48. data/frontends/default/views/_show.html.erb~ +0 -8
  49. data/frontends/default/views/_update_form.html.erb~ +0 -6
  50. data/frontends/default/views/_vertical_subform.html.erb~ +0 -12
  51. data/frontends/default/views/add_existing.js.erb~ +0 -18
  52. data/frontends/default/views/add_existing_form.html.erb~ +0 -5
  53. data/frontends/default/views/create.html.erb~ +0 -5
  54. data/frontends/default/views/edit_associated.js.erb~ +0 -13
  55. data/frontends/default/views/on_create.js.erb~ +0 -45
  56. data/frontends/default/views/on_update.js.erb~ +0 -31
  57. data/frontends/default/views/render_field.js.erb~ +0 -1
  58. data/frontends/default/views/search.html.erb~ +0 -5
  59. data/frontends/default/views/show.html.erb~ +0 -5
  60. data/frontends/default/views/update.html.erb~ +0 -8
  61. data/frontends/default/views/update_column.js.erb~ +0 -16
  62. data/lib/active_scaffold.rb~ +0 -373
  63. data/lib/active_scaffold/actions/core.rb~ +0 -203
  64. data/lib/active_scaffold/actions/create.rb~ +0 -148
  65. data/lib/active_scaffold/actions/list.rb~ +0 -196
  66. data/lib/active_scaffold/actions/nested.rb~ +0 -247
  67. data/lib/active_scaffold/actions/search.rb~ +0 -49
  68. data/lib/active_scaffold/actions/subform.rb~ +0 -27
  69. data/lib/active_scaffold/actions/update.rb~ +0 -150
  70. data/lib/active_scaffold/attribute_params.rb~ +0 -203
  71. data/lib/active_scaffold/bridges/date_picker/helper.rb~ +0 -180
  72. data/lib/active_scaffold/bridges/record_select/helpers.rb~ +0 -86
  73. data/lib/active_scaffold/bridges/shared/date_bridge.rb~ +0 -209
  74. data/lib/active_scaffold/config/base.rb~ +0 -72
  75. data/lib/active_scaffold/config/list.rb~ +0 -195
  76. data/lib/active_scaffold/config/nested.rb~ +0 -41
  77. data/lib/active_scaffold/config/search.rb~ +0 -74
  78. data/lib/active_scaffold/constraints.rb~ +0 -186
  79. data/lib/active_scaffold/data_structures/action_columns.rb~ +0 -140
  80. data/lib/active_scaffold/data_structures/action_link.rb~ +0 -179
  81. data/lib/active_scaffold/data_structures/nested_info.rb~ +0 -147
  82. data/lib/active_scaffold/extensions/action_controller_rendering.rb~ +0 -22
  83. data/lib/active_scaffold/extensions/action_view_rendering.rb~ +0 -120
  84. data/lib/active_scaffold/extensions/active_association_reflection.rb~ +0 -22
  85. data/lib/active_scaffold/extensions/cache_association.rb~ +0 -12
  86. data/lib/active_scaffold/extensions/reverse_associations.rb~ +0 -64
  87. data/lib/active_scaffold/extensions/routing_mapper.rb~ +0 -48
  88. data/lib/active_scaffold/extensions/unsaved_associated.rb~ +0 -62
  89. data/lib/active_scaffold/finder.rb~ +0 -370
  90. data/lib/active_scaffold/helpers/controller_helpers.rb~ +0 -92
  91. data/lib/active_scaffold/helpers/form_column_helpers.rb~ +0 -320
  92. data/lib/active_scaffold/helpers/id_helpers.rb~ +0 -123
  93. data/lib/active_scaffold/helpers/list_column_helpers.rb~ +0 -370
  94. data/lib/active_scaffold/helpers/search_column_helpers.rb~ +0 -263
  95. data/lib/active_scaffold/helpers/view_helpers.rb~ +0 -350
@@ -1,41 +0,0 @@
1
- module ActiveScaffold::Config
2
- class Nested < Base
3
- self.crud_type = :read
4
-
5
- def initialize(core_config)
6
- super
7
- @label = :add_existing_model
8
- self.shallow_delete = self.class.shallow_delete
9
- @action_group = self.class.action_group.clone if self.class.action_group
10
- end
11
-
12
- # global level configuration
13
- # --------------------------
14
- cattr_accessor :shallow_delete
15
- @@shallow_delete = true
16
-
17
- # instance-level configuration
18
- # ----------------------------
19
- attr_accessor :shallow_delete
20
-
21
- # Add a nested ActionLink
22
- def add_link(attribute, options = {})
23
- column = @core.columns[attribute.to_sym]
24
- unless column.nil? || column.association.nil?
25
- options.reverse_merge! :security_method => :nested_authorized?, :label => column.association.klass.model_name.human({:count => 2, :default => column.association.klass.name.pluralize})
26
- action_link = @core.link_for_association(column, options)
27
- @core.action_links.add_to_group(action_link, action_group) unless action_link.nil?
28
- else
29
-
30
- end
31
- end
32
-
33
- def add_scoped_link(named_scope, options = {})
34
- action_link = @core.link_for_association_as_scope(named_scope.to_sym, options)
35
- @core.action_links.add_to_group(action_link, action_group) unless action_link.nil?
36
- end
37
-
38
- # the label for this Nested action. used for the header.
39
- attr_writer :label
40
- end
41
- end
@@ -1,74 +0,0 @@
1
- module ActiveScaffold::Config
2
- class Search < Base
3
- self.crud_type = :read
4
-
5
- def initialize(core_config)
6
- super
7
- @text_search = self.class.text_search
8
- @live = self.class.live?
9
- @split_terms = self.class.split_terms
10
-
11
- # start with the ActionLink defined globally
12
- @link = self.class.link.clone
13
- @action_group = self.class.action_group.clone if self.class.action_group
14
- end
15
-
16
-
17
- # global level configuration
18
- # --------------------------
19
- # the ActionLink for this action
20
- cattr_accessor :link
21
- @@link = ActiveScaffold::DataStructures::ActionLink.new('show_search', :label => :search, :type => :collection, :security_method => :search_authorized?, :ignore_method => :search_ignore?)
22
-
23
- # A flag for how the search should do full-text searching in the database:
24
- # * :full: LIKE %?%
25
- # * :start: LIKE ?%
26
- # * :end: LIKE %?
27
- # * false: LIKE ?
28
- # Default is :full
29
- cattr_accessor :text_search
30
- @@text_search = :full
31
-
32
- # whether submits the search as you type
33
- cattr_writer :live
34
- def self.live?
35
- @@live
36
- end
37
-
38
- # instance-level configuration
39
- # ----------------------------
40
-
41
- # provides access to the list of columns specifically meant for the Search to use
42
- def columns
43
- # we want to delay initializing to the @core.columns set for as long as possible. Too soon and .search_sql will not be available to .searchable?
44
- unless @columns
45
- debugger
46
- self.columns = @core.columns.collect{|c| c.name if @core.columns._inheritable.include?(c.name) and c.searchable? and c.column and c.column.text?}.compact
47
- end
48
- @columns
49
- end
50
-
51
- public :columns=
52
-
53
- # A flag for how the search should do full-text searching in the database:
54
- # * :full: LIKE %?%
55
- # * :start: LIKE ?%
56
- # * :end: LIKE %?
57
- # * false: LIKE ?
58
- # Default is :full
59
- attr_accessor :text_search
60
-
61
- @@split_terms = " "
62
- cattr_accessor :split_terms
63
- attr_accessor :split_terms
64
-
65
- # the ActionLink for this action
66
- attr_accessor :link
67
-
68
- # whether submits the search as you type
69
- attr_writer :live
70
- def live?
71
- @live
72
- end
73
- end
74
- end
@@ -1,186 +0,0 @@
1
- module ActiveScaffold
2
- module Constraints
3
-
4
- protected
5
-
6
- # Returns the current constraints
7
- def active_scaffold_constraints
8
- @active_scaffold_constraints ||= active_scaffold_session_storage[:constraints] || {}
9
- end
10
-
11
- def set_active_scaffold_constraints
12
- associations_by_params = {}
13
- active_scaffold_config.model.reflect_on_all_associations.each do |association|
14
- associations_by_params[association.klass.name.foreign_key] = association.name unless association.options[:polymorphic]
15
- end
16
- params.each do |key, value|
17
- active_scaffold_constraints[associations_by_params[key]] = value if associations_by_params.include? key
18
- end
19
- end
20
-
21
- # For each enabled action, adds the constrained columns to the ActionColumns object (if it exists).
22
- # This lets the ActionColumns object skip constrained columns.
23
- #
24
- # If the constraint value is a Hash, then we assume the constraint is a multi-level association constraint (the reverse of a has_many :through) and we do NOT register the constraint column.
25
- def register_constraints_with_action_columns(association_constrained_fields = [], exclude_actions = [])
26
- debugger
27
- constrained_fields = active_scaffold_constraints.reject{|k, v| v.is_a? Hash}.keys.collect{|k| k.to_sym}
28
- constrained_fields = constrained_fields | association_constrained_fields
29
- if self.class.uses_active_scaffold?
30
- # we actually want to do this whether constrained_fields exist or not, so that we can reset the array when they don't
31
- active_scaffold_config.actions.each do |action_name|
32
- next if exclude_actions.include?(action_name)
33
- action = active_scaffold_config.send(action_name)
34
- next unless action.respond_to? :columns
35
- action.columns.constraint_columns = constrained_fields
36
- end
37
- end
38
- end
39
-
40
- # Returns search conditions based on the current scaffold constraints.
41
- #
42
- # Supports constraints based on either a column name (in which case it checks for an association
43
- # or just uses the search_sql) or a database field name.
44
- #
45
- # All of this work is primarily to support nested scaffolds in a manner generally useful for other
46
- # embedded scaffolds.
47
- def conditions_from_constraints
48
- conditions = nil
49
- debugger
50
- active_scaffold_constraints.each do |k, v|
51
- column = active_scaffold_config.columns[k]
52
- constraint_condition = if column
53
- # Assume this is a multi-level association constraint.
54
- # example:
55
- # data model: Park -> Den -> Bear
56
- # constraint: :den => {:park => 5}
57
- if v.is_a? Hash
58
- far_association = column.association.klass.reflect_on_association(v.keys.first)
59
- field = far_association.klass.primary_key
60
- table = far_association.table_name
61
-
62
- active_scaffold_includes.concat([{k => v.keys.first}]) # e.g. {:den => :park}
63
- constraint_condition_for("#{table}.#{field}", v.values.first)
64
-
65
- # association column constraint
66
- elsif column.association
67
- if column.association.macro == :has_and_belongs_to_many
68
- active_scaffold_habtm_joins.concat column.includes
69
- else
70
- active_scaffold_includes.concat column.includes
71
- end
72
- condition_from_association_constraint(column.association, v)
73
-
74
- # regular column constraints
75
- elsif column.searchable?
76
- active_scaffold_includes.concat column.includes
77
- constraint_condition_for(column.search_sql, v)
78
- end
79
- # unknown-to-activescaffold-but-real-database-column constraint
80
- elsif active_scaffold_config.model.column_names.include? k.to_s
81
- constraint_condition_for(k.to_s, v)
82
- else
83
- raise ActiveScaffold::MalformedConstraint, constraint_error(active_scaffold_config.model, k), caller
84
- end
85
-
86
- conditions = merge_conditions(conditions, constraint_condition)
87
- end
88
-
89
- conditions
90
- end
91
-
92
- # We do NOT want to use .search_sql. If anything, search_sql will refer
93
- # to a human-searchable value on the associated record.
94
- def condition_from_association_constraint(association, value)
95
- # when the reverse association is a :belongs_to, the id for the associated object only exists as
96
- # the primary_key on the other table. so for :has_one and :has_many (when the reverse is :belongs_to),
97
- # we have to use the other model's primary_key.
98
- #
99
- # please see the relevant tests for concrete examples.
100
- field = if [:has_one, :has_many].include?(association.macro)
101
- association.klass.primary_key
102
- elsif [:has_and_belongs_to_many].include?(association.macro)
103
- association.association_foreign_key
104
- else
105
- association.options[:foreign_key] || association.name.to_s.foreign_key
106
- end
107
-
108
- table = case association.macro
109
- when :has_and_belongs_to_many
110
- association.options[:join_table]
111
-
112
- when :belongs_to
113
- active_scaffold_config.model.table_name
114
-
115
- else
116
- association.table_name
117
- end
118
-
119
- if association.options[:primary_key]
120
- value = association.klass.find(value).send(association.options[:primary_key])
121
- end
122
-
123
- condition = constraint_condition_for("#{table}.#{field}", value)
124
- if association.options[:polymorphic]
125
- begin
126
- parent_scaffold = "#{session_info[:parent_scaffold].to_s.camelize}Controller".constantize
127
- condition = merge_conditions(
128
- condition,
129
- constraint_condition_for("#{table}.#{association.name}_type", parent_scaffold.active_scaffold_config.model_id.to_s)
130
- )
131
- rescue ActiveScaffold::ControllerNotFound
132
- nil
133
- end
134
- end
135
-
136
- condition
137
- end
138
-
139
- def constraint_error(klass, column_name)
140
- "Malformed constraint `#{klass}##{column_name}'. If it's a legitimate column, and you are using a nested scaffold, please specify or double-check the reverse association name."
141
- end
142
-
143
- # Applies constraints to the given record.
144
- #
145
- # Searches through the known columns for association columns. If the given constraint is an association,
146
- # it assumes that the constraint value is an id. It then does a association.klass.find with the value
147
- # and adds the associated object to the record.
148
- #
149
- # For some operations ActiveRecord will automatically update the database. That's not always ok.
150
- # If it *is* ok (e.g. you're in a transaction), then set :allow_autosave to true.
151
- def apply_constraints_to_record(record, options = {})
152
- options[:allow_autosave] = false if options[:allow_autosave].nil?
153
-
154
- active_scaffold_constraints.each do |k, v|
155
- column = active_scaffold_config.columns[k]
156
- if column and column.association
157
- if column.plural_association?
158
- record.send("#{k}").send(:<<, column.association.klass.find(v))
159
- elsif column.association.options[:polymorphic]
160
- record.send("#{k}=", params[:parent_model].constantize.find(v))
161
- else # regular singular association
162
- record.send("#{k}=", column.association.klass.find(v))
163
-
164
- # setting the belongs_to side of a has_one isn't safe. if the has_one was already
165
- # specified, rails won't automatically clear out the previous associated record.
166
- #
167
- # note that we can't take the extra step to correct this unless we're permitted to
168
- # run operations where activerecord auto-saves the object.
169
- reverse = column.association.klass.reflect_on_association(column.association.reverse)
170
- if reverse.macro == :has_one and options[:allow_autosave]
171
- record.send(k).send("#{column.association.reverse}=", record)
172
- end
173
- end
174
- else
175
- record.send("#{k}=", v)
176
- end
177
- end
178
- end
179
-
180
- private
181
-
182
- def constraint_condition_for(sql, value)
183
- value.nil? ? "#{sql} IS NULL" : ["#{sql} = ?", value]
184
- end
185
- end
186
- end
@@ -1,140 +0,0 @@
1
- module ActiveScaffold::DataStructures
2
- # A set of columns. These structures can be nested for organization.
3
- class ActionColumns < ActiveScaffold::DataStructures::Set
4
- include ActiveScaffold::Configurable
5
-
6
- # this lets us refer back to the action responsible for this link, if it exists.
7
- # the immediate need here is to get the crud_type so we can dynamically filter columns from the set.
8
- attr_accessor :action
9
-
10
- # labels are useful for the Create/Update forms, when we display columns in a grouped fashion and want to name them separately
11
- attr_writer :label
12
- def label
13
- as_(@label) if @label
14
- end
15
- def name
16
- @label
17
- end
18
-
19
- # Whether this column set is collapsed by default in contexts where collapsing is supported
20
- attr_accessor :collapsed
21
-
22
- # nests a subgroup in the column set
23
- def add_subgroup(label, &proc)
24
- columns = ActiveScaffold::DataStructures::ActionColumns.new
25
- columns.label = label
26
- columns.action = self.action
27
- columns.configure &proc
28
- self.exclude columns.collect_columns
29
- self.add columns
30
- end
31
-
32
- def include?(item)
33
- @set.each do |c|
34
- return true if !c.is_a? Symbol and c.include? item
35
- return true if c == item.to_sym
36
- end
37
- return false
38
- end
39
-
40
- def names
41
- self.collect(&:name)
42
- end
43
-
44
- def names_without_auth_check
45
- Array(@set)
46
- end
47
-
48
- protected
49
-
50
- def collect_columns
51
- @set.collect {|col| col.is_a?(ActiveScaffold::DataStructures::ActionColumns) ? col.collect_columns : col}
52
- end
53
-
54
- # called during clone or dup. makes the clone/dup deeper.
55
- def initialize_copy(from)
56
- @set = from.instance_variable_get('@set').clone
57
- end
58
-
59
- # A package of stuff to add after the configuration block. This is an attempt at making a certain level of functionality inaccessible during configuration, to reduce possible breakage from misuse.
60
- # The bulk of the package is a means of connecting the referential column set (ActionColumns) with the actual column objects (Columns). This lets us iterate over the set and yield real column objects.
61
- module AfterConfiguration
62
- # Redefine the each method to yield actual Column objects.
63
- # It will skip constrained and unauthorized columns.
64
- #
65
- # Options:
66
- # * :flatten - whether to recursively iterate on nested sets. default is false.
67
- # * :for - the record (or class) being iterated over. used for column-level security. default is the class.
68
- def each(options = {}, &proc)
69
- options[:for] ||= @columns.active_record_class
70
- self.unauthorized_columns = []
71
- @set.each do |item|
72
- unless item.is_a? ActiveScaffold::DataStructures::ActionColumns
73
- item = (@columns[item] || ActiveScaffold::DataStructures::Column.new(item.to_sym, @columns.active_record_class))
74
- next if self.skip_column?(item, options)
75
- end
76
- if item.is_a? ActiveScaffold::DataStructures::ActionColumns and options.has_key?(:flatten) and options[:flatten]
77
- item.each(options, &proc)
78
- else
79
- yield item
80
- end
81
- end
82
- end
83
-
84
- def collect_visible(options = {}, &proc)
85
- columns = []
86
- options[:for] ||= @columns.active_record_class
87
- self.unauthorized_columns = []
88
- @set.each do |item|
89
- unless item.is_a? ActiveScaffold::DataStructures::ActionColumns
90
- item = (@columns[item] || ActiveScaffold::DataStructures::Column.new(item.to_sym, @columns.active_record_class))
91
- next if self.skip_column?(item, options)
92
- end
93
- if item.is_a? ActiveScaffold::DataStructures::ActionColumns and options.has_key?(:flatten) and options[:flatten]
94
- columns = columns + item.collect(options, &proc)
95
- else
96
- columns << item
97
- end
98
- end
99
- columns
100
- end
101
-
102
- def skip_column?(column, options)
103
- result = false
104
- # skip if this matches a constrained column
105
- result = true if constraint_columns.include?(column.name.to_sym)
106
- # skip if this matches the field_name of a constrained column
107
- result = true if column.field_name and constraint_columns.include?(column.field_name.to_sym)
108
- # skip this field if it's not authorized
109
- unless options[:for].authorized_for?(:action => options[:action], :crud_type => options[:crud_type] || self.action.crud_type, :column => column.name)
110
- self.unauthorized_columns << column.name.to_sym
111
- result = true
112
- end
113
- return result
114
- end
115
-
116
- # registers a set of column objects (recursively, for all nested ActionColumns)
117
- def set_columns(columns)
118
- @columns = columns
119
- # iterate over @set instead of self to avoid dealing with security queries
120
- @set.each do |item|
121
- item.set_columns(columns) if item.respond_to? :set_columns
122
- end
123
- end
124
-
125
- attr_writer :constraint_columns
126
- def constraint_columns
127
- @constraint_columns ||= []
128
- end
129
-
130
- attr_writer :unauthorized_columns
131
- def unauthorized_columns
132
- @unauthorized_columns ||= []
133
- end
134
-
135
- def length
136
- ((@set - self.constraint_columns) - self.unauthorized_columns).length
137
- end
138
- end
139
- end
140
- end
@@ -1,179 +0,0 @@
1
- module ActiveScaffold::DataStructures
2
- class ActionLink
3
- # provides a quick way to set any property of the object from a hash
4
- def initialize(action, options = {})
5
- # set defaults
6
- self.action = action.to_s
7
- self.label = action
8
- self.confirm = false
9
- self.type = :collection
10
- self.inline = true
11
- self.method = :get
12
- self.crud_type = :delete if [:destroy].include?(action.try(:to_sym))
13
- self.crud_type = :create if [:create, :new].include?(action.try(:to_sym))
14
- self.crud_type = :update if [:edit, :update].include?(action.try(:to_sym))
15
- self.crud_type ||= :read
16
- self.parameters = {}
17
- self.html_options = {}
18
- self.column = nil
19
- self.image = nil
20
- self.dynamic_parameters = nil
21
-
22
- # apply quick properties
23
- options.each_pair do |k, v|
24
- setter = "#{k}="
25
- self.send(setter, v) if self.respond_to? setter
26
- end
27
- end
28
-
29
- # the action-path for this link. what page to request? this is required!
30
- attr_accessor :action
31
-
32
- # the controller for this action link. if nil, the current controller should be assumed.
33
- attr_writer :controller
34
-
35
- def controller
36
- @controller = @controller.call if @controller.is_a?(Proc)
37
- @controller
38
- end
39
-
40
- def static_controller?
41
- !(@controller.is_a?(Proc) || (@controller == :polymorph))
42
- end
43
-
44
- # a hash of request parameters
45
- attr_accessor :parameters
46
-
47
- # a block for dynamic_parameters
48
- attr_accessor :dynamic_parameters
49
-
50
- # the RESTful method
51
- attr_accessor :method
52
-
53
- # what string to use to represent this action
54
- attr_writer :label
55
- def label
56
- @label.is_a?(Symbol) ? as_(@label) : @label
57
- end
58
-
59
- # image to use {:name => 'arrow.png', :size => '16x16'}
60
- attr_accessor :image
61
-
62
- # if the action requires confirmation
63
- def confirm=(value)
64
- @dhtml_confirm = nil if value
65
- @confirm = value
66
- end
67
- def confirm(label = '')
68
- @confirm.is_a?(String) ? @confirm : as_(@confirm, :label => label)
69
- end
70
- def confirm?
71
- !!@confirm
72
- end
73
-
74
- # if the action uses a DHTML based (i.e. 2-phase) confirmation
75
- attr_accessor :dhtml_confirm
76
- def dhtml_confirm=(value)
77
- @confirm = nil if value
78
- @dhtml_confirm = value
79
- end
80
- def dhtml_confirm?
81
- !!@dhtml_confirm
82
- end
83
-
84
- # what method to call on the controller to see if this action_link should be visible
85
- # note that this is only the UI part of the security. to prevent URL hax0rz, you also need security on requests (e.g. don't execute update method unless authorized).
86
- attr_writer :security_method
87
- def security_method
88
- @security_method || "#{self.action}_authorized?"
89
- end
90
-
91
- def security_method_set?
92
- !!@security_method
93
- end
94
-
95
- attr_accessor :ignore_method
96
-
97
- # the crud type of the (eventual?) action. different than :method, because this crud action may not be imminent.
98
- # this is used to determine record-level authorization (e.g. record.authorized_for?(:crud_type => link.crud_type).
99
- # options are :create, :read, :update, and :delete
100
- attr_accessor :crud_type
101
-
102
- # an "inline" link is inserted into the existing page
103
- # exclusive with popup? and page?
104
- def inline=(val)
105
- @inline = (val == true)
106
- self.popup = self.page = false if @inline
107
- end
108
- def inline?; @inline end
109
-
110
- # a "popup" link displays in a separate (browser?) window. this will eventually take arguments.
111
- # exclusive with inline? and page?
112
- def popup=(val)
113
- @popup = (val == true)
114
- if @popup
115
- self.inline = self.page = false
116
-
117
- # the :method parameter doesn't mix with the :popup parameter
118
- # when/if we start using DHTML popups, we can bring :method back
119
- self.method = nil
120
- end
121
- end
122
- def popup?; @popup end
123
-
124
- # a "page" link displays by reloading the current page
125
- # exclusive with inline? and popup?
126
- def page=(val)
127
- @page = (val == true)
128
- if @page
129
- self.inline = self.popup = false
130
-
131
- # when :method is defined, ActionView adds an onclick to use a form ...
132
- # so it's best to just empty out :method whenever possible.
133
- # we only ever need to know @method = :get for things that default to POST.
134
- # the only things that default to POST are forms and ajax calls.
135
- # when @page = true, we don't use ajax.
136
- self.method = nil if method == :get
137
- end
138
- end
139
- def page?; @page end
140
-
141
- # where the result of this action should insert in the display.
142
- # for :type => :collection, supported values are:
143
- # :top
144
- # :bottom
145
- # :replace (for updating the entire table)
146
- # false (no attempt at positioning)
147
- # for :type => :member, supported values are:
148
- # :before
149
- # :replace
150
- # :after
151
- # false (no attempt at positioning)
152
- attr_writer :position
153
- def position
154
- return @position unless @position.nil? or @position == true
155
- return :replace if self.type == :member
156
- return :top if self.type == :collection
157
- raise "what should the default position be for #{self.type}?"
158
- end
159
-
160
- # what type of link this is. currently supported values are :collection and :member.
161
- attr_accessor :type
162
-
163
- # html options for the link
164
- attr_accessor :html_options
165
-
166
- # nested action_links are referencing a column
167
- attr_accessor :column
168
-
169
- # indicates that this a nested_link
170
- def nested_link?
171
- @column || (parameters && parameters[:named_scope])
172
- end
173
-
174
- # Internal use: generated eid for this action_link
175
- attr_accessor :eid
176
-
177
-
178
- end
179
- end