valtio-history 0.0.0 → 0.0.1

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 ADDED
@@ -0,0 +1,49 @@
1
+ # valtio-history
2
+
3
+ [![npm version](https://badge.fury.io/js/valtio-history.svg)](https://badge.fury.io/js/valtio-history)
4
+
5
+ valtio utility for creating a proxy state with history tracking
6
+
7
+ https://valtio.pmnd.rs/docs/api/utils/proxyWithHistory
8
+
9
+ ---
10
+
11
+ ## Migrating from `valtio/utils`
12
+
13
+ ```tsx
14
+ // replace the following line
15
+ // import { proxyWithHistory } from '`valtio/utils';
16
+
17
+ import { proxyWithHistory } from 'valtio-history';
18
+ import { useSnapshot } from 'valtio';
19
+
20
+ const state = proxyWithHistory({ count: 0 });
21
+ console.log(state.value); // ---> { count: 0 }
22
+ state.value.count += 1;
23
+ console.log(state.value); // ---> { count: 1 }
24
+ state.undo();
25
+ console.log(state.value); // ---> { count: 0 }
26
+ state.redo();
27
+ console.log(state.value); // ---> { count: 1 }
28
+
29
+ // React example
30
+ export default function App() {
31
+ const {
32
+ value,
33
+ undo,
34
+ redo,
35
+ history,
36
+ canUndo,
37
+ canRedo,
38
+ getCurrentChangeDate
39
+ } = useSnapshot(state);
40
+
41
+ ...
42
+ }
43
+ ```
44
+
45
+ ### Notable changes
46
+
47
+ - the `history` object has changes
48
+ - `history.snapshots` is renamed to `history.nodes`
49
+ - a `HistoryNode` has the structure `{ createdAt: Date; snapshot: Snapshot<T> }`
package/package.json CHANGED
@@ -1,4 +1,27 @@
1
1
  {
2
2
  "name": "valtio-history",
3
- "version": "0.0.0"
3
+ "version": "0.0.1",
4
+ "author": "Daishi Kato",
5
+ "repository": {
6
+ "type": "git",
7
+ "url": "https://github.com/valtiojs/valtio-history.git"
8
+ },
9
+ "keywords": [
10
+ "history",
11
+ "valtio",
12
+ "undo",
13
+ "redo",
14
+ "proxy",
15
+ "utility",
16
+ "valtio-utility"
17
+ ],
18
+ "dependencies": {
19
+ "tslib": "^2.3.0"
20
+ },
21
+ "peerDependencies": {
22
+ "valtio": ">=1.0.0"
23
+ },
24
+ "type": "commonjs",
25
+ "main": "./src/index.js",
26
+ "typings": "./src/index.d.ts"
4
27
  }
@@ -0,0 +1,50 @@
1
+ import type { INTERNAL_Snapshot as Snapshot } from 'valtio/vanilla';
2
+ export type HistoryNode<T> = {
3
+ createdAt: Date;
4
+ snapshot: Snapshot<T>;
5
+ };
6
+ export type History<T> = {
7
+ wip?: Snapshot<T>;
8
+ nodes: HistoryNode<T>[];
9
+ index: number;
10
+ };
11
+ /**
12
+ * proxyWithHistory
13
+ *
14
+ * This creates a new proxy with history support.
15
+ * It includes following properties:
16
+ * - value: any value (does not have to be an object)
17
+ * - history: an object holding the history of snapshots and other metadata
18
+ * - history.index: the history index to the current snapshot
19
+ * - history.nodes: the nodes of the history for each change
20
+ * - history.wip: field for holding sandbox changes; used to avoid infinite loops
21
+ * - canUndo: a function to return true if undo is available
22
+ * - undo: a function to go back history
23
+ * - canRedo: a function to return true if redo is available
24
+ * - redo: a function to go forward history
25
+ * - saveHistory: a function to save history
26
+ * - getCurrentChangeDate: gets the date of the current change
27
+ *
28
+ * [Notes]
29
+ * - Suspense/promise is not supported.
30
+ *
31
+ * @example
32
+ * import { proxyWithHistory } from 'valtio/utils'
33
+ * const state = proxyWithHistory({
34
+ * count: 1,
35
+ * })
36
+ */
37
+ export declare function proxyWithHistory<V>(initialValue: V, skipSubscribe?: boolean): {
38
+ value: V;
39
+ history: History<V> & {
40
+ $$valtioRef: true;
41
+ };
42
+ getCurrentChangeDate: () => Date;
43
+ clone: <T>(value: T) => T;
44
+ canUndo: () => boolean;
45
+ undo: () => void;
46
+ canRedo: () => boolean;
47
+ redo: () => void;
48
+ saveHistory: () => void;
49
+ subscribe: () => () => void;
50
+ };
@@ -0,0 +1,97 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.proxyWithHistory = void 0;
4
+ const vanilla_1 = require("valtio/vanilla");
5
+ const isObject = (value) => !!value && typeof value === 'object';
6
+ let refSet;
7
+ const deepClone = (value) => {
8
+ if (!refSet) {
9
+ refSet = (0, vanilla_1.unstable_buildProxyFunction)()[2];
10
+ }
11
+ if (!isObject(value) || refSet.has(value)) {
12
+ return value;
13
+ }
14
+ const baseObject = Array.isArray(value)
15
+ ? []
16
+ : Object.create(Object.getPrototypeOf(value));
17
+ Reflect.ownKeys(value).forEach((key) => {
18
+ baseObject[key] = deepClone(value[key]);
19
+ });
20
+ return baseObject;
21
+ };
22
+ /**
23
+ * proxyWithHistory
24
+ *
25
+ * This creates a new proxy with history support.
26
+ * It includes following properties:
27
+ * - value: any value (does not have to be an object)
28
+ * - history: an object holding the history of snapshots and other metadata
29
+ * - history.index: the history index to the current snapshot
30
+ * - history.nodes: the nodes of the history for each change
31
+ * - history.wip: field for holding sandbox changes; used to avoid infinite loops
32
+ * - canUndo: a function to return true if undo is available
33
+ * - undo: a function to go back history
34
+ * - canRedo: a function to return true if redo is available
35
+ * - redo: a function to go forward history
36
+ * - saveHistory: a function to save history
37
+ * - getCurrentChangeDate: gets the date of the current change
38
+ *
39
+ * [Notes]
40
+ * - Suspense/promise is not supported.
41
+ *
42
+ * @example
43
+ * import { proxyWithHistory } from 'valtio/utils'
44
+ * const state = proxyWithHistory({
45
+ * count: 1,
46
+ * })
47
+ */
48
+ function proxyWithHistory(initialValue, skipSubscribe = false) {
49
+ const proxyObject = (0, vanilla_1.proxy)({
50
+ value: initialValue,
51
+ history: (0, vanilla_1.ref)({
52
+ wip: undefined,
53
+ nodes: [],
54
+ index: -1,
55
+ }),
56
+ getCurrentChangeDate: () => {
57
+ const node = proxyObject.history.nodes[proxyObject.history.index];
58
+ return node === null || node === void 0 ? void 0 : node.createdAt;
59
+ },
60
+ clone: deepClone,
61
+ canUndo: () => proxyObject.history.index > 0,
62
+ undo: () => {
63
+ var _a;
64
+ if (proxyObject.canUndo()) {
65
+ proxyObject.value = (proxyObject.history.wip = proxyObject.clone((_a = proxyObject.history.nodes[--proxyObject.history.index]) === null || _a === void 0 ? void 0 : _a.snapshot));
66
+ }
67
+ },
68
+ canRedo: () => proxyObject.history.index < proxyObject.history.nodes.length - 1,
69
+ redo: () => {
70
+ var _a;
71
+ if (proxyObject.canRedo()) {
72
+ proxyObject.value = (proxyObject.history.wip = proxyObject.clone((_a = proxyObject.history.nodes[++proxyObject.history.index]) === null || _a === void 0 ? void 0 : _a.snapshot));
73
+ }
74
+ },
75
+ saveHistory: () => {
76
+ proxyObject.history.nodes.splice(proxyObject.history.index + 1);
77
+ proxyObject.history.nodes.push({
78
+ createdAt: new Date(),
79
+ snapshot: (0, vanilla_1.snapshot)(proxyObject).value,
80
+ });
81
+ ++proxyObject.history.index;
82
+ },
83
+ subscribe: () => (0, vanilla_1.subscribe)(proxyObject, (ops) => {
84
+ if (ops.every((op) => op[1][0] === 'value' &&
85
+ (op[0] !== 'set' || op[2] !== proxyObject.history.wip))) {
86
+ proxyObject.saveHistory();
87
+ }
88
+ }),
89
+ });
90
+ proxyObject.saveHistory();
91
+ if (!skipSubscribe) {
92
+ proxyObject.subscribe();
93
+ }
94
+ return proxyObject;
95
+ }
96
+ exports.proxyWithHistory = proxyWithHistory;
97
+ //# sourceMappingURL=history-utility.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"history-utility.js","sourceRoot":"","sources":["../../../../packages/history-utility/src/history-utility.ts"],"names":[],"mappings":"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"}
package/src/index.d.ts ADDED
@@ -0,0 +1 @@
1
+ export * from './history-utility';
package/src/index.js ADDED
@@ -0,0 +1,5 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const tslib_1 = require("tslib");
4
+ tslib_1.__exportStar(require("./history-utility"), exports);
5
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../packages/history-utility/src/index.ts"],"names":[],"mappings":";;;AAAA,4DAAkC"}