Skip to content

Instantly share code, notes, and snippets.

@MoonTahoe
Last active October 13, 2017 23:36
Show Gist options
  • Save MoonTahoe/1d43d9f9a7b5a684f6fb6421ef6bae54 to your computer and use it in GitHub Desktop.
Save MoonTahoe/1d43d9f9a7b5a684f6fb6421ef6bae54 to your computer and use it in GitHub Desktop.
Exercise: Redux Color Organizer
import C from './constants'
import { v4 } from 'uuid'
export const addColor = (title, color) =>
({
type: C.ADD_COLOR,
id: v4(),
title,
color,
timestamp: new Date().toString()
})
export const removeColor = id =>
({
type: C.REMOVE_COLOR,
id
})
export const rateColor = (id, rating) =>
({
type: C.RATE_COLOR,
id,
rating
})
export const sortColors = (sortBy="SORTED_BY_DATE") =>
({
type: C.SORT_COLORS,
sortBy
})
import { createStore, applyMiddleware } from 'redux'
import { color } from './store/reducers'
import { addColor, rateColor } from './actions'
const logger = store => next => action => {
console.log(action.type)
return next(action)
}
const alerter = store => next => action => {
alert(`dispatching ${action.type}`)
return next(action)
}
const stopper = store => next => action => {
console.log('nope')
}
const bgSetter = store => next => action => {
document.body.style.backgroundColor = action.color
return next(action)
}
const createStoreWithMiddleware = applyMiddleware(alerter, bgSetter, stopper)(createStore)
const store = createStoreWithMiddleware(color)
const render = state =>
document.body.innerHTML = `<pre>${JSON.stringify(state, null, 2)}</pre>`
render(store.getState())
store.subscribe(() => render(store.getState()))
store.dispatch(addColor("Big Blue", "#00F"))
const { id } = store.getState()
store.dispatch(rateColor(id, 5))
import C from '../constants'
import { createReducer } from 'redux-create-reducer'
export const color = createReducer({}, {
ADD_COLOR: (state, action) => ({
id: action.id,
title: action.title,
color: action.color,
timestamp: action.timestamp,
rating: 0
}),
RATE_COLOR: (state, action) =>
(state.id !== action.id) ?
state : { ...state, rating: action.rating }
})
export const colors = createReducer([], {
ADD_COLOR: (state, action) => [ ...state, color({}, action)],
RATE_COLOR: (state, action) => state.map(c => color(c, action)),
REMOVE_COLOR: (state, action) => state.filter(c => c.id !== action.id)
})
export const sort = createReducer("SORTED_BY_DATE", {
SORT_COLORS: (state, action) => action.sortBy
})
import C from '../constants'
import { color, colors, sort } from './reducers'
describe("color Reducer", () => {
it("ADD_COLOR success", () => {
const state = {}
const action = {
type: C.ADD_COLOR,
id: "111",
title: 'Test Teal',
color: '#90C3D4',
timestamp: new Date().toString()
}
const expected = {
id: "111",
title: 'Test Teal',
color: '#90C3D4',
timestamp: action.timestamp,
rating: 0
}
const result = color(state, action)
expect(result).toEqual(expected)
})
it("RATE_COLOR success", () => {
const state = {
id: "111",
title: 'Test Teal',
color: '#90C3D4',
timestamp: 'Sat Mar 12 2016 16:12:09 GMT-0800 (PST)',
rating: undefined
}
const action = {
type: C.RATE_COLOR,
id: "111",
rating: 3
}
const expected = {
id: "111",
title: 'Test Teal',
color: '#90C3D4',
timestamp: 'Sat Mar 12 2016 16:12:09 GMT-0800 (PST)',
rating: 3
}
const result = color(state, action)
expect(result).toEqual(expected)
})
})
describe("colors Reducer", () => {
it("ADD_COLOR success", () => {
const state = [
{
id: "111",
title: 'Test Teal',
color: '#90C3D4',
timestamp: 'Sat Mar 12 2016 16:12:09 GMT-0800 (PST)',
rating: 3
}
]
const action = {
type: C.ADD_COLOR,
id: "222",
title: 'Bright White',
color: '#FFFFFF',
timestamp: new Date().toString()
}
const expected = [
{
id: "111",
title: 'Test Teal',
color: '#90C3D4',
timestamp: 'Sat Mar 12 2016 16:12:09 GMT-0800 (PST)',
rating: 3
},
{
id: "222",
title: 'Bright White',
color: '#FFFFFF',
timestamp: action.timestamp,
rating: 0
}
]
const result = colors(state, action)
expect(result).toEqual(expected)
})
it("RATE_COLOR success", () => {
const state = [
{
id: "111",
title: 'Test Teal',
color: '#90C3D4',
timestamp: 'Sat Mar 12 2016 16:12:09 GMT-0800 (PST)',
rating: 3
},
{
id: "222",
title: 'Bright White',
color: '#FFFFFF',
timestamp: 'Sat Mar 12 2016 16:15:00 GMT-0800 (PST)',
rating: 0
}
]
const action = {
type: C.RATE_COLOR,
id: "222",
rating: 5
}
const expected = [
{
id: "111",
title: 'Test Teal',
color: '#90C3D4',
timestamp: 'Sat Mar 12 2016 16:12:09 GMT-0800 (PST)',
rating: 3
},
{
id: "222",
title: 'Bright White',
color: '#FFFFFF',
timestamp: 'Sat Mar 12 2016 16:15:00 GMT-0800 (PST)',
rating: 5
}
]
const actual = colors(state, action)
expect(actual).toEqual(expected)
})
it("REMOVE_COLOR success", () => {
const state = [
{
id: "111",
title: 'Test Teal',
color: '#90C3D4',
timestamp: 'Sat Mar 12 2016 16:12:09 GMT-0800 (PST)',
rating: 3
},
{
id: "222",
title: 'Bright White',
color: '#FFFFFF',
timestamp: 'Sat Mar 12 2016 16:15:00 GMT-0800 (PST)',
rating: 0
}
]
const action = {
type: C.REMOVE_COLOR,
id: "111"
}
const expected = [
{
id: "222",
title: 'Bright White',
color: '#FFFFFF',
timestamp: 'Sat Mar 12 2016 16:15:00 GMT-0800 (PST)',
rating: 0
}
]
const actual = colors(state, action)
expect(actual).toEqual(expected)
})
})
describe("sort Reducer", () => {
it("SORT_COLORS success", () => {
const state = {};
const action = {
type: C.SORT_COLORS,
sortBy: "SORTED_BY_RATING"
}
expect(sort(state, action)).toEqual("SORTED_BY_RATING")
})
})
{
"colors": [
{
"id": "8658c1d0-9eda-4a90-95e1-8001e8eb6036",
"title": "Ocean Blue",
"color": "#0070ff",
"rating": 3,
"timestamp": "Sat Mar 12 2016 16:12:09 GMT-0800 (PST)"
},
{
"id": "f9005b4e-975e-433d-a646-79df172e1dbb",
"title": "Tomato",
"color": "#d10012",
"rating": 2,
"timestamp": "Fri Mar 11 2016 12:00:00 GMT-0800 (PST)"
},
{
"id": "58d9caee-6ea6-4d7b-9984-65b145031979",
"title": "Lawn",
"color": "#67bf4f",
"rating": 1,
"timestamp": "Thu Mar 10 2016 01:11:12 GMT-0800 (PST)"
},
{
"id": "a5685c39-6bdc-4727-9188-6c9a00bf7f95",
"title": "Party Pink",
"color": "#ff00f7",
"rating": 5,
"timestamp": "Wed Mar 9 2016 03:26:00 GMT-0800 (PST)"
}
],
"sort": "SORTED_BY_DATE"
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment