@awsless/json 0.0.5 → 0.0.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.MD CHANGED
@@ -3,6 +3,13 @@
3
3
 
4
4
  The `@awsless/json` package adds support for more JavaScript native types to JSON.
5
5
 
6
+ Features:
7
+ - Lightweight / Using the JS native JSON parser.
8
+ - JSON backwards compatible.
9
+ - No precision loss.
10
+ - Includes support basic JS types.
11
+ - Extendable.
12
+
6
13
  ## The Problem
7
14
 
8
15
  JSON doesn't have support for types like:
@@ -15,6 +22,8 @@ JSON doesn't have support for types like:
15
22
 
16
23
  Having to decode & encode these type of values can get quite annoying. We try to solve this problem by encoding these types using valid JSON syntax.
17
24
 
25
+ Also `JSON.parse/stringify` don't solve the potential loss of precision problem.
26
+
18
27
  ## Basic Usage
19
28
 
20
29
  ```ts
@@ -72,6 +81,29 @@ const json = stringify(new Custom('example'), { $custom })
72
81
  const value = parse(json, { $custom })
73
82
  ```
74
83
 
84
+ ## Precision Loss
85
+
86
+ When using the native JSON.parse/stringify functions you could lose precision when parsing native numbers. And you don't always have the ability to extend JSON with your own custom types. For example when you’re communicating with a third-party API. For this reason, we have 2 utility functions that will parse the native JSON number type to your own precision-safe alternative.
87
+
88
+ ```ts
89
+ import { safeNumberParse, safeNumberStringify } from '@awsless/json';
90
+ import { BigFloat } from '@awsless/big-float';
91
+
92
+ const value = new BigFloat(1)
93
+ const json = safeNumberStringify(ONE, {
94
+ is: v => v instanceof BigFloat,
95
+ stringify: v => v.toString(),
96
+ })
97
+
98
+ console.log(json) // '1'
99
+
100
+ const result = safeNumberParse('1', {
101
+ parse: v => new BigFloat(v),
102
+ })
103
+
104
+ console.log(eq(value, result)) // true
105
+ ```
106
+
75
107
  ## Known Issue's
76
108
 
77
109
  ### Don't use the $ character inside your JSON.
package/dist/index.cjs CHANGED
@@ -22,8 +22,12 @@ var src_exports = {};
22
22
  __export(src_exports, {
23
23
  createReplacer: () => createReplacer,
24
24
  createReviver: () => createReviver,
25
+ createSafeNumberReplacer: () => createSafeNumberReplacer,
26
+ createSafeNumberReviver: () => createSafeNumberReviver,
25
27
  parse: () => parse,
26
28
  patch: () => patch,
29
+ safeNumberParse: () => safeNumberParse,
30
+ safeNumberStringify: () => safeNumberStringify,
27
31
  stringify: () => stringify,
28
32
  unpatch: () => unpatch
29
33
  });
