From b1a32888e4835152eab540385a2e6d4fc7166516 Mon Sep 17 00:00:00 2001 From: Ben Newman Date: Wed, 17 Mar 2021 16:50:39 -0400 Subject: [PATCH 1/2] Avoid assigning globalThis.process when not defined. Follow-up to #91. Some websites use the existence of a global process object to feature-detect the Node.js host environment, so it's not safe for this package to initialize globalThis.process when it does not already exist. --- packages/ts-invariant/src/invariant.ts | 10 ---------- 1 file changed, 10 deletions(-) diff --git a/packages/ts-invariant/src/invariant.ts b/packages/ts-invariant/src/invariant.ts index b0beac5..dca5380 100644 --- a/packages/ts-invariant/src/invariant.ts +++ b/packages/ts-invariant/src/invariant.ts @@ -64,15 +64,5 @@ export function setVerbosity(level: VerbosityLevel): VerbosityLevel { // also attempt to define the stub globally when it is not already defined. const processStub = global.process || { env: {} }; export { processStub as process }; -if (!global.process) try { - Object.defineProperty(globalThis, "process", { - value: processStub, - writable: true, - enumerable: false, - configurable: true - }); -} catch { - // If this fails, it isn't the end of the world. -} export default invariant; From 5fbbd73292ba73f3d04077a22a2326cd387be2bb Mon Sep 17 00:00:00 2001 From: Ben Newman Date: Wed, 17 Mar 2021 17:51:04 -0400 Subject: [PATCH 2/2] Also export processStub. This export can be imported and assigned to a local variable called `process`, which is convenient because the existing export named `process` would likely be rewritten by bundlers as tsInvariant.process, or collide with a local variable called `process`. --- packages/ts-invariant/src/invariant.ts | 12 ++++++++++-- packages/ts-invariant/src/tests.ts | 12 +++++++++++- 2 files changed, 21 insertions(+), 3 deletions(-) diff --git a/packages/ts-invariant/src/invariant.ts b/packages/ts-invariant/src/invariant.ts index dca5380..23eb3f6 100644 --- a/packages/ts-invariant/src/invariant.ts +++ b/packages/ts-invariant/src/invariant.ts @@ -61,8 +61,16 @@ export function setVerbosity(level: VerbosityLevel): VerbosityLevel { // import this process stub to avoid errors evaluating process.env.NODE_ENV. // However, because most ESM-to-CJS compilers will rewrite the process import // as tsInvariant.process, which prevents proper replacement by minifiers, we -// also attempt to define the stub globally when it is not already defined. -const processStub = global.process || { env: {} }; +// also export processStub, so you can import { invariant, processStub } from +// "ts-invariant" and assign processStub to a local variable named process. +export const processStub: { + env: Record; + [key: string]: any; +} = ( + typeof process === "object" && + typeof process.env === "object" +) ? process : { env: {} }; + export { processStub as process }; export default invariant; diff --git a/packages/ts-invariant/src/tests.ts b/packages/ts-invariant/src/tests.ts index be0aecb..13e4c8e 100644 --- a/packages/ts-invariant/src/tests.ts +++ b/packages/ts-invariant/src/tests.ts @@ -4,6 +4,7 @@ import defaultExport, { InvariantError, setVerbosity, process, + processStub, } from "./invariant"; import reactInvariant from "invariant"; @@ -144,7 +145,16 @@ describe("ts-invariant", function () { checkConsoleMethod("error", true); }); - it("should provide a usable process.env stub", function () { + it("should export a usable process polyfill", function () { + assert.strictEqual(typeof process, "object"); + assert.strictEqual(typeof process.env, "object"); + if (process.versions) { + assert.strictEqual(typeof process.versions.node, "string"); + } + }); + + it("should export a usable processStub", function () { + const process = processStub; assert.strictEqual(typeof process, "object"); assert.strictEqual(typeof process.env, "object"); if (process.versions) {