hyper-react 0.10.0 → 0.11.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (49) hide show
  1. checksums.yaml +4 -4
  2. data/.travis.yml +26 -4
  3. data/Appraisals +3 -2
  4. data/CHANGELOG.md +19 -0
  5. data/README.md +3 -3
  6. data/config.ru +2 -1
  7. data/gemfiles/opal_0.10_react_13.gemfile +13 -0
  8. data/gemfiles/opal_0.10_react_14.gemfile +13 -0
  9. data/gemfiles/opal_0.10_react_15.gemfile +13 -0
  10. data/gemfiles/opal_0.8_react_15.gemfile +1 -1
  11. data/gemfiles/opal_0.9_react_15.gemfile +1 -1
  12. data/hyper-react.gemspec +1 -1
  13. data/lib/generators/reactive_ruby/test_app/templates/assets/javascripts/components.rb +0 -1
  14. data/lib/hyper-react.rb +2 -1
  15. data/lib/react/api.rb +3 -2
  16. data/lib/react/component/class_methods.rb +2 -2
  17. data/lib/react/component/props_wrapper.rb +2 -2
  18. data/lib/react/element.rb +1 -1
  19. data/lib/react/ext/opal-jquery/element.rb +26 -0
  20. data/lib/react/state.rb +6 -5
  21. data/lib/react/test/matchers/render_html_matcher.rb +5 -0
  22. data/lib/react/test/session.rb +14 -23
  23. data/lib/react/test/utils.rb +25 -0
  24. data/lib/react/top_level.rb +12 -28
  25. data/lib/react/top_level_render.rb +29 -0
  26. data/lib/reactive-ruby/isomorphic_helpers.rb +2 -2
  27. data/lib/reactive-ruby/version.rb +1 -1
  28. data/spec/index.html.erb +1 -0
  29. data/spec/react/children_spec.rb +1 -1
  30. data/spec/react/component/base_spec.rb +2 -2
  31. data/spec/react/component_spec.rb +74 -73
  32. data/spec/react/dsl_spec.rb +24 -21
  33. data/spec/react/element_spec.rb +7 -7
  34. data/spec/react/event_spec.rb +2 -2
  35. data/spec/react/native_library_spec.rb +20 -24
  36. data/spec/react/observable_spec.rb +36 -1
  37. data/spec/react/opal_jquery_extensions_spec.rb +48 -46
  38. data/spec/react/param_declaration_spec.rb +8 -8
  39. data/spec/react/react_spec.rb +41 -28
  40. data/spec/react/test/rspec_spec.rb +1 -1
  41. data/spec/react/test/session_spec.rb +8 -20
  42. data/spec/react/test/utils_spec.rb +11 -28
  43. data/spec/react/top_level_component_spec.rb +7 -2
  44. data/spec/react/tutorial/tutorial_spec.rb +2 -2
  45. data/spec/reactive-ruby/component_loader_spec.rb +10 -4
  46. data/spec/reactive-ruby/isomorphic_helpers_spec.rb +6 -1
  47. data/spec/spec_helper.rb +2 -0
  48. data/spec/support/react/spec_helpers.rb +1 -21
  49. metadata +12 -6
@@ -1,7 +1,7 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  if opal?
4
- describe 'the React DSL' do
4
+ describe 'the React DSL', type: :component do
5
5
 
6
6
  context "render macro" do
7
7
 
@@ -14,7 +14,7 @@ describe 'the React DSL' do
14
14
  end
15
15
  end
16
16
 
17
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<div class="foo">hello</div>')
17
+ expect(Foo).to render_static_html('<div class="foo">hello</div>')
18
18
  end
19
19
 
20
20
  it "can define the render method with the render macro without a container" do
@@ -26,7 +26,7 @@ describe 'the React DSL' do
26
26
  end
27
27
  end
28
28
 
29
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<span>hello</span>')
29
+ expect(Foo).to render_static_html('<span>hello</span>')
30
30
  end
31
31
 
32
32
  it "can define the render method with the render macro with a application defined container" do
