1

I'm trying to map over an array of objects and use the name key to pass it to the options prop in react-select. Can I just do this using regular JS? I'm trying to incorporate this example.

My mock data

    mock.onGet("/dataschemas").reply(200, {
  data: [
    {
      id: "2147483599",
      selfUri: "/dataschemas/2147483599",
      name: "Book Catalog"
    },
    {
      id: "2147483600",
      selfUri: "/dataschemas/2147483600",
      name: "Business Articles"
    },
    {
      id: "2147483602",
      selfUri: "/dataschemas/2147483602",
      name: "Phone Data"
    }
  ]
});

In cDM I'm updating state with the response and storing it in schemas

  componentDidMount() {
    axios.get("/dataschemas").then(function(response) {
      console.log(response.data.data);
      this.setState({
        schemas: response.data.data
      });
      console.log(this.state.schemas);
    });
  }

Then in my select component I'm setting the schemas to the options prop and mapping over that in the values prop

<Select
  id="color"
  options={this.state.schemas}
  isMulti={false}
  value={this.state.schemas.filter(
    ({ name }) => name === this.state.name
  )}
  getOptionLabel={({ name }) => name}
  getOptionValue={({ id }) => id}
  onChange={({ value }) => this.setState({ name: value })}
  onBlur={this.handleBlur}
/>

I can't seem to get the right values in props, to display the dataschema names in the dropdown selection in my codesandbox example

More info on react-select docs pertaining to this issue

DJ2
  • 1,721
  • 3
  • 34
  • 74
  • 1
    specifically, you are using `function` when you should be using an arrow `response =>` – azium Jan 24 '19 at 05:28
  • 1
    https://codesandbox.io/s/23jx8op9l0 – azium Jan 24 '19 at 05:29
  • 1
    This is an issue, I forgot to change it to use `response =>` – DJ2 Jan 24 '19 at 05:35
  • The docs I was reading on the mock adapter were using ES5 instead of ES6 and I overlooked the difference – DJ2 Jan 24 '19 at 05:42
  • 2
    This was improperly marked as a duplicate. The mentioned "duplicate" questions are about a different, unrelated issue that happened to be present in the codesandbox, not the actual issue being asked about. – George Jan 24 '19 at 05:43
  • Yeah I'm not sure how to undo my vote – azium Jan 24 '19 at 05:50

3 Answers3

1

The <Select> component's value prop expect a single object/value. However in the following code:

this.state.schemas.filter(
  ({ name }) => name === this.state.name
)

Calling .filter on an array returns another array. So you're passing an array to value, not a single object. You just need to add a [0] to unwrap the array:

this.state.schemas.filter(
  ({ name }) => name === this.state.name
)[0]

Or use .find instead:

this.state.schemas.find(
  ({ name }) => name === this.state.name
)
George
  • 4,147
  • 24
  • 33
1

here's a working codesandbox

it seems like the problem was that you were using function syntax instead of fat arrow syntax and as a result this was being bound incorrectly so this.setState was undefined

enter image description here

more info about the difference between function and fat arrow syntax here

How does this work? I like to think of it as fat arrow functions don’t have their own or don’t change the context of ‘this’. They leave it alone so that it stays the same as the context in which the function was created.

For debugging future issues like this, I recommend starting off by looking at the javascript console errors -- the initial tip was an error there that this.setState was undefined

wmp224
  • 447
  • 3
  • 11
  • 1
    This answer addresses an issue that happened to be present in the codesanbox, not the actual react-select issue that the question was asking about. – George Jan 24 '19 at 05:46
  • @GeorgeP my interpretation of the question was that this was the issue "I can't seem to get the right values in props, to display the dataschema names in the dropdown selection in my codesandbox example" as a result of the incorrect setState call, no values were populating in the dropdown because this.state.schemas was []... based on the console.logs it seems like this was the underlying problem that they were asking about – wmp224 Jan 24 '19 at 05:48
-2

You are trying to access state from inside the response function scope. change your componentDidMount to this:

async componentDidMount() {
  const response = await axios.get("/dataschemas");
  if (response.data && response.data.data) {
    this.setState({ schemas: response.data.data });
  }
}
Manu Sodhi
  • 92
  • 1
  • 3