Skip to content

Commit

Permalink
Use tsup to build and modernize build artifacts
Browse files Browse the repository at this point in the history
  • Loading branch information
markerikson committed Apr 10, 2023
1 parent 17cfe4e commit 3ad1df5
Show file tree
Hide file tree
Showing 6 changed files with 144 additions and 50 deletions.
14 changes: 5 additions & 9 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,18 +2,15 @@
"name": "immer",
"version": "10.0.0-beta.6",
"description": "Create your next immutable state by mutating the current one",
"main": "dist/index.js",
"module": "dist/immer.mjs",
"main": "./dist/cjs/index.js",
"module": "./dist/immer.legacy-esm.js",
"exports": {
".": {
"types": "./dist/immer.d.ts",
"import": "./dist/immer.mjs",
"require": "./dist/index.js"
"require": "./dist/cjs/index.js"
}
},
"umd:main": "dist/immer.umd.production.min.js",
"unpkg": "dist/immer.umd.production.min.js",
"jsdelivr": "dist/immer.umd.production.min.js",
"jsnext:main": "dist/immer.mjs",
"react-native": "dist/immer.mjs",
"source": "src/immer.ts",
Expand All @@ -27,12 +24,11 @@
"watch": "jest --watch",
"coverage": "jest --coverage",
"coveralls": "jest --coverage && cat ./coverage/lcov.info | ./node_modules/.bin/coveralls && rm -rf ./coverage",
"build": "rimraf dist/ && tsdx build --name immer --format esm,cjs,umd && mv dist/immer.esm.js dist/immer.mjs && yarn build:flow",
"build:flow": "cpx 'src/types/index.js.flow' dist -v",
"build": "tsup",
"publish-docs": "cd website && GIT_USER=mweststrate USE_SSH=true yarn docusaurus deploy",
"start": "cd website && yarn start",
"test:size": "yarn build && yarn import-size --report . produce enableMapSet enablePatches",
"test:sizequick": "tsdx build --name immer --format esm && yarn import-size . produce"
"test:sizequick": "yarn build && yarn import-size . produce"
},
"husky": {
"hooks": {
Expand Down
3 changes: 2 additions & 1 deletion src/core/finalize.ts
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,8 @@ function finalizeProperty(
rootPath?: PatchPath,
targetIsSet?: boolean
) {
if (__DEV__ && childValue === targetObject) die(5)
if (process.env.NODE_ENV === "development" && childValue === targetObject)
die(5)
if (isDraft(childValue)) {
const path =
rootPath &&
Expand Down
10 changes: 8 additions & 2 deletions src/core/proxy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -220,12 +220,18 @@ each(objectTraps, (key, fn) => {
}
})
arrayTraps.deleteProperty = function(state, prop) {
if (__DEV__ && isNaN(parseInt(prop as any))) die(13)
if (process.env.NODE_ENV === "development" && isNaN(parseInt(prop as any)))
die(13)
// @ts-ignore
return arrayTraps.set!.call(this, state, prop, undefined)
}
arrayTraps.set = function(state, prop, value) {
if (__DEV__ && prop !== "length" && isNaN(parseInt(prop as any))) die(14)
if (
process.env.NODE_ENV === "development" &&
prop !== "length" &&
isNaN(parseInt(prop as any))
)
die(14)
return objectTraps.set!.call(this, state[0], prop, value, state[0])
}

Expand Down
2 changes: 1 addition & 1 deletion src/plugins/patches.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ import {

export function enablePatches() {
const errorOffset = 16
if (__DEV__) {
if (process.env.NODE_ENV === "development") {
errors.push(
'Sets cannot have "replace" patches.',
function(op: string) {
Expand Down
75 changes: 38 additions & 37 deletions src/utils/errors.ts
Original file line number Diff line number Diff line change
@@ -1,42 +1,43 @@
export const errors = __DEV__
? [
// All error codes, starting by 0:
function(plugin: string) {
return `The plugin for '${plugin}' has not been loaded into Immer. To enable the plugin, import and call \`enable${plugin}()\` when initializing your application.`
},
function(thing: string) {
return `produce can only be called on things that are draftable: plain objects, arrays, Map, Set or classes that are marked with '[immerable]: true'. Got '${thing}'`
},
"This object has been frozen and should not be mutated",
function(data: any) {
return (
"Cannot use a proxy that has been revoked. Did you pass an object from inside an immer function to an async process? " +
data
)
},
"An immer producer returned a new value *and* modified its draft. Either return a new value *or* modify the draft.",
"Immer forbids circular references",
"The first or second argument to `produce` must be a function",
"The third argument to `produce` must be a function or undefined",
"First argument to `createDraft` must be a plain object, an array, or an immerable object",
"First argument to `finishDraft` must be a draft returned by `createDraft`",
function(thing: string) {
return `'current' expects a draft, got: ${thing}`
},
"Object.defineProperty() cannot be used on an Immer draft",
"Object.setPrototypeOf() cannot be used on an Immer draft",
"Immer only supports deleting array indices",
"Immer only supports setting array indices and the 'length' property",
function(thing: string) {
return `'original' expects a draft, got: ${thing}`
}
// Note: if more errors are added, the errorOffset in Patches.ts should be increased
// See Patches.ts for additional errors
]
: []
export const errors =
process.env.NODE_ENV === "development"
? [
// All error codes, starting by 0:
function(plugin: string) {
return `The plugin for '${plugin}' has not been loaded into Immer. To enable the plugin, import and call \`enable${plugin}()\` when initializing your application.`
},
function(thing: string) {
return `produce can only be called on things that are draftable: plain objects, arrays, Map, Set or classes that are marked with '[immerable]: true'. Got '${thing}'`
},
"This object has been frozen and should not be mutated",
function(data: any) {
return (
"Cannot use a proxy that has been revoked. Did you pass an object from inside an immer function to an async process? " +
data
)
},
"An immer producer returned a new value *and* modified its draft. Either return a new value *or* modify the draft.",
"Immer forbids circular references",
"The first or second argument to `produce` must be a function",
"The third argument to `produce` must be a function or undefined",
"First argument to `createDraft` must be a plain object, an array, or an immerable object",
"First argument to `finishDraft` must be a draft returned by `createDraft`",
function(thing: string) {
return `'current' expects a draft, got: ${thing}`
},
"Object.defineProperty() cannot be used on an Immer draft",
"Object.setPrototypeOf() cannot be used on an Immer draft",
"Immer only supports deleting array indices",
"Immer only supports setting array indices and the 'length' property",
function(thing: string) {
return `'original' expects a draft, got: ${thing}`
}
// Note: if more errors are added, the errorOffset in Patches.ts should be increased
// See Patches.ts for additional errors
]
: []

export function die(error: number, ...args: any[]): never {
if (__DEV__) {
if (process.env.NODE_ENV === "development") {
const e = errors[error]
const msg = typeof e === "function" ? e.apply(null, args as any) : e
throw new Error(`[Immer] ${msg}`)
Expand Down
90 changes: 90 additions & 0 deletions tsup.config.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
import {defineConfig, Options} from "tsup"
import fs from "fs"

export default defineConfig(options => {
const commonOptions: Partial<Options> = {
entry: {
immer: "src/immer.ts"
},
sourcemap: true,
...options
}

const productionOptions = {
minify: true,
define: {
"process.env.NODE_ENV": JSON.stringify("production")
}
}

return [
// ESM, standard bundler dev, embedded `process` references
{
...commonOptions,
format: ["esm"],
dts: true,
clean: true,
sourcemap: true,
onSuccess() {
// Support Flow types
fs.copyFileSync("src/types/index.js.flow", "dist/index.js.flow")
}
},
// ESM, Webpack 4 support. Target ES2018 syntax to compile away optional chaining and spreads
{
...commonOptions,
entry: {
"immer.legacy-esm": "src/immer.ts"
},
// ESBuild outputs `'.mjs'` by default for the 'esm' format. Force '.js'
outExtension: () => ({js: ".js"}),
target: "es2017",
format: ["esm"],
sourcemap: true
},
// ESM for use in browsers. Minified, with `process` compiled away
{
...commonOptions,
...productionOptions,
entry: {
"immer.production": "src/immer.ts"
},
format: ["esm"],
outExtension: () => ({js: ".mjs"})
},
// CJS development
{
...commonOptions,
entry: {
"immer.cjs.development": "src/immer.ts"
},
format: "cjs",

outDir: "./dist/cjs/"
},
// CJS production
{
...commonOptions,
...productionOptions,
entry: {
"immer.cjs.production": "src/immer.ts"
},
format: "cjs",
outDir: "./dist/cjs/",
onSuccess: () => {
// Write the CJS index file
fs.writeFileSync(
"dist/cjs/index.js",
`
'use strict'
if (process.env.NODE_ENV === 'production') {
module.exports = require('./immer.cjs.production.min.js')
} else {
module.exports = require('./immer.cjs.development.js')
}`
)
}
}
]
})

0 comments on commit 3ad1df5

Please sign in to comment.