diff --git a/SUMMARY.md b/SUMMARY.md
index 59ebd73..fd99e92 100644
--- a/SUMMARY.md
+++ b/SUMMARY.md
@@ -24,10 +24,13 @@
* [Reducer](/docs/REDUX.md#reducer)
* [Store](/docs/REDUX.md#store)
* [Views](/docs/VIEWS.md)
- * [Begin](/docs/VIEWS.md#begin)
+ * [IndexView](/docs/VIEWS.md#indexview)
* [Alternatives](/docs/VIEWS.md#alternatives)
+* [Reducers](/docs/REDUCERS.md)
+ * [IndexReducer](/docs/REDUCERS.md#indexreducer)
+ * [Connecting the reducer](/docs/REDUCERS.md#connecting)
* [Containers](/docs/CONTAINERS.md)
* [Initialize](/docs/CONTAINERS.md#initialize)
- * [Begin](/docs/CONTAINERS.md#begin)
+ * [IndexContainer](/docs/CONTAINERS.md#indexcontainer)
* [Styles](/docs/STYLES.md)
* [Tests](/docs/TESTS.md)
diff --git a/docs/CONTAINERS.md b/docs/CONTAINERS.md
index 4ec8c0c..2996a2c 100644
--- a/docs/CONTAINERS.md
+++ b/docs/CONTAINERS.md
@@ -13,7 +13,7 @@ and the type definitions for it
yarn add -D @types/react-redux
```
-### Begin
+### IndexContainer
We begin by creating a file called `IndexContainer.ts` inside our `index`-folder inside `src/modules`
> All containers will have the same "prefix" as their accompanied **views**, a.k.a. `[Pagename]Container.ts`
diff --git a/docs/REDUCERS.md b/docs/REDUCERS.md
new file mode 100644
index 0000000..54c44d6
--- /dev/null
+++ b/docs/REDUCERS.md
@@ -0,0 +1,346 @@
+# Reducers
+
+Now we build our business logic, also known as **reducers**. Stay calm, this will be a bit more complicated then anything before.
+
+### IndexReducer
+
+We begin by creating a file called `IndexReducer.ts` in the `src/modules/index`-folder
+> Our **reducers** follow the naming pattern of `[Foldername]Reducer`
+
+```typescript
+import { MiddlewareAPI } from 'redux';
+import { Observable } from 'rxjs/observable';
+import { ajax } from 'rxjs/observable/dom/ajax';
+import 'rxjs/add/operator/delay';
+import 'rxjs/add/operator/map';
+import 'rxjs/add/operator/mapTo';
+import { Epic, combineEpics, ActionsObservable } from 'redux-observable';
+import { DefaultAction } from '../../redux/utils';
+import Todo from '../../common/Todo';
+
+export class IndexState {
+ readonly title: string = '';
+ readonly todos: Todo[] = [];
+ readonly loading: boolean = false;
+}
+
+type SET_TITLE = 'boilerplate/Index/SET_TITLE';
+const SET_TITLE: SET_TITLE = 'boilerplate/Index/SET_TITLE';
+type SAVE_TODO = 'boilerplate/Index/SAVE_TODO';
+const SAVE_TODO: SAVE_TODO = 'boilerplate/Index/SAVE_TODO';
+type SAVE_TODO_SUCCESS = 'boilerplate/Index/SAVE_TODO_SUCCESS';
+const SAVE_TODO_SUCCESS: SAVE_TODO_SUCCESS = 'boilerplate/Index/SAVE_TODO_SUCCESS';
+type SET_DONE = 'boilerplate/Index/SET_DONE';
+const SET_DONE: SET_DONE = 'boilerplate/Index/SET_DONE';
+type SET_DONE_SUCCESS = 'boilerplate/Index/SET_DONE_SUCCESS';
+const SET_DONE_SUCCESS: SET_DONE_SUCCESS = 'boilerplate/Index/SET_DONE_SUCCESS';
+
+type SetTitleAction = { type: SET_TITLE, payload: string };
+export const setTitle = (title: string): SetTitleAction => ({ type: SET_TITLE, payload: title });
+type SaveTodoAction = { type: SAVE_TODO };
+export const saveTodo = (): SaveTodoAction => ({ type: SAVE_TODO });
+type SaveTodoSuccessAction = { type: SAVE_TODO_SUCCESS };
+const saveTodoSuccess = (): SaveTodoSuccessAction => ({ type: SAVE_TODO_SUCCESS });
+type SetDoneAction = { type: SET_DONE, payload: number };
+export const setDone = (i: number) => ({ type: SET_DONE, payload: i });
+type SetDoneSuccessAction = { type: SET_DONE_SUCCESS, payload: number };
+const setDoneSuccess = (i: number): SetDoneSuccessAction => ({ type: SET_DONE_SUCCESS, payload: i });
+
+export type IndexActions = SetTitleAction | SaveTodoAction | SaveTodoSuccessAction | SetDoneAction | SetDoneSuccessAction | DefaultAction;
+
+const saveTodoEpic: Epic = (action$: ActionsObservable): Observable =>
+ action$.ofType(SAVE_TODO)
+ .delay(1000)
+ .mapTo(saveTodoSuccess());
+
+const setDoneEpic: Epic = (action$: ActionsObservable): Observable =>
+ action$.ofType(SET_DONE)
+ .delay(1000)
+ .map((action: SetDoneAction) => setDoneSuccess(action.payload));
+
+export const IndexEpics = combineEpics(saveTodoEpic, setDoneEpic);
+
+const IndexReducer = (state: IndexState = new IndexState(), action: IndexActions = DefaultAction): IndexState => {
+ switch (action.type) {
+ case SET_TITLE:
+ return { ...state, title: action.payload };
+ case SAVE_TODO:
+ return { ...state, loading: true };
+ case SAVE_TODO_SUCCESS:
+ return {
+ ...state,
+ title: '',
+ todos: state.todos.concat(new Todo(state.todos.length + 1, state.title)),
+ loading: false,
+ };
+ case SET_DONE:
+ return { ...state, loading: true };
+ case SET_DONE_SUCCESS:
+ return {
+ ...state,
+ todos: state.todos.map(t => t.id === action.payload ? t.setDone() : t),
+ loading: false,
+ };
+ default:
+ return state;
+ }
+};
+
+export default IndexReducer;
+```
+
+---
+
+First we define the **state** for our `IndexReducer`
+> **Reducers** usually define their own **state** and we'll show you [later](#connecting) how to connect it to the main **reducer** and **state**
+
+```typescript
+import Todo from '../../common/Todo';
+
+export class IndexState {
+ readonly title: string = '';
+ readonly todos: Todo[] = [];
+ readonly loading: boolean = false;
+}
+```
+which is fairly simple. Here we define the `IndexState` as a class, with the given properties (*make sure you add default values for required properties so you can instantiate it!*), with the `title` for the current `Todo` the user is creating, `todos` for the list of current `Todo`s and `loading` to show the user whether the application is performing an async call or not.
+
+---
+
+Next up we define our [action types](http://redux.js.org/docs/basics/Actions.html)
+```typescript
+type SET_TITLE = 'boilerplate/Index/SET_TITLE';
+const SET_TITLE: SET_TITLE = 'boilerplate/Index/SET_TITLE';
+type SAVE_TODO = 'boilerplate/Index/SAVE_TODO';
+const SAVE_TODO: SAVE_TODO = 'boilerplate/Index/SAVE_TODO';
+type SAVE_TODO_SUCCESS = 'boilerplate/Index/SAVE_TODO_SUCCESS';
+const SAVE_TODO_SUCCESS: SAVE_TODO_SUCCESS = 'boilerplate/Index/SAVE_TODO_SUCCESS';
+type SET_DONE = 'boilerplate/Index/SET_DONE';
+const SET_DONE: SET_DONE = 'boilerplate/Index/SET_DONE';
+type SET_DONE_SUCCESS = 'boilerplate/Index/SET_DONE_SUCCESS';
+const SET_DONE_SUCCESS: SET_DONE_SUCCESS = 'boilerplate/Index/SET_DONE_SUCCESS';
+```
+which **redux** recommends to be constant `string`s. The reason we first define a `type` for the action type is to get **TypeScript** to do [some of the work for us](https://spin.atomicobject.com/2016/09/27/typed-redux-reducers-typescript-2-0/), by ensuring that each instance of the action type has the same value, so for example a constant of `SET_TITLE: SET_TITLE = 'notcorrect'` would raise a compiler error from **TypeScript** as it is not equal to `boilerplate/Index/SET_TITLE`.
+> Here we follow the [redux-ducks](https://github.com/erikras/ducks-modular-redux) naming pattern of the format `applicationName/ViewName/ACTION_TYPE`
+
+---
+
+Next we define our **action creators** which are functions that return an **action**
+```typescript
+type SetTitleAction = { type: SET_TITLE, payload: string };
+export const setTitle = (title: string): SetTitleAction => ({ type: SET_TITLE, payload: title });
+type SaveTodoAction = { type: SAVE_TODO };
+export const saveTodo = (): SaveTodoAction => ({ type: SAVE_TODO });
+type SaveTodoSuccessAction = { type: SAVE_TODO_SUCCESS };
+const saveTodoSuccess = (): SaveTodoSuccessAction => ({ type: SAVE_TODO_SUCCESS });
+type SetDoneAction = { type: SET_DONE, payload: number };
+export const setDone = (i: number) => ({ type: SET_DONE, payload: i });
+type SetDoneSuccessAction = { type: SET_DONE_SUCCESS, payload: number };
+const setDoneSuccess = (i: number): SetDoneSuccessAction => ({ type: SET_DONE_SUCCESS, payload: i });
+```
+of a specific type with a specific `payload` (*which is the way to pass new information to the **reducer***). In this case we also first define the `type` for each of the possible **actions** at the same time as the **action creator**.
+
+---
+
+After defining our **actions** and **action creators** we also create a combined type of all of them
+```typescript
+import { DefaultAction } from '../../redux/utils';
+
+export type IndexActions = SetTitleAction | SaveTodoAction | SaveTodoSuccessAction | SetDoneAction | SetDoneSuccessAction | DefaultAction;
+```
+to allow us to later define when we want to receive an **action** for our `Index`-page and later combine them to create a shared type for all the **actions** in our application.
+
+---
+
+Next we define our [Epics](https://redux-observable.js.org/docs/basics/Epics.html)
+```typescript
+import { Observable } from 'rxjs/observable';
+import 'rxjs/add/operator/delay';
+import 'rxjs/add/operator/map';
+import 'rxjs/add/operator/mapTo';
+import { Epic, combineEpics, ActionsObservable } from 'redux-observable';
+
+const saveTodoEpic: Epic = (action$: ActionsObservable): Observable =>
+ action$.ofType(SAVE_TODO)
+ .delay(1000)
+ .mapTo(saveTodoSuccess());
+
+const setDoneEpic: Epic = (action$: ActionsObservable): Observable =>
+ action$.ofType(SET_DONE)
+ .delay(1000)
+ .map((action: SetDoneAction) => setDoneSuccess(action.payload));
+
+export const IndexEpics = combineEpics(saveTodoEpic, setDoneEpic);
+```
+which are [redux-observable's](https://redux-observable.js.org) way of handling side-effects in **Redux** (*like AJAX calls etc.*). At the end we combine all our **Epics** in this file to a single exportable **Epic** called `IndexEpics` (*so we only need to import one variable when we want access to these later*).
+> The importing part may look a little weird, but it's because [RxJS](http://reactivex.io/rxjs/) is a rather large library, we can either import everything using `import * as RxJS from 'rxjs'` or import only the parts we need as shown above, which will allow any proper [minifier](https://developers.google.com/speed/docs/insights/MinifyResources) like [UglifyJS](https://github.com/mishoo/UglifyJS) include only the needed parts from **RxJS**
+
+The first line
+```typescript
+const saveTodoEpic: Epic = (action$: ActionsObservable): Observable =>
+```
+defines an **Epic** which takes in as the first type argument the `type` for the `Actions` the epic takes in (*and returns*), in this case `IndexActions` which we defined earlier, and as the second argument the type of the **State** it takes in (*which isn't needed this time, so undefined will do*). An **Epic** is a function that takes in a [stream](https://en.wikipedia.org/wiki/Stream_(computing)) (*in this case of the type `ActionsObservable`*) which includes items of the `type` given as the first type argument and returns another stream (*in this case an [`Observable`](http://reactivex.io/documentation/observable.html), which `ActionsObservable` is based on*) which includes items of the same `type` as the input stream.
+> In JavaScript the convention is to append a `$` to all variables names that are **streams**, to let the developer know that they are dealing with one
+
+The second line
+```typescript
+ action$.ofType(SET_DONE)
+```
+utilizes the inbuilt function `ofType(key: string)` of `ActionsObservable`, which basically filters out all **actions** that do not have the `type`-property of the given argument.
+> A more verbose, but maybe a simpler to understand version would be to write
+```typescript
+action$.filter(action => action.type === SET_DONE)
+```
+> If you find yourself needing to understand the types of the components provided by **redux-observable** I suggest reading [this](https://github.com/redux-observable/redux-observable/blob/master/index.d.ts)
+
+The third and fourth line
+```typescript
+ .delay(1000)
+ .mapTo(saveTodoSuccess());
+```
+include the actual functionality of our **Epic**. In this case **after** we receive an **action** of the type `SET_DONE` we wait for 1 second (*`delay`takes milliseconds as argument*) and then we return an **action** of the type `SAVE_TODO_SUCCESS` (*in this case using [`mapTo`](http://reactivex.io/rxjs/class/es6/Observable.js~Observable.html#instance-method-mapTo) as we just want to return a new **Action***).
+> If you wanted to return multiple actions, say `SET_DONE_SUCCESS` and an imaginary `SEND_PUSH_NOTIFICATION` you could do it using [`mergeMap`](http://reactivex.io/rxjs/class/es6/Observable.js~Observable.html#instance-method-mergeMap), which is kind of like `flatMap`, like so:
+```typescript
+import 'rxjs/add/observable/from';
+import 'rxjs/add/operator/mergeMap';
+...
+ action$.ofType(SET_DONE)
+ .mergeMap((action: SetDoneAction) => Observable.from([
+ setDoneSuccess(action.payload),
+ // SEND_PUSH_NOTIFICATION,
+ // OTHER ACTIONS,
+ ]));
+```
+
+The other **Epic** is otherwirse similar, but it uses [`map`](http://reactivex.io/rxjs/class/es6/Observable.js~Observable.html#instance-method-map)
+```typescript
+ .delay(1000)
+ .map((action: SetDoneAction) => setDoneSuccess(action.payload));
+```
+to return an action of the type `SET_DONE_SUCCESS`, using the payload of the incoming action.
+
+> If you wanted to do an AJAX call, you would go about it like this:
+```typescript
+import { ajax } from 'rxjs/observable/dom/ajax';
+...
+ action$.ofType(AJAX_CALL).mergeMap((action: AjaxCallAction) =>
+ // For a get JSON call
+ ajax.getJSON('url', { headers: 'go here' })
+ .map(response => someAction(response))
+ .catch(err => errorAction(err)));
+ // For all other calls, just select the correct verb
+ ajax.post('url', payload, { headers: 'go here' })
+ .map(response => someAction(response))
+ .catch(err => errorAction(err));
+```
+> **Redux-observable** is built upon [RxJS](http://reactivex.io/), the JavaScript implemention of **ReactiveX** and most issues you will run into will be **RxJS** issues
+
+---
+
+Finally we define the rest of our business logic, a.k.a. the **reducer** itself
+```typescript
+const IndexReducer = (state: IndexState = new IndexState(), action: IndexActions = DefaultAction): IndexState => {
+ switch (action.type) {
+ case SET_TITLE:
+ return { ...state, title: action.payload };
+ case SAVE_TODO:
+ return { ...state, loading: true };
+ case SAVE_TODO_SUCCESS:
+ return {
+ ...state,
+ title: '',
+ todos: state.todos.concat(new Todo(state.todos.length + 1, state.title)),
+ loading: false,
+ };
+ case SET_DONE:
+ return { ...state, loading: true };
+ case SET_DONE_SUCCESS:
+ return {
+ ...state,
+ todos: state.todos.map(t => t.id === action.payload ? t.setDone() : t),
+ loading: false,
+ };
+ default:
+ return state;
+ }
+};
+```
+for which I suggest to break from the **redux-ducks** pattern by using the naming convention of `[Pagename]Reducer`. The important thing to remember with **reducers** is that they have to be [functional](https://en.wikipedia.org/wiki/Functional_programming), a.k.a. they are not allowed to mutate the incoming information.
+
+On the first line we define the signature of our `IndexReducer`
+```typescript
+const IndexReducer = (state: IndexState = new IndexState(), action: IndexActions = DefaultAction): IndexState =>
+```
+where we define it to take to parameters (*as all **reducers***), our `IndexState` (*with a default for the empty state*) and an action. `IndexReducer` will also return an `IndexState` (*as all **reducers***).
+
+Next we do the actual logic which all **reducers** are built upon
+```typescript
+ switch (action.type) {
+ case SET_TITLE:
+ return { ...state, title: action.payload };
+ case SAVE_TODO:
+ return { ...state, loading: true };
+ case SAVE_TODO_SUCCESS:
+ return {
+ ...state,
+ title: '',
+ todos: state.todos.concat(new Todo(state.todos.length + 1, state.title)),
+ loading: false,
+ };
+ case SET_DONE:
+ return { ...state, loading: true };
+ case SET_DONE_SUCCESS:
+ return {
+ ...state,
+ todos: state.todos.map(t => t.id === action.payload ? t.setDone() : t),
+ loading: false,
+ };
+ default:
+ return state;
+ }
+```
+which is a [`switch`](https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Statements/switch)-statement over the type-property of the incoming **action**. In each `case` we do something (*except the `default`-one, where you traditionally just return the incoming **state***) to add value to that **action**, such as setting the `title` to the `payload` in the **action** in case the **action** is a `SET_TITLE`-action. Notice how we are using the [spread syntax](https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Operators/Spread_operator) to immutably create a new version of the state, thus holding true to the immutability of **reducers**.
+> Other options are to use [`Object.assign({}, ...)`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/assign) or [Immutable](https://facebook.github.io/immutable-js/)
+
+### Connecting the reducer
+
+Remember our [root-reducer](/REDUX.md#reducer)? Now we connect our `IndexReducer` to it.
+
+First the **reducer** itself
+```typescript
+import { combineReducers } from 'redux';
+import IndexReducer from '../modulex/index/IndexReducer';
+
+const reducer = combineReducers({
+ index: IndexReducer,
+});
+```
+where we add the `IndexReducer` under the key `index`, which is very important, as when `combineReducers` combines included **reducers** it will put their specific state under the key given, in the global **state**-object.
+
+Next we add the `IndexState` to our global `State`-class (*this is just to allow us to define the type and initialize it for tests later on*)
+```typescript
+import { IndexState } from '../modules/index/IndexReducer';
+
+export class State {
+ readonly index: IndexState = new IndexState();
+}
+```
+where we define that the global `State`-object has a property `index` of the type `IndexState` (*as our `combineReducer` already says, but we want to be explicit here*).
+
+Then we want to add our **Epics** into the global `epics` constant
+```typescript
+import { combineEpics } from 'redux-observable';
+import { IndexEpics } from '../modules/index/IndexReducer';
+
+export const epics = combineEpics(IndexEpics);
+```
+by including it as a parameter to `combineEpics`.
+
+Finally we add our `IndexActions` to the global `Actions`-type
+```typescript
+import { DefaultAction } from './utils';
+import { IndexActions } from '../modules/index/IndexReducer';
+
+export type Actions = DefaultAction | IndexActions;
+```
+where we say that `Actions` is a type where the value is either of a type of `DefaultAction` or one of the `IndexActions`.
diff --git a/docs/REDUX.md b/docs/REDUX.md
index b77d61b..2da6969 100644
--- a/docs/REDUX.md
+++ b/docs/REDUX.md
@@ -23,7 +23,7 @@ export const DefaultAction: DefaultAction = { type: '' };
### Reducer
-Now we will define our root-reducer in a file called `store.ts` inside the folder `redux`:
+Now we will define our root-reducer in a file called `reducer.ts` inside the folder `redux`:
```typescript
import { combineReducers } from 'redux';
import { combineEpics } from 'redux-observable';
diff --git a/docs/VIEWS.md b/docs/VIEWS.md
index 54709c6..06d4353 100644
--- a/docs/VIEWS.md
+++ b/docs/VIEWS.md
@@ -2,7 +2,7 @@
Now we are ready to start working towards the beef of the application: different pages (or views).
-### Begin
+### IndexView
We will begin by creating a file called `IndexView.tsx` (*remember that 'x' in the end of the file type means that it contains [jsx](https://facebook.github.io/react/docs/jsx-in-depth.html)*) inside a folder called `index` inside the `components`-folder:
> All of our pages will be inside folders named after the page, in this case **Index** and the view will be named `[Pagename]View.tsx`
diff --git a/src/modules/index/IndexReducer.ts b/src/modules/index/IndexReducer.ts
index ed3b7d2..8296c4a 100644
--- a/src/modules/index/IndexReducer.ts
+++ b/src/modules/index/IndexReducer.ts
@@ -1,6 +1,4 @@
-import { MiddlewareAPI } from 'redux';
import { Observable } from 'rxjs/observable';
-import { ajax } from 'rxjs/observable/dom/ajax';
import 'rxjs/add/operator/delay';
import 'rxjs/add/operator/map';
import 'rxjs/add/operator/mapTo';
@@ -50,6 +48,8 @@ export const setDoneEpic: Epic = (action$: ActionsObser
.delay(testDelay)
.map((action: SetDoneAction) => setDoneSuccess(action.payload));
+export const IndexEpics = combineEpics(saveTodoEpic, setDoneEpic);
+
const IndexReducer = (state: IndexState = new IndexState(), action: IndexActions = DefaultAction): IndexState => {
switch (action.type) {
case SET_TITLE:
@@ -76,6 +76,4 @@ const IndexReducer = (state: IndexState = new IndexState(), action: IndexActions
}
};
-export const IndexEpics = combineEpics(saveTodoEpic, setDoneEpic);
-
export default IndexReducer;