Skip to content

Commit

Permalink
Correctly skip non-plain objects
Browse files Browse the repository at this point in the history
  • Loading branch information
papb committed Sep 16, 2020
1 parent 8b83798 commit a7b9c7e
Show file tree
Hide file tree
Showing 6 changed files with 37 additions and 5 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
node_modules
dist
yarn.lock
5 changes: 4 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"name": "tree-shortcut",
"version": "1.0.0",
"description": "Simplify an object tree with a shortcut. TypeScript supported. Zero dependencies.",
"description": "Simplify an object tree with a shortcut. TypeScript supported.",
"license": "MIT",
"repository": "papb/tree-shortcut",
"author": {
Expand Down Expand Up @@ -39,6 +39,9 @@
"skip",
"chop"
],
"dependencies": {
"is-plain-obj": "^2.1.0"
},
"devDependencies": {
"@ava/typescript": "^1.1.1",
"@types/lodash.clonedeep": "^4.5.6",
Expand Down
4 changes: 2 additions & 2 deletions readme.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# tree-shortcut ![Build Status](https://github.com/papb/tree-shortcut/workflows/CI/badge.svg)
# tree-shortcut ![Build Status](https://github.com/papb/tree-shortcut/workflows/CI/badge.svg) [![install size](https://packagephobia.com/badge?p=tree-shortcut)](https://packagephobia.com/result?p=tree-shortcut)

> Simplify an object tree with a shortcut. TypeScript supported. Zero dependencies.
> Simplify an object tree with a shortcut. TypeScript supported.

## Install
Expand Down
6 changes: 4 additions & 2 deletions source/core.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import { isPlainObject } from './is-plain-object';

type AnyObject = Record<string, unknown>;
type AnyArray = readonly any[];
type PropOrNever<O, Prop> = Prop extends string | number ? (O extends Record<Prop, any> ? O[Prop] : never) : never;
Expand Down Expand Up @@ -31,13 +33,13 @@ export type TreeShortcut<

function pick(tree: any, field: string): any {
if (Array.isArray(tree)) return tree.map(x => pick(x, field));
if (!tree || typeof tree !== 'object') return tree;
if (!isPlainObject(tree)) return tree;
return tree[field];
}

function treeShortcutHelper(tree: any, from: string, to: string, name: string): any {
if (Array.isArray(tree)) return tree.map(x => treeShortcutHelper(x, from, to, name));
if (!tree || typeof tree !== 'object') return tree;
if (!isPlainObject(tree)) return tree;

const keys = Object.keys(tree);
const result: any = {};
Expand Down
5 changes: 5 additions & 0 deletions source/is-plain-object.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import isPlainObject_ = require('is-plain-obj');

export function isPlainObject(value: any): value is Record<string | number | symbol, unknown> {
return isPlainObject_(value);
}
21 changes: 21 additions & 0 deletions test/test.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import test from 'ava';
import { expectTypeOf } from 'expect-type';
import cloneDeep = require('lodash.clonedeep');
import { isPlainObject } from '../source/is-plain-object';
import treeShortcut = require('../source');
import { TreeShortcut } from '../source/core';

Expand Down Expand Up @@ -162,3 +163,23 @@ test('Does not modify input', t => {
t.deepEqual(tree1, tree1memo);
t.deepEqual(tree2, tree2memo);
});

test('Does not mess with non-plain objects', t => {
expectTypeOf<TreeShortcut<{ foo: { bar: Date }; qux: Date }, 'foo', 'bar', 'baz'>>()
.toEqualTypeOf<{ baz: Date; qux: Date }>();

const date = new Date();

// `is-plain-object` sanity check
t.true(isPlainObject({}));
t.false(isPlainObject(null));
t.false(isPlainObject(date));

const tree = [{ a: date, b: null, c: undefined, d: 4, e: { f: date } }];
const expected = [{ a: date, b: null, c: undefined, d: 4, x: date }];

t.deepEqual(
treeShortcut(tree, 'e', 'f', 'x'),
expected,
);
});

0 comments on commit a7b9c7e

Please sign in to comment.