add archive

This commit is contained in:
sveisvei
2016-10-25 22:53:38 +02:00
committed by Ivar Conradi Østhus
parent fa01ebe2af
commit 223d0a1421
9 changed files with 163 additions and 38 deletions
@@ -0,0 +1,15 @@
import { connect } from 'react-redux';
import ListComponent from './archive-list-component';
import { fetchArchive, revive } from '../../store/archive-actions';
const mapStateToProps = (state) => {
const archive = state.archive.get('list').toArray(); // eslint-disable-line no-shadow
return {
archive,
};
};
const ArchiveListContainer = connect(mapStateToProps, { fetchArchive, revive })(ListComponent);
export default ArchiveListContainer;
@@ -0,0 +1,48 @@
import React, { Component } from 'react';
import { List, ListItem, ListSubHeader } from 'react-toolbox/lib/list';
import FontIcon from 'react-toolbox/lib/font_icon';
import Chip from 'react-toolbox/lib/chip';
import Switch from 'react-toolbox/lib/switch';
const ArchivedFeature = ({ feature, revive }) => {
const { name, description, enabled, strategies } = feature; // eslint-disable-line no-shadow
const actions = [
<div>{strategies && strategies.map(s => <Chip><small>{s.name}</small></Chip>)}</div>,
<FontIcon style={{ cursor: 'pointer' }} value="restore" onClick={() => revive(feature)} />,
];
const leftActions = [
<Switch disabled checked={enabled} />,
];
return (
<ListItem
key={name}
leftActions={leftActions}
rightActions={actions}
caption={name}
legend={(description && description.substring(0, 100)) || '-'}
/>
);
};
class ArchiveList extends Component {
componentDidMount () {
this.props.fetchArchive();
}
render () {
const { archive, revive } = this.props;
return (
<List ripple >
<ListSubHeader caption="Archive" />
{archive.length > 0 ?
archive.map((feature, i) => <ArchivedFeature key={i} feature={feature} revive={revive} />) :
<ListItem caption="No archived feature toggles" />}
</List>
);
}
}
export default ArchiveList;
@@ -10,6 +10,6 @@ const mapStateToProps = (state) => {
};
};
const StrategiesListContainer = connect(mapStateToProps, { fetchHistory })(ListComponent);
const HistoryListContainer = connect(mapStateToProps, { fetchHistory })(ListComponent);
export default StrategiesListContainer;
export default HistoryListContainer;
@@ -1,13 +1,7 @@
import React, { Component } from 'react';
import { List, ListItem, ListSubHeader, ListDivider } from 'react-toolbox/lib/list';
import FontIcon from 'react-toolbox/lib/font_icon';
import Chip from 'react-toolbox/lib/chip';
import { List, ListItem, ListSubHeader } from 'react-toolbox/lib/list';
class StrategiesListComponent extends Component {
static contextTypes = {
router: React.PropTypes.object,
}
class HistoryList extends Component {
componentDidMount () {
this.props.fetchHistory();
@@ -33,7 +27,7 @@ class StrategiesListComponent extends Component {
}
render () {
const { history } = this.props;
const { history } = this.props; // eslint-disable-line no-shadow
return (
<List ripple >
@@ -61,4 +55,4 @@ class StrategiesListComponent extends Component {
}
export default StrategiesListComponent;
export default HistoryList;
@@ -0,0 +1,36 @@
const URI = '/archive';
const headers = {
'Accept': 'application/json',
'Content-Type': 'application/json',
};
function throwIfNotSuccess (response) {
if (!response.ok) {
let error = new Error('API call failed');
error.status = response.status;
throw error;
}
return response;
}
function fetchAll () {
return fetch(`${URI}/features`)
.then(throwIfNotSuccess)
.then(response => response.json());
}
function revive (feature) {
return fetch(`${URI}/revive`, {
method: 'POST',
headers,
body: JSON.stringify(feature),
}).then(throwIfNotSuccess);
}
module.exports = {
fetchAll,
revive,
};
@@ -1,28 +1,6 @@
import React, { Component } from 'react';
import { Card, CardTitle, CardText } from 'react-toolbox';
import React from 'react';
import Archive from '../../component/archive/archive-container';
const render = () => <Archive />;
export default class Archive extends Component {
render () {
return (
<Card>
<CardTitle>Archived Feture Toggles</CardTitle>
<CardText>
<p>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam pharetra finibus
ullamcorper. Proin laoreet faucibus venenatis. Aenean quis leo finibus, maximus
nisi finibus, fringilla ex. Nam mollis congue orci eu consectetur. Aliquam a
massa quis tortor vestibulum lacinia. Phasellus nisi velit, mattis vel nulla
a, rhoncus porta dui. Vestibulum viverra augue in pellentesque tincidunt.
Aliquam rhoncus nunc ipsum, sed vehicula leo dictum in. Phasellus accumsan
elis sem, in ullamcorper nisi accumsan vitae. Nullam vitae consectetur mi,
sed vulputate augue. In quis augue tellus. Duis convallis cursus elit, in
interdum nisl pulvinar viverra. Sed vel ornare sapien, eu consectetur metus.
Vivamus at porta nisl. Nullam in aliquam nisl.
</p>
</CardText>
</Card>
);
}
};
export default render;
@@ -0,0 +1,33 @@
import api from '../data/archive-api';
export const REVIVE_TOGGLE = 'REVIVE_TOGGLE';
export const RECEIVE_ARCHIVE = 'RECEIVE_ARCHIVE';
export const ERROR_RECEIVE_ARCHIVE = 'ERROR_RECEIVE_ARCHIVE';
const receiveArchive = (json) => ({
type: RECEIVE_ARCHIVE,
value: json.features,
});
const reviveToggle = (archiveFeatureToggle) => ({
type: REVIVE_TOGGLE,
value: archiveFeatureToggle,
});
const errorReceiveArchive = (statusCode) => ({
type: ERROR_RECEIVE_ARCHIVE,
statusCode,
});
export function revive (featureToggle) {
return dispatch => api.revive(featureToggle)
.then(() => dispatch(reviveToggle(featureToggle)))
.catch(error => dispatch(errorReceiveArchive(error)));
}
export function fetchArchive () {
return dispatch => api.fetchAll()
.then(json => dispatch(receiveArchive(json)))
.catch(error => dispatch(errorReceiveArchive(error)));
}
@@ -0,0 +1,19 @@
import { List, Map as $Map } from 'immutable';
import { RECEIVE_ARCHIVE, REVIVE_TOGGLE } from './archive-actions';
function getInitState () {
return new $Map({ list: new List() });
}
const archiveStore = (state = getInitState(), action) => {
switch (action.type) {
case REVIVE_TOGGLE:
return state.update('list', (list) => list.remove(list.indexOf(action.value)));
case RECEIVE_ARCHIVE:
return state.set('list', new List(action.value));
default:
return state;
}
};
export default archiveStore;
@@ -3,12 +3,14 @@ import features from './feature-store';
import strategies from './strategy-store';
import input from './input-store';
import history from './history-store'; // eslint-disable-line
import archive from './archive-store';
const unleashStore = combineReducers({
features,
strategies,
input,
history,
archive,
});
export default unleashStore;