brick 1.0.158 → 1.0.160

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: 326ec09b1c28cf7c54e54bae9ea6ceed7d7e476a177be0a41af14e04f7cc3d11
4
- data.tar.gz: 0507c22a2acf86c58737ecfedeb1a1f5ed6979b5263b28c6d6e77b0e9500ab7c
3
+ metadata.gz: 735ad34b99ba52ae2575c786fdee6c359c5c53e6d2edf53b19bbb5d1f02869ec
4
+ data.tar.gz: c603e9adebe13192e4be8724b51d563a6b39f89b15c61fab253debb9fc959a66
5
5
  SHA512:
6
- metadata.gz: d6803593a5c3e17ef40005c405017ed4e7519024ca172a077ad377c201a7b2e2caf2a8b4bc5a0ef63f091124a44199ffd3b386db7d6b5d51352f2e3327537d81
7
- data.tar.gz: 486b0a15422b0d3150b575c8d19c24cc3434e3fd8f35335d2e490e1e69e423995a2032de913def73b4f4df0e2789c6f4af7d61930db5cc144d0a0cb76be3ebdc
6
+ metadata.gz: 14b5a64e366d218ac78bb3ec26370cddcdb506ee292974321a76331a40d272a33ce49b9cb4911314a7e33835bf44255dda73c04449062e159b499e2e0d88c61f
7
+ data.tar.gz: cfa821c073296681b4b49e0d58538e076ac50ae1ea65b2df6ea8af1c92477842ee737c3d5950d803ce45f52daf48fca065f28bf6cc6a5e6518c408a64305ada6
@@ -97,11 +97,13 @@ if Object.const_defined?('ActionPack') && !ActionPack.respond_to?(:version)
97
97
  end
98
98
  end
99
99
  end
100
- require 'action_view' # Needed for Rails <= 4.0
101
- if Object.const_defined?('ActionView') && !ActionView.respond_to?(:version)
102
- module ActionView
103
- def self.version
104
- ActionPack.version
100
+ if Bundler.locked_gems&.dependencies.key?('action_view')
101
+ require 'action_view' # Needed for Rails <= 4.0
102
+ if Object.const_defined?('ActionView') && !ActionView.respond_to?(:version)
103
+ module ActionView
104
+ def self.version
105
+ ActionPack.version
106
+ end
105
107
  end
106
108
  end
107
109
  end
@@ -30,14 +30,14 @@
30
30
 
31
31
  # Drag something like HierModel#name onto the rows and have it automatically add five columns -- where type=zone / where type = section / etc
32
32
 
33
- # Support for Postgres / MySQL enums (add enum to model, use model enums to make a drop-down in the UI)
34
-
35
- # Currently quadrupling up routes
36
-
37
33
  # Modal pop-up things for editing large text / date ranges / hierarchies of data
38
34
 
39
35
  # For recognised self-references, have the show page display all related objects up to the parent (or the start of a circular reference)
40
36
 
37
+ # When creating or updating an object through an auto-generated controller, it always goes to an auto-generated view template even if the user has supplied their own index.html.erb (or similar) view template
38
+
39
+ # Upon creation of a new object, when going to the index page, highlight this new object and scroll it into view (likely to the very bottom of everything, although might be sorted differently)
40
+
41
41
  # ==========================================================
42
42
  # Dynamically create model or controller classes when needed
43
43
  # ==========================================================
@@ -2199,7 +2199,8 @@ class Object
2199
2199
  render json: { result: ::Brick.unexclude_column(table_name, col) }
2200
2200
  else
2201
2201
  @_lookup_context.instance_variable_set("@#{singular_table_name}".to_sym,
2202
- model.send(:create, send(params_name_sym)))
2202
+ (created_obj = model.send(:create, send(params_name_sym))))
2203
+ # %%% Surface any errors to the user in a flash message
2203
2204
  @_lookup_context.instance_variable_set(:@_brick_model, model)
2204
2205
  index
2205
2206
  render :index
