The library for web and native user interfaces.
use key="foo" for all components
flattenChildren was only using key when child.mountInContainerNode exists, which is defined on ReactCompositeComponent, and not ReactNativeComponent. This uses the isValidComponent() fn to see if we should use this key.
CommitSyncScript committed
Jun 4, 2013 at 12:15 UTC
4b81de93d3733ecc5d4dcaab7efad2a5eef1937d
2 files changed
+84
-2
src/core/__tests__/ReactIdentity-test.js
new
+83
@@ -0,0 +1,83 @@
1
+/**
2
+ * @jsx React.DOM
3
+ * @emails react-core
4
+ */
5
+
6
+"use strict";
7
+
8
+var React;
9
+var ReactTestUtils;
10
+var reactComponentExpect;
11
+
12
+describe('ReactIdentity', function() {
13
+
14
+ beforeEach(function() {
15
+ require('mock-modules').autoMockOff().dumpCache();
16
+ React = require('React');
17
+ ReactTestUtils = require('ReactTestUtils');
18
+ reactComponentExpect = require('reactComponentExpect');
19
+ });
20
+
21
+ it('should allow keyed objects to express identity', function() {
22
+ var instance =
23
+ <div>
24
+ {{
25
+ first: <div />,
26
+ second: <div />
27
+ }}
28
+ </div>;
29
+
30
+ React.renderComponent(instance, document.createElement('div'));
31
+ var node = instance.getDOMNode();
32
+ reactComponentExpect(instance).toBeDOMComponentWithChildCount(2);
33
+ expect(node.childNodes[0].id).toEqual('.reactRoot[0].:0:first');
34
+ expect(node.childNodes[1].id).toEqual('.reactRoot[0].:0:second');
35
+ });
36
+
37
+ it('should allow key property to express identity', function() {
38
+ var instance =
39
+ <div>
40
+ <div key="apple" />
41
+ <div key="banana" />
42
+ </div>;
43
+
44
+ React.renderComponent(instance, document.createElement('div'));
45
+ var node = instance.getDOMNode();
46
+ reactComponentExpect(instance).toBeDOMComponentWithChildCount(2);
47
+ expect(node.childNodes[0].id).toEqual('.reactRoot[0].:apple');
48
+ expect(node.childNodes[1].id).toEqual('.reactRoot[0].:banana');
49
+ });
50
+
51
+ it('should use instance identity', function() {
52
+
53
+ var Wrapper = React.createClass({
54
+ render: function() {
55
+ return <a key="i_get_overwritten">{this.props.children}</a>;
56
+ }
57
+ });
58
+
59
+ var instance =
60
+ <div>
61
+ <Wrapper key="wrap1"><span key="squirrel" /></Wrapper>
62
+ <Wrapper key="wrap2"><span key="bunny" /></Wrapper>
63
+ <Wrapper><span key="chipmunk" /></Wrapper>
64
+ </div>;
65
+
66
+ React.renderComponent(instance, document.createElement('div'));
67
+ var node = instance.getDOMNode();
68
+ reactComponentExpect(instance).toBeDOMComponentWithChildCount(3);
69
+ expect(node.childNodes[0].id)
70
+ .toEqual('.reactRoot[0].:wrap1');
71
+ expect(node.childNodes[0].firstChild.id)
72
+ .toEqual('.reactRoot[0].:wrap1.:squirrel');
73
+ expect(node.childNodes[1].id)
74
+ .toEqual('.reactRoot[0].:wrap2');
75
+ expect(node.childNodes[1].firstChild.id)
76
+ .toEqual('.reactRoot[0].:wrap2.:bunny');
77
+ expect(node.childNodes[2].id)
78
+ .toEqual('.reactRoot[0].:2');
79
+ expect(node.childNodes[2].firstChild.id)
80
+ .toEqual('.reactRoot[0].:2.:chipmunk');
81
+ });
82
+
83
+});
src/utils/flattenChildren.js
+1
-2
@@ -51,8 +51,7 @@ var flattenChildrenImpl = function(res, children, nameSoFar) {
51
if (Array.isArray(children)) {
52
for (var i = 0; i < children.length; i++) {
53
var child = children[i];
54
- key = child && child.mountInContainerNode &&
55
- (child._key || child.props.key);
54
+ key = child && (child._key || (child.props && child.props.key));
55
escapedKey = key ? escapeTextForBrowser(key) : ('' + i);
56
flattenChildrenImpl(
57
res,