tatsu tatsu - 3 years ago 227
React JSX Question

Debounce implementation

I'm having difficulty implementing lodash :

I'm trying to make it so that my input field triggers my check if exist API call every second after keystrokes end rather than every second.

(Ill separate the updateInput function later so that first it sets the input value then it calls the debounced API call method that I should create.)

import React, { Component } from 'react';
import _ from 'lodash';
import { Input, Row, Col } from 'reactstrap';
import loading from '../../../../img/loading.gif';

class InputTypeComponent extends Component {

constructor(props) {
super(props);
const initialValue = props.value;
this.state = {
...initialValue,
};
this.updateInput = this.updateInput.bind(this);
this.handleProviderChange = this.handleProviderChange.bind(this);
this.updateInput = _.debounce(this.updateInput, 1000);
}

componentWillMount() {
this.setState({ inputIcon: this.props.icon.inputIcon });
}

componentWillReceiveProps(newProps) {
const response = newProps.response;
const old = this.props.response;
const { id, onChange } = this.props;
if (response !== old && response.objectIdentifier === id) {
let number = 2;
if (response.objectName === '') {
number = 0;
} else if (response.activ) {
if (response.isthere) {
number = 4;
} else {
number = 3;
}
}
this.setState({ inputIcon: number });
onChange({ icon: {
...this.props.icon,
inputIcon: number,
} }, this.props.id);
}
}

onRemove = () => {
this.props.onRemove(this.props.id);
};

onChange = () => {
this.props.onChange(this.props.id);
};

updateInput(event) {
const { onChange, exists } = this.props;
const inputValue = event.target.value.toUpperCase();
this.setState({ input: inputValue });
onChange({ value: {
...this.state,
input: inputValue,
} }, this.props.id);
const placeHolder = this.props.placeholder.toLowerCase();
const objectIdentifier = this.props.id;
const payload = {
objectType: placeHolder,
objectName: inputValue,
objectIdentifier,
objectFisrt: '',
};
exists(payload);
}

render() {
const { placeholder, provider, size } = this.props;
const { inputIcon } = this.state;
this.type = placeholder;
return (
<Row>
<Col xs="8">
<Row>
<Col xs="11">
<Input
value={this.state.input}
onChange={this.updateInput}
placeholder={placeholder}
/>
</Col>
<Col xs="1" className="margintop noPadding">
{{
0: (
<div />
),
1: (
<img className="colorImgBlue" src={loading} alt="loading" />
),
2: (
<i className="fa fa-times red iconsize" />
),
3: (
<i className="fa fa-check text-success iconsize" />
),
4: (
<i className="fa fa-check text-success iconsize" />
),
default: (
<div />
),
}[inputIcon]}
</Col>
</Row>
</Col>
</Row>
);
}


this broke my code now the UpdateInput function never triggers.

docs and blogs on all this are sparce so I've nowhere else to go.

enter image description here

Answer Source

The error message is actually pointing you at the cause of the error:

Warning: This synthetic event is reused for performance reasons. If you're seeing this, you're accessing the property target on a released/nullified synthetic event. This is set to null ... See fb.me/react-event-pooling

React manages all the DOM events for you, and as part of its internal performance optimizations it maintains a pool of events and re-uses the objects for new events as they come in. However, when React is done passing the event through the component tree it nulls out all the fields.

When you defer updateInput lodash only calls updateInputs after React has cleared out the shared event object.

The way to fix this is to divide your method into two parts - the first that grabs the information you need off of the synthetic event and the second which actually does the work you want debounced:

constructor() {
  this.onInput = this.onInput.bind(this);
  this.updateInput = _.debounce(this.updateInput.bind(this), 1000);
}
onInput(event) {
  const inputValue = event.target.value.toUpperCase();
  this.updateInput(inputValue);
}
updateInput(inputValue) {
  // Details omitted for brevity
}
Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download