# Building an Awesome Todo List App

**URL:** <https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214>\
**Category:** programming\
**Created:** [March 20, 2017, 3:22am UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214 "2017-03-20T03:22:50Z")\
**Posts on this page:** 20\
**Page:** 2

<div class="post-metadata">

**Author:** ![MegxD](https://avatars.discourse-cdn.com/v4/letter/m/73ab20/32.png) [@MegxD](https://forum.kirupa.com/u/MegxD)\
**Post date:** [January 2, 2018, 5:53am UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/22 "2018-01-02T05:53:11Z")

</div>

Thank you for your reply. Yes, that’s true. I check it before. Its returning ‘undefined’. How it is possible, that I have the same code like on your tutorial and in my code is error?

 ![image](https://canada1.discourse-cdn.com/flex011/uploads/kirupa/original/2X/f/f1c43e0ecc78286a20e00ae26215a4718d443457.png)

---

<div class="post-metadata">

**Author:** ![senocular](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/senocular/32/7217_2.png) [@senocular](https://forum.kirupa.com/u/senocular)\
**Post date:** [January 2, 2018, 2:13pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/23 "2018-01-02T14:13:11Z")

</div>

Is your `state` being properly initialized in the constructor? And is entries getting defined with:

```auto
<TodoItems entries={this.state.items}/>

```

?

---

<div class="post-metadata">

**Author:** ![MegxD](https://avatars.discourse-cdn.com/v4/letter/m/73ab20/32.png) [@MegxD](https://forum.kirupa.com/u/MegxD)\
**Post date:** [January 2, 2018, 6:32pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/24 "2018-01-02T18:32:59Z")

</div>

There was my mistake, thank you for your time.  
Next time I will be more watchful.

---

<div class="post-metadata">

**Author:** ![senocular](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/senocular/32/7217_2.png) [@senocular](https://forum.kirupa.com/u/senocular)\
**Post date:** [January 2, 2018, 6:47pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/25 "2018-01-02T18:47:04Z")

</div>

Glad you figured it out! 🙂

---

<div class="post-metadata">

**Author:** ![Andy\_Stav](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/andy_stav/32/8952_2.png) [@Andy\_Stav](https://forum.kirupa.com/u/Andy_Stav)\
**Post date:** [January 22, 2018, 6:46pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/26 "2018-01-22T18:46:52Z")

</div>

hi there, love the walkthrough but having some trouble.

At the part whee we try to get the tasks to print on the page, but when i hit enter they are only logging to the console.

```auto
// todoitems.js

import React, { Component } from 'react';

class TodoItems extends Component {
  constructor(props, context) {
    super(props, context);

  

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

  createTasks(item) {
    return <li key={item.key}>{item.text}</li>;
  }

  render() {
    var todoEntries = this.props.entries;
    var listItems = todoEntries.map(this.createTasks);

    return (
      <ul className='theList'>
        {listItems}
      </ul>
    );
  }
}

export default TodoItems;

```

```auto
// todolist.js 

import React, { Component } from 'react';
import TodoItems from '../TodoItems/TodoItems';
import '../TodoList/TodoList.css';

class TodoList extends Component {
  constructor(props, context) {
    super(props, context);

    this.state = {
      items: []
    };

    this.addItem = this.addItem.bind(this);

  }

  addItem(e) {
    const itemArray = this.state.items;

    if (this._inputElement.value !== '') {
      itemArray.unshift({
        text: this._inputElement.value,
        key: Date.now()
      });

      this._inputElement.value = '';
    }
    console.log(itemArray);

    e.preventDefault();
  }

  render() {
    return (
      <div className="todoListMain">
        <div className="header">
          <form onSubmit={this.addItem}>
            <input ref={(a) => this._inputElement = a}
              placeholder="enter task">
            </input>
            <button type="submit">add</button>
          </form>
        </div>
        <TodoItems entries={this.state.items}/>
      </div>
    );
  }
}
export default TodoList;

```

thanks! cannot see what is going wrong here!

---

<div class="post-metadata">

**Author:** ![joe241](https://avatars.discourse-cdn.com/v4/letter/j/74df32/32.png) [@joe241](https://forum.kirupa.com/u/joe241)\
**Post date:** [January 28, 2018, 2:21pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/27 "2018-01-28T14:21:11Z")

</div>

Hi all,

I struggled with the deleteItem method for a while. This was very helpful in explaining how filter works

> **[Array.prototype.filter()](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/filter)**
>
> The filter() method creates a new array with all elements that pass the test implemented by the provided function.

---

<div class="post-metadata">

**Author:** ![kirupa](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/kirupa/32/11616_2.png) [@kirupa](https://forum.kirupa.com/u/kirupa)\
**Post date:** [January 28, 2018, 7:41pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/28 "2018-01-28T19:41:00Z")

</div>

I just noticed this. If you add a `console.log` in your render methods, are you seeing them getting called?

---

<div class="post-metadata">

**Author:** ![Serwus](https://avatars.discourse-cdn.com/v4/letter/s/258eb7/32.png) [@Serwus](https://forum.kirupa.com/u/Serwus)\
**Post date:** [February 7, 2018, 7:12pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/29 "2018-02-07T19:12:16Z")

</div>

I have a qustion. Why file “index.css” doesn’t work at all? I followed whole tutorial and everything works fine, but this one file doen’t change anything in page look at all. ☹ It doesn’t even matter if I comment this file or not. It look like it isn’t loaded anyway.

EDIT: I just needed to center it and worked centering it in html file, but I still wonder why it doesn’t work. I attached this css file as was metioned in the tutorial. 😥

---

<div class="post-metadata">

**Author:** ![senocular](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/senocular/32/7217_2.png) [@senocular](https://forum.kirupa.com/u/senocular)\
**Post date:** [February 7, 2018, 7:20pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/30 "2018-02-07T19:20:48Z")

</div>

It should work. For example it adds a blue background color to the page as seen in the live version here:

[https://www.kirupa.com/react/examples/todolist/index.html](https://www.kirupa.com/react/examples/todolist/index.html)

Do you not have a blue background in your version?

---

<div class="post-metadata">

**Author:** ![Serwus](https://avatars.discourse-cdn.com/v4/letter/s/258eb7/32.png) [@Serwus](https://forum.kirupa.com/u/Serwus)\
**Post date:** [February 7, 2018, 7:30pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/31 "2018-02-07T19:30:13Z")

</div>

No. ☹ It looks like this:

 ![task](https://canada1.discourse-cdn.com/flex011/uploads/kirupa/original/2X/a/a0316b872a2387d64ef60b3de616a9885c3af9a1.png)  
I centered and changed color of other elements in their css file. Index.css is without changes.

---

<div class="post-metadata">

**Author:** ![senocular](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/senocular/32/7217_2.png) [@senocular](https://forum.kirupa.com/u/senocular)\
**Post date:** [February 7, 2018, 7:44pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/32 "2018-02-07T19:44:08Z")

</div>

Yup, it’s definitely not being picked up. Given that the other CSS file is working, it means it _can_ work. The question is why its not now.

Some things to check:

- Is the import statement correctly targeting the index file in the right location (in same folder)?
- Is capitalization correct for the filename file path?
- Are there any syntactic errors in the CSS file?

---

<div class="post-metadata">

**Author:** ![Serwus](https://avatars.discourse-cdn.com/v4/letter/s/258eb7/32.png) [@Serwus](https://forum.kirupa.com/u/Serwus)\
**Post date:** [February 7, 2018, 8:04pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/33 "2018-02-07T20:04:12Z")

</div>

```
import "./index.css";

```

When I changed this import into not existing, it gave me error in browser. I suppose this file is being imported after all.  
Content of my index.css file:

```
body {
  padding: 50px;
  background-color: #66CCFF;
  font-family: sans-serif;
}
#container {
  display: flex;
  justify-content: center;
}

```

All files exept html are inside src directory. ☹

EDIT: I have found the way to make this work: I needed to put css file into public directory and refer it this way in index.html:

```
  <head>
    <link rel="stylesheet" type="text/css" href="mystyle.css">
  </head>

```

It is not exactly what I wanted to do, but now it finally works. Thank you for replies and your time!

EDIT2:  
I ALSO FOUND THE REASON why it didn’t work from the beggining. When I coppied code from tutorial, it added some wierd, two-spaces long tabulator inside css file, so tags weren’t closed and I didn’t notice it in my text editor. D: I changed it into real two spaces and it started to work perfectly!

---

<div class="post-metadata">

**Author:** ![Nipun\_Bharti](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/nipun_bharti/32/8980_2.png) [@Nipun\_Bharti](https://forum.kirupa.com/u/Nipun_Bharti)\
**Post date:** [February 12, 2018, 9:31am UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/34 "2018-02-12T09:31:45Z")

</div>

I have the same issue. When I use console.log for todoEntries, it displays but not for listItems.

---

<div class="post-metadata">

**Author:** ![zdanowiczkonrad](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/zdanowiczkonrad/32/9007_2.png) [@zdanowiczkonrad](https://forum.kirupa.com/u/zdanowiczkonrad)\
**Post date:** [March 1, 2018, 10:54am UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/35 "2018-03-01T10:54:55Z")

</div>

Hi! Many thanks for your effort in building a good tutorial. Kudos for trying to focus as much attention on the React itself as needed (by providing your own CSS styles, for instance, or using create-react-app instead of forcing a reader to deep dive into another concept that is not relevant to react apparently).

I’d propose to reduce the noise even more by:

- always using arrow expression class method declaration to avoid redundant binding (thus confusing the reader if he wants to add a new method and forgets about binding)
- removing a react dependency to the animation library
- using `entries.map` directly in the render method, not an auxiliary method. This resembles the well known templating standards like vue.js/angular/moustache and leads to less confusion.

I also noticed you are using a mutable operation to manipulate the state, which is a bad thing (although happens to work good on your code). I think that a lot of confusion in the comments is related to that. Speaking about:

```auto
var entriesList = this.state.entries;
entriesList.unshift({...new entry...});
this.setState({entries: entriesList});

```

unshift will cause a state mutation, because even though you operate on entriesList variable, it points on the one of state’s field. It would be much cleaner with:

```auto
this.setState({ entries: this.state.entries.concat({... new entry ...}) });

```

Hope you find my advices helpful or reasonable, but of course you don’t have to 100% agree with all of them. I am open to your comments and the discussion, or even better ideas!

---

<div class="post-metadata">

**Author:** ![kirupa](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/kirupa/32/11616_2.png) [@kirupa](https://forum.kirupa.com/u/kirupa)\
**Post date:** [March 3, 2018, 4:59pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/36 "2018-03-03T16:59:24Z")

</div>

Hi @zdanowiczkonrad!  
Thanks for the detailed answer. I agree with all of your points. Comments for them:

> always using arrow expression class method declaration to avoid redundant binding (thus confusing the reader if he wants to add a new method and forgets about binding)

I tried to be consistent with the React documentation here. I discussed the various options for auto-binding in a different tutorial, but for consistency I describe explicitly using `bind` in the constructor as needed.

> removing a react dependency to the animation library

Adding a dependency for something that could be done using just regular CSSTransitionGroup does seem a bit heavyweight, but this library was just too simple. I also wanted to highlight how easy it is to add a 3rd party library and integrate it as part of your app.

> using entries.map directly in the render method, not an auxiliary method. This resembles the well known templating standards like vue.js/angular/moustache and leads to less confusion.

I use `map` in later tutorials, but I kept it in its expanded form here. One of the reasons is that these tutorials target a beginner audience, and I try to minimize the number of concepts they would be unfamiliar with. For more advanced React tutorials, map will be used more and more.

Lastly, good catch on the `setState` method. @senocular brought that up as well. I’ll update the code by using both `concat` and `prevState`, as recommended.

🙂

---

<div class="post-metadata">

**Author:** ![webguync](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/webguync/32/2434_2.png) [@webguync](https://forum.kirupa.com/u/webguync)\
**Post date:** [March 21, 2018, 11:14pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/37 "2018-03-21T23:14:22Z")

</div>

I am getting this same error. What is the resolution?

---

<div class="post-metadata">

**Author:** ![kirupa](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/kirupa/32/11616_2.png) [@kirupa](https://forum.kirupa.com/u/kirupa)\
**Post date:** [March 22, 2018, 4:28pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/38 "2018-03-22T16:28:09Z")

</div>

There may be a copy/paste issue. Can you try writing that method manually and see if it fixes it?

---

<div class="post-metadata">

**Author:** ![webguync](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/webguync/32/2434_2.png) [@webguync](https://forum.kirupa.com/u/webguync)\
**Post date:** [March 22, 2018, 5:51pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/39 "2018-03-22T17:51:50Z")

</div>

Hi Kirupa,  
I did type manually, here is the code. Do you see a syntax error?

```auto
deleteItem(key){
        var filteredItems = this.state.items.filter(function(item){
        return (item.key !== key);
    });

    this.setState({
        items:filteredItems
    });
}

```

---

<div class="post-metadata">

**Author:** ![kirupa](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/kirupa/32/11616_2.png) [@kirupa](https://forum.kirupa.com/u/kirupa)\
**Post date:** [March 22, 2018, 6:19pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/40 "2018-03-22T18:19:48Z")

</div>

Can you attach your JS file to this response? I’ll do a diff and see if there is some random spacing or character throwing things off. What you’ve posted looks good to me!

---

<div class="post-metadata">

**Author:** ![webguync](https://yyz1.discourse-cdn.com/flex011/user_avatar/forum.kirupa.com/webguync/32/2434_2.png) [@webguync](https://forum.kirupa.com/u/webguync)\
**Post date:** [March 22, 2018, 6:31pm UTC](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214/41 "2018-03-22T18:31:29Z")

</div>

yes, here it is.

[TodoList.js](https://forum.kirupa.com/uploads/short-url/aikow9mr6mi5vPRi4F4qgwKfKEb.js) (1.5 KB)

[Previous page](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214.md?page=1)

[Next page](https://forum.kirupa.com/t/building-an-awesome-todo-list-app/636214.md?page=3)