@@ -40,7 +40,7 @@ describe 'the React DSL' do
40
40
  render Bar, p1: "fred"
41
41
  end
42
42
 
43
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<span>hello fred</span>')
43
+ expect(Foo).to render_static_html('<span>hello fred</span>')
44
44
  end
45
45
  end
46
46
 
@@ -53,7 +53,7 @@ describe 'the React DSL' do
53
53
  end
54
54
  end
55
55
 
56
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<div>hello</div>')
56
+ expect(Foo).to render_static_html('<div>hello</div>')
57
57
  end
58
58
 
59
59
  it "will pass converted props through event handlers" do
@@ -77,7 +77,7 @@ describe 'the React DSL' do
77
77
  end
78
78
  end
79
79
 
80
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<div>hello</div>')
80
+ expect(Foo).to render_static_html('<div>hello</div>')
81
81
  end
82
82
 
83
83
  it "has a .span short hand String method" do
@@ -89,7 +89,7 @@ describe 'the React DSL' do
89
89
  end
90
90
  end
91
91
 
92
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<div><span>hello</span><span>goodby</span></div>')
92
+ expect(Foo).to render_static_html('<div><span>hello</span><span>goodby</span></div>')
93
93
  end
94
94
 
95
95
  it "has a .br short hand String method" do
@@ -113,7 +113,7 @@ describe 'the React DSL' do
113
113
  end
114
114
  end
115
115
 
116
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<table><tr><td>hello</td></tr></table>')
116
+ expect(Foo).to render_static_html('<table><tr><td>hello</td></tr></table>')
117
117
  end
118
118
 
119
119
  it "has a .para short hand String method" do
@@ -125,7 +125,7 @@ describe 'the React DSL' do
125
125
  end
126
126
  end
127
127
 
128
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<div><p>hello</p></div>')
128
+ expect(Foo).to render_static_html('<div><p>hello</p></div>')
129
129
  end
130
130
 
131
131
  it 'can do a method call on a class name that is not a direct sibling' do
@@ -141,8 +141,8 @@ describe 'the React DSL' do
141
141
  Comp()
142
142
  end
143
143
  end
144
- expect(React.render_to_static_markup(React.create_element(Mod::NestedMod::NestedComp)))
145
- .to eq('<span>Mod::Comp</span>')
144
+ expect(Mod::NestedMod::NestedComp)
145
+ .to render_static_html('<span>Mod::Comp</span>')
146
146
  end
147
147
 
148
148
  it 'raises a meaningful error if a Constant Name is not actually a component' do
@@ -187,7 +187,7 @@ describe 'the React DSL' do
187
187
  end
188
188
  end
189
189
 
190
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<span>a man walks into a bar</span>')
190
+ expect(Foo).to render_static_html('<span>a man walks into a bar</span>')
191
191
  end
192
192
 
193
193
  it "can add class names by the haml .class notation" do
@@ -206,7 +206,7 @@ describe 'the React DSL' do
206
206
  end
207
207
  end
208
208
 
209
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<span class="other-class the-class">a man walks into a bar</span>')
209
+ expect(Foo).to render_static_html('<span class="other-class the-class">a man walks into a bar</span>')
210
210
  end
211
211
 
212
212
  it "can use the 'class' keyword for classes" do
@@ -218,7 +218,7 @@ describe 'the React DSL' do
218
218
  end
219
219
  end
220
220
 
221
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<span class="the-class">hello</span>')
221
+ expect(Foo).to render_static_html('<span class="the-class">hello</span>')
222
222
  end
223
223
 
224
224
  it "can generate a unrendered node using the .as_node method" do # div { "hello" }.as_node
@@ -230,7 +230,8 @@ describe 'the React DSL' do
230
230
  end
231
231
  end
232
232
 
233
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<span data-size="12">React::Element</span>')
233
+ expect(Foo)
234
+ .to render_static_html('<span data-size="12">React::Element</span>')
234
235
  end
235
236
 
236
237
  it "can use the dangerously_set_inner_HTML param" do
@@ -242,7 +243,7 @@ describe 'the React DSL' do
242
243
  end
