From b72dfd6e02a55d4eb80aa28ab85bab24197b683d Mon Sep 17 00:00:00 2001 From: Ben Newman Date: Sun, 20 Jan 2019 11:25:56 -0500 Subject: [PATCH] Stop importing shallowEqual from fbjs/lib/shallowEqual. This shaves a tiny amount of bundle size, but more importantly it implements shallowEqual using TypeScript, and avoids one of the few remaining uses of require. --- package-lock.json | 23 ++--------------------- package.json | 1 - src/Mutation.tsx | 2 +- src/Query.tsx | 2 +- src/Subscriptions.tsx | 2 +- src/queryRecycler.ts | 2 +- src/utils/shallowEqual.ts | 32 ++++++++++++++++++++++++++++++++ 7 files changed, 38 insertions(+), 26 deletions(-) create mode 100644 src/utils/shallowEqual.ts diff --git a/package-lock.json b/package-lock.json index 4577af588c..69db37c7a1 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2416,7 +2416,8 @@ "core-js": { "version": "2.5.7", "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.5.7.tgz", - "integrity": "sha512-RszJCAxg/PP6uzXVXL6BsxSXx/B05oJAQ2vkJRjyjrEcNVycaqOmNb5OTxZPE3xa5gwZduqza6L9JOCenh/Ecw==" + "integrity": "sha512-RszJCAxg/PP6uzXVXL6BsxSXx/B05oJAQ2vkJRjyjrEcNVycaqOmNb5OTxZPE3xa5gwZduqza6L9JOCenh/Ecw==", + "dev": true }, "core-util-is": { "version": "1.0.2", @@ -3345,26 +3346,6 @@ "bser": "^2.0.0" } }, - "fbjs": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fbjs/-/fbjs-1.0.0.tgz", - "integrity": "sha512-MUgcMEJaFhCaF1QtWGnmq9ZDRAzECTCRAF7O6UZIlAlkTs1SasiX9aP0Iw7wfD2mJ7wDTNfg2w7u5fSCwJk1OA==", - "requires": { - "core-js": "^2.4.1", - "fbjs-css-vars": "^1.0.0", - "isomorphic-fetch": "^2.1.1", - "loose-envify": "^1.0.0", - "object-assign": "^4.1.0", - "promise": "^7.1.1", - "setimmediate": "^1.0.5", - "ua-parser-js": "^0.7.18" - } - }, - "fbjs-css-vars": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/fbjs-css-vars/-/fbjs-css-vars-1.0.1.tgz", - "integrity": "sha512-IM+v/C40MNZWqsLErc32e0TyIk/NhkkQZL0QmjBh6zi1eXv0/GeVKmKmueQX7nn9SXQBQbTUcB8zuexIF3/88w==" - }, "filename-regex": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", diff --git a/package.json b/package.json index 70bb6806a0..121e0ee309 100644 --- a/package.json +++ b/package.json @@ -151,7 +151,6 @@ "zen-observable-ts": "0.8.13" }, "dependencies": { - "fbjs": "^1.0.0", "hoist-non-react-statics": "^3.0.0", "invariant": "^2.2.2", "lodash.isequal": "^4.5.0", diff --git a/src/Mutation.tsx b/src/Mutation.tsx index dd20d9103d..1046ab1b21 100644 --- a/src/Mutation.tsx +++ b/src/Mutation.tsx @@ -4,7 +4,7 @@ import ApolloClient, { PureQueryOptions, ApolloError, FetchPolicy } from 'apollo import { DataProxy } from 'apollo-cache'; const invariant = require('invariant'); import { DocumentNode, GraphQLError } from 'graphql'; -const shallowEqual = require('fbjs/lib/shallowEqual'); +import shallowEqual from './utils/shallowEqual'; import { OperationVariables, RefetchQueriesProviderFn } from './types'; import { parser, DocumentType } from './parser'; diff --git a/src/Query.tsx b/src/Query.tsx index 185db0883f..d110fd2b0f 100644 --- a/src/Query.tsx +++ b/src/Query.tsx @@ -15,7 +15,7 @@ import { parser, DocumentType, IDocumentDefinition } from './parser'; import { getClient } from './component-utils'; import { RenderPromises } from './getDataFromTree'; -const shallowEqual = require('fbjs/lib/shallowEqual'); +import shallowEqual from './utils/shallowEqual'; const invariant = require('invariant'); export type ObservableQueryFields = Pick< diff --git a/src/Subscriptions.tsx b/src/Subscriptions.tsx index 3da5c684f1..39c702aa94 100644 --- a/src/Subscriptions.tsx +++ b/src/Subscriptions.tsx @@ -8,7 +8,7 @@ import { ZenObservable } from 'zen-observable-ts'; import { OperationVariables } from './types'; import { getClient } from './component-utils'; -const shallowEqual = require('fbjs/lib/shallowEqual'); +import shallowEqual from './utils/shallowEqual'; const invariant = require('invariant'); export interface SubscriptionResult { diff --git a/src/queryRecycler.ts b/src/queryRecycler.ts index 4c2d50424a..fee49ed04e 100644 --- a/src/queryRecycler.ts +++ b/src/queryRecycler.ts @@ -2,7 +2,7 @@ import { ObservableQuery } from 'apollo-client'; import { ZenObservable } from 'zen-observable-ts'; import { QueryOpts } from './types'; -const shallowEqual = require('fbjs/lib/shallowEqual'); +import shallowEqual from './utils/shallowEqual'; // XXX move this logic to ObservableQuery / QueryManager in apollo-client diff --git a/src/utils/shallowEqual.ts b/src/utils/shallowEqual.ts new file mode 100644 index 0000000000..b35dd0fb5a --- /dev/null +++ b/src/utils/shallowEqual.ts @@ -0,0 +1,32 @@ +const { hasOwnProperty } = Object.prototype; + +function is(x: any, y: any) { + if (x === y) { + return x !== 0 || y !== 0 || 1 / x === 1 / y; + } + return x !== x && y !== y; +} + +function isObject(obj: any): obj is { [key: string]: any } { + return obj !== null && typeof obj === "object"; +} + +export default function shallowEqual(objA: any, objB: any) { + if (is(objA, objB)) { + return true; + } + + if (!isObject(objA) || !isObject(objB)) { + return false; + } + + const keys = Object.keys(objA); + + if (keys.length !== Object.keys(objB).length) { + return false; + } + + return keys.every( + key => hasOwnProperty.call(objB, key) && is(objA[key], objB[key]), + ); +}