From b905a8bedbefd82473a668ace898c2d281a42ce1 Mon Sep 17 00:00:00 2001
From: "allcontributors[bot]"
<46447321+allcontributors[bot]@users.noreply.github.com>
Date: Tue, 2 Feb 2021 10:31:39 +0100
Subject: [PATCH 1/4] docs: add samtgarson as a contributor (#113)
* docs: update README.md [skip ci]
* docs: update .all-contributorsrc [skip ci]
Co-authored-by: allcontributors[bot] <46447321+allcontributors[bot]@users.noreply.github.com>
---
.all-contributorsrc | 9 +++++++++
README.md | 3 ++-
2 files changed, 11 insertions(+), 1 deletion(-)
diff --git a/.all-contributorsrc b/.all-contributorsrc
index 0922be2..a97defe 100644
--- a/.all-contributorsrc
+++ b/.all-contributorsrc
@@ -104,6 +104,15 @@
"code",
"ideas"
]
+ },
+ {
+ "login": "samtgarson",
+ "name": "Sam Garson",
+ "avatar_url": "https://avatars.githubusercontent.com/u/6242344?v=4",
+ "profile": "https://www.samgarson.com",
+ "contributions": [
+ "bug"
+ ]
}
],
"badgeTemplate": "-orange.svg?style=flat-square\" alt=\"All Contributors\"/>",
diff --git a/README.md b/README.md
index 0a52d0e..de11812 100644
--- a/README.md
+++ b/README.md
@@ -8,7 +8,7 @@
-
+
@@ -237,6 +237,7 @@ Thanks goes to these wonderful people ([emoji key](https://allcontributors.org/d
Piotr Monwid-Olechnowicz 🤔 |
Alex Johansson 💻 ⚠️ |
Simon Edelmann 🐛 💻 🤔 |
+ Sam Garson 🐛 |
From 753cc5d053f95c3fbc1502688d663e504d4849c7 Mon Sep 17 00:00:00 2001
From: "allcontributors[bot]"
<46447321+allcontributors[bot]@users.noreply.github.com>
Date: Tue, 2 Feb 2021 10:33:09 +0100
Subject: [PATCH 2/4] docs: add markhughes as a contributor (#114)
* docs: update README.md [skip ci]
* docs: update .all-contributorsrc [skip ci]
Co-authored-by: allcontributors[bot] <46447321+allcontributors[bot]@users.noreply.github.com>
---
.all-contributorsrc | 9 +++++++++
README.md | 3 ++-
2 files changed, 11 insertions(+), 1 deletion(-)
diff --git a/.all-contributorsrc b/.all-contributorsrc
index a97defe..8461c17 100644
--- a/.all-contributorsrc
+++ b/.all-contributorsrc
@@ -113,6 +113,15 @@
"contributions": [
"bug"
]
+ },
+ {
+ "login": "markhughes",
+ "name": "Mark Hughes",
+ "avatar_url": "https://avatars.githubusercontent.com/u/1357323?v=4",
+ "profile": "http://twitter.com/_markeh",
+ "contributions": [
+ "bug"
+ ]
}
],
"badgeTemplate": "-orange.svg?style=flat-square\" alt=\"All Contributors\"/>",
diff --git a/README.md b/README.md
index de11812..e291427 100644
--- a/README.md
+++ b/README.md
@@ -8,7 +8,7 @@
-
+
@@ -238,6 +238,7 @@ Thanks goes to these wonderful people ([emoji key](https://allcontributors.org/d
Alex Johansson 💻 ⚠️ |
Simon Edelmann 🐛 💻 🤔 |
Sam Garson 🐛 |
+ Mark Hughes 🐛 |
From c80ccba1e243c06b30271163446989d38b6943c4 Mon Sep 17 00:00:00 2001
From: Simon Knott
Date: Wed, 3 Feb 2021 08:50:36 +0100
Subject: [PATCH 3/4] Implement "allowProps" (#115)
---
src/class-registry.ts | 31 ++++++++++++++++++++++++++++++-
src/index.test.ts | 27 ++++++++++++++++++++++++++-
src/index.ts | 6 +++---
src/transformer.ts | 13 ++++++++++++-
4 files changed, 71 insertions(+), 6 deletions(-)
diff --git a/src/class-registry.ts b/src/class-registry.ts
index 1f12fd0..211a757 100644
--- a/src/class-registry.ts
+++ b/src/class-registry.ts
@@ -1,4 +1,33 @@
import { Registry } from './registry';
import { Class } from './types';
-export const ClassRegistry = new Registry(c => c.name);
+export interface RegisterOptions {
+ identifier?: string;
+ allowProps?: string[];
+}
+
+class _ClassRegistry extends Registry {
+ constructor() {
+ super(c => c.name);
+ }
+
+ private classToAllowedProps = new Map();
+
+ register(value: Class, options?: string | RegisterOptions): void {
+ if (typeof options === 'object') {
+ if (options.allowProps) {
+ this.classToAllowedProps.set(value, options.allowProps);
+ }
+
+ super.register(value, options.identifier);
+ } else {
+ super.register(value, options);
+ }
+ }
+
+ getAllowedProps(value: Class): string[] | undefined {
+ return this.classToAllowedProps.get(value);
+ }
+}
+
+export const ClassRegistry = new _ClassRegistry();
diff --git a/src/index.test.ts b/src/index.test.ts
index 0a33c9c..3cc5d27 100644
--- a/src/index.test.ts
+++ b/src/index.test.ts
@@ -16,6 +16,7 @@ describe('stringify & parse', () => {
output: JSONValue | ((v: JSONValue) => void);
outputAnnotations?: Annotations;
customExpectations?: (value: any) => void;
+ dontExpectEquality?: boolean;
}
> = {
'works for objects': {
@@ -514,6 +515,27 @@ describe('stringify & parse', () => {
},
},
+ 'works with custom allowedProps': {
+ input: () => {
+ class User {
+ constructor(public username: string, public password: string) {}
+ }
+ SuperJSON.registerClass(User, { allowProps: ['username'] });
+ return new User('bongocat', 'supersecurepassword');
+ },
+ output: {
+ username: 'bongocat',
+ },
+ outputAnnotations: {
+ values: [['class', 'User']],
+ },
+ customExpectations(value) {
+ expect(value.password).toBeUndefined();
+ expect(value.username).toBe('bongocat');
+ },
+ dontExpectEquality: true,
+ },
+
'works for undefined, issue #48': {
input: undefined,
output: null,
@@ -561,6 +583,7 @@ describe('stringify & parse', () => {
output: expectedOutput,
outputAnnotations: expectedOutputAnnotations,
customExpectations,
+ dontExpectEquality,
},
] of Object.entries(cases)) {
test(testName, () => {
@@ -578,7 +601,9 @@ describe('stringify & parse', () => {
expect(meta).toEqual(expectedOutputAnnotations);
const untransformed = SuperJSON.deserialize({ json, meta });
- expect(untransformed).toEqual(inputValue);
+ if (!dontExpectEquality) {
+ expect(untransformed).toEqual(inputValue);
+ }
customExpectations?.(untransformed);
});
}
diff --git a/src/index.ts b/src/index.ts
index 52caaac..ab3fe24 100644
--- a/src/index.ts
+++ b/src/index.ts
@@ -8,7 +8,7 @@ import {
Class,
JSONValue,
} from './types';
-import { ClassRegistry } from './class-registry';
+import { ClassRegistry, RegisterOptions } from './class-registry';
import { SymbolRegistry } from './symbol-registry';
import {
CustomTransfomer,
@@ -52,8 +52,8 @@ const stringify = (object: SuperJSONValue): string =>
export const parse = (string: string): T =>
deserialize(JSON.parse(string));
-const registerClass = (v: Class, identifier?: string) =>
- ClassRegistry.register(v, identifier);
+const registerClass = (v: Class, options?: RegisterOptions) =>
+ ClassRegistry.register(v, options);
const registerSymbol = (v: Symbol, identifier?: string) =>
SymbolRegistry.register(v, identifier);
diff --git a/src/transformer.ts b/src/transformer.ts
index aee8956..0b8d26a 100644
--- a/src/transformer.ts
+++ b/src/transformer.ts
@@ -232,7 +232,18 @@ const classRule = compositeTransformation(
const identifier = ClassRegistry.getIdentifier(clazz.constructor);
return ['class', identifier!];
},
- v => v,
+ clazz => {
+ const allowedProps = ClassRegistry.getAllowedProps(clazz.constructor);
+ if (!allowedProps) {
+ return clazz;
+ }
+
+ const result: any = {};
+ allowedProps.forEach(prop => {
+ result[prop] = clazz[prop];
+ });
+ return result;
+ },
(v, a) => {
const clazz = ClassRegistry.getValue(a[1]);
From e97fd0034ab74bda969b0b1d32519bdb9f5687a3 Mon Sep 17 00:00:00 2001
From: Simon Knott
Date: Wed, 3 Feb 2021 08:50:49 +0100
Subject: [PATCH 4/4] Fix #108 (#111)
* Error.stack should not be included by default
* Add regression test
---
src/index.test.ts | 19 ++++++++++++++++---
src/transformer.ts | 1 -
2 files changed, 16 insertions(+), 4 deletions(-)
diff --git a/src/index.test.ts b/src/index.test.ts
index 3cc5d27..dad287d 100644
--- a/src/index.test.ts
+++ b/src/index.test.ts
@@ -189,9 +189,6 @@ describe('stringify & parse', () => {
output: ({ e }: any) => {
expect(e.name).toBe('Error');
expect(e.message).toBe('epic fail');
- expect(e.stack.startsWith('Error: epic fail\n at Suite.')).toBe(
- true
- );
},
outputAnnotations: {
values: {
@@ -868,3 +865,19 @@ test('regression #95: no undefined', () => {
expect(parsed).toEqual(input);
});
+
+test('regression #108: Error#stack should not be included by default', () => {
+ const input = new Error("Beep boop, you don't wanna see me. I'm an error!");
+ expect(input).toHaveProperty('stack');
+
+ const { stack: thatShouldBeUndefined } = SuperJSON.parse(
+ SuperJSON.stringify(input)
+ ) as any;
+ expect(thatShouldBeUndefined).toBeUndefined();
+
+ SuperJSON.allowErrorProps('stack');
+ const { stack: thatShouldExist } = SuperJSON.parse(
+ SuperJSON.stringify(input)
+ ) as any;
+ expect(thatShouldExist).toEqual(input.stack);
+});
diff --git a/src/transformer.ts b/src/transformer.ts
index 0b8d26a..ad2735e 100644
--- a/src/transformer.ts
+++ b/src/transformer.ts
@@ -107,7 +107,6 @@ const simpleRules = [
const baseError: any = {
name: v.name,
message: v.message,
- stack: v.stack,
};
allowedErrorProps.forEach(prop => {