243
244
  end
244
245
 
245
- expect(React.render_to_static_markup(React.create_element(Foo))).to eq('<div>Hello&nbsp;&nbsp;Goodby</div>')
246
+ expect(Foo).to render_static_html('<div>Hello&nbsp;&nbsp;Goodby</div>')
246
247
  end
247
248
 
248
249
  it 'should convert a hash param to hyphenated html attributes if in React::HASH_ATTRIBUTES' do
@@ -254,8 +255,8 @@ describe 'the React DSL' do
254
255
  end
255
256
  end
256
257
 
257
- expect(React.render_to_static_markup(React.create_element(Foo)))
258
- .to eq('<div data-foo="bar" aria-foo-bar="foo"></div>')
258
+ expect(Foo)
259
+ .to render_static_html('<div data-foo="bar" aria-foo-bar="foo"></div>')
259
260
  end
260
261
 
261
262
  it 'should not convert a hash param to hyphenated html attributes if not in React::HASH_ATTRIBUTES' do
@@ -267,8 +268,10 @@ describe 'the React DSL' do
267
268
  end
268
269
  end
269
270
 
270
- expect(React.render_to_static_markup(React.create_element(Foo)))
271
- .to eq('<div title="{&quot;bar&quot;=&gt;&quot;foo&quot;}"></div>')
271
+ expect(Foo)
272
+ .to render_static_html(
273
+ '<div title="{&quot;bar&quot;=&gt;&quot;foo&quot;}"></div>'
274
+ )
272
275
  end
273
276
 
274
277
  it "will remove all elements passed as params from the rendering buffer" do
@@ -290,7 +293,7 @@ describe 'the React DSL' do
290
293
  end
291
294
  end
292
295
 
293
- expect(React.render_to_static_markup(React.create_element(Test))).to eq('<div><b>hello</b><b>hello</b></div>')
296
+ expect(Test).to render_static_html('<div><b>hello</b><b>hello</b></div>')
294
297
  end
295
298
  end
296
299
  end
@@ -3,7 +3,7 @@ require "spec_helper"
3
3
  if opal?
4
4
  # require 'reactrb/new-event-name-convention' # this require will get rid of any error messages but
5
5
  # the on method will no longer attach to the param prefixed with _on
6
- describe React::Element do
6
+ describe React::Element, type: :component do
7
7
  it 'bridges `type` of native React.Element attributes' do
8
8
  element = React.create_element('div')
9
9
  expect(element.element_type).to eq("div")
@@ -110,20 +110,20 @@ describe React::Element do
110
110
  it 'is subscribable through `on(:event_name)` method' do
111
111
  expect { |b|
112
112
  element = React.create_element("div").on(:click, &b)
113
- instance = renderElementToDocument(element)
114
- simulateEvent(:click, instance)
113
+ dom_node = React::Test::Utils.render_into_document(element)
114
+ React::Test::Utils.simulate(:click, dom_node)
115
115
  }.to yield_with_args(React::Event)
116
116
 
117
117
  expect { |b|
118
118
  element = React.create_element("div").on(:key_down, &b)
119
- instance = renderElementToDocument(element)
120
- simulateEvent(:keyDown, instance, {key: "Enter"})
119
+ dom_node = React::Test::Utils.render_into_document(element)
120
+ React::Test::Utils.simulate(:keyDown, dom_node, {key: "Enter"})
121
121
  }.to yield_control
122
122
 
123
123
  expect { |b|
124
124
  element = React.create_element("form").on(:submit, &b)
125
- instance = renderElementToDocument(element)
126
- simulateEvent(:submit, instance, {})
125
+ dom_node = React::Test::Utils.render_into_document(element)
126
+ React::Test::Utils.simulate(:submit, dom_node)
127
127
  }.to yield_control
128
128
  end
129
129
 
@@ -17,8 +17,8 @@ describe React::Event do
17
17
  expect(event).to respond_to(:prevent_default)
18
18
  expect(event).to respond_to(:stop_propagation)
19
19
  end
