frails 0.6.0 → 0.7.0

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: 9e2019a4307891e5178133fc9f650899438107417cb2e27114fd312d76fb27ee
4
- data.tar.gz: 81257e95be178039ff24d51d75edc4fb901e537a22376db859f7f22cebe66b4d
3
+ metadata.gz: c46b468e5c618fbfbcab851db75178b94bbf788ca6e4c7b93566b4ce464ee31a
4
+ data.tar.gz: 2cee5f81db2822473ffa13290e7a9e6ac63f30294fa184c02f9a5b0eaaff02ba
5
5
  SHA512:
6
- metadata.gz: '095364fec3c7b02572e771e2ca5edbf82baecb1ebd36bc8eb94c2cc93a3238c0b8853daa8af32fec36532a34a18c4346ed45c128202c0a855d72129b3461d40b'
7
- data.tar.gz: 7f75601a78753eecd204a8c45767bcf9529a3936145b236d9d216f0a2348ce1f90c95b0b1bed70cecbd2518166bac5f2434f40b8b7006696ab949281366b6428
6
+ metadata.gz: aa838a5fb3e936d75ded9a596498c961fc815d95e44af492150362bb72b20d1c15c4f0b535bb99967befeda92449bfe778c23cb53521cd875720b5095c674f75
7
+ data.tar.gz: 5f71ddc5d01739ef50da31ea5edc20b3d4f126e4b52c751eb0196e3324e5fc93f43cdc81fa46885b4a2d9df4536af9f39f0f963620bf4bde98f4f25b965cbdf5
data/.gitignore CHANGED
@@ -8,4 +8,8 @@
8
8
  /spec/reports/
9
9
  /tmp/
10
10
  .DS_Store
11
- *.log
11
+ *.log
12
+ .byebug_history
13
+ test/dummy/node_modules
14
+ test/dummy/tmp
15
+ test/dummy/log
@@ -6,7 +6,7 @@ Style/ModuleFunction:
6
6
  Enabled: false
7
7
  Style/ClassAndModuleChildren:
8
8
  Enabled: false
9
- Metrics/LineLength:
9
+ Layout/LineLength:
10
10
  Max: 100
11
11
  Layout/IndentationConsistency:
12
12
  EnforcedStyle: indented_internal_methods
data/Gemfile CHANGED
@@ -16,4 +16,10 @@ gemspec
16
16
  # To use a debugger
17
17
  # gem 'byebug', group: [:development, :test]
18
18
 
19
- gem 'rubocop', require: false
19
+ gem 'rubocop', require: false, group: :development
20
+
21
+ group :test do
22
+ gem 'byebug'
23
+ gem 'm'
24
+ gem 'minitest', '~> 5.0'
25
+ end
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- frails (0.5.1)
4
+ frails (0.7.0)
5
5
  nokogiri (>= 1.10.4)
6
6
  rack-proxy (>= 0.6.5)
7
7
  rails (>= 6.0)
@@ -9,126 +9,130 @@ PATH
9
9
  GEM
10
10
  remote: https://rubygems.org/
11
11
  specs:
12
- actioncable (6.0.0)
13
- actionpack (= 6.0.0)
12
+ actioncable (6.0.2.1)
13
+ actionpack (= 6.0.2.1)
14
14
  nio4r (~> 2.0)
15
15
  websocket-driver (>= 0.6.1)
16
- actionmailbox (6.0.0)
17
- actionpack (= 6.0.0)
18
- activejob (= 6.0.0)
19
- activerecord (= 6.0.0)
20
- activestorage (= 6.0.0)
21
- activesupport (= 6.0.0)
16
+ actionmailbox (6.0.2.1)
17
+ actionpack (= 6.0.2.1)
18
+ activejob (= 6.0.2.1)
19
+ activerecord (= 6.0.2.1)
20
+ activestorage (= 6.0.2.1)
21
+ activesupport (= 6.0.2.1)
22
22
  mail (>= 2.7.1)
