Skip to content

Commit 4ee013b

Browse files
authored
re-introduce last-util fn for better typing (#41)
* re-introduce last-util fn for better typing * remove lodash.last
1 parent ccdc54b commit 4ee013b

File tree

8 files changed

+30
-37
lines changed

8 files changed

+30
-37
lines changed

package-lock.json

Lines changed: 0 additions & 14 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@
1616
"immer": "^6.0.1",
1717
"keycode": "^2.2.0",
1818
"lodash.get": "^4.4.2",
19-
"lodash.last": "^3.0.0",
2019
"node-fetch": "^2.6.0",
2120
"react": "^16.11.0",
2221
"react-dom": "^16.11.0",
@@ -60,7 +59,6 @@
6059
"@firebase/component": "^0.1.1",
6160
"@testing-library/react": "^9.3.2",
6261
"@types/lodash.get": "^4.4.6",
63-
"@types/lodash.last": "^3.0.6",
6462
"@types/react-router-dom": "^5.1.2",
6563
"husky": "^3.0.9",
6664
"jest-fetch-mock": "^3.0.1",

src/components/Firestore/DocumentEditor/index.tsx

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,6 @@
1515
*/
1616

1717
import React, { useEffect } from 'react';
18-
import last from 'lodash.last';
1918
import { TextField } from '@rmwc/textfield';
2019

2120
import * as actions from './actions';
@@ -26,7 +25,7 @@ import {
2625
DocumentProvider,
2726
} from './store';
2827
import { FirestoreMap } from '../models';
29-
import { isMap, isArray, getFieldType } from '../utils';
28+
import { isMap, isArray, lastFieldName, getFieldType } from '../utils';
3029

3130
/** Entry point for a Document/Field editor */
3231
const DocumentEditor: React.FC<{
@@ -89,7 +88,7 @@ const NestedEditor: React.FC<{ path: string[] }> = ({ path }) => {
8988
return (
9089
<>
9190
<div style={{ display: 'flex' }}>
92-
<TextField readOnly value={last(path)} placeholder="Field" />
91+
<TextField readOnly value={lastFieldName(path)} placeholder="Field" />
9392
<TextField readOnly value={getFieldType(state)} placeholder="Type" />
9493
<TextField
9594
value={JSON.stringify(state)}

src/components/Firestore/DocumentEditor/store.tsx

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,12 +16,11 @@
1616

1717
import React from 'react';
1818
import get from 'lodash.get';
19-
import last from 'lodash.last';
2019
import produce from 'immer';
2120
import { Action, createReducer } from 'typesafe-actions';
2221

2322
import * as actions from './actions';
24-
import { isMap, isArray, getParentPath } from '../utils';
23+
import { isMap, isArray, lastFieldName, getParentPath } from '../utils';
2524
import { FirestoreAny, FirestoreMap } from '../models';
2625

2726
const reducer = createReducer<FirestoreMap, Action>({})
@@ -33,7 +32,7 @@ const reducer = createReducer<FirestoreMap, Action>({})
3332
produce((draft, { payload }) => {
3433
const parent = get(draft, getParentPath(payload.path)) || draft;
3534
if (isMap(parent)) {
36-
parent[last(payload.path) as string] = payload.value;
35+
parent[lastFieldName(payload.path)] = payload.value;
3736
} else if (isArray(parent)) {
3837
parent.push(payload.value);
3938
}
@@ -44,9 +43,9 @@ const reducer = createReducer<FirestoreMap, Action>({})
4443
produce((draft, { payload }) => {
4544
const parent = get(draft, getParentPath(payload.path)) || draft;
4645
if (isMap(parent)) {
47-
parent[last(payload.path) as string] = payload.value;
46+
parent[lastFieldName(payload.path)] = payload.value;
4847
} else if (isArray(parent)) {
49-
parent[Number(last(payload.path))] = payload.value;
48+
parent[Number(lastFieldName(payload.path))] = payload.value;
5049
} else {
5150
return payload.value;
5251
}
@@ -57,9 +56,9 @@ const reducer = createReducer<FirestoreMap, Action>({})
5756
produce((draft, { payload }) => {
5857
const parent = get(draft, getParentPath(payload)) || draft;
5958
if (isMap(parent)) {
60-
delete parent[last(payload) as string];
59+
delete parent[lastFieldName(payload)];
6160
} else if (isArray(parent)) {
62-
parent.splice(Number(last(payload)), 1);
61+
parent.splice(Number(lastFieldName(payload)), 1);
6362
}
6463
})
6564
);

src/components/Firestore/DocumentPreview/FieldPreview.tsx

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -18,12 +18,17 @@ import React, { useState } from 'react';
1818
import { firestore } from 'firebase';
1919
import { ListItem, ListItemMeta } from '@rmwc/list';
2020
import { IconButton } from '@rmwc/icon-button';
21-
import last from 'lodash.last';
2221

2322
import { updateField, deleteField } from './api';
2423
import InlineEditor from './InlineEditor';
2524
import { useDocumentState, useFieldState } from './store';
26-
import { getFieldType, isPrimitive, isMap, isArray } from '../utils';
25+
import {
26+
getFieldType,
27+
isPrimitive,
28+
isMap,
29+
isArray,
30+
lastFieldName,
31+
} from '../utils';
2732

2833
const FieldPreview: React.FC<{
2934
path: string[];
@@ -63,7 +68,7 @@ const FieldPreview: React.FC<{
6368

6469
return isEditing ? (
6570
<InlineEditor
66-
value={{ [last(path) as string]: state }}
71+
value={{ [lastFieldName(path)]: state }}
6772
path={path}
6873
onCancel={() => {
6974
setIsEditing(false);
@@ -77,7 +82,7 @@ const FieldPreview: React.FC<{
7782
<>
7883
<ListItem onClick={() => setIsExpanded(!isExpanded)}>
7984
<span>
80-
{last(path)}:{JSON.stringify(state)}
85+
{lastFieldName(path)}:{JSON.stringify(state)}
8186
</span>
8287
({getFieldType(state)})
8388
<ListItemMeta>
@@ -112,7 +117,7 @@ const FieldPreview: React.FC<{
112117
</ListItem>
113118
{addPath && isAddingField && (
114119
<InlineEditor
115-
value={{ [last(addPath) as string]: '' }}
120+
value={{ [lastFieldName(addPath)]: '' }}
116121
path={addPath}
117122
onCancel={() => {
118123
setIsAddingField(false);

src/components/Firestore/DocumentPreview/InlineEditor.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,12 +15,12 @@
1515
*/
1616

1717
import React, { useState } from 'react';
18-
import last from 'lodash.last';
1918
import { Card, CardActionButtons, CardActionButton } from '@rmwc/card';
2019
import { Elevation } from '@rmwc/elevation';
2120

2221
import DocumentEditor from '../DocumentEditor';
2322
import { FirestoreMap } from '../models';
23+
import { lastFieldName } from '../utils';
2424

2525
/** Editor entry point for a selected field */
2626
const InlineEditor: React.FC<{
@@ -43,7 +43,7 @@ const InlineEditor: React.FC<{
4343
function handleSave(e: React.MouseEvent<HTMLButtonElement>) {
4444
e.stopPropagation();
4545
// TODO key could change in the editor
46-
onSave(last(path)!, internalValue);
46+
onSave(lastFieldName(path), internalValue);
4747
}
4848

4949
return (

src/components/Firestore/DocumentPreview/api.tsx

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,9 @@
1515
*/
1616

1717
import { firestore } from 'firebase';
18-
import last from 'lodash.last';
1918

2019
import { FirestoreArray, FirestoreAny, FirestoreMap } from '../models';
21-
import { isMap, isArray } from '../utils';
20+
import { isMap, isArray, lastFieldName } from '../utils';
2221

2322
export function deleteField(
2423
documentRef: firestore.DocumentReference,
@@ -97,7 +96,7 @@ function adjustPayloadForArray(
9796

9897
if (
9998
topLevelArray === nestedObjectToModify &&
100-
Number(last(fieldPath)) >= (topLevelArray as {}[]).length
99+
Number(lastFieldName(fieldPath)) >= (topLevelArray as {}[]).length
101100
) {
102101
// Appending a new element to the top-level array
103102
return [
@@ -109,7 +108,8 @@ function adjustPayloadForArray(
109108
} else {
110109
// Deal with deleting from an array
111110
if (nestedObjectToModify instanceof Array) {
112-
const valueToDelete = nestedObjectToModify[Number(last(fieldPath))];
111+
const valueToDelete =
112+
nestedObjectToModify[Number(lastFieldName(fieldPath))];
113113
if (
114114
nestedObjectToModify !== topLevelArray ||
115115
nestedObjectToModify.indexOf(valueToDelete) !==

src/components/Firestore/utils.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,12 @@ export function getParentPath(path: string[]) {
2828
return path.slice(0, path.length - 1);
2929
}
3030

31+
export function lastFieldName(path: string[]): string {
32+
if (!path.length)
33+
throw new Error(`${path} is empty and has no _last_ field name`);
34+
return path[path.length - 1];
35+
}
36+
3137
export function getFieldType(value: FirestoreAny): FieldType {
3238
if (value === null) {
3339
return FieldType.NULL;

0 commit comments

Comments
 (0)