20
- instance = renderElementToDocument(element)
21
- simulateEvent(:click, instance)
20
+ dom_node = React::Test::Utils.render_into_document(element)
21
+ React::Test::Utils.simulate(:click, dom_node)
22
22
  end
23
23
  end
24
24
  end
@@ -17,7 +17,7 @@ module NativeLibraryTestModule
17
17
  end
18
18
  end
19
19
 
20
- describe "React::NativeLibrary" do
20
+ describe "React::NativeLibrary", type: :component do
21
21
 
22
22
  after(:each) do
23
23
  %x{
@@ -52,8 +52,7 @@ describe "React::NativeLibrary" do
52
52
  Foo.class_eval do
53
53
  imports "NativeLibrary.FunctionalComponent"
54
54
  end
55
- expect(React.render_to_static_markup(
56
- React.create_element(Foo, name: "There"))).to eq('<div>Hello There</div>')
55
+ expect(Foo).to render_static_html('<div>Hello There</div>').with_params(name: "There")
57
56
  end
58
57
  end
59
58
 
@@ -69,7 +68,7 @@ describe "React::NativeLibrary" do
69
68
  expect(React::API.native_react_component?(`window.NativeComponent`)).to be_truthy
70
69
  expect(React::API.native_react_component?(`{render: function render() {}}`)).to be_falsy
71
70
  expect(React::API.native_react_component?(`window.DoesntExist`)).to be_falsy
72
- expect(React::API.native_react_component?(``)).to be_falsy
71
+ expect(React::API.native_react_component?()).to be_falsy
73
72
  end
74
73
 
75
74
  it "will import a React.js library into the Ruby name space" do
@@ -87,8 +86,8 @@ describe "React::NativeLibrary" do
87
86
  Foo.class_eval do
88
87
  imports "NativeLibrary"
89
88
  end
90
- expect(React.render_to_static_markup(
91
- React.create_element(Foo::NativeComponent, name: "There"))).to eq('<div>Hello There</div>')
89
+ expect(Foo::NativeComponent)
90
+ .to render_static_html('<div>Hello There</div>').with_params(name: "There")
92
91
  end
93
92
 
94
93
  it "will import a nested React.js library into the Ruby name space" do
@@ -107,8 +106,8 @@ describe "React::NativeLibrary" do
107
106
  Foo.class_eval do
108
107
  imports "NativeLibrary"
109
108
  end
110
- expect(React.render_to_static_markup(
111
- React.create_element(Foo::NestedLibrary::NativeComponent, name: "There"))).to eq('<div>Hello There</div>')
109
+ expect(Foo::NestedLibrary::NativeComponent)
110
+ .to render_static_html('<div>Hello There</div>').with_params(name: "There")
112
111
  end
113
112
 
114
113
  it "will rename an imported a React.js component" do
@@ -127,8 +126,8 @@ describe "React::NativeLibrary" do
127
126
  imports "NativeLibrary"
128
127
  rename "NativeComponent" => "Bar"
129
128
  end
130
- expect(React.render_to_static_markup(
131
- React.create_element(Foo::Bar, name: "There"))).to eq('<div>Hello There</div>')
129
+ expect(Foo::Bar)
130
+ .to render_static_html('<div>Hello There</div>').with_params(name: "There")
132
131
  end
133
132
 
134
133
  it "will give a reasonable error when failing to import a renamed component" do
@@ -164,8 +163,8 @@ describe "React::NativeLibrary" do
164
163
  Foo.class_eval do
165
164
  imports "NativeComponent"
166
165
  end
167
- expect(React.render_to_static_markup(
168
- React.create_element(Foo, name: "There"))).to eq('<div>Hello There</div>')
166
+ expect(Foo)
167
+ .to render_static_html('<div>Hello There</div>').with_params(name: "There")
169
168
 
170
169
  end
171
170
 
@@ -184,8 +183,8 @@ describe "React::NativeLibrary" do
184
183
  Foo.class_eval do
185
184
  imports "NativeLibrary.NativeComponent"
186
185
  end
187
- expect(React.render_to_static_markup(
188
- React.create_element(Foo, name: "There"))).to eq('<div>Hello There</div>')
186
+ expect(Foo)
187
+ .to render_static_html('<div>Hello There</div>').with_params(name: "There")
189
188
 
190
189
  end
191
190
 
@@ -234,8 +233,7 @@ describe "React::NativeLibrary" do
234
233
  }
