Thursday, 15 May 2014

javascript - Best practice for ReactJS form components -



javascript - Best practice for ReactJS form components -

i looking best practice have reactjs component responsible form users edit given entity. simplified illustration here. actual forms in many cases have several more fields , more gui functionality.

react.createclass({ getinitialstate: function() { homecoming { entity: { property1: null, property2: null } }; }, handlechange: function(e) { var entity = this.state.entity; switch(e.target.name) { case 'property1': entity.property1 = e.target.value; break; case 'property2': entity.property2 = e.target.value; break; } this.setstate({ entity: entity }); }, render: function() { homecoming ( <div classname="entity-form"> <form onchange={this.handlechange}> <input type="text" name="property1" value={this.state.entity.property1} /> <br /> <textarea name="property2" value={this.state.entity.property2}></textarea> <br /> </form> </div> ); } });

the fields of form straight editing entity object, saved restful api. want component updated user alter fields, gui react based on input during typing (like validations, info etc).

in theory, have whole state object represent entity beingness edited, every property of entity first level state variables. however, want able add together additional state variables gui functions , other things related component going do, prefer entity object 1 state variable "entity" state variable above. object of course of study more complicated object, backbone model or similar, in simplified example, utilize simple object whit required properties.

so, in search of best practice way create react components purpose, have questions:

props or state.

in case, have chosen set entity object content form in state variable instead of prop. able update object during form input without having phone call parent , update props. far react experience goes, best practice form component this.

controlled or uncontrolled inputs.

in simplified illustration above, utilize controlled inputs. leads updating state , re-rendering component on every alter (like every character entered of text field). best practice? thing component has total command of happens, instead of having defaultvalue paramters, , on event (like user pressing save button), component extract values, update entity , save server. there reasons (or opinions) on if controlled or uncontrolled inputs should used in cases this?

onchange form or every input

the illustration has onchange on form tag, , causes handlechange method called every time of fields in form changed. however, since inputs controlled (have value parameters), react complains input fields not have onchange property. mean having mutual onchange on form tag bad practice, , should remove , set onchange on every single field instead?

updating individual properties

in above example, utilize switch based on input field beingness update (when handlechange called). guess instead create sure field names in sync property names of entity, , can set properties of entity object in handlechange based on name of field event (e.target.name). however, makes hard have individual needs per field, if fields update entity property directly. guess alternativ switch default block setting based on name of input, , case blocks field require other ways of updating (like filtering value before setting on entity). please comment if know much improve way of handeling field updates way.

updating state entity

one big problem of example, way entity object updated. since entity variable in handlechange set entity object current state, pointer, , updating entity variable alter object in state. react pages should never update state directly. 1 of reasons have experienced when updating state way before calling setstate. if having shouldcomponentupdate method, prevstate contain new state, since content of prevstate argument sent shouldcomponentupdate based on in state when setstate called. far know, there no simple way clone object in javascript. question is, when having whole objects need update properties of (and not touching other values in object) instead of running setstate of single state variable, best way without causing theese kinds of state mixups?

anything going alter goes in state. if you're looking @ loading existing entity , editing it, want controlled inputs, , want set values accordingly. tend remain away defaultvalue in cases (outside of dropdowns) this ties in previous question. if specify value, using controlled input, , have provide onchange handler controlled input, otherwise set in stone. benefit of controlled inputs users can't edit them, if had properties locked downwards (maybe read only, security reasons), when user attempts save, if edited html directly, react should pull property's value vdom representation (could wrong here, believe i've tested before). anyway, have have onchange set straight on controlled inputs. far using event delgation (at form level), isn't bad practice @ lot of events, specific scenario (controlled inputs) need onchange events specified each element. not exclusively sure inquire on 1 is, used refs instead of target.name. so, you're right in should never alter state directly, , tricky bit docs. react going alter state directly, it's going in implementation through setstate. if alter state outside of method call, unexpected things happen , errors thrown.

shouldcomponentupdate shallow comparisons, there few solutions here.

one stringify objects, quick , dirty object comparison, don't recommend it, works.

a improve solution, , 1 have used react + flux implement propertychanged bool, , check in shouldcomponentupdate.

now, require aware of setting when things change, i.e., changed deeper in object graph. propertyone object property gets changed in handlechange method. validate input wish, set propertychanged = true, and need implement componentdidupdate. we're making assumption here, if component has updated, set propertychanged false don't have farther triggering of unwanted updates. hope makes sense. it's kinda one-way notifypropertychanged.

i'm providing quick illustration of more dynamic implementation allows add together more properties object (only shallow properties in implementation, write more robust solution). allow me know if have farther questions or if didn't reply something.

http://jsfiddle.net/rpv9trhh/

var e = { prop1: 'test', prop2: 'wee', prop3: 'another property', propfour: 'oh yeah!' }; var formcomp = react.createclass({ getinitialstate: function(){ homecoming { entity: this.props.entity } }, render: function() { var ent = this.state.entity; var = this; var inputs = []; for(var key in ent){ inputs.push(<input key={key} style={{display:'block'}} type="text" ref={key} onchange={that._propertychanged.bind(null, key)} value={ent[key]} />) } homecoming <form> {inputs} <input type="button" onclick={this._savechanges} value="save changes" /> </form>; }, _propertychanged: function(propname) { var nextprop = this.refs[propname].getdomnode().value; var nextentity = this.state.entity; nextentity[propname] = nextprop; this.setstate({ entity: nextentity }); }, _savechanges: function() { var updatedentity = this.state.entity; for(var key in updatedentity){ alert(updatedentity[key]); } //todo: phone call service save entity, i.e. actioncreators.saveentity(updatedentity); } }); react.rendercomponent(<formcomp entity={e} />, document.body);

javascript forms reactjs

No comments:

Post a Comment