From 5fd8f4a1e4589d22a00417a4f011345378603e17 Mon Sep 17 00:00:00 2001 From: Geoff Pleiss Date: Tue, 27 Jan 2015 11:17:41 -0500 Subject: [PATCH] fix(react-button): add prop validation - Fix large/block props to be booleans, not strings [#86938454] --- src/pivotal-ui/components/buttons.scss | 4 +- .../components/pivnet_homepage.scss | 2 +- src/pivotal-ui/javascripts/buttons.jsx | 122 ++++++------------ .../javascripts/mixins/button-mixin.js | 22 ++++ test/javascripts/button_spec.js | 20 +-- 5 files changed, 66 insertions(+), 104 deletions(-) create mode 100644 src/pivotal-ui/javascripts/mixins/button-mixin.js diff --git a/src/pivotal-ui/components/buttons.scss b/src/pivotal-ui/components/buttons.scss index f3b504dca..470a36877 100644 --- a/src/pivotal-ui/components/buttons.scss +++ b/src/pivotal-ui/components/buttons.scss @@ -150,7 +150,7 @@ Buttons use the button tag by default. If you'd like a link rather than a button To make a button large, set the `large` property to true. ```react_example_table - + Big Button ``` @@ -158,7 +158,7 @@ To make a button large, set the `large` property to true. To make a button full-width, set the `block` property to true. ```react_example - + Danger Zone ``` diff --git a/src/pivotal-ui/components/pivnet_homepage.scss b/src/pivotal-ui/components/pivnet_homepage.scss index db3f1683a..9c0b046c8 100644 --- a/src/pivotal-ui/components/pivnet_homepage.scss +++ b/src/pivotal-ui/components/pivnet_homepage.scss @@ -22,7 +22,7 @@ var PivnetHomepage = React.createClass({
- Join + Join

To download and evaluate all products and services

diff --git a/src/pivotal-ui/javascripts/buttons.jsx b/src/pivotal-ui/javascripts/buttons.jsx index 26d4a6a52..6e6bcc703 100644 --- a/src/pivotal-ui/javascripts/buttons.jsx +++ b/src/pivotal-ui/javascripts/buttons.jsx @@ -1,130 +1,86 @@ 'use strict'; -var React = require('react'); -var _ = require('lodash'); +var React = require('react/addons'); +var classSet = React.addons.classSet; + +var ButtonMixin = require('./mixins/button-mixin'); var UIButton = React.createClass({ - acceptedTypes: ['default', 'default-alt', 'primary', 'lowlight', 'danger', 'highlight', 'highlight-alt'], - render: function () { - var classes = ['btn']; + mixins: [ButtonMixin], - if (_.contains(this.acceptedTypes, this.props.type)) { - classes.push('btn-' + this.props.type); - } else { - classes.push('btn-default'); - } + render: function () { + var {block, href, large, type, children, ...others} = this.props; - if (this.props.block) { - classes.push('btn-block'); - } + var classes = classSet({ + btn: true, + 'btn-block': block, + 'btn-lg': large + }); - if (this.props.large) { - classes.push('btn-lg'); + if (type) { + classes += ' btn-' + type; + } else { + classes += ' btn-default'; } - classes = classes.join(" "); - - if (this.props.href) { + if (href) { return ( - {this.props.children} + {children} ); } else { return ( - + ); } } }); var DefaultButton = React.createClass({ - getDefaultProps: function () { - return { - type: 'default' - }; - }, - + mixins: [ButtonMixin], render: function render() { - return ( - {this.props.children} - ); + return ; } }); -var DefaultAltButton = React.createClass({ - getDefaultProps: function () { - return { - type: 'default-alt' - }; - }, +var DefaultAltButton = React.createClass({ + mixins: [ButtonMixin], render: function render() { - return ( - {this.props.children} - ); + return ; } }); -var PrimaryButton = React.createClass({ - getDefaultProps: function () { - return { - type: 'primary' - }; - }, +var PrimaryButton = React.createClass({ + mixins: [ButtonMixin], render: function render() { - return ( - {this.props.children} - ); + return ; } }); -var LowlightButton = React.createClass({ - getDefaultProps: function () { - return { - type: 'lowlight' - }; - }, +var LowlightButton = React.createClass({ + mixins: [ButtonMixin], render: function render() { - return ( - {this.props.children} - ); + return ; } }); -var DangerButton = React.createClass({ - getDefaultProps: function () { - return { - type: 'danger' - }; - }, +var DangerButton = React.createClass({ + mixins: [ButtonMixin], render: function render() { - return ( - {this.props.children} - ); + return ; } }); -var HighlightButton = React.createClass({ - getDefaultProps: function () { - return { - type: 'highlight' - }; - }, +var HighlightButton = React.createClass({ + mixins: [ButtonMixin], render: function render() { - return ( - {this.props.children} - ); + return ; } }); -var HighlightAltButton = React.createClass({ - getDefaultProps: function () { - return { - type: 'highlight-alt' - }; - }, +var HighlightAltButton = React.createClass({ + mixins: [ButtonMixin], render: function render() { - return ( - {this.props.children} - ); + return ; } }); diff --git a/src/pivotal-ui/javascripts/mixins/button-mixin.js b/src/pivotal-ui/javascripts/mixins/button-mixin.js new file mode 100644 index 000000000..4e3c15ff2 --- /dev/null +++ b/src/pivotal-ui/javascripts/mixins/button-mixin.js @@ -0,0 +1,22 @@ +'use strict'; + +var React = require('react'); + +var ButtonMixin = { + propTypes: { + block: React.PropTypes.bool, + href: React.PropTypes.string, + large: React.PropTypes.bool, + type: React.PropTypes.oneOf([ + 'default', + 'default-alt', + 'primary', + 'lowlight', + 'danger', + 'highlight', + 'highlight-alt' + ]) + } +}; + +module.exports = ButtonMixin; diff --git a/test/javascripts/button_spec.js b/test/javascripts/button_spec.js index 29b9c9755..3c313940e 100644 --- a/test/javascripts/button_spec.js +++ b/test/javascripts/button_spec.js @@ -60,27 +60,11 @@ describe('UIButton', function() { }); }); - describe("when type attribute is invalid", function() { - beforeEach(function(){ - React.render( - UIButton({ - type: "fop" - }), - this.node - ); - }); - - it("does not add the type class to the button", function() { - expect($('#container button.btn')).not.toHaveClass('btn-fop'); - expect($('#container button.btn')).toHaveClass('btn-default'); - }); - }); - describe("when block is true", function() { beforeEach(function(){ React.render( UIButton({ - block: "true" + block: true }), this.node ); @@ -95,7 +79,7 @@ describe('UIButton', function() { beforeEach(function(){ React.render( UIButton({ - large: "true" + large: true }), this.node );