235
234
  })
236
235
  }
237
- expect(React.render_to_static_markup(
238
- React.create_element(Foo))).to eq('<div>Hello There</div>')
236
+ expect(Foo).to render_static_html('<div>Hello There</div>')
239
237
  end
240
238
 
241
239
  it 'will automatically import a React.js component when referenced in another component with the _as_node suffix' do
@@ -254,8 +252,7 @@ describe "React::NativeLibrary" do
254
252
  }
255
253
  })
256
254
  }
257
- expect(React.render_to_static_markup(
258
- React.create_element(Foo))).to eq('<div><div>Hello There</div><div>Hello There</div></div>')
255
+ expect(Foo).to render_static_html('<div><div>Hello There</div><div>Hello There</div></div>')
259
256
  end
260
257
 
261
258
  it "will automatically import a React.js component in a library when referenced in another component with the _as_node suffix" do
@@ -276,8 +273,7 @@ describe "React::NativeLibrary" do
276
273
  })
277
274
  }
278
275
  }
279
- expect(React.render_to_static_markup(
280
- React.create_element(Foo))).to eq('<div><div>Hello There</div><div>Hello There</div></div>')
276
+ expect(Foo).to render_static_html('<div><div>Hello There</div><div>Hello There</div></div>')
281
277
  end
282
278
 
283
279
  it "will automatically import a React.js component when referenced as a constant" do
@@ -289,8 +285,8 @@ describe "React::NativeLibrary" do
289
285
  }
290
286
  })
291
287
  }
292
- expect(React.render_to_static_markup(
293
- React.create_element(NativeComponent, name: "There"))).to eq('<div>Hello There</div>')
288
+ expect(NativeComponent)
289
+ .to render_static_html('<div>Hello There</div>').with_params(name: "There")
294
290
  end
295
291
 
296
292
  it "will automatically import a native library containing a React.js component" do
@@ -322,8 +318,8 @@ describe "React::NativeLibrary" do
322
318
  })
323
319
  }
324
320
  }
325
- expect(React.render_to_static_markup(
326
- React.create_element(NativeLibrary::NativeComponent, name: "There"))).to eq('<div>Hello There</div>')
321
+ expect(NativeLibrary::NativeComponent)
322
+ .to render_static_html('<div>Hello There</div>').with_params(name: "There")
327
323
  end
328
324
 
329
325
  it "will produce a sensible error if the component is not in the library" do
@@ -1,7 +1,42 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  if opal?
4
+
4
5
  describe 'React::Observable' do
5
- # tbd
6
+ it "allows to set value on Observable" do
7
+ stub_const 'Zoo', Class.new {
8
+ include React::Component
9
+ param :foo, type: React::Observable
10
+ before_mount do
11
+ params.foo! 4
12
+ end
13
+
14
+ def render
15
+ nil
16
+ end
17
+ }
18
+
19
+ stub_const 'Foo', Class.new
20
+ Foo.class_eval do
21
+ include React::Component
22
+
23
+ def render
24
+ div do
25
+ Zoo(foo: state.foo! )
26
+ span { state.foo.to_s }
27
+ end
28
+ end
29
+ end
30
+
31
+ instance = React::Test::Utils.render_into_document(React.create_element(Foo))
32
+ html = `#{instance.dom_node}.innerHTML`
33
+ # data-reactid appear in earlier versions of reactjs
34
+ %x{
35
+ var REGEX_REMOVE_IDS = /\s?data-reactid="[^"]+"/g;
36
+ html = html.replace(REGEX_REMOVE_IDS, '');
37
+ }
38
+ expect(html).to eq('<span></span><span>4</span>')
39
+ end
6
40
  end
41
+
7
42
  end