23
- actionmailer (6.0.0)
24
- actionpack (= 6.0.0)
25
- actionview (= 6.0.0)
26
- activejob (= 6.0.0)
23
+ actionmailer (6.0.2.1)
24
+ actionpack (= 6.0.2.1)
25
+ actionview (= 6.0.2.1)
26
+ activejob (= 6.0.2.1)
27
27
  mail (~> 2.5, >= 2.5.4)
28
28
  rails-dom-testing (~> 2.0)
29
- actionpack (6.0.0)
30
- actionview (= 6.0.0)
31
- activesupport (= 6.0.0)
32
- rack (~> 2.0)
29
+ actionpack (6.0.2.1)
30
+ actionview (= 6.0.2.1)
31
+ activesupport (= 6.0.2.1)
32
+ rack (~> 2.0, >= 2.0.8)
33
33
  rack-test (>= 0.6.3)
34
34
  rails-dom-testing (~> 2.0)
35
35
  rails-html-sanitizer (~> 1.0, >= 1.2.0)
36
- actiontext (6.0.0)
37
- actionpack (= 6.0.0)
38
- activerecord (= 6.0.0)
39
- activestorage (= 6.0.0)
40
- activesupport (= 6.0.0)
36
+ actiontext (6.0.2.1)
37
+ actionpack (= 6.0.2.1)
38
+ activerecord (= 6.0.2.1)
39
+ activestorage (= 6.0.2.1)
40
+ activesupport (= 6.0.2.1)
41
41
  nokogiri (>= 1.8.5)
42
- actionview (6.0.0)
43
- activesupport (= 6.0.0)
42
+ actionview (6.0.2.1)
43
+ activesupport (= 6.0.2.1)
44
44
  builder (~> 3.1)
45
45
  erubi (~> 1.4)
46
46
  rails-dom-testing (~> 2.0)
47
47
  rails-html-sanitizer (~> 1.1, >= 1.2.0)
48
- activejob (6.0.0)
49
- activesupport (= 6.0.0)
48
+ activejob (6.0.2.1)
49
+ activesupport (= 6.0.2.1)
50
50
  globalid (>= 0.3.6)
51
- activemodel (6.0.0)
52
- activesupport (= 6.0.0)
53
- activerecord (6.0.0)
54
- activemodel (= 6.0.0)
55
- activesupport (= 6.0.0)
56
- activestorage (6.0.0)
57
- actionpack (= 6.0.0)
58
- activejob (= 6.0.0)
59
- activerecord (= 6.0.0)
51
+ activemodel (6.0.2.1)
52
+ activesupport (= 6.0.2.1)
53
+ activerecord (6.0.2.1)
54
+ activemodel (= 6.0.2.1)
55
+ activesupport (= 6.0.2.1)
56
+ activestorage (6.0.2.1)
57
+ actionpack (= 6.0.2.1)
58
+ activejob (= 6.0.2.1)
59
+ activerecord (= 6.0.2.1)
60
60
  marcel (~> 0.3.1)
61
- activesupport (6.0.0)
61
+ activesupport (6.0.2.1)
62
62
  concurrent-ruby (~> 1.0, >= 1.0.2)
63
63
  i18n (>= 0.7, < 2)
64
64
  minitest (~> 5.1)
65
65
  tzinfo (~> 1.1)
66
- zeitwerk (~> 2.1, >= 2.1.8)
66
+ zeitwerk (~> 2.2)
67
67
  ast (2.4.0)
68
- builder (3.2.3)
69
- concurrent-ruby (1.1.5)
70
- crass (1.0.5)
68
+ builder (3.2.4)
69
+ byebug (11.1.1)
70
+ concurrent-ruby (1.1.6)
71
+ crass (1.0.6)
71
72
  erubi (1.9.0)
72
73
  globalid (0.4.2)
73
74
  activesupport (>= 4.2.0)
74
- i18n (1.7.0)
75
+ i18n (1.8.2)
75
76
  concurrent-ruby (~> 1.0)
76
- jaro_winkler (1.5.3)
77
- loofah (2.3.0)
77
+ jaro_winkler (1.5.4)
78
+ loofah (2.4.0)
78
79
  crass (~> 1.0.2)
79
80
  nokogiri (>= 1.5.9)
81
+ m (1.5.1)
82
+ method_source (>= 0.6.7)
83
+ rake (>= 0.9.2.2)
80
84
  mail (2.7.1)
