Skip to content

Commit

Permalink
[FEAT] Add rename dataset reducer (#1362)
Browse files Browse the repository at this point in the history
* Add rename dataset reducer
* Fix inter-test dependency with functions that mutate input
* Add reducer test
* Prettier fixes
* Drop unnecessary clones

Signed-off-by: Nick Rabinowitz <public@nickrabinowitz.com>

Co-authored-by: Nick Rabinowitz <public@nickrabinowitz.com>
  • Loading branch information
heshan0131 and nrabinowitz committed Dec 7, 2020
1 parent 027985a commit f33c76b
Show file tree
Hide file tree
Showing 10 changed files with 86 additions and 7 deletions.
9 changes: 9 additions & 0 deletions src/actions/vis-state-actions.d.ts
Expand Up @@ -243,6 +243,15 @@ export function updateVisData(
config: AddDataToMapPayload['config']
): Merge<UpdateVisDataUpdaterAction, {type: ActionTypes.UPDATE_VIS_DATA}>;

export type RenameDatasetUpdaterAction = {
dataId: string;
label: string;
};
export function renameDataset(
dataId: string,
label: string
): Merge<RenameDatasetUpdaterAction, {type: ActionTypes.RENAME_DATASET}>;

export type ToggleFilterAnimationUpdaterAction = {
idx;
};
Expand Down
17 changes: 17 additions & 0 deletions src/actions/vis-state-actions.js
Expand Up @@ -405,6 +405,23 @@ export function updateVisData(datasets, options, config) {
};
}

/**
* Rename an existing dataset in `visState`
* @memberof visStateActions
* @param dataId - ***required** Id of the dataset to update
* @param label - ***required** New name for the dataset
* @returns action
* @type {typeof import('./vis-state-actions').renameDataset}
* @public
*/
export function renameDataset(dataId, label) {
return {
type: ActionTypes.RENAME_DATASET,
dataId,
label
};
}

/**
* Start and end filter animation
* @memberof visStateActions
Expand Down
1 change: 1 addition & 0 deletions src/constants/action-types.d.ts
Expand Up @@ -28,6 +28,7 @@ export type ActionType = {
SHOW_DATASET_TABLE: string;
UPDATE_LAYER_BLENDING: string;
UPDATE_VIS_DATA: string;
RENAME_DATASET: string;
TOGGLE_FILTER_ANIMATION: string;
UPDATE_FILTER_ANIMATION_SPEED: string;
PLAY_ANIMATION: string;
Expand Down
1 change: 1 addition & 0 deletions src/constants/action-types.js
Expand Up @@ -80,6 +80,7 @@ const ActionTypes = {
SHOW_DATASET_TABLE: `${ACTION_PREFIX}SHOW_DATASET_TABLE`,
UPDATE_LAYER_BLENDING: `${ACTION_PREFIX}UPDATE_LAYER_BLENDING`,
UPDATE_VIS_DATA: `${ACTION_PREFIX}UPDATE_VIS_DATA`,
RENAME_DATASET: `${ACTION_PREFIX}RENAME_DATASET`,
TOGGLE_FILTER_ANIMATION: `${ACTION_PREFIX}TOGGLE_FILTER_ANIMATION`,
UPDATE_FILTER_ANIMATION_SPEED: `${ACTION_PREFIX}UPDATE_FILTER_ANIMATION_SPEED`,
PLAY_ANIMATION: `${ACTION_PREFIX}PLAY_ANIMATION`,
Expand Down
4 changes: 3 additions & 1 deletion src/processors/data-processor.js
Expand Up @@ -406,6 +406,7 @@ export function analyzerTypeToFieldType(aType) {

/**
* Process data where each row is an object, output can be passed to [`addDataToMap`](../actions/actions.md#adddatatomap)
* NOTE: This function may mutate input.
* @param rawData an array of row object, each object should have the same number of keys
* @returns dataset containing `fields` and `rows`
* @type {typeof import('./data-processor').processRowObject}
Expand Down Expand Up @@ -443,7 +444,8 @@ export function processRowObject(rawData) {
/**
* Process GeoJSON [`FeatureCollection`](http://wiki.geojson.org/GeoJSON_draft_version_6#FeatureCollection),
* output a data object with `{fields: [], rows: []}`.
* The data object can be wrapped in a `dataset` and pass to [`addDataToMap`](../actions/actions.md#adddatatomap)
* The data object can be wrapped in a `dataset` and passed to [`addDataToMap`](../actions/actions.md#adddatatomap)
* NOTE: This function may mutate input.
*
* @param rawData raw geojson feature collection
* @returns dataset containing `fields` and `rows`
Expand Down
4 changes: 4 additions & 0 deletions src/reducers/vis-state-updaters.d.ts
Expand Up @@ -430,6 +430,10 @@ export function updateVisDataUpdater(
state: VisState,
action: VisStateActions.UpdateVisDataUpdaterAction
): VisState;
export function renameDatasetUpdater(
state: VisState,
action: VisStateActions.RenameDatasetUpdaterAction
): VisState;
export function toggleFilterAnimationUpdater(
state: VisState,
action: VisStateActions.ToggleFilterAnimationUpdaterAction
Expand Down
25 changes: 25 additions & 0 deletions src/reducers/vis-state-updaters.js
Expand Up @@ -1305,6 +1305,31 @@ export const updateVisDataUpdater = (state, action) => {
};
/* eslint-enable max-statements */