@@ -1,66 +1,68 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  if opal?
4
- describe 'Element' do
5
- after(:each) do
6
- React::API.clear_component_class_cache
7
- end
4
+ describe 'opal-jquery extensions' do
5
+ describe 'Element' do
6
+ after(:each) do
7
+ React::API.clear_component_class_cache
8
+ end
8
9
 
9
- it 'will reuse the wrapper componet class for the same Element' do
10
- stub_const 'Foo', Class.new(React::Component::Base)
11
- Foo.class_eval do
12
- param :name
13
- def render
14
- "hello #{params.name}"
15
- end
10
+ it 'will reuse the wrapper componet class for the same Element' do
11
+ stub_const 'Foo', Class.new(React::Component::Base)
12
+ Foo.class_eval do
13
+ param :name
14
+ def render
15
+ "hello #{params.name}"
16
+ end
16
17
 
17
- def component_will_unmount
18
+ def component_will_unmount
18
19
 
20
+ end
19
21
  end
20
- end
21
22
 
22
- expect_any_instance_of(Foo).to_not receive(:component_will_unmount)
23
+ expect_any_instance_of(Foo).to_not receive(:component_will_unmount)
23
24
 
24
- test_div = Element.new(:div)
25
- test_div.render { Foo(name: 'fred') }
26
- test_div.render { Foo(name: 'freddy') }
27
- expect(Element[test_div].find('span').html).to eq('hello freddy')
28
- end
25
+ test_div = Element.new(:div)
26
+ test_div.render { Foo(name: 'fred') }
27
+ test_div.render { Foo(name: 'freddy') }
28
+ expect(Element[test_div].find('span').html).to eq('hello freddy')
29
+ end
29
30
 
30
- it 'renders a top level component using render with a block' do
31
- stub_const 'Foo', Class.new(React::Component::Base)
32
- Foo.class_eval do
33
- param :name
34
- def render
35
- "hello #{params.name}"
31
+ it 'renders a top level component using render with a block' do
32
+ stub_const 'Foo', Class.new(React::Component::Base)
33
+ Foo.class_eval do
34
+ param :name
35
+ def render
36
+ "hello #{params.name}"
37
+ end
36
38
  end
39
+ test_div = Element.new(:div)
40
+ test_div.render { Foo(name: 'fred') }
41
+ expect(Element[test_div].find('span').html).to eq('hello fred')
37
42
  end
38
- test_div = Element.new(:div)
39
- test_div.render { Foo(name: 'fred') }
40
- expect(Element[test_div].find('span').html).to eq('hello fred')
41
- end
42
43
 
43
- it 'renders a top level component using render with a container and params ' do
44
- test_div = Element.new(:div)
45
- test_div.render(:span, id: :render_test_span) { 'hello' }
46
- expect(Element[test_div].find('#render_test_span').html).to eq('hello')
47
- end
44
+ it 'renders a top level component using render with a container and params ' do
45
+ test_div = Element.new(:div)
46
+ test_div.render(:span, id: :render_test_span) { 'hello' }
47
+ expect(Element[test_div].find('#render_test_span').html).to eq('hello')
48
+ end
48
49
 
49
- it 'will find the DOM node given a react element' do
50
- stub_const 'Foo', Class.new(React::Component::Base)
51
- Foo.class_eval do
52
- def render
53
- div { 'hello' }
50
+ it 'will find the DOM node given a react element' do
51
+ stub_const 'Foo', Class.new(React::Component::Base)
52
+ Foo.class_eval do
53
+ def render
54
+ div { 'hello' }
55
+ end
54
56
  end
55
- end
56
57
 
57
- expect(Element[renderToDocument(Foo)].html).to eq('hello')
58
- end
58
+ expect(Element[renderToDocument(Foo)].html).to eq('hello')
59
+ end
59
60
 
60
- it "accepts plain js object as selector" do
61
- expect {
62
- Element[`window`]
63
- }.not_to raise_error
61
+ it "accepts plain js object as selector" do
62
+ expect {
63
+ Element[`window`]
64
+ }.not_to raise_error
65
+ end
64
66
  end
65
67
  end
66
68
  end