81
85
  mini_mime (>= 0.1.1)
82
86
  marcel (0.3.3)
83
87
  mimemagic (~> 0.3.2)
84
88
  method_source (0.9.2)
85
- mimemagic (0.3.3)
89
+ mimemagic (0.3.4)
86
90
  mini_mime (1.0.2)
87
91
  mini_portile2 (2.4.0)
88
- minitest (5.12.2)
92
+ minitest (5.14.0)
89
93
  nio4r (2.5.2)
90
- nokogiri (1.10.4)
94
+ nokogiri (1.10.8)
91
95
  mini_portile2 (~> 2.4.0)
92
- parallel (1.17.0)
93
- parser (2.6.4.1)
96
+ parallel (1.19.1)
97
+ parser (2.7.0.2)
94
98
  ast (~> 2.4.0)
95
- rack (2.0.7)
99
+ rack (2.2.2)
96
100
  rack-proxy (0.6.5)
97
101
  rack
98
102
  rack-test (1.1.0)
99
103
  rack (>= 1.0, < 3)
100
- rails (6.0.0)
101
- actioncable (= 6.0.0)
102
- actionmailbox (= 6.0.0)
103
- actionmailer (= 6.0.0)
104
- actionpack (= 6.0.0)
105
- actiontext (= 6.0.0)
106
- actionview (= 6.0.0)
107
- activejob (= 6.0.0)
108
- activemodel (= 6.0.0)
109
- activerecord (= 6.0.0)
110
- activestorage (= 6.0.0)
111
- activesupport (= 6.0.0)
104
+ rails (6.0.2.1)
105
+ actioncable (= 6.0.2.1)
106
+ actionmailbox (= 6.0.2.1)
107
+ actionmailer (= 6.0.2.1)
108
+ actionpack (= 6.0.2.1)
109
+ actiontext (= 6.0.2.1)
110
+ actionview (= 6.0.2.1)
111
+ activejob (= 6.0.2.1)
112
+ activemodel (= 6.0.2.1)
113
+ activerecord (= 6.0.2.1)
114
+ activestorage (= 6.0.2.1)
115
+ activesupport (= 6.0.2.1)
112
116
  bundler (>= 1.3.0)
113
- railties (= 6.0.0)
117
+ railties (= 6.0.2.1)
114
118
  sprockets-rails (>= 2.0.0)
115
119
  rails-dom-testing (2.0.3)
116
120
  activesupport (>= 4.2.0)
117
121
  nokogiri (>= 1.6)
118
122
  rails-html-sanitizer (1.3.0)
119
123
  loofah (~> 2.3)
120
- railties (6.0.0)
121
- actionpack (= 6.0.0)
122
- activesupport (= 6.0.0)
124
+ railties (6.0.2.1)
125
+ actionpack (= 6.0.2.1)
126
+ activesupport (= 6.0.2.1)
123
127
  method_source
124
128
  rake (>= 0.8.7)
125
129
  thor (>= 0.20.3, < 2.0)
126
130
  rainbow (3.0.0)
127
- rake (13.0.0)
128
- rubocop (0.74.0)
131
+ rake (13.0.1)
132
+ rubocop (0.79.0)
129
133
  jaro_winkler (~> 1.5.1)
130
134
  parallel (~> 1.10)
131
- parser (>= 2.6)
135
+ parser (>= 2.7.0.1)
132
136
  rainbow (>= 2.2.2, < 4.0)
133
137
  ruby-progressbar (~> 1.7)
134
138
  unicode-display_width (>= 1.4.0, < 1.7)
@@ -140,22 +144,25 @@ GEM
140
144
  actionpack (>= 4.0)
141
145
  activesupport (>= 4.0)
142
146
  sprockets (>= 3.0.0)
143
- thor (0.20.3)
147
+ thor (1.0.1)
144
148
  thread_safe (0.3.6)
145
- tzinfo (1.2.5)
149
+ tzinfo (1.2.6)
146
150
  thread_safe (~> 0.1)
147
- unicode-display_width (1.6.0)
151
+ unicode-display_width (1.6.1)
148
152
  websocket-driver (0.7.1)