@@ -1667,89 +1667,9 @@ end
1667
1667
  end
1668
1668
  %>
1669
1669
  <br><br>
1670
- <%= form_for(obj.becomes(#{model_name}), options) do |f| %>
1671
- <table class=\"shadow\">
1672
- <% has_fields = false
1673
- # If it's a new record, set any default polymorphic types
1674
- bts.each do |_k, v|
1675
- if v[2]
1676
- @#{obj_name}.send(\"#\{model.brick_foreign_type(v.first)}=\", v[1].first&.first&.name)
1677
- end
1678
- end if @#{obj_name}.new_record?
1679
- rtans = #{model_name}.rich_text_association_names if #{model_name}.respond_to?(:rich_text_association_names)
1680
- (#{model_name}.column_names + (rtans || [])).each do |k|
1681
- next if (#{(pk.map(&:to_s) || []).inspect}.include?(k) && !bts.key?(k)) ||
1682
- ::Brick.config.metadata_columns.include?(k)
1683
-
1684
- col = #{model_name}.columns_hash[k]
1685
- if !col && rtans&.include?(k)
1686
- k = k[10..-1] if k.start_with?('rich_text_')
1687
- col = (rt_col ||= ActiveRecord::ConnectionAdapters::Column.new(
1688
- '', nil, ActiveRecord::ConnectionAdapters::SqlTypeMetadata.new(sql_type: 'varchar', type: :text)
1689
- )
1690
- )
1691
- end
1692
- val = @#{obj_name}.attributes[k] %>
1693
- <tr>
1694
- <th class=\"show-field\"<%= \" title=\\\"#\{col&.comment}\\\"\".html_safe if col&.respond_to?(:comment) && !col&.comment.blank? %>>
1695
- <% has_fields = true
1696
- if (bt = bts[k])
1697
- # Add a final member in this array with descriptive options to be used in <select> drop-downs
1698
- bt_name = bt[1].map { |x| x.first.name }.join('/')
1699
- # %%% Only do this if the user has permissions to edit this bt field
1700
- if bt[2] # Polymorphic?
1701
- poly_class_name = orig_poly_name = @#{obj_name}.send(model.brick_foreign_type(bt.first))
1702
- bt_pair = nil
1703
- loop do
1704
- bt_pair = bt[1].find { |pair| pair.first.name == poly_class_name }
1705
- # Accommodate any valid STI by going up the chain of inheritance
1706
- break unless bt_pair.nil? && poly_class_name = ::Brick.existing_stis[poly_class_name]
1707
- end
1708
- puts \"*** Might be missing an STI class called #\{orig_poly_name\} whose base class should have this:
1709
- *** has_many :#{table_name}, as: :#\{bt.first\}
1710
- *** Can probably auto-configure everything using these lines in an initialiser:
1711
- *** Brick.sti_namespace_prefixes = { '::#\{orig_poly_name\}' => 'SomeParentModel' }
1712
- *** Brick.polymorphics = { '#{table_name}.#\{bt.first\}' => ['SomeParentModel'] }\" if bt_pair.nil?
1713
- # descrips = @_brick_bt_descrip[bt.first][bt_class]
1714
- poly_id = @#{obj_name}.send(\"#\{bt.first\}_id\")
1715
- # bt_class.order(obj_pk = bt_class.primary_key).each { |obj| option_detail << [obj.brick_descrip(nil, obj_pk), obj.send(obj_pk)] }
1716
- end
1717
- bt_pair ||= bt[1].first # If there's no polymorphism (or polymorphism status is unknown), just get the first one
1718
- bt_class = bt_pair&.first
1719
- if bt.length < 4
1720
- bt << (option_detail = [[\"(No #\{bt_name\} chosen)\", '^^^brick_NULL^^^']])
1721
- # %%% Accommodate composite keys for obj.pk at the end here
1722
- collection, descrip_cols = bt_class&.order(Arel.sql(\"#\{bt_class.table_name}.#\{obj_pk = bt_class.primary_key}\"))&.brick_list
1723
- collection&.brick_(:each) do |obj|
1724
- option_detail << [
1725
- obj.brick_descrip(
1726
- descrip_cols&.first&.map { |col2| obj.send(col2.last) },
1727
- obj_pk
1728
- ), obj.send(obj_pk)
1729
- ]
1730
- end
1731
- end %>
1732
- BT <%= bt_class&.bt_link(bt.first) || orig_poly_name %>
1733
- <% else %>
1734
- <%= #{model_name}.human_attribute_name(k, { default: k }) %>
1735
- <% end %>
1736
- </th>
1737
- <td>
1738
- <%= f.brick_field(k, html_options = {}, val, col, bt, bt_class, bt_name, bt_pair) %>
1739
- </td>
1740
- </tr>
1741
- <% end
1742
- if has_fields %>
1743
- <tr><td colspan=\"2\"><%= f.submit({ class: 'update' }) %></td></tr>
1744
- <% else %>
1745
- <tr><td colspan=\"2\">(No displayable fields)</td></tr>
1746
- <% end %>
1747
- </table>#{
1748
- "<%= begin
1749
- ::Brick::Rails.display_binary(obj&.blob&.download, 500_000)&.html_safe
1750
- rescue
1751
- end %>" if model_name == 'ActiveStorage::Attachment'}
1752
- <% end %>
1670
+
1671
+ <%= # Write out the mega-form
1672
+ brick_form_for(obj, options, #{model_name}, bts, #{pk.inspect}) %>
1753
1673
 
1754
1674
  #{unless args.first == 'new'
1755
1675
  # Was: confirm_are_you_sure = ActionView.version < ::Gem::Version.new('7.0') ? "data: { confirm: 'Delete #\{model_name} -- Are you sure?' }" : "form: { data: { turbo_confirm: 'Delete #\{model_name} -- Are you sure?' } }"
@@ -67,9 +67,14 @@ module Brick::Rails::FormBuilder
67
67
  when :boolean
68
68
  out << self.check_box(method.to_sym)
69
69
  when :integer, :decimal, :float
70
- digit_pattern = col_type == :integer ? '\d*' : '\d*(?:\.\d*|)'
71
- # Used to do this for float / decimal: self.number_field method.to_sym
72
- out << self.text_field(method.to_sym, { pattern: digit_pattern, class: 'check-validity' })
70
+ if model.respond_to?(:attribute_types) && (enum_type = model.attribute_types[method]).is_a?(ActiveRecord::Enum::EnumType)
71
+ opts = enum_type.send(:mapping)&.each_with_object([]) { |v, s| s << [v.first, v.first] } || []
72
+ out << self.select(method.to_sym, [["(No #{method} chosen)", '^^^brick_NULL^^^']] + opts, { value: val || '^^^brick_NULL^^^' }, options)
73
+ else
74
+ digit_pattern = col_type == :integer ? '\d*' : '\d*(?:\.\d*|)'
75
+ # Used to do this for float / decimal: self.number_field method.to_sym
76
+ out << self.text_field(method.to_sym, { pattern: digit_pattern, class: 'check-validity' })
77
+ end
73
78
  when *DT_PICKERS.keys
74
79
  template.instance_variable_set(:@_date_fields_present, true)
75
80
  out << self.text_field(method.to_sym, { class: DT_PICKERS[col_type] })
@@ -203,6 +203,100 @@ module Brick::Rails::FormTags
203
203
  out.html_safe
204
204
  end # brick_grid
205
205
 
206
+ # Our mega show/new/update form
207
+ def brick_form_for(obj, options = {}, model = obj.class, bts = {}, pk = (obj.class.primary_key || []))
208
+ pk = [pk] unless pk.is_a?(Array)
209
+ pk.map!(&:to_s)
210
+ form_for(obj.becomes(model), options) do |f|
211
+ out = +'<table class="shadow">'
212
+ has_fields = false
213
+ # If it's a new record, set any default polymorphic types
214
+ bts&.each do |_k, v|
215
+ if v[2]
216
+ obj.send("#{model.brick_foreign_type(v.first)}=", v[1].first&.first&.name)
217
+ end
218
+ end if obj.new_record?
219
+ rtans = model.rich_text_association_names if model.respond_to?(:rich_text_association_names)
220
+ (model.column_names + (rtans || [])).each do |k|
221
+ next if (pk.include?(k) && !bts.key?(k)) ||
222
+ ::Brick.config.metadata_columns.include?(k)
223
+
224
+ col = model.columns_hash[k]
225
+ if !col && rtans&.include?(k)
226
+ k = k[10..-1] if k.start_with?('rich_text_')
227
+ col = (rt_col ||= ActiveRecord::ConnectionAdapters::Column.new(
228
+ '', nil, ActiveRecord::ConnectionAdapters::SqlTypeMetadata.new(sql_type: 'varchar', type: :text)
229
+ )
230
+ )
231
+ end
232
+ val = obj.attributes[k]
233
+ out << "
234
+ <tr>
235
+ <th class=\"show-field\"#{" title=\"#{col&.comment}\"".html_safe if col&.respond_to?(:comment) && !col&.comment.blank?}>"
236
+ has_fields = true
237
+ if (bt = bts[k])
238
+ # Add a final member in this array with descriptive options to be used in <select> drop-downs
239
+ bt_name = bt[1].map { |x| x.first.name }.join('/')
240
+ # %%% Only do this if the user has permissions to edit this bt field
241
+ if bt[2] # Polymorphic?
242
+ poly_class_name = orig_poly_name = obj.send(model.brick_foreign_type(bt.first))
243
+ bt_pair = nil
244
+ loop do
245
+ bt_pair = bt[1].find { |pair| pair.first.name == poly_class_name }
246
+ # Accommodate any valid STI by going up the chain of inheritance
247
+ break unless bt_pair.nil? && poly_class_name = ::Brick.existing_stis[poly_class_name]
248
+ end
249
+ puts "*** Might be missing an STI class called #{orig_poly_name} whose base class should have this:
250
+ *** has_many :#{table_name}, as: :#{bt.first}
251
+ *** Can probably auto-configure everything using these lines in an initialiser:
252
+ *** Brick.sti_namespace_prefixes = { '::#{orig_poly_name}' => 'SomeParentModel' }
253
+ *** Brick.polymorphics = { '#{table_name}.#{bt.first}' => ['SomeParentModel'] }" if bt_pair.nil?
254
+ # descrips = @_brick_bt_descrip[bt.first][bt_class]
255
+ poly_id = obj.send("#{bt.first}_id")
256
+ # bt_class.order(obj_pk = bt_class.primary_key).each { |obj| option_detail << [obj.brick_descrip(nil, obj_pk), obj.send(obj_pk)] }
257
+ end
258
+ bt_pair ||= bt[1].first # If there's no polymorphism (or polymorphism status is unknown), just get the first one
259
+ bt_class = bt_pair&.first
260
+ if bt.length < 4
261
+ bt << (option_detail = [["(No #{bt_name} chosen)", '^^^brick_NULL^^^']])
262
+ # %%% Accommodate composite keys for obj.pk at the end here
263
+ collection, descrip_cols = bt_class&.order(Arel.sql("#{bt_class.table_name}.#{obj_pk = bt_class.primary_key}"))&.brick_list
264
+ collection&.brick_(:each) do |obj|
265
+ option_detail << [
266
+ obj.brick_descrip(
267
+ descrip_cols&.first&.map { |col2| obj.send(col2.last) },
268
+ obj_pk
269
+ ), obj.send(obj_pk)
270
+ ]
271
+ end
272
+ end
273
+ out << "BT #{bt_class&.bt_link(bt.first) || orig_poly_name}"
274
+ else
275
+ out << model.human_attribute_name(k, { default: k })
276
+ end
277
+ out << "
278
+ </th>
279
+ <td>
280
+ #{f.brick_field(k, html_options = {}, val, col, bt, bt_class, bt_name, bt_pair)}
281
+ </td>
282
+ </tr>"
283
+ end
284
+ if has_fields
285
+ out << "<tr><td colspan=\"2\">#{f.submit({ class: 'update' })}</td></tr>"
286
+ else
287
+ out << '<tr><td colspan="2">(No displayable fields)</td></tr>'
288
+ end
289
+ out << '</table>'
290
+ if model.name == 'ActiveStorage::Attachment'
291
+ begin
292
+ out << ::Brick::Rails.display_binary(obj&.blob&.download, 500_000)&.html_safe
293
+ rescue
294
+ end
295
+ end
296
+ out.html_safe
297
+ end
298
+ end # brick_form_for
299
+
206
300
  def link_to_brick(*args, **kwargs)
207
301
  return unless ::Brick.config.mode == :on
208
302
 
@@ -5,7 +5,7 @@ module Brick
5
5
  module VERSION
6
6
  MAJOR = 1
7
7
  MINOR = 0
8
- TINY = 158
8
+ TINY = 160
9
9
 
10
10
  # PRE is nil unless it's a pre-release (beta, RC, etc.)
11
11
  PRE = nil
data/lib/brick.rb CHANGED
@@ -1112,20 +1112,22 @@ require 'active_record/relation'
1112
1112
  require 'active_record/relation/query_methods' if ActiveRecord.version < ::Gem::Version.new('5')
1113
1113
  require 'rails/railtie' if ActiveRecord.version < ::Gem::Version.new('4.2')
1114
1114
 
1115
- # Rake tasks
1116
- class Railtie < ::Rails::Railtie
1117
- Dir.glob("#{File.expand_path(__dir__)}/brick/tasks/**/*.rake").each { |task| load task }
1118
- end
1115
+ if Object.const_defined?('Rails')
1116
+ # Rake tasks
1117
+ class Railtie < ::Rails::Railtie
1118
+ Dir.glob("#{File.expand_path(__dir__)}/brick/tasks/**/*.rake").each { |task| load task }
1119
+ end
1119
1120
 
1120
- # Rails < 4.2 does not have env
1121
- module ::Rails
1122
- unless respond_to?(:env)
1123
- def self.env
1124
- @_env ||= ActiveSupport::StringInquirer.new(ENV["RAILS_ENV"] || ENV["RACK_ENV"] || "development")
1125
- end
1121
+ # Rails < 4.2 does not have env
1122
+ module ::Rails
1123
+ unless respond_to?(:env)
1124
+ def self.env
1125
+ @_env ||= ActiveSupport::StringInquirer.new(ENV["RAILS_ENV"] || ENV["RACK_ENV"] || "development")
1126
+ end
1126
1127
 
1127
- def self.env=(environment)
1128
- @_env = ActiveSupport::StringInquirer.new(environment)
1128
+ def self.env=(environment)
1129
+ @_env = ActiveSupport::StringInquirer.new(environment)
1130
+ end
1129
1131
  end
1130
1132
  end
1131
1133
  end
@@ -1,5 +1,7 @@
1
1
  module Brick
2
2
  module MigrationBuilder
3
+ include FancyGets
4
+
3
5
  # Many SQL types are the same as their migration data type name:
4
6
  # text, integer, bigint, date, boolean, decimal, float
5
7
  # These however are not:
@@ -8,7 +8,6 @@ require 'generators/brick/migration_builder'
8
8
  module Brick
9
9
  # Auto-generates migration files
10
10
  class MigrationsGenerator < ::Rails::Generators::Base
11
- include FancyGets
12
11
  include ::Brick::MigrationBuilder
13
12
 
14
13
  desc 'Auto-generates migration files for an existing database.'
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: brick
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.158
4
+ version: 1.0.160
5
5
  platform: ruby
6
6
  authors:
7
7
  - Lorin Thwaits
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-07-29 00:00:00.000000000 Z
11
+ date: 2023-08-08 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activerecord