mirror of
https://github.com/facebook/react.git
synced 2025-11-01 09:12:30 +00:00
Remove transferPropsTo
I'd like to outlaw prop mutation altogether, and now seems like a fine time to remove transferPropsTo. Test Plan: jest
This commit is contained in:
Vendored
+5
-6
@@ -2,12 +2,11 @@
|
||||
// Bootstrap's classes
|
||||
var BootstrapButton = React.createClass({
|
||||
render: function() {
|
||||
// transferPropsTo() is smart enough to merge classes provided
|
||||
// to this component.
|
||||
return this.transferPropsTo(
|
||||
<a href="javascript:;" role="button" className="btn">
|
||||
{this.props.children}
|
||||
</a>
|
||||
return (
|
||||
<a {...this.props}
|
||||
href="javascript:;"
|
||||
role="button"
|
||||
className={(this.props.className || '') + ' btn'} />
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
Vendored
+6
-2
@@ -101,11 +101,15 @@ var JQueryMobilePage = React.createClass({
|
||||
},
|
||||
|
||||
render: function() {
|
||||
return this.transferPropsTo(React.DOM.div(null,
|
||||
var props = {};
|
||||
for (var key in this.props) {
|
||||
props[key] = this.props[key];
|
||||
}
|
||||
return React.DOM.div(props,
|
||||
JQueryMobileHeader({title:'Page ' + this.props.id, headerTheme:this.props.headerTheme}),
|
||||
JQueryMobileContent(null, this.props.children),
|
||||
JQueryMobileFooter(null)
|
||||
));
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
@@ -110,8 +110,14 @@ todolist.NewItemForm = React.createClass({
|
||||
return false;
|
||||
},
|
||||
render: function(){
|
||||
return this.transferPropsTo(
|
||||
React.DOM.input({ref:"text", onKeyDown:this.props.onEnter && this._handleNewItemKeyDown})
|
||||
);
|
||||
var props = {};
|
||||
for (var key in this.props) {
|
||||
if (key !== "onEnter") {
|
||||
props[key] = this.props[key];
|
||||
}
|
||||
}
|
||||
props.ref = "text";
|
||||
props.onKeyDown = this.props.onEnter && this._handleNewItemKeyDown;
|
||||
return React.DOM.input(props);
|
||||
}
|
||||
});
|
||||
|
||||
@@ -14,7 +14,6 @@
|
||||
var ReactElement = require('ReactElement');
|
||||
var ReactErrorUtils = require('ReactErrorUtils');
|
||||
var ReactInstanceMap = require('ReactInstanceMap');
|
||||
var ReactPropTransferer = require('ReactPropTransferer');
|
||||
var ReactPropTypeLocations = require('ReactPropTypeLocations');
|
||||
var ReactPropTypeLocationNames = require('ReactPropTypeLocationNames');
|
||||
|
||||
@@ -826,7 +825,6 @@ var ReactClassMixin = {
|
||||
var ReactClassBase = function() {};
|
||||
assign(
|
||||
ReactClassBase.prototype,
|
||||
ReactPropTransferer.Mixin,
|
||||
ReactClassMixin
|
||||
);
|
||||
|
||||
@@ -834,7 +832,6 @@ assign(
|
||||
* Module for creating composite components.
|
||||
*
|
||||
* @class ReactClass
|
||||
* @extends ReactPropTransferer
|
||||
*/
|
||||
var ReactClass = {
|
||||
|
||||
|
||||
@@ -96,8 +96,6 @@ function transferInto(props, newProps) {
|
||||
*/
|
||||
var ReactPropTransferer = {
|
||||
|
||||
TransferStrategies: TransferStrategies,
|
||||
|
||||
/**
|
||||
* Merge two props objects using TransferStrategies.
|
||||
*
|
||||
@@ -109,55 +107,6 @@ var ReactPropTransferer = {
|
||||
return transferInto(assign({}, oldProps), newProps);
|
||||
},
|
||||
|
||||
/**
|
||||
* @lends {ReactPropTransferer.prototype}
|
||||
*/
|
||||
Mixin: {
|
||||
|
||||
/**
|
||||
* Transfer props from this component to a target component.
|
||||
*
|
||||
* Props that do not have an explicit transfer strategy will be transferred
|
||||
* only if the target component does not already have the prop set.
|
||||
*
|
||||
* This is usually used to pass down props to a returned root component.
|
||||
*
|
||||
* @param {ReactElement} element Component receiving the properties.
|
||||
* @return {ReactElement} The supplied `component`.
|
||||
* @final
|
||||
* @protected
|
||||
*/
|
||||
transferPropsTo: function(element) {
|
||||
invariant(
|
||||
element._owner && element._owner.getPublicInstance() === this,
|
||||
'%s: You can\'t call transferPropsTo() on a component that you ' +
|
||||
'don\'t own, %s. This usually means you are calling ' +
|
||||
'transferPropsTo() on a component passed in as props or children.',
|
||||
this.constructor.displayName,
|
||||
typeof element.type === 'string' ?
|
||||
element.type :
|
||||
element.type.displayName
|
||||
);
|
||||
|
||||
if (__DEV__) {
|
||||
if (!didWarn) {
|
||||
didWarn = true;
|
||||
warning(
|
||||
false,
|
||||
'transferPropsTo is deprecated. ' +
|
||||
'See http://fb.me/react-transferpropsto for more information.'
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// Because elements are immutable we have to merge into the existing
|
||||
// props object rather than clone it.
|
||||
transferInto(element.props, this.props);
|
||||
|
||||
return element;
|
||||
}
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = ReactPropTransferer;
|
||||
|
||||
@@ -1,188 +0,0 @@
|
||||
/**
|
||||
* Copyright 2013-2014, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*
|
||||
* @emails react-core
|
||||
*/
|
||||
|
||||
"use strict";
|
||||
|
||||
var React;
|
||||
var ReactTestUtils;
|
||||
var reactComponentExpect;
|
||||
|
||||
var TestComponent;
|
||||
|
||||
describe('ReactPropTransferer', function() {
|
||||
|
||||
beforeEach(function() {
|
||||
require('mock-modules').dumpCache();
|
||||
|
||||
React = require('React');
|
||||
ReactTestUtils = require('ReactTestUtils');
|
||||
reactComponentExpect = require('reactComponentExpect');
|
||||
|
||||
// We expect to get a warning from transferPropsTo since it's deprecated
|
||||
spyOn(console, 'warn');
|
||||
|
||||
TestComponent = React.createClass({
|
||||
render: function() {
|
||||
var result = this.transferPropsTo(
|
||||
<input
|
||||
className="textinput"
|
||||
style={{display: 'block', color: 'green'}}
|
||||
type="text"
|
||||
value=""
|
||||
/>
|
||||
);
|
||||
expect(console.warn).toHaveBeenCalled();
|
||||
return result;
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
it('should leave explicitly specified properties intact', function() {
|
||||
var instance = <TestComponent type="radio" />;
|
||||
instance = ReactTestUtils.renderIntoDocument(instance);
|
||||
|
||||
reactComponentExpect(instance)
|
||||
.expectRenderedChild()
|
||||
.toBeComponentOfType('input')
|
||||
.scalarPropsEqual({
|
||||
className: 'textinput',
|
||||
style: {display: 'block', color: 'green'},
|
||||
type: 'text',
|
||||
value: ''
|
||||
});
|
||||
});
|
||||
|
||||
it('should transfer unspecified properties', function() {
|
||||
var instance = <TestComponent placeholder="Type here..." />;
|
||||
instance = ReactTestUtils.renderIntoDocument(instance);
|
||||
|
||||
reactComponentExpect(instance)
|
||||
.expectRenderedChild()
|
||||
.toBeComponentOfType('input')
|
||||
.scalarPropsEqual({placeholder: 'Type here...'});
|
||||
});
|
||||
|
||||
it('should transfer using merge strategies', function() {
|
||||
var instance =
|
||||
<TestComponent
|
||||
className="hidden_elem"
|
||||
style={{width: '100%', display: 'none'}}
|
||||
/>;
|
||||
instance = ReactTestUtils.renderIntoDocument(instance);
|
||||
|
||||
reactComponentExpect(instance)
|
||||
.expectRenderedChild()
|
||||
.toBeComponentOfType('input')
|
||||
.scalarPropsEqual({
|
||||
className: 'textinput hidden_elem',
|
||||
style: {
|
||||
color: 'green',
|
||||
display: 'block',
|
||||
width: '100%'
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
it('should not transfer children', function() {
|
||||
var ChildrenTestComponent = React.createClass({
|
||||
render: function() {
|
||||
return this.transferPropsTo(<div />);
|
||||
}
|
||||
});
|
||||
|
||||
var instance =
|
||||
<ChildrenTestComponent>
|
||||
<span>Hello!</span>
|
||||
</ChildrenTestComponent>;
|
||||
|
||||
instance = ReactTestUtils.renderIntoDocument(instance);
|
||||
reactComponentExpect(instance)
|
||||
.expectRenderedChild()
|
||||
.toBeDOMComponentWithTag('div')
|
||||
.toBeDOMComponentWithNoChildren();
|
||||
});
|
||||
|
||||
it('should not transfer ref or key', function() {
|
||||
var TestComponent = React.createClass({
|
||||
render: function() {
|
||||
expect(this.props.ref).toBeUndefined();
|
||||
expect(this.props.key).toBeUndefined();
|
||||
return <div />;
|
||||
}
|
||||
});
|
||||
var OuterTestComponent = React.createClass({
|
||||
render: function() {
|
||||
return this.transferPropsTo(<TestComponent />);
|
||||
}
|
||||
});
|
||||
var OuterOuterTestComponent = React.createClass({
|
||||
render: function() {
|
||||
return <OuterTestComponent ref="testref" key="testkey" />;
|
||||
}
|
||||
});
|
||||
|
||||
ReactTestUtils.renderIntoDocument(<OuterOuterTestComponent />);
|
||||
});
|
||||
|
||||
it('should not transferPropsTo() a component you don\'t own', function() {
|
||||
var Parent = React.createClass({
|
||||
render: function() {
|
||||
return <Child><span /></Child>;
|
||||
}
|
||||
});
|
||||
|
||||
var Child = React.createClass({
|
||||
render: function() {
|
||||
return this.transferPropsTo(this.props.children);
|
||||
}
|
||||
});
|
||||
|
||||
expect(function() {
|
||||
ReactTestUtils.renderIntoDocument(<Parent />);
|
||||
}).toThrow(
|
||||
'Invariant Violation: ' +
|
||||
'Child: You can\'t call transferPropsTo() on a component that you ' +
|
||||
'don\'t own, span. ' +
|
||||
'This usually means you are calling transferPropsTo() on a component ' +
|
||||
'passed in as props or children.'
|
||||
);
|
||||
});
|
||||
|
||||
it('uses the default instead of the transferred prop (regress)', function() {
|
||||
|
||||
var Child = React.createClass({
|
||||
|
||||
getDefaultProps: function() {
|
||||
return {
|
||||
x: 2
|
||||
};
|
||||
},
|
||||
|
||||
render: function() {
|
||||
expect(this.props.x).toBe(2);
|
||||
return <div />;
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
var Parent = React.createClass({
|
||||
|
||||
render: function() {
|
||||
return this.transferPropsTo(<Child />);
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
ReactTestUtils.renderIntoDocument(<Parent x={5} />);
|
||||
|
||||
});
|
||||
|
||||
});
|
||||
@@ -25,8 +25,8 @@ var CHILDREN_PROP = keyOf({children: null});
|
||||
* this is to add a CSS class.
|
||||
*
|
||||
* @param {object} child child component you'd like to clone
|
||||
* @param {object} props props you'd like to modify. They will be merged
|
||||
* as if you used `transferPropsTo()`.
|
||||
* @param {object} props props you'd like to modify. className and style will be
|
||||
* merged automatically.
|
||||
* @return {object} a clone of child with props merged in.
|
||||
*/
|
||||
function cloneWithProps(child, props) {
|
||||
|
||||
Reference in New Issue
Block a user