149
153
  websocket-extensions (>= 0.1.0)
150
154
  websocket-extensions (0.1.4)
151
- zeitwerk (2.2.0)
155
+ zeitwerk (2.2.2)
152
156
 
153
157
  PLATFORMS
154
158
  ruby
155
159
 
156
160
  DEPENDENCIES
161
+ byebug
157
162
  frails!
163
+ m
164
+ minitest (~> 5.0)
158
165
  rubocop
159
166
 
160
167
  BUNDLED WITH
161
- 2.0.2
168
+ 2.1.4
data/README.md CHANGED
@@ -8,6 +8,13 @@ Frails is a modern asset pipeline for [Rails](https://rubyonrails.org), built on
8
8
  - Full Webpack control without fighting with the likes of Webpacker.
9
9
  - Embrace modern front end practices.
10
10
 
11
+ PLUS...
12
+
13
+ - Side loaded layouts, views and partials.
14
+ - Components
15
+ - React + SSR
16
+ - Ruby/HTML
17
+
11
18
  ## Installation
12
19
 
13
20
  Frails is designed to work only within a Rails application, so must be installed in an existing Rails app. It also requires Node.js and a valid `package.json` file in your app root.
data/Rakefile CHANGED
@@ -5,8 +5,8 @@ require 'rake/testtask'
5
5
 
6
6
  Rake::TestTask.new(:test) do |t|
7
7
  t.libs << 'test'
8
- t.libs << 'lib'
9
8
  t.test_files = FileList['test/**/*_test.rb']
9
+ t.verbose = true
10
10
  end
11
11
 
12
12
  task default: :test
@@ -27,6 +27,10 @@ module Frails
27
27
  def manifest_path
28
28
  ENV['FRAILS_MANIFEST_PATH'] || 'manifest.json'
29
29
  end
30
+
31
+ def components_path
32
+ @components_path ||= Rails.root.join('app', 'components')
33
+ end
30
34
  end
31
35
 
32
36
  require 'frails/log_subscriber'
@@ -3,9 +3,20 @@
3
3
  module Frails::Component
4
4
  end
5
5
 
6
+ module ActionView
7
+ extend ActiveSupport::Autoload
8
+
9
+ # Make sure ActionView::SyntaxErrorInTemplate is loaded.
10
+ eager_autoload do
11
+ autoload_at 'action_view/template/error' do
12
+ autoload :SyntaxErrorInTemplate
13
+ end
14
+ end
15
+ end
16
+
6
17
  require 'frails/component/renderer_concerns'
7
- require 'frails/component/component_renderer'
8
- require 'frails/component/react_component_renderer'
9
- require 'frails/component/abstract_component'
10
- require 'frails/component/plain_component'
11
- require 'frails/component/react_component'
18
+ require 'frails/component/renderer'
19
+ require 'frails/component/react_renderer'
20
+ require 'frails/component/abstract'
21
+ require 'frails/component/base'
22
+ require 'frails/component/react'
@@ -1,12 +1,14 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- class Frails::Component::AbstractComponent
3
+ class Frails::Component::Abstract
4
4
  include ActiveSupport::Callbacks
5
5
 
6
6
  define_callbacks :render
7
7
 
8
- def initialize(view, options)
9
- @view, @options = view, options
8
+ def initialize(view, path, options)
9
+ @view = view
10
+ @path = path
11
+ @options = options
10
12
 
11
13
  expand_instance_vars
12
14
  end
@@ -24,19 +26,19 @@ class Frails::Component::AbstractComponent
24
26
  # rubocop:disable Lint/ShadowedException, Style/MissingRespondToMissing
25
27
  def method_missing(method, *args, &block)
26
28
  super
27
- rescue NoMethodError, NameError => e1
29
+ rescue NoMethodError, NameError => e
28
30
  # the error is not mine, so just releases it as is.
29
- raise e1 if e1.name != method
31
+ raise e if e.name != method
30
32
 
31
33
  begin
32
34
  @view.send method, *args, &block
33
- rescue NoMethodError => e2
34
- raise e2 if e2.name != method
35
+ rescue NoMethodError => e
36
+ raise e if e.name != method
35
37
 
36
38
  raise NoMethodError.new("undefined method `#{method}' for either #{self} or #{@view}",
37
39
  method)
38
- rescue NameError => e2
39
- raise e2 if e2.name != method
40
+ rescue NameError => e
41
+ raise e if e.name != method
40
42
 
41
43
  raise NameError.new("undefined local variable `#{method}' for either #{self} or #{@view}",
42
44
  method)
@@ -1,9 +1,9 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- class Frails::Component::PlainComponent < Frails::Component::AbstractComponent
4
- PRIVATE_METHODS = %i[render method_missing locals].freeze
3
+ class Frails::Component::Base < Frails::Component::Abstract
4
+ PRIVATE_METHODS = %i[render method_missing locals to_partial_path].freeze
5
5
 
6
- def initialize(view, options)
6
+ def initialize(view, path, options)
7
7
  super
8
8
 
9
9
  @locals = @options.fetch(:locals, @options)
@@ -16,4 +16,8 @@ class Frails::Component::PlainComponent < Frails::Component::AbstractComponent
16
16
  end
17
17
  hash.merge @locals
18
18
  end
19
+
20
+ def to_partial_path
21
+ "#{@path}/index"
22
+ end
19
23
  end
@@ -1,17 +1,15 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- class Frails::Component::ReactComponent < Frails::Component::AbstractComponent
3
+ class Frails::Component::React < Frails::Component::Abstract
4
4
  attr_accessor :class_name, :props, :tag, :prerender, :content_loader
5
5
 
6
- def initialize(view, options)
7
- @view, @options = view, options
6
+ def initialize(view, path, options)
7
+ super
8
8
 
9
9
  @class_name = @options.fetch(:class, nil)
10
10
  @props = @options.fetch(:props, {})
11
11
  @tag = @options.fetch(:tag, :div)
12
12
  @prerender = @options.fetch(:prerender, false)
13
13
  @content_loader = @options.fetch(:content_loader, false)
14
-
15
- expand_instance_vars
16
14
  end
17
15
  end
@@ -1,12 +1,16 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- class Frails::Component::ReactComponentRenderer
3
+ require 'frails/utils'
4
+
5
+ class Frails::Component::ReactRenderer
4
6
  include Frails::Component::RendererConcerns
5
7
 
6
8
  def render(context, options, &block)
7
9
  @view = context
8
- @component = options.delete(:component).to_s
9
- @presenter = presenter_class.new(@view, options)
10
+ @component = options.delete(:component)
11
+
12
+ klass = presenter_class
13
+ @presenter = klass.new(@view, @component, options)
10
14
 
11
15
  @children = @view.capture(&block) if block_given?
12
16
 
@@ -20,20 +24,22 @@ class Frails::Component::ReactComponentRenderer
20
24
  @prerender = @presenter.prerender
21
25
  @content_loader = @presenter.content_loader
22
26
  @props = camelize_keys(@presenter.props)
23
- @props[:children] = @children if @children
27
+ @props[:children] = @children if instance_variable_defined?(:@children)
24
28
 
25
29
  @prerender && render_inline_styles
26
30
 
27
- rendered_tag = content_tag do
28
- @prerender ? React::Renderer.new.render(@component, @props).html_safe : loader
29
- end
31
+ rendered_tag = if @prerender
32
+ content_tag { React::Renderer.new.render(@component, @props).html_safe }
33
+ else
34
+ loader || content_tag { nil }
35
+ end
30
36
 
31
37
  @prerender ? move_console_replay_script(rendered_tag) : rendered_tag
32
38
  end
33
39
  end
34
40
 
35
41
  def presenter_class
36
- super || Frails::Component::ReactComponent
42
+ super || Frails::Component::React
37
43
  end
38
44
 
39
45
  def data_for_content_tag
@@ -47,17 +53,21 @@ class Frails::Component::ReactComponentRenderer
47
53
  end
48
54
 
49
55
  def content_tag(&block)
50
- classes = "js__reactComponent #{@presenter.class_name}"
51
- @view.content_tag @presenter.tag, class: classes, data: data_for_content_tag, &block
56
+ class_names = "js__reactComponent #{@presenter.class_name}"
57
+ @view.content_tag @presenter.tag, class: class_names, data: data_for_content_tag, &block
52
58
  end
53
59
 
54
60
  def camelize_keys(data)
55
- data.deep_transform_keys { |key| key.to_s.camelize :lower }
61
+ data.deep_transform_keys do |key|
62
+ Frails::Utils.camelize key.to_s, :lower, convert_slashes: false
63
+ end
56
64
  end
57
65
 
58
66
  def loader
59
- @content_loader ? @view.render(@content_loader) : nil
60
- end
67
+ return unless @content_loader
68
+
69
+ @view.render @content_loader, class_name: 'js__reactComponent', data: data_for_content_tag
70
+ end
61
71
 
62
72
  # Grab the server-rendered console replay script and move it outside the container div.
63
73
  #
@@ -1,18 +1,43 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- class Frails::Component::ComponentRenderer < ActionView::PartialRenderer
3
+ class Frails::Component::Renderer < ActionView::PartialRenderer
4
4
  include Frails::Component::RendererConcerns
5
5
 
6
+ # Overwritten to make sure we don't lookup partials. Even though this inherits from the
7
+ # PartialRenderer, component templates do not have the underscore prefix that partials have.
8
+ #
9
+ # Additionally, this will ensure that ONLY the app/components directory is used as the only view
10
+ # path to search within when looking up the component template.
11
+ def find_template(path, locals)
12
+ path_count = @lookup_context.view_paths.size
13
+ @lookup_context.view_paths.unshift Frails.components_path
14
+ old_paths = @lookup_context.view_paths.pop(path_count)
15
+
16
+ prefixes = path.include?('/') ? [] : @lookup_context.prefixes
17
+ result = @lookup_context.find_template(path, prefixes, false, locals, @details)
18
+
19
+ @lookup_context.view_paths.unshift(*old_paths)
20
+ @lookup_context.view_paths.pop
21
+
22
+ result
23
+ end
24
+
6
25
  def render(context, options, &block)
7
26
  @view = context
8
- @component = options.delete(:component).to_s
9
- @presenter = presenter_class.new(@view, options)
27
+ @component = options.delete(:component)
28
+
29
+ klass = presenter_class
30
+ @presenter = klass.new(@view, @component, options)
31
+
32
+ @children = block_given? ? @view.capture(&block) : nil
33
+ options[:partial] = @presenter
10
34
 
11
35
  result = @presenter.run_callbacks :render do
12
36
  if @presenter.respond_to?(:render)
13
37
  @presenter.render(&block)
14
38
  else
15
39
  options[:locals] = @presenter.locals
40
+ options[:locals][:children] = @children
16
41
  super context, options, block
17
42
  end
18
43
  end
@@ -23,7 +48,7 @@ class Frails::Component::ComponentRenderer < ActionView::PartialRenderer
23
48
  private
24
49
 
25
50
  def presenter_class
26
- super || Frails::Component::PlainComponent
51
+ super || Frails::Component::Base
27
52
  end
28
53
 
29
54
  def apply_styles(content)
@@ -68,7 +93,7 @@ class Frails::Component::ComponentRenderer < ActionView::PartialRenderer
68
93
  def stylesheet_path
69
94
  @stylesheet_path ||= begin
70
95
  style_file = "#{@component}/index.css"
71
- Rails.root.join('app', 'components', style_file).relative_path_from(Rails.root)
96
+ Frails.components_path.join(style_file).relative_path_from(Rails.root)
72
97
  end
73
98
  end
74
99
  end
@@ -6,7 +6,13 @@ module Frails::Component::RendererConcerns
6
6
  private
7
7
 
8
8
  def presenter_class
9
- klass_file = Rails.root.join('app', 'components', "#{@component}_component.rb")
9
+ if @component.is_a?(Class) && @component < Frails::Component::Base
10
+ klass = @component
11
+ @component = @component.to_s.underscore
12
+ return klass
13
+ end
14
+
15
+ klass_file = Frails.components_path.join("#{@component}_component.rb")
10
16
  klass_file.exist? && "#{@component.to_s.camelcase}Component".constantize
11
17
  end
12
18
 
@@ -17,13 +23,13 @@ module Frails::Component::RendererConcerns
17
23
  # Don't inline the styles if already inlined.
18
24
  return if inlined_stylesheets.include?(@component)
19
25
 
20
- Frails.manifest.read!(stylesheet_entry_file, :stylesheet) do |path, src|
26
+ Frails.manifest.read(stylesheet_entry_file, :stylesheet) do |path, src|
21
27
  @view.content_for :component_styles do
22
28
  @view.content_tag(:style, src, { data: { href: path } }, false)
23
29
  end
24
- end
25
30
 
26
- inlined_stylesheets << @component
31
+ inlined_stylesheets << @component
32
+ end
27
33
  end
28
34
 
29
35
  def inlined_stylesheets
@@ -0,0 +1,19 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Frails
4
+ module Component
5
+ module TestHelpers
6
+ def render_inline(options = {}, locals = {}, &block)
7
+ Nokogiri::HTML(controller.view_context.render(options, locals, &block))
8
+ end
9
+
10
+ def controller
11
+ @controller ||= ApplicationController.new.tap { |c| c.request = request }
12
+ end
13
+
14
+ def request
15
+ @request ||= ActionDispatch::TestRequest.create
16
+ end
17
+ end
18
+ end
19
+ end
@@ -1,16 +1,15 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Frails::Helper
4
- def render(options = {}, locals = {}, &block)
4
+ def render(options = {}, *locals, &block)
5
5
  sload_assets = respond_to?(:side_load_assets?) ? side_load_assets? : false
6
6
 
7
7
  case options
8
8
  when Hash
9
9
  in_rendering_context(options) do
10
- options[:side_load_assets] = sload_assets
11
-
12
10
  return view_renderer.render_component(self, options, &block) if options.key?(:component)
13
11
 
12
+ options[:side_load_assets] = sload_assets
14
13
  if block_given?
15
14
  view_renderer.render_partial(self, options.merge(partial: options[:layout]), &block)
16
15
  else
@@ -18,8 +17,12 @@ module Frails::Helper
18
17
  end
19
18
  end
20
19
  else
20
+ if options.is_a?(Class) && options < Frails::Component::Base
21
+ return view_renderer.render_component(self, { component: options, locals: locals }, &block)
22
+ end
23
+
21
24
  view_renderer.render_partial(self, side_load_assets: sload_assets, partial: options,
22
- locals: locals, &block)
25
+ locals: locals.extract_options!, &block)
23
26
  end
