Gleichmut
Gleichmut

Reputation: 6989

Access to outer react component from referenced component

I have a React.Component that renders references to others which are defined via const

Here is part of my code

const TodoList = ({data, remove}) => {
  let source = data.map((todo) => {
    return (<TodoItem todo={todo} id={todo.id} remove={remove}/>)
  }) 

  return (<ul>{source}</ul>)
}

export default class HomePage extends React.Component {

  constructor(props) {
    super(props);
    console.log("Start home page")

    this.state = {
      data: []
    }

    this.getAllTasks = this.getAllTasks.bind(this);
  }

  render() {
    return (
      <div className={styles.content}>
        <h1>Home Page</h1>
        <p className={styles.welcomeText}>Thanks for joining!</p>
        <button onClick={this.getAllTasks}>Request all tasks</button>
        <button onClick={this.getSpecificTask}>Get specific task</button>
        <button onClick={this.createTask}>Create task</button>
        <button onClick={this.editTask}>Edit task</button>
        <button onClick={this.deleteTask}>Delete task</button>

        <div id="container">
          <TodoForm addTodo={this.addTodo.bind(this)} />
          <TodoList 
            todos={this.state.data}
            remove={this.handleRemove.bind(this)} />
        </div>
      </div>
    );
  }
}

I am facing issues after adding TodoForm and TodoListto the render. First of them is inner state of TodoList is undefined. By being more specific:

page.js:85 Uncaught TypeError: Cannot read property 'map' of undefined
    at TodoList (page.js:85)

First of all I haven't committed enough time to find out how that's all work under the hood (have a different main tech stack and tight deadline for this app). Source code shows data is obtain via autogenerated reference _ref3 that is passed from outer class.

I you see outer class defines and init the data structure, so data should be defined.

Do you see the issue I missed here?

Upvotes: 0

Views: 43

Answers (2)

Rikin
Rikin

Reputation: 5473

As other solution/answer mentioned you were not destructuring properly thus you encountered the error.

Apart from above solution you can alias it for local scope name data as below:

const TodoList = ({todos: data, remove}) => {    // <---------------------
                   ^^^^^^^^^^^
  let source = data.map((todo) => {
    return (<TodoItem todo={todo} id={todo.id} remove={remove}/>)
  }) 

  return (<ul>{source}</ul>)
}

You are getting an object in TodoList which happens to be your props which you are trying to destructure which has to match key by key but you can alias is using : for local name scoping generalized purpose.

Upvotes: 1

ibtsam
ibtsam

Reputation: 1710

Okay you are not destructuring properly do it as this

const TodoList = ({todos, remove}) => {
 let source = todos.map((todo) => {
 return (<TodoItem todo={todo} id={todo.id} remove={remove}/>)
 }) 

return (<ul>{source}</ul>)
}

You are passing prop as todos and destructuring it as data

Hope it helps

Upvotes: 4

Related Questions