[
  {
    "path": ".gitignore",
    "content": "dist\n/*.example.*\n\n# Logs\nlogs\n*.log\nnpm-debug.log*\n\n# Runtime data\npids\n*.pid\n*.seed\n\n# Directory for instrumented libs generated by jscoverage/JSCover\nlib-cov\n\n# Coverage directory used by tools like istanbul\ncoverage\n\n# Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files)\n.grunt\n\n# node-waf configuration\n.lock-wscript\n\n# Compiled binary addons (http://nodejs.org/api/addons.html)\nbuild/Release\n\n# Dependency directory\n# https://docs.npmjs.com/misc/faq#should-i-check-my-node-modules-folder-into-git\nnode_modules\n### JetBrains template\n# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio\n\n*.iml\n\n## Directory-based project format:\n.idea/\n# if you remove the above rule, at least ignore the following:\n\n# User-specific stuff:\n# .idea/workspace.xml\n# .idea/tasks.xml\n# .idea/dictionaries\n\n# Sensitive or high-churn files:\n# .idea/dataSources.ids\n# .idea/dataSources.xml\n# .idea/sqlDataSources.xml\n# .idea/dynamic.xml\n# .idea/uiDesigner.xml\n\n# Gradle:\n# .idea/gradle.xml\n# .idea/libraries\n\n# Mongo Explorer plugin:\n# .idea/mongoSettings.xml\n\n## File-based project format:\n*.ipr\n*.iws\n\n## Plugin-specific files:\n\n# IntelliJ\n/out/\n\n# mpeltonen/sbt-idea plugin\n.idea_modules/\n\n# JIRA plugin\natlassian-ide-plugin.xml\n\n# Crashlytics plugin (for Android Studio and IntelliJ)\ncom_crashlytics_export_strings.xml\ncrashlytics.properties\ncrashlytics-build.properties\n\n"
  },
  {
    "path": "README.md",
    "content": "# Todo App using React Redux Webpack\n\nYet another Todo app using React Redux and Webpack. \n\nThe content is based on the example in the \n[great Redux tutorial by Dan Abramov](https://egghead.io/series/getting-started-with-redux).\n\nThe aim here was to keep it *really* simple to get started with these technologies.\n\n## Deps\n\n    npm install\n\nThis repository is meant to be used with npm 3. For version 2 also install:\n\n    npm install --save-dev babel-plugin-transform-object-rest-spread\n    npm install --save-dev babel-plugin-transform-class-properties\n\n## Build\n\n    node_modules/.bin/webpack\n\n## Dev\n\n    node_modules/.bin/webpack-dev-server --hot --inline\n"
  },
  {
    "path": "app/index.html",
    "content": "<!doctype html>\n<html lang=\"en-US\">\n<head>\n    <meta charset=\"UTF-8\">\n    <title>todo</title>\n</head>\n<body>\n    <h1>todo</h1>\n\n    <div id=\"app-root\"></div>\n\n    <script src=\"js/app.js\"></script>\n</body>\n</html>\n"
  },
  {
    "path": "app/js/actions/index.js",
    "content": "let nextTodoId = 0;\n\nexport const addTodo = (text) => {\n  return {\n    type: 'ADD_TODO',\n    id: nextTodoId++,\n    text\n  };\n};\n\nexport const toggleTodo = (id) => {\n  return {\n    type: 'TOGGLE_TODO',\n    id\n  };\n};\n\nexport const setVisibilityFilter = (filter) => {\n  return {\n    type: 'SET_VISIBILITY_FILTER',\n    filter\n  };\n};\n"
  },
  {
    "path": "app/js/app.js",
    "content": "import ReactDOM from 'react-dom';\n\nimport AppRoot from './components/AppRoot.jsx';\n\nReactDOM.render(\n  AppRoot,\n  document.getElementById('app-root')\n);\n"
  },
  {
    "path": "app/js/components/AddTodo.jsx",
    "content": "import React from 'react';\nimport { connect } from 'react-redux';\n\nimport { addTodo } from '../actions';\n\nlet AddTodo = ({ dispatch }) => {\n  let input;\n\n  return (\n    <div>\n      <input ref={node => {\n        input = node;\n      }} />\n      <button onClick={() => {\n        dispatch(addTodo(input.value));\n        input.value = '';\n      }}>\n        Add Todo\n      </button>\n    </div>\n  );\n};\nexport default connect()(AddTodo);"
  },
  {
    "path": "app/js/components/AppRoot.jsx",
    "content": "import React from 'react';\nimport { Provider } from 'react-redux';\n\nimport AddTodo from './AddTodo.jsx';\nimport TodoList from './TodoList.jsx';\nimport Footer from './Footer.jsx';\nimport store from '../store';\n\n\nconst TodoApp = () => (\n  <div>\n    <AddTodo />\n    <TodoList />\n    <Footer />\n  </div>\n);\n\nexport default (\n  <Provider store={store}>\n    <TodoApp />\n  </Provider>\n)"
  },
  {
    "path": "app/js/components/Footer.jsx",
    "content": "import React from 'react';\nimport { connect } from 'react-redux';\n\nimport { setVisibilityFilter } from '../actions';\n\nconst Link = ({\n  active,\n  children,\n  onClick\n  }) => {\n  if (active) {\n    return <span>{children}</span>;\n  }\n\n  return (\n    <a href='#'\n       onClick={e => {\n         e.preventDefault();\n         onClick();\n       }}\n      >\n      {children}\n    </a>\n  );\n};\n\nconst mapStateProps = (\n  state,\n  ownProps\n) => {\n  return {\n    active:\n      ownProps.filter ===\n      state.visibilityFilter\n  };\n};\nconst mapDispatchProps = (\n  dispatch,\n  ownProps\n) => {\n  return {\n    onClick: () => {\n      dispatch(\n        setVisibilityFilter(ownProps.filter)\n      );\n    }\n  };\n};\n\nconst FilterLink = connect(\n  mapStateProps,\n  mapDispatchProps\n)(Link);\n\nexport default () => (\n  <p>\n    Show:\n    {' '}\n    <FilterLink filter='SHOW_ALL'>\n      All\n    </FilterLink>\n    {', '}\n    <FilterLink filter='SHOW_ACTIVE'>\n      Active\n    </FilterLink>\n    {', '}\n    <FilterLink filter='SHOW_COMPLETED'>\n      Completed\n    </FilterLink>\n  </p>\n);"
  },
  {
    "path": "app/js/components/TodoList.jsx",
    "content": "import React from 'react';\nimport { connect } from 'react-redux';\n\nimport { toggleTodo } from '../actions';\n\nconst Todo = ({\n  onClick,\n  completed,\n  text\n  }) => (\n  <li\n    onClick={onClick}\n    style={{\n      textDecoration:\n        completed ?\n          'line-through' :\n          'none'\n    }}\n    className={\n        completed ?\n          'completed' :\n          ''\n    }\n    >\n    {text}\n  </li>\n);\n\nconst TodoList = ({\n  todos,\n  onTodoClick\n  }) => (\n  <ul>\n    {todos.map(todo =>\n        <Todo\n          key={todo.id}\n          {...todo}\n          onClick={() => onTodoClick(todo.id)}\n          />\n    )}\n  </ul>\n);\n\nconst getVisibleTodos = (\n  todos,\n  filter\n) => {\n  switch (filter) {\n    case 'SHOW_ALL':\n      return todos;\n    case 'SHOW_COMPLETED':\n      return todos.filter(\n          t => t.completed\n      );\n    case 'SHOW_ACTIVE':\n      return todos.filter(\n          t => !t.completed\n      );\n  }\n}\n\nconst mapStateToProps = (\n  state\n) => {\n  return {\n    todos: getVisibleTodos(\n      state.todos,\n      state.visibilityFilter\n    )\n  };\n};\nconst mapDispatchToProps = (\n  dispatch\n) => {\n  return {\n    onTodoClick: (id) => {\n      dispatch(toggleTodo(id));\n    }\n  };\n};\nexport default connect(\n  mapStateToProps,\n  mapDispatchToProps\n)(TodoList);"
  },
  {
    "path": "app/js/store/index.js",
    "content": "import { createStore, combineReducers } from 'redux';\n\nconst todo = (state, action) => {\n  switch (action.type) {\n    case 'ADD_TODO':\n      return {\n        id: action.id,\n        text: action.text,\n        completed: false\n      };\n    case 'TOGGLE_TODO':\n      if (state.id !== action.id) {\n        return state;\n      }\n\n      return {\n        ...state,\n        completed: !state.completed\n      };\n    default:\n      return state;\n  }\n};\n\nconst todos = (state = [], action) => {\n  switch (action.type) {\n    case 'ADD_TODO':\n      return [\n        ...state,\n        todo(undefined, action)\n      ];\n    case 'TOGGLE_TODO':\n      return state.map(t =>\n          todo(t, action)\n      );\n    default:\n      return state;\n  }\n};\n\nconst visibilityFilter = (\n  state = 'SHOW_ALL',\n  action\n) => {\n  switch (action.type) {\n    case 'SET_VISIBILITY_FILTER':\n      return action.filter;\n    default:\n      return state;\n  }\n};\n\nconst todoApp = combineReducers({\n  todos,\n  visibilityFilter\n});\n\nexport default createStore(todoApp)"
  },
  {
    "path": "package.json",
    "content": "{\n  \"name\": \"Todo\",\n  \"version\": \"0.0.0\",\n  \"description\": \"Todo app using React, Redux and Webpack. Based on the example from Dan Abramov's excellent tutorial (https://egghead.io/series/getting-started-with-redux)\",\n  \"scripts\": {\n    \"build\": \"webpack\",\n    \"start\": \"webpack-dev-server --hot --inline\"\n  },\n  \"keywords\": [\n    \"todo\"\n  ],\n  \"author\": \"\",\n  \"license\": \"MIT\",\n  \"devDependencies\": {\n    \"babel-core\": \"^6.3.26\",\n    \"babel-loader\": \"^6.2.0\",\n    \"babel-plugin-react-transform\": \"^2.0.0\",\n    \"babel-plugin-syntax-class-properties\": \"^6.3.13\",\n    \"babel-plugin-syntax-decorators\": \"^6.3.13\",\n    \"babel-plugin-syntax-object-rest-spread\": \"^6.3.13\",\n    \"babel-preset-es2015\": \"^6.3.13\",\n    \"babel-preset-react\": \"^6.3.13\",\n    \"babel-preset-stage-0\": \"^6.3.13\",\n    \"file-loader\": \"^0.8.5\",\n    \"react-hot-loader\": \"^1.3.0\",\n    \"webpack\": \"^1.12.9\",\n    \"webpack-dev-server\": \"^1.14.0\"\n  },\n  \"dependencies\": {\n    \"react\": \"^0.14.5\",\n    \"react-dom\": \"^0.14.5\",\n    \"react-redux\": \"^4.0.6\",\n    \"redux\": \"^3.0.5\"\n  }\n}\n"
  },
  {
    "path": "webpack.config.js",
    "content": "module.exports = {\n  entry: {\n    javascript: \"./app/js/app.js\",\n    html: \"./app/index.html\"\n  },\n  output: {\n    path: __dirname + \"/dist\",\n    filename: \"./js/app.js\"\n  },\n  module: {\n    loaders: [\n      {\n        test: /\\.html$/,\n        loader: \"file?name=[name].[ext]\"\n      },\n      {\n        test: /\\.jsx?$/,\n        exclude: /node_modules/,\n        loaders: [\"react-hot\", 'babel?'+JSON.stringify(\n          {\n            presets: ['react', 'es2015'],\n            \"plugins\": [\n              \"syntax-class-properties\",\n              \"syntax-decorators\",\n              \"syntax-object-rest-spread\",\n\n              \"transform-class-properties\",\n              \"transform-object-rest-spread\"\n            ]\n          }\n        )]\n      }\n    ]\n  }\n};"
  }
]