24
27
  end
25
28
 
@@ -69,8 +69,8 @@ class Frails::Manifest
69
69
  end
70
70
 
71
71
  begin
72
- open("http://#{Frails.dev_server.host_with_port}#{path}").read
73
- rescue OpenURI::HTTPError => e
72
+ URI.open("http://#{Frails.dev_server.host_with_port}#{path}").read
73
+ rescue OpenURI::HTTPError
74
74
  handle_missing_entry path
75
75
  end
76
76
  end
@@ -4,7 +4,7 @@ module Frails
4
4
  module Monkey
5
5
  module ActionView
6
6
  module Renderer
7
- def render_to_object(context, options) # :nodoc:
7
+ def render_to_object(context, options)
8
8
  if options.key?(:partial)
9
9
  render_partial_to_object(context, options)
10
10
  elsif options.key?(:component)
@@ -15,19 +15,18 @@ module Frails
15
15
  end
16
16
 
17
17
  # Direct access to partial rendering.
18
- def render_component(context, options, &block) #:nodoc:
18
+ def render_component(context, options, &block)
19
19
  render_component_to_object(context, options, &block).body
20
20
  end
21
21
 
22
22
  def render_component_to_object(context, options, &block)
23
23
  component = options[:component].to_s
24
24
 
25
- result = if Rails.root.join('app', 'components', component, 'index.entry.jsx').exist?
26
- Frails::Component::ReactComponentRenderer.new.render(context, options, &block)
25
+ result = if Frails.components_path.join(component, 'index.entry.jsx').exist?
26
+ Frails::Component::ReactRenderer.new.render(context, options, &block)
27
27
  else
