hot-glue 0.5.3 → 0.5.5

Sign up to get free protection for your applications and to get access to all the features.
Files changed (32) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/test.yml +0 -1
  3. data/.gitignore +12 -5
  4. data/README.md +162 -42
  5. data/lib/generators/hot_glue/install_generator.rb +13 -13
  6. data/lib/generators/hot_glue/layout/builder.rb +11 -8
  7. data/lib/generators/hot_glue/layout_strategy/base.rb +31 -0
  8. data/lib/generators/hot_glue/layout_strategy/bootstrap.rb +41 -0
  9. data/lib/generators/hot_glue/layout_strategy/hot_glue.rb +82 -0
  10. data/lib/generators/hot_glue/layout_strategy/tailwind.rb +28 -0
  11. data/lib/generators/hot_glue/markup_templates/base.rb +3 -3
  12. data/lib/generators/hot_glue/markup_templates/erb.rb +90 -80
  13. data/lib/generators/hot_glue/scaffold_generator.rb +103 -110
  14. data/lib/generators/hot_glue/templates/controller.rb.erb +14 -40
  15. data/lib/generators/hot_glue/templates/erb/_form.erb +1 -1
  16. data/lib/generators/hot_glue/templates/erb/_line.erb +3 -3
  17. data/lib/generators/hot_glue/templates/erb/_list.erb +6 -11
  18. data/lib/generators/hot_glue/templates/erb/_new_button.erb +1 -1
  19. data/lib/generators/hot_glue/templates/erb/_new_form.erb +1 -1
  20. data/lib/generators/hot_glue/templates/erb/_show.erb +3 -3
  21. data/lib/generators/hot_glue/templates/erb/create.turbo_stream.erb +2 -2
  22. data/lib/generators/hot_glue/templates/erb/destroy.turbo_stream.erb +2 -2
  23. data/lib/generators/hot_glue/templates/erb/edit.erb +1 -1
  24. data/lib/generators/hot_glue/templates/erb/edit.turbo_stream.erb +1 -1
  25. data/lib/generators/hot_glue/templates/erb/index.erb +3 -6
  26. data/lib/generators/hot_glue/templates/erb/update.turbo_stream.erb +1 -1
  27. data/lib/generators/hot_glue/templates/system_spec.rb.erb +3 -1
  28. data/lib/hot-glue.rb +0 -4
  29. data/lib/hotglue/engine.rb +1 -1
  30. data/lib/hotglue/version.rb +1 -1
  31. metadata +6 -3
  32. data/lib/generators/hot_glue/helpers.rb +0 -13