/**
* Rename an existing dataset in `visState`
* @memberof visStateUpdaters
* @type {typeof import('./vis-state-updaters').renameDatasetUpdater}
* @public
*/
export function renameDatasetUpdater(state, action) {
const {dataId, label} = action;
const {datasets} = state;
const existing = datasets[dataId];
return existing
? {
...state,
datasets: {
...datasets,
[dataId]: {
...existing,
label
}
}
}
: // No-op if the dataset doesn't exist
state;
}

/**
* When a user clicks on the specific map closing icon
* the application will close the selected map
Expand Down
2 changes: 2 additions & 0 deletions src/reducers/vis-state.js
Expand Up @@ -105,6 +105,8 @@ const actionHandler = {

[ActionTypes.UPDATE_VIS_DATA]: visStateUpdaters.updateVisDataUpdater,

[ActionTypes.RENAME_DATASET]: visStateUpdaters.renameDatasetUpdater,

[ActionTypes.SET_FEATURES]: visStateUpdaters.setFeaturesUpdater,

[ActionTypes.DELETE_FEATURE]: visStateUpdaters.deleteFeatureUpdater,
Expand Down
23 changes: 20 additions & 3 deletions test/node/reducers/vis-state-test.js
Expand Up @@ -51,7 +51,7 @@ import {
fields as geojsonFields
} from 'test/fixtures/geojson';

import tripGeojson, {timeStampDomain} from 'test/fixtures/trip-geojson';
import tripGeojson, {timeStampDomain, tripDataInfo} from 'test/fixtures/trip-geojson';
import {mockPolygonFeature, mockPolygonFeature2, mockPolygonData} from 'test/fixtures/polygon';

// test helpers
Expand Down Expand Up @@ -1392,7 +1392,7 @@ test('#visStateReducer -> UPDATE_VIS_DATA.4.Geojson -> geojson data', t => {
const expectedLayerData = {
data: geojsonData.features.map((f, i) => ({
...f,
properties: {...f.properties, index: i}
properties: {...f.properties, TRIPS: f.properties.TRIPS || null, index: i}
}))
};

Expand All @@ -1410,7 +1410,7 @@ test('#visStateReducer -> UPDATE_VIS_DATA.4.Geojson -> geojson data', t => {
t.deepEqual(
initialState.layerData[0].data,
expectedLayerData.data,
'should save geojson to datasets'
'should save geojson to layer data'
);

t.end();
Expand Down Expand Up @@ -1963,6 +1963,23 @@ test('#visStateReducer -> setFilter.dynamicDomain & cpu', t => {
t.end();
});

test('#visStateReducer -> RENAME_DATASET', t => {
const initialState = StateWTripGeojson.visState;

t.equal(
initialState.datasets[tripDataInfo.id].label,
tripDataInfo.label,
'Initial label as expected'
);

const newLabel = 'New label!!!11';
const updated = reducer(initialState, VisStateActions.renameDataset(tripDataInfo.id, newLabel));

t.equal(updated.datasets[tripDataInfo.id].label, newLabel, 'Updated label as expected');

t.end();
});

test('#visStateReducer -> SET_FILTER.name', t => {
const oldState = StateWFilters.visState;
const oldFilter0 = oldState.filters[0];
Expand Down
7 changes: 4 additions & 3 deletions test/node/utils/data-processor-test.js
Expand Up @@ -22,6 +22,7 @@ import test from 'tape';
import sinon from 'sinon';
import {console as Console} from 'global/window';
import {DATA_TYPES} from 'type-analyzer';
import cloneDeep from 'lodash.clonedeep';

import testData, {
dataWithNulls,
Expand Down Expand Up @@ -118,7 +119,7 @@ test('Processor -> processCsvData', t => {
t.throws(() => processCsvData(''), 'should throw if csv is empty');

// load sample dataset csv as text
const {fields, rows} = processCsvData(testData);
const {fields, rows} = processCsvData(cloneDeep(testData));

t.equal(rows.length, testAllData.length, `should return ${testAllData.length} rows`);

Expand Down Expand Up @@ -188,7 +189,7 @@ test('Processor -> processCsv.wkt', t => {
});

test('Processor => processGeojson', t => {
const {fields, rows} = processGeojson(geojsonData);
const {fields, rows} = processGeojson(cloneDeep(geojsonData));

t.equal(fields.length, geojsonFields.length, 'should have same field length');
fields.forEach((f, i) => {
Expand All @@ -203,7 +204,7 @@ test('Processor => processGeojson', t => {
});

test('Processor => processGeojson: with style property', t => {
const {fields, rows} = processGeojson(geoJsonWithStyle);
const {fields, rows} = processGeojson(cloneDeep(geoJsonWithStyle));

t.deepEqual(fields, geoStyleFields, 'should preserve objects in geojson properties');
t.deepEqual(rows, geoStyleRows, 'should preserve objects in geojson properties');
Expand Down

0 comments on commit f33c76b

Please sign in to comment.