Commit a3cf92a7 authored by Florent Chehab's avatar Florent Chehab
Browse files

Automatic generation of actions and reducers for Redux

parent adc1d2fe
let swig = require('swig');
let fs = require('fs');
let path = require('path');
let saving_dir = path.normalize(path.dirname(__filename) + "/../src/generated/")
if (!fs.existsSync(saving_dir)){
fs.mkdirSync(saving_dir);
}
let templates_dir = path.dirname(__filename) + '/templates/';
let templates = [
'action-types',
'actions',
'reducers'
]
let config = [
{
NAME: 'UNIVERSITIES',
name: 'universities'
}, {
NAME: 'COUNTRIES',
name: 'countries'
}
]
templates.forEach(function (filename) {
let template = swig.compileFile(templates_dir + filename + '.tpl');
let output = "";
config.forEach(function (obj) {
output += template(obj) + "\n\n";
})
fs.writeFile(saving_dir + filename + ".js", output, function (err) {
if (err) {
return console.log(err);
};
});
});
export const {{NAME}}_HAS_ERROR = '{{NAME}}_HAS_ERROR'
export const {{NAME}}_IS_LOADING = '{{NAME}}_IS_LOADING'
export const {{NAME}}_FETCH_DATA_SUCCESS = '{{NAME}}_FETCH_DATA_SUCCESS'
export const {{NAME}}_INVALIDATED = '{{NAME}}_INVALIDATED'
import { import {
COUNTRIES_HAS_ERROR, {{NAME}}_HAS_ERROR,
COUNTRIES_IS_LOADING, {{NAME}}_IS_LOADING,
COUNTRIES_FETCH_DATA_SUCCESS, {{NAME}}_FETCH_DATA_SUCCESS,
COUNTRIES_INVALIDATED {{NAME}}_INVALIDATED
} from "../constants/action-types"; } from "./action-types";
export function countriesHasError(bool) { export function {{name}}HasError(bool) {
return { return {
type: COUNTRIES_HAS_ERROR, type: {{NAME}}_HAS_ERROR,
hasError: bool hasError: bool
}; };
} }
export function countriesIsLoading(bool) { export function {{name}}IsLoading(bool) {
return { return {
type: COUNTRIES_IS_LOADING, type: {{NAME}}_IS_LOADING,
isLoading: bool isLoading: bool
}; };
} }
export function countriesInvalidated(bool) { export function {{name}}Invalidated(bool) {
return { return {
type: COUNTRIES_INVALIDATED, type: {{NAME}}_INVALIDATED,
invalidated: bool invalidated: bool
}; };
} }
export function countriesFetchDataSuccess(countries) { export function {{name}}FetchDataSuccess({{name}}) {
countriesInvalidated(false) {{name}}Invalidated(false)
return { return {
type: COUNTRIES_FETCH_DATA_SUCCESS, type: {{NAME}}_FETCH_DATA_SUCCESS,
countries, {{name}},
countriesFetchedAt: Date.now() {{name}}FetchedAt: Date.now()
}; };
} }
export function countriesFetchData(url) { export function {{name}}FetchData(url) {
return (dispatch) => { return (dispatch) => {
dispatch(countriesIsLoading(true)); dispatch({{name}}IsLoading(true));
fetch(url) fetch(url)
.then((response) => { .then((response) => {
...@@ -48,15 +48,15 @@ export function countriesFetchData(url) { ...@@ -48,15 +48,15 @@ export function countriesFetchData(url) {
throw Error(response.statusText); throw Error(response.statusText);
} }
dispatch(countriesIsLoading(false)); dispatch({{name}}IsLoading(false));
return response; return response;
}) })
.then((response) => response.json()) .then((response) => response.json())
.then((countries) => { .then(({{name}}) => {
dispatch(countriesInvalidated(false)); dispatch({{name}}Invalidated(false));
dispatch(countriesFetchDataSuccess(countries)); dispatch({{name}}FetchDataSuccess({{name}}));
}) })
.catch(() => dispatch(countriesHasError(true))); .catch(() => dispatch({{name}}HasError(true)));
}; };
} }
\ No newline at end of file
import { import {
COUNTRIES_HAS_ERROR, {{NAME}}_HAS_ERROR,
COUNTRIES_IS_LOADING, {{NAME}}_IS_LOADING,
COUNTRIES_FETCH_DATA_SUCCESS, {{NAME}}_FETCH_DATA_SUCCESS,
COUNTRIES_INVALIDATED {{NAME}}_INVALIDATED
} from "../constants/action-types"; } from "./action-types";
export function countriesHasError(state = false, action) { export function {{name}}HasError(state = false, action) {
switch (action.type) { switch (action.type) {
case COUNTRIES_HAS_ERROR: case {{NAME}}_HAS_ERROR:
return action.hasError; return action.hasError;
default: default:
...@@ -16,9 +16,9 @@ export function countriesHasError(state = false, action) { ...@@ -16,9 +16,9 @@ export function countriesHasError(state = false, action) {
} }
} }
export function countriesIsLoading(state = false, action) { export function {{name}}IsLoading(state = false, action) {
switch (action.type) { switch (action.type) {
case COUNTRIES_IS_LOADING: case {{NAME}}_IS_LOADING:
return action.isLoading; return action.isLoading;
default: default:
...@@ -26,9 +26,9 @@ export function countriesIsLoading(state = false, action) { ...@@ -26,9 +26,9 @@ export function countriesIsLoading(state = false, action) {
} }
} }
export function countriesInvalidated(state = false, action) { export function {{name}}Invalidated(state = false, action) {
switch (action.type) { switch (action.type) {
case COUNTRIES_INVALIDATED: case {{NAME}}_INVALIDATED:
return action.invalidated; return action.invalidated;
default: default:
...@@ -36,12 +36,12 @@ export function countriesInvalidated(state = false, action) { ...@@ -36,12 +36,12 @@ export function countriesInvalidated(state = false, action) {
} }
} }
export function countriesFetched(state = { countries: [], countriesFetchedAt: null }, action) { export function {{name}}Fetched(state = { {{name}}: [], {{name}}FetchedAt: null }, action) {
switch (action.type) { switch (action.type) {
case COUNTRIES_FETCH_DATA_SUCCESS: case {{NAME}}_FETCH_DATA_SUCCESS:
return { return {
countries: action.countries, {{name}}: action.{{name}},
fetchedAt: action.countriesFetchedAt fetchedAt: action.{{name}}FetchedAt
} }
default: default:
......
generated
\ No newline at end of file
import {
UNIVERSITIES_HAS_ERROR,
UNIVERSITIES_IS_LOADING,
UNIVERSITIES_FETCH_DATA_SUCCESS,
UNIVERSITIES_INVALIDATED
} from "../constants/action-types";
export function universitiesHasError(bool) {
return {
type: UNIVERSITIES_HAS_ERROR,
hasError: bool
};
}
export function universitiesIsLoading(bool) {
return {
type: UNIVERSITIES_IS_LOADING,
isLoading: bool
};
}
export function universitiesInvalidated(bool) {
return {
type: UNIVERSITIES_INVALIDATED,
invalidated: bool
};
}
export function universitiesFetchDataSuccess(universities) {
universitiesInvalidated(false)
return {
type: UNIVERSITIES_FETCH_DATA_SUCCESS,
universities,
universitiesFetchedAt: Date.now()
};
}
export function universitiesFetchData(url) {
return (dispatch) => {
dispatch(universitiesIsLoading(true));
fetch(url)
.then((response) => {
if (!response.ok) {
throw Error(response.statusText);
}
dispatch(universitiesIsLoading(false));
return response;
})
.then((response) => response.json())
.then((universities) => {
dispatch(universitiesInvalidated(false));
dispatch(universitiesFetchDataSuccess(universities));
})
.catch(() => dispatch(universitiesHasError(true)));
};
}
\ No newline at end of file
...@@ -28,7 +28,7 @@ import { ...@@ -28,7 +28,7 @@ import {
import { import {
countriesFetchData, countriesFetchData,
} from '../actions/countries'; } from '../generated/actions';
import PageMap from './pages/PageMap'; import PageMap from './pages/PageMap';
......
...@@ -6,7 +6,7 @@ import { Map, TileLayer, Marker, Popup, LayersControl, FeatureGroup, Circle, Lay ...@@ -6,7 +6,7 @@ import { Map, TileLayer, Marker, Popup, LayersControl, FeatureGroup, Circle, Lay
import { import {
universitiesFetchData, universitiesFetchData,
universitiesInvalidated universitiesInvalidated
} from '../../actions/universities'; } from '../../generated/actions';
......
...@@ -6,7 +6,7 @@ import { withStyles } from '@material-ui/core/styles'; ...@@ -6,7 +6,7 @@ import { withStyles } from '@material-ui/core/styles';
import { import {
universitiesInvalidated universitiesInvalidated
} from '../../actions/universities'; } from '../../generated/actions';
const styles = theme => ({ const styles = theme => ({
......
export const UNIVERSITIES_HAS_ERROR = 'UNIVERSITIES_HAS_ERROR'
export const UNIVERSITIES_IS_LOADING = 'UNIVERSITIES_IS_LOADING'
export const UNIVERSITIES_FETCH_DATA_SUCCESS = 'UNIVERSITIES_FETCH_DATA_SUCCESS'
export const UNIVERSITIES_INVALIDATED = 'UNIVERSITIES_INVALIDATED'
export const COUNTRIES_HAS_ERROR = 'COUNTRIES_HAS_ERROR'
export const COUNTRIES_IS_LOADING = 'COUNTRIES_IS_LOADING'
export const COUNTRIES_FETCH_DATA_SUCCESS = 'COUNTRIES_FETCH_DATA_SUCCESS'
export const COUNTRIES_INVALIDATED = 'COUNTRIES_INVALIDATED'
import { combineReducers } from 'redux'; import { combineReducers } from 'redux';
import { import {
universitiesFetched, universitiesFetched,
universitiesHasError, universitiesHasError,
universitiesIsLoading, universitiesIsLoading,
universitiesInvalidated universitiesInvalidated,
} from './universities';
import {
countriesFetched, countriesFetched,
countriesHasError, countriesHasError,
countriesIsLoading, countriesIsLoading,
countriesInvalidated countriesInvalidated
} from './countries'; } from '../generated/reducers';
const rootReducer = combineReducers({ const rootReducer = combineReducers({
......
import {
UNIVERSITIES_HAS_ERROR,
UNIVERSITIES_IS_LOADING,
UNIVERSITIES_FETCH_DATA_SUCCESS,
UNIVERSITIES_INVALIDATED
} from "../constants/action-types";
export function universitiesHasError(state = false, action) {
switch (action.type) {
case UNIVERSITIES_HAS_ERROR:
return action.hasError;
default:
return state;
}
}
export function universitiesIsLoading(state = false, action) {
switch (action.type) {
case UNIVERSITIES_IS_LOADING:
return action.isLoading;
default:
return state;
}
}
export function universitiesInvalidated(state = false, action) {
switch (action.type) {
case UNIVERSITIES_INVALIDATED:
return action.invalidated;
default:
return state;
}
}
export function universitiesFetched(state = { universities: [], universitiesFetchedAt: null }, action) {
switch (action.type) {
case UNIVERSITIES_FETCH_DATA_SUCCESS:
return {
universities: action.universities,
fetchedAt: action.universitiesFetchedAt
}
default:
return state;
}
}
\ No newline at end of file
...@@ -339,6 +339,12 @@ ...@@ -339,6 +339,12 @@
"integrity": "sha1-6GuBnGAs+IIa1jdBNpjx3sAhhHo=", "integrity": "sha1-6GuBnGAs+IIa1jdBNpjx3sAhhHo=",
"dev": true "dev": true
}, },
"amdefine": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz",
"integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU=",
"dev": true
},
"ansi-escapes": { "ansi-escapes": {
"version": "3.1.0", "version": "3.1.0",
"resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.1.0.tgz", "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.1.0.tgz",
...@@ -479,6 +485,12 @@ ...@@ -479,6 +485,12 @@
"integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=", "integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=",
"dev": true "dev": true
}, },
"async": {
"version": "0.2.10",
"resolved": "https://registry.npmjs.org/async/-/async-0.2.10.tgz",
"integrity": "sha1-trvgsGdLnXGXCMo43owjfLUmw9E=",
"dev": true
},
"async-each": { "async-each": {
"version": "1.0.1", "version": "1.0.1",
"resolved": "https://registry.npmjs.org/async-each/-/async-each-1.0.1.tgz", "resolved": "https://registry.npmjs.org/async-each/-/async-each-1.0.1.tgz",
...@@ -4928,6 +4940,24 @@ ...@@ -4928,6 +4940,24 @@
"mimic-fn": "^1.0.0" "mimic-fn": "^1.0.0"
} }
}, },
"optimist": {
"version": "0.6.1",
"resolved": "https://registry.npmjs.org/optimist/-/optimist-0.6.1.tgz",
"integrity": "sha1-2j6nRob6IaGaERwybpDrFaAZZoY=",
"dev": true,
"requires": {
"minimist": "~0.0.1",
"wordwrap": "~0.0.2"
},
"dependencies": {
"wordwrap": {
"version": "0.0.3",
"resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.3.tgz",
"integrity": "sha1-o9XabNXAvAAI03I0u68b7WMFkQc=",
"dev": true
}
}
},
"optionator": { "optionator": {
"version": "0.8.2", "version": "0.8.2",
"resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz", "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz",
...@@ -6347,6 +6377,69 @@ ...@@ -6347,6 +6377,69 @@
"has-flag": "^3.0.0" "has-flag": "^3.0.0"
} }
}, },
"swig": {
"version": "1.4.2",
"resolved": "https://registry.npmjs.org/swig/-/swig-1.4.2.tgz",
"integrity": "sha1-QIXKBFM2kQS11IPihBs5t64aq6U=",
"dev": true,
"requires": {
"optimist": "~0.6",
"uglify-js": "~2.4"
},
"dependencies": {
"camelcase": {
"version": "1.2.1",
"resolved": "https://registry.npmjs.org/camelcase/-/camelcase-1.2.1.tgz",
"integrity": "sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk=",
"dev": true
},
"decamelize": {
"version": "1.2.0",
"resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz",
"integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=",
"dev": true
},
"source-map": {
"version": "0.1.34",
"resolved": "https://registry.npmjs.org/source-map/-/source-map-0.1.34.tgz",
"integrity": "sha1-p8/omux7FoLDsZjQrPtH19CQVms=",
"dev": true,
"requires": {
"amdefine": ">=0.0.4"
}
},
"uglify-js": {
"version": "2.4.24",
"resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.4.24.tgz",
"integrity": "sha1-+tV1XB4Vd2WLsG/5q25UjJW+vW4=",
"dev": true,
"requires": {
"async": "~0.2.6",
"source-map": "0.1.34",
"uglify-to-browserify": "~1.0.0",
"yargs": "~3.5.4"
}
},
"wordwrap": {
"version": "0.0.2",
"resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.2.tgz",
"integrity": "sha1-t5Zpu0LstAn4PVg8rVLKF+qhZD8=",
"dev": true
},
"yargs": {
"version": "3.5.4",
"resolved": "https://registry.npmjs.org/yargs/-/yargs-3.5.4.tgz",
"integrity": "sha1-2K/49mXpTDS9JZvevRv68N3TU2E=",
"dev": true,
"requires": {
"camelcase": "^1.0.2",
"decamelize": "^1.0.0",
"window-size": "0.1.0",
"wordwrap": "0.0.2"
}
}
}
},
"symbol-observable": { "symbol-observable": {
"version": "1.0.4", "version": "1.0.4",
"resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-1.0.4.tgz", "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-1.0.4.tgz",
...@@ -6536,6 +6629,12 @@ ...@@ -6536,6 +6629,12 @@
} }
} }
}, },
"uglify-to-browserify": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/uglify-to-browserify/-/uglify-to-browserify-1.0.2.tgz",
"integrity": "sha1-bgkk1r2mta/jSeOabWMoUKD4grc=",
"dev": true
},
"uglifyjs-webpack-plugin": { "uglifyjs-webpack-plugin": {
"version": "1.3.0", "version": "1.3.0",
"resolved": "https://registry.npmjs.org/uglifyjs-webpack-plugin/-/uglifyjs-webpack-plugin-1.3.0.tgz", "resolved": "https://registry.npmjs.org/uglifyjs-webpack-plugin/-/uglifyjs-webpack-plugin-1.3.0.tgz",
...@@ -6851,6 +6950,12 @@ ...@@ -6851,6 +6950,12 @@
"integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=", "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=",
"dev": true "dev": true
}, },
"window-size": {