@@ -0,0 +1,82 @@
1
+ class LayoutStrategy::HotGlue < LayoutStrategy::Base
2
+ def button_column_style
3
+ 'style="flex-basis: 150px'
4
+ end
5
+
6
+ def button_style
7
+ 'style="flex-basis: ' + (100 - (column_width * builder.columns.count)).floor.to_s + '%;"'
8
+ end
9
+
10
+ def column_width
11
+ each_col * builder.columns.count
12
+ end
13
+
14
+ def column_headings_col_style
15
+ " style='flex-basis: #{column_width}%'"
16
+ end
17
+
18
+ def container_name
19
+ "scaffold-container"
20
+ end
21
+
22
+ def downnest_column_style
23
+ 'style="flex-basis: ' + each_downnest_width.to_s + '%;'
24
+ end
25
+
26
+ def downnest_style
27
+ 'style="flex-basis: ' + each_downnest_width.to_s + '%"'
28
+ end
29
+
30
+ def each_downnest_width
31
+ builder.downnest_children.count == 1 ? 33 : (53/builder.downnest_children.count).floor
32
+ end
33
+
34
+ def list_classes
35
+ "scaffold-list"
36
+ end
37
+
38
+ def row_classes
39
+ "scaffold-row"
40
+ end
41
+
42
+ def column_classes_for_form_fields
43
+ "scaffold-cell"
44
+ end
45
+
46
+ def row_heading_classes
47
+ "scaffold-heading-row"
48
+ end
49
+ def column_classes_for_line_fields
50
+ "scaffold-cell"
51
+ end
52
+
53
+ def column_classes_for_column_headings
54
+ "scaffold-cell"
55
+ end
56
+
57
+ def col_width
58
+ downnest_size = case (builder.downnest_children.count)
59
+ when 0
60
+ downnest_size = 0
61
+ when 1
62
+ downnest_size = 40
63
+
64
+ else
65
+ downnest_size = 60
66
+
67
+ end
68
+ 100 - downnest_size - 5
69
+ end
70
+
71
+ def page_begin
72
+ '<div class=" scaffold-index-<%= plural %>">'
73
+ end
74
+
75
+ def page_end
76
+ '</div>'
77
+ end
78
+
79
+ def style_with_flex_basis(perc_width)
80
+ " style='flex-basis: #{perc_width}%'"
81
+ end
82
+ end
@@ -0,0 +1,28 @@
1
+
2
+
3
+ class LayoutStrategy::Tailwind < LayoutStrategy::Base
4
+ def button_classes; ""; end
5
+ def button_column_style; "" ; end
6
+ def button_style ; ""; end
7
+ def column_headings_col_style; "" ; end
8
+ def column_width; ""; end
9
+ def column_classes_for_line_fields; ""; end
10
+ def column_classes_for_form_fields; ""; end
11
+ def column_classes_for_column_headings; ""; end
12
+ def col_width; 100; end
13
+ def container_name; ""; end
14
+ def downnest_style ; ""; end
15
+ def downnest_column_style ; "" ; end
16
+ def each_col
17
+ return col_width if builder.columns.count == 0
18
+ (col_width/(builder.columns.count)).to_i
19
+ end
20
+
21
+ def list_classes; "overflow-x-auto w-full"; end
22
+ def row_classes; "grid grid-cols-4 gap-x-16 py-5 px-4 text-sm text-gray-700 border-b border-gray-200 dark:border-gray-700"; end
23
+ def row_heading_classes; "grid grid-cols-4 gap-x-16 p-4 text-sm font-medium text-gray-900 bg-gray-100 border-t border-b border-gray-200 dark:bg-gray-800 dark:border-gray-700 dark:text-white"; end
24
+ def page_begin; '<div class="overflow-hidden min-w-max"> '; end
25
+ def page_end ; '</div> '; end
26
+ def style_with_flex_basis(x); "" ; end
27
+
28
+ end
@@ -1,7 +1,7 @@
1
1
  module HotGlue
2
2
  class TemplateBase
3
- def initialize()
3
+ def initialize(layout_strategy: )
4
+ @layout_strategy = layout_strategy
4
5
  end
5
-
6
6
  end
7
- end
7
+ end
@@ -3,7 +3,7 @@ module HotGlue
3
3
 
4
4
  attr_accessor :path, :singular, :singular_class,
5
5
  :magic_buttons, :small_buttons,
6
- :show_only, :column_width, :layout, :perc_width,
6
+ :show_only, :column_width, :layout_strategy, :perc_width,
7
7
  :ownership_field, :form_labels_position,
8
8
  :inline_list_labels,
9
9
  :columns, :column_width, :col_identifier, :singular,
@@ -16,14 +16,7 @@ module HotGlue
16
16
  text.lines.collect{|line| add_spaces + line}.join("")
17
17
  end
18
18
 
