Yurii
Yurii

Reputation: 301

React, trying to check if a value is present in array

I have an array licenseKeys in React state, and need to push to it all new values of lisenceKey's that user types to input fields. It works, but when I'm trying to check whether value of new key is present in array this.state.licenseKeys.includes(this.state.licenseKey), I'm getting an error Uncaught TypeError: Cannot read property 'includes' of undefined. I tried to use an arrow function with some instead, but I got the same error Uncaught TypeError: Cannot read property 'some' of undefined. What am I doing wrong here?

 if (localStorage.getItem("formData")) {
  this.state = JSON.parse(localStorage.getItem("formData"));
} else {
  this.state = {
    ppks: [],
    alert: false,
    ipState: "",
    portState: "",
    userNameState: "",
    passwordState: "",
    licenseKey: "",
    licenseKeys: [],
    licenseKeysObject: []
   // refreshButttonDisabled: true
}    
    }

 licenseKeysSetter = () => {
    if (this.state.licenseKey !== "" && this.state.licenseKeys.includes(this.state.licenseKey) === false){          
        this.setState({
            licenseKeys: [ ...this.state.licenseKeys || [], this.state.licenseKey]              
        }, () => {
            console.log(this.state.licenseKeys);            
        });
    }   
  }
.....
<ul>
      {ppkData.map((item, index) => {   
       if (item.model === "8l") {  
        return (
          <div className="ppkCard" key={index + 1}>

          <form>
          <div className="input-group input-group-sm mb-3">
          <div className="input-group-prepend">
            <span className="input-group-text" id="inputGroup-sizing-sm">Enter License Key</span>
          </div>
          <input type="text"
                 className="form-control"
                 placeholder="000-000-000-000-000-000" 
                 onChange={this.licenseKeysHandler}
                 value={this.state.licenseKey || ''} 
                 aria-label="Small" 
                 aria-describedby="inputGroup-sizing-sm" />
        </div>       
        <button type="button" onClick={this.licenseKeysSetter} >Save</button>     
        </form>
.........
 licenseKeysHandler = (event) => {      
    this.setState({licenseKey: event.target.value}, () => {
        console.log(this.state.licenseKey);
    })      
  }

Upvotes: 0

Views: 126

Answers (2)

Aprillion
Aprillion

Reputation: 22304

If localStorage does not include all keys necessary in the state (e.g. after a new version release), you can separate initial state from loading localStorage like this:

class MyComponent() {
  state = {
    ppks: [],
    alert: false,
    ipState: "",
    portState: "",
    userNameState: "",
    passwordState: "",
    licenseKey: "",
    licenseKeys: [],
    licenseKeysObject: []
  }  
  componentDidMount() {
    this.setState(JSON.parse(localStorage.getItem("formData")))   
  }
  ...
}

Upvotes: 1

Yurii
Yurii

Reputation: 301

I changed code like this, and it works fine for me...

 licenseKeysSetter = () => {
    //console.log(this.state.licenseKey);
    console.log(this.state.licenseKeys);
    //console.log(this.state);
    if (this.state.licenseKeys === undefined) {
        if (this.state.licenseKey !== "" ){         
        this.setState({
            licenseKeys: [ ...this.state.licenseKeys || [], this.state.licenseKey]              
        }, () => {
            console.log(this.state.licenseKeys);            
        });
    } 
  } else {      
    if (this.state.licenseKey !== "" && !this.state.licenseKeys.includes(this.state.licenseKey)){            
        //console.log(this.state.licenseKeys);
        this.setState({
            licenseKeys: [ ...this.state.licenseKeys || [], this.state.licenseKey]              
        }, () => {
            console.log(this.state.licenseKeys);            
        });
    }  
    }   
  }

Upvotes: 0

Related Questions