28
- options[:partial] = "#{component}/index"
29
- Frails::Component::ComponentRenderer.new(@lookup_context)
30
- .render(context, options, &block)
28
+ Frails::Component::Renderer.new(@lookup_context)
29
+ .render(context, options, &block)
31
30
  end
32
31
 
33
32
  ::ActionView::AbstractRenderer::RenderedTemplate.new result, nil, nil
@@ -0,0 +1,22 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Frails
4
+ module Utils
5
+ def self.camelize(term, first_letter = :upper, convert_slashes: true)
6
+ # If we are not converting slashes, and `first_letter` is `:lower`, this ensures that the
7
+ # first letter after a slash is not capitalized.
8
+ string = if !convert_slashes && first_letter == :lower
9
+ term.split('/').map { |str| str.camelize :lower }.join('/')
10
+ else
11
+ term.camelize first_letter
12
+ end
13
+
14
+ # Reverses the effect of ActiveSupport::Inflector.camelize converting slashes into `::`. If
15
+ # the keyword argument `convert_slashes:` is false (default: true), we can avoid
16
+ # converting slashes to `::`.
17
+ string.gsub!('::', '/') unless convert_slashes
18
+
19
+ string
20
+ end
21
+ end
22
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Frails
4
- VERSION = '0.6.0'
4
+ VERSION = '0.7.0'
5
5
  end
