-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Created a redux flash messages library
- Loading branch information
Showing
15 changed files
with
820 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
{ | ||
"presets": ["es2015", "react"], | ||
"plugins": [ | ||
"transform-object-rest-spread", | ||
"transform-async-to-generator", | ||
["transform-runtime", { | ||
"polyfill": false, | ||
"regenerator": true | ||
}], | ||
"transform-flow-strip-types" | ||
] | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
[ignore] | ||
lib/ | ||
|
||
[include] | ||
|
||
[libs] | ||
|
||
[options] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,18 @@ | ||
# See https://help.github.com/ignore-files/ for more about ignoring files. | ||
|
||
# Build output | ||
/lib | ||
|
||
# dependencies | ||
/node_modules | ||
|
||
# testing | ||
/coverage | ||
|
||
# misc | ||
.DS_Store | ||
.env | ||
npm-debug.log* | ||
yarn-debug.log* | ||
yarn-error.log* | ||
.vscode |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
tests | ||
.babelrc | ||
.vscode | ||
coverage | ||
.flowconfig | ||
src |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
Copyright 2016-2017 42BV (http://www.42.nl) | ||
|
||
Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at | ||
|
||
http://www.apache.org/licenses/LICENSE-2.0 | ||
Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,207 @@ | ||
# About | ||
|
||
This library makes it easy to create flash messages and to store them in a Redux store. | ||
|
||
What makes this project a little different from most flash message libraries is that it is UI agnostic. This library does not render the FlashMessages for you it only stores them! | ||
|
||
# Installation | ||
|
||
`npm install redux-flash-messages --save` | ||
|
||
# Getting started. | ||
|
||
We assume you have a working Redux project, if you do not yet have Redux add Redux to your project by following the Redux's instructions. | ||
|
||
First install the following dependencies in the package.json: | ||
|
||
1. "react-redux": "5.0.3", | ||
2. "redux": "3.6.0", | ||
|
||
Now add the flash-message-reducer to your rootReducer for example: | ||
|
||
```JavaScript | ||
// @flow | ||
|
||
import { combineReducers } from 'redux'; | ||
import { reducer as formReducer } from 'redux-form'; | ||
|
||
import type { FlashMessageStore } from '../jarb-redux-form'; | ||
import { flashMessage } from '../jarb-redux-form'; | ||
|
||
export type Store = { | ||
flashMessage: FlashMessageStore | ||
}; | ||
|
||
// Use ES6 object literal shorthand syntax to define the object shape | ||
const rootReducer = combineReducers({ | ||
flashMessage | ||
}); | ||
|
||
export default rootReducer; | ||
``` | ||
|
||
This should add the FlashMessageStore to Redux, which will store | ||
the flash messages. | ||
|
||
Next you have to configure the flashMessages module: | ||
|
||
```JavaScript | ||
import { createStore } from 'redux'; | ||
import { configureFlashMessages } from 'redux-flash-messages'; | ||
|
||
export const store = createStore( | ||
rootReducer, | ||
); | ||
|
||
configureFlashMessages({ | ||
// The dispatch function for the Redux store. | ||
dispatch: store.dispatch | ||
}); | ||
``` | ||
|
||
The redux-flash-messages module must be configured before the application is rendered. | ||
|
||
# Rendering flash messages | ||
|
||
Next we need to render the flash messages from the Redux store. How you do this is entirely up to you, but here is a small example: | ||
|
||
```JavaScript | ||
// @flow | ||
|
||
import React, { Component } from 'react'; | ||
import { connect } from 'react-redux'; | ||
|
||
import type { Store } from '../../../redux/root-reducer'; | ||
import type { Dispatch } from '../../../redux/models'; | ||
|
||
import type { FlashMessage as FlashMessageShape } from 'redux-flash-messages'; | ||
import { removeFlashMessage } from 'redux-flash-messages'; | ||
|
||
import './FlashMessage.css'; | ||
|
||
type Props = { | ||
messages: Array<FlashMessageShape>, | ||
dispatch: Dispatch | ||
}; | ||
|
||
export class FlashMessage extends Component<void, Props, void> { | ||
|
||
onFlashMessageClick(flashMessage: FlashMessageShape) { | ||
/* | ||
Make sure the onClick is called when a user clicks | ||
on the flash message. | ||
Otherwise callbacks on Flash Messages will not work. | ||
*/ | ||
flashMessage.onClick(flashMessage); | ||
|
||
// This implementation deletes the flash message when it is clicked. | ||
this.props.dispatch(removeFlashMessage(flashMessage.id)); | ||
} | ||
|
||
render() { | ||
const messages = this.props.messages; | ||
|
||
return ( | ||
<div> | ||
{ messages.map((message) => this.renderMessage(message))} | ||
</div> | ||
); | ||
} | ||
|
||
/* | ||
This renders a rather simple flash message. | ||
But you could and should use the 'type' property to | ||
render the flash message in a different style for each 'type'. | ||
*/ | ||
renderMessage(message: FlashMessageShape) { | ||
return ( | ||
<div | ||
key={ message.id } | ||
className={ `flash-message ${message.type}`} | ||
onClick={ () => this.onFlashMessageClick(message) } | ||
> | ||
{ message.text } | ||
</div> | ||
); | ||
} | ||
} | ||
|
||
export default connect((store: Store) => { | ||
return { | ||
messages: store.flashMessage.messages | ||
}; | ||
})(FlashMessage); | ||
``` | ||
|
||
Where the contents of 'FlashMessage.css' is: | ||
|
||
```CSS | ||
.flash-message { | ||
position: absolute; | ||
width: 100%; | ||
height: 50px; | ||
text-align: center; | ||
z-index: 9000; | ||
background-color: white; | ||
border: black solid 2px; | ||
padding: 12.5px 0; | ||
} | ||
``` | ||
|
||
# Sending flash messages | ||
|
||
Now that we can see the flash messages we can use the following convenience methods to send flash messages: | ||
|
||
```JavaScript | ||
import { addError, addWarning, addSuccess, addInfo, addApocalypse } from '../src/service'; | ||
|
||
// Renders a message for 10000 milliseconds | ||
addError({ text: 'Epic error', data: { age: 12 }, onClick: (flashMessage) => { | ||
console.log('I was clicked'); | ||
console.log(flashMessage); | ||
}}); | ||
|
||
// Renders a message for 7000 milliseconds | ||
addWarning({ text: 'Epic warning', data: { tree: 'house' }, onClick: (flashMessage) => { | ||
console.log('I was clicked'); | ||
console.log(flashMessage); | ||
}}); | ||
|
||
// Renders a message for 2000 milliseconds | ||
addSuccess({ text: 'Epic success', data: { win: true }, onClick: (flashMessage) => { | ||
console.log('I was clicked'); | ||
console.log(flashMessage); | ||
}}); | ||
|
||
// Renders a message for 5000 milliseconds | ||
addInfo({ text: 'Epic info', data: { yo: 'man' }, onClick: (flashMessage) => { | ||
console.log('I was clicked'); | ||
console.log(flashMessage); | ||
}}); | ||
|
||
// Renders a message which is not automatically removed | ||
addApocalypse({ text: 'TOTAL ANNIHILATION', data: { fail: true }, onClick: (flashMessage) => { | ||
console.log('I was clicked'); | ||
console.log(flashMessage); | ||
}}); | ||
``` | ||
|
||
The `onClick` and the `data` keys are optional. The `data` | ||
key can be used to send whatever `data` you want to the | ||
component which renders the flash message. | ||
|
||
# Creating a custom flash message type. | ||
|
||
If the default types are not enough you can always create your own flash message creator: | ||
|
||
You do this by calling `addFlashMessageOfType` manually. | ||
|
||
```JavaScript | ||
import { addFlashMessageOfType } from '../src/service'; | ||
|
||
export function addNotice({ text, onClick, data }: FlashMessageConfig) { | ||
addFlashMessageOfType('NOTICE', 1000, text, onClick, data); | ||
} | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,53 @@ | ||
{ | ||
"name": "redux-flash-messages", | ||
"version": "0.0.1", | ||
"description": "Storing flash messages and removing them via Redux.", | ||
"files": [ | ||
"lib" | ||
], | ||
"main": "lib/index.js", | ||
"repository": { | ||
"type": "git", | ||
"url": "git+https://github.com/42BV/redux-flash-messages.git" | ||
}, | ||
"keywords": [ | ||
"redux", | ||
"flash-messages" | ||
], | ||
"author": "Maarten Hus", | ||
"license": "ISC", | ||
"bugs": { | ||
"url": "https://github.com/42BV/redux-flash-messages/issues" | ||
}, | ||
"homepage": "https://github.com/42BV/redux-flash-messages#readme", | ||
"peerDependencies": { | ||
"redux": "^3.6.0" | ||
}, | ||
"devDependencies": { | ||
"babel": "6.23.0", | ||
"babel-cli": "6.24.0", | ||
"babel-jest": "19.0.0", | ||
"babel-plugin-transform-async-to-generator": "6.22.0", | ||
"babel-plugin-transform-flow-strip-types": "6.22.0", | ||
"babel-plugin-transform-object-rest-spread": "6.23.0", | ||
"babel-plugin-transform-runtime": "6.23.0", | ||
"babel-preset-es2015": "6.22.0", | ||
"babel-preset-react": "6.23.0", | ||
"babel-runtime": "6.23.0", | ||
"flow-bin": "0.39.0", | ||
"flow-copy-source": "1.1.0", | ||
"jest": "19.0.2", | ||
"react": "15.4.2", | ||
"react-addons-test-utils": "15.4.2", | ||
"react-dom": "15.4.2", | ||
"regenerator-runtime": "0.10.3" | ||
}, | ||
"scripts": { | ||
"test": "jest test", | ||
"coverage": "npm test -- --coverage", | ||
"flow": "flow", | ||
"prepublish": "npm run flow && npm test && npm run babel-prepublish && npm run flow-prepublish", | ||
"babel-prepublish": "babel src/ -d lib", | ||
"flow-prepublish": "flow-copy-source src lib" | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,31 @@ | ||
// @flow | ||
|
||
export type Config = { | ||
// The dispatch function for the Redux store. | ||
dispatch: () => void, | ||
}; | ||
|
||
let config: Config | null = null; | ||
|
||
/** | ||
* Configures the FlashMessages libary. | ||
* | ||
* @param {Config} The new configuration | ||
*/ | ||
export function configureFlashMessages(c: Config) { | ||
config = c; | ||
} | ||
|
||
/** | ||
* Either returns the a Config or throws an error when the | ||
* config is not yet initialized. | ||
* | ||
* @returns The Config | ||
*/ | ||
export function getConfig(): Config { | ||
if (config === null) { | ||
throw new Error('The flash message service is not initialized.'); | ||
} else { | ||
return config; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
// @flow | ||
|
||
import type { FlashMessage } from './models'; | ||
|
||
type Action = { | ||
type: string, | ||
payload: any | ||
}; | ||
|
||
export const ADD_FLASH_MESSAGE = 'ADD_FLASH_MESSAGE'; | ||
export const REMOVE_FLASH_MESSAGE = 'REMOVE_MESSAGE'; | ||
|
||
export type FlashMessageStore = { | ||
messages: Array<FlashMessage> | ||
}; | ||
|
||
export const initialState: FlashMessageStore = { | ||
messages: [], | ||
}; | ||
|
||
export function flashMessage(state: FlashMessageStore = initialState, action: Action): FlashMessageStore { | ||
switch(action.type) { | ||
case ADD_FLASH_MESSAGE: { | ||
const messages = [...state.messages, action.payload.flashMessage]; | ||
return { ...state, messages}; | ||
} | ||
|
||
case REMOVE_FLASH_MESSAGE: { | ||
const flashMessageId = action.payload.flashMessageId; | ||
|
||
const messages = state.messages.filter((f) => flashMessageId !== f.id); | ||
return { ...state, messages }; | ||
} | ||
|
||
default: { | ||
return state; | ||
} | ||
} | ||
} | ||
|
||
export function addFlashMessage(flashMessage: FlashMessage): Action { | ||
return { type: ADD_FLASH_MESSAGE, payload: { flashMessage } }; | ||
} | ||
|
||
export function removeFlashMessage(flashMessageId: number): Action { | ||
return { type: REMOVE_FLASH_MESSAGE, payload: { flashMessageId } }; | ||
} |
Oops, something went wrong.