@@ -136,12 +140,47 @@ var patch = (value, types = {}) => {
136
140
  var unpatch = (value, types = {}) => {
137
141
  return JSON.parse(stringify(value, types));
138
142
  };
143
+
144
+ // src/safe-number/parse.ts
145
+ var safeNumberParse = (json, props) => {
146
+ return JSON.parse(
147
+ json,
148
+ // @ts-ignore
149
+ createSafeNumberReviver(props)
150
+ );
151
+ };
152
+ var createSafeNumberReviver = (props) => {
153
+ return function(_, value, context) {
154
+ if (typeof value === "number") {
155
+ return props.parse(context.source);
156
+ }
157
+ return value;
158
+ };
159
+ };
160
+
161
+ // src/safe-number/stringify.ts
162
+ var safeNumberStringify = (value, props) => {
163
+ return JSON.stringify(value, createSafeNumberReplacer(props));
164
+ };
165
+ var createSafeNumberReplacer = (props) => {
166
+ return function(key, value) {
167
+ const original = this[key];
168
+ if (props.is(original)) {
169
+ return JSON.rawJSON(props.stringify(original));
170
+ }
171
+ return value;
172
+ };
173
+ };
139
174
  // Annotate the CommonJS export names for ESM import in node:
140
175
  0 && (module.exports = {
141
176
  createReplacer,
142
177
  createReviver,
178
+ createSafeNumberReplacer,
179
+ createSafeNumberReviver,
143
180
  parse,
144
181
  patch,
182
+ safeNumberParse,
183
+ safeNumberStringify,
145
184
  stringify,
146
185
  unpatch
147
186
  });
package/dist/index.d.cts CHANGED
@@ -9,11 +9,28 @@ declare const patch: (value: unknown, types?: SerializableTypes) => any;
9
9
  declare const unpatch: (value: unknown, types?: SerializableTypes) => any;
10
10
 
11
11
  declare const parse: (json: string, types?: SerializableTypes) => any;
12
- type Reviver = (this: any, key: string, value: any) => any;
13
- declare const createReviver: (types?: SerializableTypes) => Reviver;
12
+ type Reviver$1 = (this: any, key: string, value: any) => any;
13
+ declare const createReviver: (types?: SerializableTypes) => Reviver$1;
14
14
 
15
15
  declare const stringify: (value: unknown, types?: SerializableTypes) => string;
16
+ type Replacer$1 = (this: any, key: string, value: any) => any;
17
+ declare const createReplacer: (types?: SerializableTypes) => Replacer$1;
18
+
19
+ type Props$1 = {
20
+ parse: (value: string) => unknown;
21
+ };
22
+ declare const safeNumberParse: (json: string, props: Props$1) => any;
23
+ type Reviver = (this: any, key: string, value: any, context: {
24
+ source: string;
25
+ }) => any;
26
+ declare const createSafeNumberReviver: (props: Props$1) => Reviver;
27
+
28
+ type Props<T> = {
29
+ is: (value: unknown) => value is T;
30
+ stringify: (value: T) => string;
31
+ };
32
+ declare const safeNumberStringify: <T>(value: unknown, props: Props<T>) => string;
16
33
  type Replacer = (this: any, key: string, value: any) => any;
17
- declare const createReplacer: (types?: SerializableTypes) => Replacer;
34
+ declare const createSafeNumberReplacer: <T>(props: Props<T>) => Replacer;
18
35
 
19
- export { type Serializable, createReplacer, createReviver, parse, patch, stringify, unpatch };
36
+ export { type Serializable, createReplacer, createReviver, createSafeNumberReplacer, createSafeNumberReviver, parse, patch, safeNumberParse, safeNumberStringify, stringify, unpatch };
package/dist/index.d.ts CHANGED
@@ -9,11 +9,28 @@ declare const patch: (value: unknown, types?: SerializableTypes) => any;
9
9
  declare const unpatch: (value: unknown, types?: SerializableTypes) => any;
10
10
 
11
11
  declare const parse: (json: string, types?: SerializableTypes) => any;
12
- type Reviver = (this: any, key: string, value: any) => any;
13
- declare const createReviver: (types?: SerializableTypes) => Reviver;
12
+ type Reviver$1 = (this: any, key: string, value: any) => any;
13
+ declare const createReviver: (types?: SerializableTypes) => Reviver$1;
14
14
 
15
15
  declare const stringify: (value: unknown, types?: SerializableTypes) => string;
16
+ type Replacer$1 = (this: any, key: string, value: any) => any;
17
+ declare const createReplacer: (types?: SerializableTypes) => Replacer$1;
18
+
19
+ type Props$1 = {
20
+ parse: (value: string) => unknown;
21
+ };
22
+ declare const safeNumberParse: (json: string, props: Props$1) => any;
23
+ type Reviver = (this: any, key: string, value: any, context: {
24
+ source: string;
25
+ }) => any;
26
+ declare const createSafeNumberReviver: (props: Props$1) => Reviver;
27
+
28
+ type Props<T> = {
29
+ is: (value: unknown) => value is T;
30
+ stringify: (value: T) => string;
31
+ };
32
+ declare const safeNumberStringify: <T>(value: unknown, props: Props<T>) => string;
16
33
  type Replacer = (this: any, key: string, value: any) => any;
17
- declare const createReplacer: (types?: SerializableTypes) => Replacer;
34
+ declare const createSafeNumberReplacer: <T>(props: Props<T>) => Replacer;
18
35
 
19
- export { type Serializable, createReplacer, createReviver, parse, patch, stringify, unpatch };
36
+ export { type Serializable, createReplacer, createReviver, createSafeNumberReplacer, createSafeNumberReviver, parse, patch, safeNumberParse, safeNumberStringify, stringify, unpatch };
package/dist/index.js CHANGED
@@ -105,11 +105,46 @@ var patch = (value, types = {}) => {
105
105
  var unpatch = (value, types = {}) => {
106
106
  return JSON.parse(stringify(value, types));
107
107
  };
108
+
109
+ // src/safe-number/parse.ts
110
+ var safeNumberParse = (json, props) => {
111
+ return JSON.parse(
112
+ json,
113
+ // @ts-ignore
114
+ createSafeNumberReviver(props)
115
+ );
116
+ };
117
+ var createSafeNumberReviver = (props) => {
118
+ return function(_, value, context) {
119
+ if (typeof value === "number") {
120
+ return props.parse(context.source);
121
+ }
122
+ return value;
123
+ };
124
+ };
125
+
126
+ // src/safe-number/stringify.ts
127
+ var safeNumberStringify = (value, props) => {
128
+ return JSON.stringify(value, createSafeNumberReplacer(props));
129
+ };
130
+ var createSafeNumberReplacer = (props) => {
131
+ return function(key, value) {
132
+ const original = this[key];
133
+ if (props.is(original)) {
134
+ return JSON.rawJSON(props.stringify(original));
135
+ }
136
+ return value;
137
+ };
138
+ };
108
139
  export {
109
140
  createReplacer,
110
141
  createReviver,
142
+ createSafeNumberReplacer,
143
+ createSafeNumberReviver,
111
144
  parse,
112
145
  patch,
146
+ safeNumberParse,
147
+ safeNumberStringify,
113
148
  stringify,
114
149
  unpatch
115
150
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@awsless/json",
3
- "version": "0.0.5",
3
+ "version": "0.0.6",
4
4
  "license": "MIT",
5
5
  "type": "module",
6
6
  "keywords": [