19
- def magic_button_output(*args)
20
- path = args[0][:path]
21
- # path_helper_singular = args[0][:path_helper_singular]
22
- # path_helper_args = args[0][:path_helper_args]
23
- singular = args[0][:singular]
24
- magic_buttons = args[0][:magic_buttons]
25
- small_buttons = args[0][:small_buttons]
26
-
19
+ def magic_button_output(path:, singular:, magic_buttons:, small_buttons: )
27
20
  magic_buttons.collect{ |button_name|
28
21
  "<%= form_with model: #{singular}, url: #{path}, html: {style: 'display: inline', data: {\"turbo-confirm\": 'Are you sure you want to #{button_name} this #{singular}?'}} do |f| %>
29
22
  <%= f.hidden_field :#{button_name}, value: \"#{button_name}\" %>
@@ -36,13 +29,8 @@ module HotGlue
36
29
  @columns = args[0][:columns]
37
30
  @column_width = args[0][:column_width]
38
31
  @col_identifier = args[0][:col_identifier]
39
- @layout = args[0][:layout]
40
32
 
41
- if layout == "hotglue"
42
- col_style = " style='flex-basis: #{column_width}%'"
43
- else
44
- col_style = ""
45
- end
33
+ col_style = @layout_strategy.column_headings_col_style
46
34
 
47
35
  result = columns.map{ |column|
48
36
  "<div class='#{col_identifier}'" + col_style + ">" + column.map(&:to_s).map{|col_name| "#{col_name.humanize}"}.join("<br />") + "</div>"
@@ -59,16 +47,17 @@ module HotGlue
59
47
  @columns = args[0][:columns]
60
48
  @show_only = args[0][:show_only]
61
49
  @singular_class = args[0][:singular_class]
62
- @col_identifier = args[0][:col_identifier]
63
50
  @ownership_field = args[0][:ownership_field]
64
51
  @form_labels_position = args[0][:form_labels_position]
65
52
  @form_placeholder_labels = args[0][:form_placeholder_labels]
66
53
  @hawk_keys = args[0][:hawk_keys]
67
-
68
54
  @singular = args[0][:singular]
55
+
56
+ column_classes = args[0][:col_identifier]
57
+
69
58
  singular = @singular
70
59
  result = columns.map{ |column|
71
- " <div class='#{col_identifier}' >" +
60
+ " <div class='#{column_classes}' >" +
72
61
  column.map { |col|
73
62
  field_result =
74
63
  if show_only.include?(col.to_sym)
@@ -81,12 +70,14 @@ module HotGlue
81
70
  case type
82
71
  when :integer
83
72
  integer_result(col)
73
+ when :uuid
74
+ uuid_result(col)
84
75
  when :string
85
76
  string_result(col, sql_type, limit)
86
77
  when :text
87
78
  text_result(col, sql_type, limit)
88
79
  when :float
89
- field_output(col, nil, 5, col_identifier)
80
+ field_output(col, nil, 5, column_classes)
90
81
  when :datetime
91
82
  "<%= datetime_field_localized(f, :#{col}, #{singular}.#{col}, '#{ col.to_s.humanize }', #{@auth ? @auth+'.timezone' : 'nil'}) %>"
92
83
  when :date
@@ -122,36 +113,46 @@ module HotGlue
122
113
  def integer_result(col)
123
114
  # look for a belongs_to on this object
124
115
  if col.to_s.ends_with?("_id")
125
- assoc_name = col.to_s.gsub("_id","")
126
- assoc = eval("#{singular_class}.reflect_on_association(:#{assoc_name})")
127
- if assoc.nil?
128
- exit_message = "*** Oops. on the #{singular_class} object, there doesn't seem to be an association called '#{assoc_name}'"
129
- exit
130
- end
131
-
132
- is_owner = col == ownership_field
133
- assoc_class_name = assoc.active_record.name
134
- display_column = HotGlue.derrive_reference_name(assoc_class_name)
135
-
136
- if @hawk_keys[assoc.foreign_key.to_sym]
137
- hawk_definition = @hawk_keys[assoc.foreign_key.to_sym]
138
- hawk_root = hawk_definition[0]
139
- hawk_scope = hawk_definition[1]
140
- hawked_association = "#{hawk_root}.#{hawk_scope}"
141
- else
142
- hawked_association = "#{assoc.class_name}.all"
143
- end
144
-
145
- (is_owner ? "<% unless @#{assoc_name} %>\n" : "") +
146
- " <%= f.collection_select(:#{col}, #{hawked_association}, :id, :#{display_column}, {prompt: true, selected: @#{singular}.#{col} }, class: 'form-control') %>\n" +
147
- (is_owner ? "<% else %>\n <%= @#{assoc_name}.#{display_column} %>" : "") +
148
- (is_owner ? "\n<% end %>" : "")
149
-
116
+ association_result(col)
150
117
  else
151
118
  " <%= f.text_field :#{col}, value: #{@singular}.#{col}, autocomplete: 'off', size: 4, class: 'form-control', type: 'number'" + (@form_placeholder_labels ? ", placeholder: '#{col.to_s.humanize}'" : "") + " %>\n " + "\n"
152
119
  end
153
120
  end
154
121
 
122
+
123
+ def uuid_result(col)
124
+ association_result(col)
125
+ end
126
+
127
+
128
+ def association_result(col)
129
+ assoc_name = col.to_s.gsub("_id","")
130
+ assoc = eval("#{singular_class}.reflect_on_association(:#{assoc_name})")
131
+ if assoc.nil?
132
+ exit_message = "*** Oops. on the #{singular_class} object, there doesn't seem to be an association called '#{assoc_name}'"
133
+ exit
134
+ end
135
+
136
+ is_owner = col == ownership_field
137
+ assoc_class_name = assoc.active_record.name
138
+ display_column = HotGlue.derrive_reference_name(assoc_class_name)
139
+
140
+ if @hawk_keys[assoc.foreign_key.to_sym]
141
+ hawk_definition = @hawk_keys[assoc.foreign_key.to_sym]
142
+ hawk_root = hawk_definition[0]
143
+ hawk_scope = hawk_definition[1]
144
+ hawked_association = "#{hawk_root}.#{hawk_scope}"
145
+ else
146
+ hawked_association = "#{assoc.class_name}.all"
147
+ end
148
+
149
+ (is_owner ? "<% unless @#{assoc_name} %>\n" : "") +
150
+ " <%= f.collection_select(:#{col}, #{hawked_association}, :id, :#{display_column}, {prompt: true, selected: @#{singular}.#{col} }, class: 'form-control') %>\n" +
151
+ (is_owner ? "<% else %>\n <%= @#{assoc_name}.#{display_column} %>" : "") +
152
+ (is_owner ? "\n<% end %>" : "")
153
+
154
+ end
155
+
155
156
  def string_result(col, sql_type, limit)
156
157
  if sql_type == "varchar" || sql_type == "character varying"
157
158
  field_output(col, nil, limit || 40, col_identifier)
@@ -216,18 +217,14 @@ module HotGlue
216
217
  @singular_class = args[0][:singular_class]
217
218
  @singular = args[0][:singular]
218
219
  @perc_width = args[0][:perc_width]
219
- @layout = args[0][:layout]
220
- @col_identifier = args[0][:col_identifier] || (layout == "bootstrap" ? "col-md-2" : "scaffold-cell")
220
+ @col_identifier = @layout_strategy.column_classes_for_line_fields
221
+
221
222
  @inline_list_labels = args[0][:inline_list_labels] || 'omit'
222
223
 
223
224
  columns_count = columns.count + 1
224
225
  perc_width = (@perc_width).floor
225
226
 
226
- if layout == "bootstrap"
227
- style_with_flex_basis = ""
228
- else
229
- style_with_flex_basis = " style='flex-basis: #{perc_width}%'"
230
- end
227
+ style_with_flex_basis = @layout_strategy.style_with_flex_basis(perc_width)
231
228
 
232
229
  result = columns.map{ |column|
233
230
  "<div class='#{col_identifier}'#{style_with_flex_basis}>" +
@@ -238,14 +235,30 @@ module HotGlue
238
235
  limit = eval("#{singular_class}.columns_hash['#{col}']").limit
239
236
  sql_type = eval("#{singular_class}.columns_hash['#{col}']").sql_type
240
237
 
241
- field_output = case type
242
- when :integer
243
- # look for a belongs_to on this object
244
- if col.ends_with?("_id")
238
+ field_output =
239
+ case type
240
+ when :integer
241
+ # look for a belongs_to on this object
242
+ if col.ends_with?("_id")
243
+ assoc_name = col.to_s.gsub("_id","")
244
+ assoc = eval("#{singular_class}.reflect_on_association(:#{assoc_name})")
245
+
246
+ if assoc.nil?
247
+ exit_message = "*** Oops. on the #{singular_class} object, there doesn't seem to be an association called '#{assoc_name}'"
248
+ puts exit_message
249
+ exit
250
+ # raise(HotGlue::Error,exit_message)
251
+ end
252
+ assoc_class_name = assoc.active_record.name
253
+ display_column = HotGlue.derrive_reference_name(assoc_class_name)
254
+ "<%= #{singular}.#{assoc.name.to_s}.try(:#{display_column}) || '<span class=\"content alert-danger\">MISSING</span>'.html_safe %>"
255
+
256
+ else
257
+ "<%= #{singular}.#{col}%>"
258
+ end
245
259
 
260
+ when :uuid
246
261
  assoc_name = col.to_s.gsub("_id","")
247
-
248
-
249
262
  assoc = eval("#{singular_class}.reflect_on_association(:#{assoc_name})")
250
263
 
251
264
  if assoc.nil?
@@ -258,37 +271,34 @@ module HotGlue
258
271
  display_column = HotGlue.derrive_reference_name(assoc_class_name)
259
272
  "<%= #{singular}.#{assoc.name.to_s}.try(:#{display_column}) || '<span class=\"content alert-danger\">MISSING</span>'.html_safe %>"
260
273
 
261
- else
274
+ when :float
275
+ width = (limit && limit < 40) ? limit : (40)
262
276
  "<%= #{singular}.#{col}%>"
263
- end
264
- when :float
265
- width = (limit && limit < 40) ? limit : (40)
266
- "<%= #{singular}.#{col}%>"
267
- when :string
268
- width = (limit && limit < 40) ? limit : (40)
269
- "<%= #{singular}.#{col} %>"
270
- when :text
271
- "<%= #{singular}.#{col} %>"
272
- when :datetime
273
- "<% unless #{singular}.#{col}.nil? %>
277
+ when :string
278
+ width = (limit && limit < 40) ? limit : (40)
279
+ "<%= #{singular}.#{col} %>"
280
+ when :text
281
+ "<%= #{singular}.#{col} %>"
282
+ when :datetime
283
+ "<% unless #{singular}.#{col}.nil? %>
274
284
  <%= #{singular}.#{col}.in_time_zone(current_timezone).strftime('%m/%d/%Y @ %l:%M %p ') + timezonize(current_timezone) %>
275
285
  <% else %>
276
286
  <span class='alert-danger'>MISSING</span>
277
287
  <% end %>"
278
- when :date
279
- "<% unless #{singular}.#{col}.nil? %>
288
+ when :date
289
+ "<% unless #{singular}.#{col}.nil? %>
280
290
  <%= #{singular}.#{col} %>
281
291
  <% else %>
282
292
  <span class='alert-danger'>MISSING</span>
283
293
  <% end %>"
284
- when :time
285
- "<% unless #{singular}.#{col}.nil? %>
294
+ when :time
295
+ "<% unless #{singular}.#{col}.nil? %>
286
296
  <%= #{singular}.#{col}.in_time_zone(current_timezone).strftime('%l:%M %p ') + timezonize(current_timezone) %>
287
297
  <% else %>
288
298
  <span class='alert-danger'>MISSING</span>
289
299
  <% end %>"
290
- when :boolean
291
- "
300
+ when :boolean
301
+ "
292
302
  <% if #{singular}.#{col}.nil? %>
293
303
  <span class='alert-danger'>MISSING</span>
294
304
  <% elsif #{singular}.#{col} %>
@@ -297,8 +307,9 @@ module HotGlue
297
307
  NO
298
308
  <% end %>
299
309
 
300
- " when :enum
301
- enum_type = eval("#{singular_class}.columns.select{|x| x.name == '#{col}'}[0].sql_type")
310
+ "
311
+ when :enum
312
+ enum_type = eval("#{singular_class}.columns.select{|x| x.name == '#{col}'}[0].sql_type")
302
313
 
303
314
  "
304
315
  <% if #{singular}.#{col}.nil? %>
@@ -308,8 +319,7 @@ module HotGlue
308
319
  <% end %>
309
320
 
310
321
  "
311
- end #end of switch
312
-
322
+ end #end of switch
313
323
 
314
324
  label = "<br/><label class='small form-text text-muted'>#{col.to_s.humanize}</label>"
315
325
 
@@ -319,4 +329,4 @@ module HotGlue
319
329
  }.join("\n")
320
330
  end
321
331
  end
322
- end
332
+ end