data/yarn.lock CHANGED
@@ -26,9 +26,9 @@ fs.realpath@^1.0.0:
26
26
  integrity sha1-FQStJSMVjKpA20onh8sBQRmU6k8=
27
27
 
28
28
  glob@^7.1.4:
29
- version "7.1.4"
30
- resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.4.tgz#aa608a2f6c577ad357e1ae5a5c26d9a8d1969255"
31
- integrity sha512-hkLPepehmnKk41pUGm3sYxoFs/umurYfYJCerbXEyFIWcAzvpipAgVkBqqT9RBKMGjnq6kMuyYwha6csxbiM1A==
29
+ version "7.1.6"
30
+ resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.6.tgz#141f33b81a7c2492e125594307480c46679278a6"
31
+ integrity sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==
32
32
  dependencies:
33
33
  fs.realpath "^1.0.0"
34
34
  inflight "^1.0.4"
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: frails
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.0
4
+ version: 0.7.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Joel Moss
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2019-10-23 00:00:00.000000000 Z
11
+ date: 2020-02-14 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: nokogiri
@@ -75,12 +75,13 @@ files:
75
75
  - index.js
76
76
  - lib/frails.rb
77
77
  - lib/frails/component.rb
78
- - lib/frails/component/abstract_component.rb
79
- - lib/frails/component/component_renderer.rb
80
- - lib/frails/component/plain_component.rb
81
- - lib/frails/component/react_component.rb
82
- - lib/frails/component/react_component_renderer.rb
78
+ - lib/frails/component/abstract.rb
79
+ - lib/frails/component/base.rb
80
+ - lib/frails/component/react.rb
81
+ - lib/frails/component/react_renderer.rb
82
+ - lib/frails/component/renderer.rb
83
83
  - lib/frails/component/renderer_concerns.rb
84
+ - lib/frails/component/test_helpers.rb
84
85
  - lib/frails/dev_server.rb
85
86
  - lib/frails/dev_server_proxy.rb
86
87
  - lib/frails/helper.rb
@@ -93,6 +94,7 @@ files:
93
94
  - lib/frails/monkey/action_view/template_renderer.rb
94
95
  - lib/frails/railtie.rb
95
96
  - lib/frails/side_load_assets.rb
97
+ - lib/frails/utils.rb
96
98
  - lib/frails/version.rb
97
99
  - lib/install/template.rb
98
100
  - lib/tasks/frails.rake
@@ -122,7 +124,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
122
124
  - !ruby/object:Gem::Version
123
125
  version: '0'
124
126
  requirements: []
125
- rubygems_version: 3.0.3
127
+ rubygems_version: 3.1.2
126
128
  signing_key:
127
129
  specification_version: 4
128
130
  summary: A Modern [F]ront End on [Rails] and Webpack