@buley/dash 0.0.30 → 2.1.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 +82 -65
- package/dist/src/engine/ai.d.ts +10 -0
- package/dist/src/engine/ai.js +46 -0
- package/dist/src/engine/sqlite.d.ts +31 -0
- package/dist/src/engine/sqlite.js +255 -0
- package/dist/src/engine/vec_extension.d.ts +5 -0
- package/dist/src/engine/vec_extension.js +10 -0
- package/dist/src/index.d.ts +3 -0
- package/dist/src/index.js +3 -0
- package/dist/src/mcp/server.d.ts +8 -0
- package/dist/src/mcp/server.js +87 -0
- package/dist/src/reactivity/signal.d.ts +3 -0
- package/dist/src/reactivity/signal.js +31 -0
- package/dist/src/sync/backup.d.ts +12 -0
- package/dist/src/sync/backup.js +44 -0
- package/dist/src/sync/connection.d.ts +16 -0
- package/dist/src/sync/connection.js +29 -0
- package/dist/src/sync/provider.d.ts +11 -0
- package/dist/src/sync/provider.js +67 -0
- package/dist/tsconfig.tsbuildinfo +1 -0
- package/package.json +33 -31
- package/.coveralls.yml +0 -1
- package/.github/workflows/opencommit.yml +0 -33
- package/.github/workflows/testing.yml +0 -20
- package/.gitmodules +0 -0
- package/behaviors/cache.dev.js +0 -282
- package/behaviors/changes.dev.js +0 -337
- package/behaviors/collect.dev.js +0 -40
- package/behaviors/examples/async.dev.js +0 -17
- package/behaviors/firebase.dev.js +0 -283
- package/behaviors/live.dev.js +0 -67
- package/behaviors/map.dev.js +0 -54
- package/behaviors/mapreduce.dev.js +0 -68
- package/behaviors/match.dev.js +0 -66
- package/behaviors/patch.dev.js +0 -69
- package/behaviors/rest.dev.js +0 -340
- package/behaviors/shorthand.dev.js +0 -59
- package/behaviors/stats.dev.js +0 -672
- package/dist/behaviors/index.js +0 -142
- package/dist/database/index.js +0 -76
- package/dist/databases/index.js +0 -121
- package/dist/entry/index.js +0 -166
- package/dist/index.js +0 -93
- package/dist/indexes/index.js +0 -153
- package/dist/store/index.js +0 -97
- package/dist/stores/index.js +0 -90
- package/dist/utilities/index.js +0 -174
- package/documentation/database/closing.md +0 -3
- package/documentation/database/getting.md +0 -1
- package/documentation/database/opening.md +0 -5
- package/documentation/database/removing.md +0 -3
- package/documentation/databases.md +0 -21
- package/documentation/entries.md +0 -13
- package/documentation/entry/adding.md +0 -1
- package/documentation/entry/getting.md +0 -4
- package/documentation/entry/putting.md +0 -0
- package/documentation/entry/removing.md +0 -3
- package/documentation/entry/updating.md +0 -0
- package/documentation/general/security.md +0 -10
- package/documentation/general/transaction/requests.md +0 -3
- package/documentation/general/transactions.md +0 -5
- package/documentation/index/creating.md +0 -1
- package/documentation/index/getting.md +0 -1
- package/documentation/index/iterating.md +0 -1
- package/documentation/index/removing.md +0 -1
- package/documentation/indexes.md +0 -3
- package/documentation/key/cursors.md +0 -5
- package/documentation/key/range/bounds.md +0 -11
- package/documentation/key/range/direction.md +0 -1
- package/documentation/key/ranges.md +0 -3
- package/documentation/keys.md +0 -12
- package/documentation/objectstore/clearing.md +0 -1
- package/documentation/objectstore/creating.md +0 -1
- package/documentation/objectstore/getting.md +0 -1
- package/documentation/objectstore/iteration.md +0 -1
- package/documentation/objectstore/removing.md +0 -1
- package/documentation/overview.md +0 -5
- package/documentation/stores.md +0 -13
- package/jest.config.js +0 -12
- package/src/behaviors/index.ts +0 -140
- package/src/database/index.ts +0 -81
- package/src/databases/index.ts +0 -127
- package/src/entry/index.ts +0 -183
- package/src/index/index.ts +0 -61
- package/src/index.ts +0 -96
- package/src/indexes/index.ts +0 -151
- package/src/store/index.ts +0 -102
- package/src/stores/index.ts +0 -90
- package/src/utilities/index.ts +0 -349
- package/tests/behaviors/behaviors.spec.ts +0 -123
- package/tests/database/database.spec.ts +0 -177
- package/tests/databases/databases.spec.ts +0 -199
- package/tests/entry/entry.spec.ts +0 -252
- package/tests/index/index.spec.ts +0 -94
- package/tests/indexes/indexes.spec.ts +0 -203
- package/tests/store/store.spec.ts +0 -164
- package/tests/stores/stores.spec.ts +0 -148
- package/tests/utilities/clone.spec.ts +0 -48
- package/tests/utilities/cloneError.spec.ts +0 -33
- package/tests/utilities/contains.spec.ts +0 -28
- package/tests/utilities/exists.spec.ts +0 -21
- package/tests/utilities/is.spec.ts +0 -37
- package/tests/utilities/isArray.spec.ts +0 -21
- package/tests/utilities/isBoolean.spec.ts +0 -23
- package/tests/utilities/isEmpty.spec.ts +0 -45
- package/tests/utilities/isFunction.spec.ts +0 -30
- package/tests/utilities/isNumber.spec.ts +0 -29
- package/tests/utilities/isObject.spec.ts +0 -42
- package/tests/utilities/isRegEx.spec.ts +0 -33
- package/tests/utilities/isString.spec.ts +0 -25
- package/tests/utilities/isnt.spec.ts +0 -50
- package/tests/utilities/randomId.spec.ts +0 -39
- package/tests/utilities/safeApply.spec.ts +0 -49
- package/tests/utilities/safeEach.spec.ts +0 -38
- package/tests/utilities/safeIterate.spec.ts +0 -47
- package/tsconfig.json +0 -16
|
@@ -1,203 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
import indexesMethods from '../../src/indexes';
|
|
3
|
-
import { DashContext } from '../../src/utilities';
|
|
4
|
-
|
|
5
|
-
describe('indexesMethods', () => {
|
|
6
|
-
let mockSuccessCallback: jest.Mock;
|
|
7
|
-
let mockErrorCallback: jest.Mock;
|
|
8
|
-
let mockCompleteCallback: jest.Mock;
|
|
9
|
-
|
|
10
|
-
beforeEach(() => {
|
|
11
|
-
mockSuccessCallback = jest.fn();
|
|
12
|
-
mockErrorCallback = jest.fn();
|
|
13
|
-
mockCompleteCallback = jest.fn();
|
|
14
|
-
});
|
|
15
|
-
|
|
16
|
-
describe('get', () => {
|
|
17
|
-
it('should retrieve indexes from the object store and call on_success', async () => {
|
|
18
|
-
const mockObjectStore = {
|
|
19
|
-
indexNames: ['index1', 'index2']
|
|
20
|
-
};
|
|
21
|
-
|
|
22
|
-
const get_ctx: DashContext = {
|
|
23
|
-
objectstore: mockObjectStore as unknown as IDBObjectStore,
|
|
24
|
-
on_success: mockSuccessCallback
|
|
25
|
-
};
|
|
26
|
-
|
|
27
|
-
await indexesMethods.get(get_ctx);
|
|
28
|
-
|
|
29
|
-
expect(get_ctx.indexes).toEqual(['index1', 'index2']);
|
|
30
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(get_ctx);
|
|
31
|
-
});
|
|
32
|
-
});
|
|
33
|
-
|
|
34
|
-
describe('add', () => {
|
|
35
|
-
it('should add an index to the object store and call on_success', async () => {
|
|
36
|
-
const mockObjectStore = {
|
|
37
|
-
createIndex: jest.fn()
|
|
38
|
-
};
|
|
39
|
-
|
|
40
|
-
const add_ctx: DashContext = {
|
|
41
|
-
objectstore: mockObjectStore as unknown as IDBObjectStore,
|
|
42
|
-
index: 'newIndex',
|
|
43
|
-
index_key_path: 'keyPath',
|
|
44
|
-
index_unique: true,
|
|
45
|
-
on_success: mockSuccessCallback
|
|
46
|
-
};
|
|
47
|
-
|
|
48
|
-
await indexesMethods.add(add_ctx);
|
|
49
|
-
|
|
50
|
-
expect(mockObjectStore.createIndex).toHaveBeenCalledWith('newIndex', 'keyPath', {
|
|
51
|
-
unique: true,
|
|
52
|
-
multiEntry: false
|
|
53
|
-
});
|
|
54
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(add_ctx);
|
|
55
|
-
});
|
|
56
|
-
});
|
|
57
|
-
|
|
58
|
-
describe('remove', () => {
|
|
59
|
-
it('should remove an index from the object store and call on_success', async () => {
|
|
60
|
-
const mockObjectStore = {
|
|
61
|
-
deleteIndex: jest.fn()
|
|
62
|
-
};
|
|
63
|
-
|
|
64
|
-
const remove_ctx: DashContext = {
|
|
65
|
-
objectstore: mockObjectStore as unknown as IDBObjectStore,
|
|
66
|
-
index: 'indexToRemove',
|
|
67
|
-
on_success: mockSuccessCallback
|
|
68
|
-
};
|
|
69
|
-
|
|
70
|
-
await indexesMethods.remove(remove_ctx);
|
|
71
|
-
|
|
72
|
-
expect(mockObjectStore.deleteIndex).toHaveBeenCalledWith('indexToRemove');
|
|
73
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(remove_ctx);
|
|
74
|
-
});
|
|
75
|
-
});
|
|
76
|
-
|
|
77
|
-
describe('getEntries', () => {
|
|
78
|
-
it('should retrieve entries from an index and call on_success for each entry and on_complete at the end', async () => {
|
|
79
|
-
jest.setTimeout(10000); // Increase timeout to 10 seconds
|
|
80
|
-
|
|
81
|
-
let callCount = 0;
|
|
82
|
-
const mockEntries = [
|
|
83
|
-
{ id: 1, name: 'Entry1' },
|
|
84
|
-
{ id: 2, name: 'Entry2' }
|
|
85
|
-
];
|
|
86
|
-
|
|
87
|
-
const mockCursor = {
|
|
88
|
-
value: mockEntries[0],
|
|
89
|
-
continue: jest.fn(() => {
|
|
90
|
-
callCount++;
|
|
91
|
-
if (callCount >= mockEntries.length) {
|
|
92
|
-
mockRequest.result = null; // Simulate end of the cursor
|
|
93
|
-
} else {
|
|
94
|
-
mockCursor.value = mockEntries[callCount];
|
|
95
|
-
}
|
|
96
|
-
mockRequest.onsuccess(new Event('success'));
|
|
97
|
-
}),
|
|
98
|
-
};
|
|
99
|
-
|
|
100
|
-
const mockRequest = {
|
|
101
|
-
result: mockCursor as { value: { id: number; name: string; }; continue: jest.Mock<void, [], any>; } | null,
|
|
102
|
-
onsuccess: (ev: Event) => {
|
|
103
|
-
// your code here
|
|
104
|
-
},
|
|
105
|
-
};
|
|
106
|
-
|
|
107
|
-
const mockObjectStore = {
|
|
108
|
-
index: jest.fn(() => ({
|
|
109
|
-
openCursor: jest.fn(() => mockRequest),
|
|
110
|
-
})),
|
|
111
|
-
};
|
|
112
|
-
|
|
113
|
-
const mockSuccessCallback = jest.fn();
|
|
114
|
-
const mockCompleteCallback = jest.fn();
|
|
115
|
-
|
|
116
|
-
const get_ctx: DashContext = {
|
|
117
|
-
objectstore: mockObjectStore as unknown as IDBObjectStore,
|
|
118
|
-
index: 'indexName',
|
|
119
|
-
on_success: mockSuccessCallback,
|
|
120
|
-
on_complete: mockCompleteCallback,
|
|
121
|
-
};
|
|
122
|
-
|
|
123
|
-
const getEntriesPromise = indexesMethods.getEntries(get_ctx);
|
|
124
|
-
|
|
125
|
-
// Trigger the first onsuccess callback
|
|
126
|
-
if (mockRequest.onsuccess) {
|
|
127
|
-
mockRequest.onsuccess(new Event('success'));
|
|
128
|
-
}
|
|
129
|
-
|
|
130
|
-
await getEntriesPromise;
|
|
131
|
-
|
|
132
|
-
expect(mockObjectStore.index).toHaveBeenCalledWith('indexName');
|
|
133
|
-
expect(mockSuccessCallback).toHaveBeenCalledTimes(2); // Called for two entries
|
|
134
|
-
expect(mockSuccessCallback).toHaveBeenNthCalledWith(1, mockEntries[0]);
|
|
135
|
-
expect(mockSuccessCallback).toHaveBeenNthCalledWith(2, mockEntries[1]);
|
|
136
|
-
expect(mockCompleteCallback).toHaveBeenCalledWith(get_ctx);
|
|
137
|
-
});
|
|
138
|
-
|
|
139
|
-
});
|
|
140
|
-
|
|
141
|
-
describe('countEntries', () => {
|
|
142
|
-
it('should count entries in the object store index and call on_success', async () => {
|
|
143
|
-
const mockObjectStore = {
|
|
144
|
-
index: jest.fn().mockReturnValue({
|
|
145
|
-
count: jest.fn().mockReturnValue({
|
|
146
|
-
addEventListener: (event: string, callback: () => void) => {
|
|
147
|
-
if (event === 'success') callback();
|
|
148
|
-
},
|
|
149
|
-
result: 5
|
|
150
|
-
})
|
|
151
|
-
})
|
|
152
|
-
};
|
|
153
|
-
|
|
154
|
-
const count_ctx: DashContext = {
|
|
155
|
-
objectstore: mockObjectStore as unknown as IDBObjectStore,
|
|
156
|
-
index: 'testIndex',
|
|
157
|
-
on_success: mockSuccessCallback
|
|
158
|
-
};
|
|
159
|
-
|
|
160
|
-
await indexesMethods.countEntries(count_ctx);
|
|
161
|
-
|
|
162
|
-
expect(mockObjectStore.index).toHaveBeenCalledWith('testIndex');
|
|
163
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(count_ctx);
|
|
164
|
-
expect(count_ctx.total).toBe(5);
|
|
165
|
-
});
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
it('should handle errors and call on_error', async () => {
|
|
169
|
-
const mockObjectStore = {
|
|
170
|
-
index: jest.fn().mockReturnValue({
|
|
171
|
-
count: jest.fn().mockReturnValue({
|
|
172
|
-
addEventListener: (event: string, callback: (event: any) => void) => {
|
|
173
|
-
if (event === 'error') {
|
|
174
|
-
const mockErrorEvent = { target: { error: new Error('Test Error') } };
|
|
175
|
-
callback(mockErrorEvent);
|
|
176
|
-
}
|
|
177
|
-
}
|
|
178
|
-
})
|
|
179
|
-
})
|
|
180
|
-
};
|
|
181
|
-
|
|
182
|
-
const count_ctx: DashContext = {
|
|
183
|
-
objectstore: mockObjectStore as unknown as IDBObjectStore,
|
|
184
|
-
index: 'testIndex',
|
|
185
|
-
on_error: mockErrorCallback
|
|
186
|
-
};
|
|
187
|
-
|
|
188
|
-
try {
|
|
189
|
-
// Await the function call
|
|
190
|
-
await indexesMethods.countEntries(count_ctx);
|
|
191
|
-
} catch (ctx: any) {
|
|
192
|
-
// Expect the error to be part of the returned context
|
|
193
|
-
expect(ctx.error).toEqual(new Error('Test Error'));
|
|
194
|
-
|
|
195
|
-
// Ensure the error callback is called with the correct context
|
|
196
|
-
expect(mockErrorCallback).toHaveBeenCalledWith(count_ctx);
|
|
197
|
-
}
|
|
198
|
-
});
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
});
|
|
202
|
-
|
|
203
|
-
});
|
|
@@ -1,164 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
import storeMethods from '../../src/store';
|
|
3
|
-
import { DashContext } from '../../src/utilities';
|
|
4
|
-
|
|
5
|
-
describe('storeMethods', () => {
|
|
6
|
-
// Mock functions to be used in tests
|
|
7
|
-
const mockSuccessCallback = jest.fn();
|
|
8
|
-
const mockErrorCallback = jest.fn();
|
|
9
|
-
|
|
10
|
-
beforeEach(() => {
|
|
11
|
-
// Reset mock functions before each test
|
|
12
|
-
mockSuccessCallback.mockReset();
|
|
13
|
-
mockErrorCallback.mockReset();
|
|
14
|
-
});
|
|
15
|
-
|
|
16
|
-
describe('clear', () => {
|
|
17
|
-
it('should clear the object store and call on_success', async () => {
|
|
18
|
-
const mockRequest = {
|
|
19
|
-
addEventListener: jest.fn((event, callback) => {
|
|
20
|
-
if (event === 'success') {
|
|
21
|
-
setTimeout(() => {
|
|
22
|
-
callback();
|
|
23
|
-
}, 0); // Simulate async success event
|
|
24
|
-
}
|
|
25
|
-
}),
|
|
26
|
-
};
|
|
27
|
-
|
|
28
|
-
const clear_ctx: DashContext = {
|
|
29
|
-
objectstore: {
|
|
30
|
-
clear: jest.fn(() => mockRequest),
|
|
31
|
-
} as unknown as IDBObjectStore,
|
|
32
|
-
on_success: mockSuccessCallback,
|
|
33
|
-
};
|
|
34
|
-
|
|
35
|
-
await storeMethods.clear(clear_ctx);
|
|
36
|
-
expect(clear_ctx.objectstore?.clear).toHaveBeenCalled();
|
|
37
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(clear_ctx);
|
|
38
|
-
});
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
it('should handle errors when clearing the object store', () => {
|
|
42
|
-
const mockRequest = { addEventListener: jest.fn((event: string, callback: EventListenerOrEventListenerObject) => {
|
|
43
|
-
if (event === 'error') (callback as EventListener)({ target: { error: new Error('Clear Error') } } as any);
|
|
44
|
-
}) };
|
|
45
|
-
|
|
46
|
-
const clear_ctx: DashContext = {
|
|
47
|
-
objectstore: {
|
|
48
|
-
clear: jest.fn(() => mockRequest),
|
|
49
|
-
} as unknown as IDBObjectStore,
|
|
50
|
-
on_error: mockErrorCallback,
|
|
51
|
-
};
|
|
52
|
-
|
|
53
|
-
return storeMethods.clear(clear_ctx).catch((ctx: DashContext) => {
|
|
54
|
-
expect(clear_ctx.objectstore?.clear).toHaveBeenCalled();
|
|
55
|
-
expect(mockErrorCallback).toHaveBeenCalledWith(ctx);
|
|
56
|
-
expect(ctx.error.message).toBe('Clear Error');
|
|
57
|
-
});
|
|
58
|
-
});
|
|
59
|
-
});
|
|
60
|
-
|
|
61
|
-
describe('remove', () => {
|
|
62
|
-
it('should remove an entry from the object store and call on_success', () => {
|
|
63
|
-
const mockRequest = { addEventListener: jest.fn((event: string, callback: EventListenerOrEventListenerObject) => {
|
|
64
|
-
if (event === 'success') (callback as EventListener)(new Event('success'));
|
|
65
|
-
}) };
|
|
66
|
-
|
|
67
|
-
const remove_ctx: DashContext = {
|
|
68
|
-
objectstore: {
|
|
69
|
-
delete: jest.fn(() => mockRequest),
|
|
70
|
-
} as unknown as IDBObjectStore,
|
|
71
|
-
key: 'testKey',
|
|
72
|
-
on_success: mockSuccessCallback,
|
|
73
|
-
};
|
|
74
|
-
|
|
75
|
-
return storeMethods.remove(remove_ctx).then((ctx: DashContext) => {
|
|
76
|
-
expect(remove_ctx.objectstore?.delete).toHaveBeenCalledWith('testKey');
|
|
77
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(ctx);
|
|
78
|
-
});
|
|
79
|
-
});
|
|
80
|
-
|
|
81
|
-
it('should handle errors when removing an entry', () => {
|
|
82
|
-
const mockRequest = { addEventListener: jest.fn((event: string, callback: EventListenerOrEventListenerObject) => {
|
|
83
|
-
if (event === 'error') (callback as EventListener)({ target: { error: new Error('Remove Error') } } as any);
|
|
84
|
-
}) };
|
|
85
|
-
|
|
86
|
-
const remove_ctx: DashContext = {
|
|
87
|
-
objectstore: {
|
|
88
|
-
delete: jest.fn(() => mockRequest),
|
|
89
|
-
} as unknown as IDBObjectStore,
|
|
90
|
-
key: 'testKey',
|
|
91
|
-
on_error: mockErrorCallback,
|
|
92
|
-
};
|
|
93
|
-
|
|
94
|
-
return storeMethods.remove(remove_ctx).catch((ctx: DashContext) => {
|
|
95
|
-
expect(remove_ctx.objectstore?.delete).toHaveBeenCalledWith('testKey');
|
|
96
|
-
expect(mockErrorCallback).toHaveBeenCalledWith(ctx);
|
|
97
|
-
expect(ctx.error.message).toBe('Remove Error');
|
|
98
|
-
});
|
|
99
|
-
});
|
|
100
|
-
});
|
|
101
|
-
|
|
102
|
-
describe('get', () => {
|
|
103
|
-
it('should retrieve an entry from the object store and call on_success', () => {
|
|
104
|
-
const mockRequest = { addEventListener: jest.fn((event: string, callback: EventListenerOrEventListenerObject) => {
|
|
105
|
-
if (event === 'success') (callback as EventListener)(new Event('success'));
|
|
106
|
-
}), result: 'testEntry' };
|
|
107
|
-
|
|
108
|
-
const get_ctx: DashContext = {
|
|
109
|
-
objectstore: {
|
|
110
|
-
get: jest.fn(() => mockRequest),
|
|
111
|
-
} as unknown as IDBObjectStore,
|
|
112
|
-
key: 'testKey',
|
|
113
|
-
on_success: mockSuccessCallback,
|
|
114
|
-
};
|
|
115
|
-
|
|
116
|
-
return storeMethods.get(get_ctx).then((ctx: DashContext) => {
|
|
117
|
-
expect(get_ctx.objectstore?.get).toHaveBeenCalledWith('testKey');
|
|
118
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(ctx);
|
|
119
|
-
expect(ctx.entry).toBe('testEntry');
|
|
120
|
-
});
|
|
121
|
-
});
|
|
122
|
-
|
|
123
|
-
it('should handle errors when retrieving an entry', () => {
|
|
124
|
-
const mockRequest = { addEventListener: jest.fn((event: string, callback: EventListenerOrEventListenerObject) => {
|
|
125
|
-
if (event === 'error') (callback as EventListener)({ target: { error: new Error('Get Error') } } as any);
|
|
126
|
-
}) };
|
|
127
|
-
|
|
128
|
-
const get_ctx: DashContext = {
|
|
129
|
-
objectstore: {
|
|
130
|
-
get: jest.fn(() => mockRequest),
|
|
131
|
-
} as unknown as IDBObjectStore,
|
|
132
|
-
key: 'testKey',
|
|
133
|
-
on_error: mockErrorCallback,
|
|
134
|
-
};
|
|
135
|
-
|
|
136
|
-
return storeMethods.get(get_ctx).catch((ctx: DashContext) => {
|
|
137
|
-
expect(get_ctx.objectstore?.get).toHaveBeenCalledWith('testKey');
|
|
138
|
-
expect(mockErrorCallback).toHaveBeenCalledWith(ctx);
|
|
139
|
-
expect(ctx.error.message).toBe('Get Error');
|
|
140
|
-
});
|
|
141
|
-
});
|
|
142
|
-
|
|
143
|
-
it('should reject if the entry is missing', () => {
|
|
144
|
-
const mockRequest = { addEventListener: jest.fn((event: string, callback: EventListenerOrEventListenerObject) => {
|
|
145
|
-
if (event === 'success') (callback as EventListener)(new Event('success'));
|
|
146
|
-
}), result: undefined };
|
|
147
|
-
|
|
148
|
-
const get_ctx: DashContext = {
|
|
149
|
-
objectstore: {
|
|
150
|
-
get: jest.fn(() => mockRequest),
|
|
151
|
-
} as unknown as IDBObjectStore,
|
|
152
|
-
key: 'testKey',
|
|
153
|
-
on_error: mockErrorCallback,
|
|
154
|
-
};
|
|
155
|
-
|
|
156
|
-
return storeMethods.get(get_ctx).catch((ctx: DashContext) => {
|
|
157
|
-
expect(get_ctx.objectstore?.get).toHaveBeenCalledWith('testKey');
|
|
158
|
-
expect(mockErrorCallback).toHaveBeenCalledWith(ctx);
|
|
159
|
-
expect(ctx.error.message).toBe('missing');
|
|
160
|
-
expect(ctx.error.name).toBe('DashNoEntry');
|
|
161
|
-
});
|
|
162
|
-
});
|
|
163
|
-
});
|
|
164
|
-
});
|
|
@@ -1,148 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
import storesMethods from '../../src/stores';
|
|
3
|
-
import { DashContext } from '../../src/utilities';
|
|
4
|
-
|
|
5
|
-
describe('storesMethods', () => {
|
|
6
|
-
// Mock functions to be used in tests
|
|
7
|
-
const mockSuccessCallback = jest.fn();
|
|
8
|
-
const mockErrorCallback = jest.fn();
|
|
9
|
-
|
|
10
|
-
beforeEach(() => {
|
|
11
|
-
// Reset mock functions before each test
|
|
12
|
-
mockSuccessCallback.mockReset();
|
|
13
|
-
mockErrorCallback.mockReset();
|
|
14
|
-
});
|
|
15
|
-
|
|
16
|
-
const mockDb = {
|
|
17
|
-
name: 'mockDb',
|
|
18
|
-
version: 1,
|
|
19
|
-
objectStoreNames: ['store1', 'store2'],
|
|
20
|
-
createObjectStore: jest.fn(() => ({
|
|
21
|
-
createIndex: jest.fn(),
|
|
22
|
-
})),
|
|
23
|
-
deleteObjectStore: jest.fn(),
|
|
24
|
-
transaction: jest.fn(() => ({
|
|
25
|
-
objectStore: jest.fn(() => ({
|
|
26
|
-
clear: jest.fn(),
|
|
27
|
-
})),
|
|
28
|
-
db: {},
|
|
29
|
-
mode: 'readwrite',
|
|
30
|
-
error: null,
|
|
31
|
-
onabort: null,
|
|
32
|
-
oncomplete: null,
|
|
33
|
-
onerror: null,
|
|
34
|
-
addEventListener: jest.fn(),
|
|
35
|
-
removeEventListener: jest.fn(),
|
|
36
|
-
dispatchEvent: jest.fn(),
|
|
37
|
-
})),
|
|
38
|
-
close: jest.fn(),
|
|
39
|
-
onabort: null,
|
|
40
|
-
onclose: null,
|
|
41
|
-
onerror: null,
|
|
42
|
-
onversionchange: null,
|
|
43
|
-
} as unknown as IDBDatabase;
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
describe('get', () => {
|
|
47
|
-
it('should retrieve object store names and call on_success', () => {
|
|
48
|
-
const get_ctx: DashContext = { db: mockDb, on_success: mockSuccessCallback };
|
|
49
|
-
|
|
50
|
-
storesMethods.get(get_ctx);
|
|
51
|
-
|
|
52
|
-
expect(get_ctx.stores).toEqual(['store1', 'store2']); // Check store names
|
|
53
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(get_ctx); // Success callback should be called
|
|
54
|
-
});
|
|
55
|
-
});
|
|
56
|
-
|
|
57
|
-
describe('add', () => {
|
|
58
|
-
it('should add a new object store and call on_success', () => {
|
|
59
|
-
const mockRequest = {
|
|
60
|
-
result: {
|
|
61
|
-
createObjectStore: jest.fn(() => ({
|
|
62
|
-
createIndex: jest.fn(),
|
|
63
|
-
})),
|
|
64
|
-
},
|
|
65
|
-
} as IDBRequest<any>;
|
|
66
|
-
|
|
67
|
-
const add_ctx: DashContext = {
|
|
68
|
-
request: mockRequest, // Mock the request object and its result
|
|
69
|
-
store: 'newStore',
|
|
70
|
-
store_key_path: 'id',
|
|
71
|
-
auto_increment: true,
|
|
72
|
-
indexes: [{ name: 'index1', keyPath: 'key1', unique: true }],
|
|
73
|
-
on_success: mockSuccessCallback,
|
|
74
|
-
};
|
|
75
|
-
|
|
76
|
-
storesMethods.add(add_ctx);
|
|
77
|
-
|
|
78
|
-
expect(mockRequest.result.createObjectStore).toHaveBeenCalledWith('newStore', { keyPath: 'id', autoIncrement: true });
|
|
79
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(add_ctx); // Success callback should be called
|
|
80
|
-
});
|
|
81
|
-
|
|
82
|
-
it('should throw an error if database is undefined', () => {
|
|
83
|
-
const add_ctx: DashContext = { db: undefined, on_error: mockErrorCallback };
|
|
84
|
-
|
|
85
|
-
expect(() => storesMethods.add(add_ctx)).toThrow('Database is undefined');
|
|
86
|
-
});
|
|
87
|
-
});
|
|
88
|
-
|
|
89
|
-
describe('remove', () => {
|
|
90
|
-
it('should remove an object store and call on_success', () => {
|
|
91
|
-
const remove_ctx: DashContext = { db: mockDb, store: 'storeToRemove', on_success: mockSuccessCallback };
|
|
92
|
-
|
|
93
|
-
storesMethods.remove(remove_ctx);
|
|
94
|
-
|
|
95
|
-
expect(mockDb.deleteObjectStore).toHaveBeenCalledWith('storeToRemove');
|
|
96
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(remove_ctx); // Success callback should be called
|
|
97
|
-
});
|
|
98
|
-
});
|
|
99
|
-
|
|
100
|
-
describe('clearAll', () => {
|
|
101
|
-
it('should clear all object stores and call on_success on transaction complete', () => {
|
|
102
|
-
const mockTransaction = {
|
|
103
|
-
objectStore: jest.fn(() => ({
|
|
104
|
-
clear: jest.fn(),
|
|
105
|
-
})),
|
|
106
|
-
addEventListener: jest.fn((event, callback) => {
|
|
107
|
-
if (event === 'complete') callback(); // Trigger complete event
|
|
108
|
-
}),
|
|
109
|
-
oncomplete: jest.fn(),
|
|
110
|
-
};
|
|
111
|
-
|
|
112
|
-
const mockDb = {
|
|
113
|
-
name: 'mockDb',
|
|
114
|
-
objectStoreNames: ['store1', 'store2'],
|
|
115
|
-
transaction: jest.fn(() => mockTransaction),
|
|
116
|
-
createObjectStore: jest.fn(),
|
|
117
|
-
deleteObjectStore: jest.fn(),
|
|
118
|
-
} as unknown as IDBDatabase;
|
|
119
|
-
|
|
120
|
-
const clear_ctx: DashContext = { db: mockDb, on_success: mockSuccessCallback, on_error: mockErrorCallback };
|
|
121
|
-
|
|
122
|
-
storesMethods.clearAll(clear_ctx);
|
|
123
|
-
|
|
124
|
-
expect(mockDb.transaction).toHaveBeenCalledWith(['store1', 'store2'], 'readwrite');
|
|
125
|
-
expect(mockSuccessCallback).toHaveBeenCalledWith(clear_ctx); // Success callback should be called
|
|
126
|
-
});
|
|
127
|
-
|
|
128
|
-
it('should call on_error when transaction encounters an error', () => {
|
|
129
|
-
const failingMockDb: unknown = {
|
|
130
|
-
...mockDb,
|
|
131
|
-
transaction: jest.fn(() => ({
|
|
132
|
-
objectStore: jest.fn(() => ({
|
|
133
|
-
clear: jest.fn(),
|
|
134
|
-
})),
|
|
135
|
-
addEventListener: jest.fn((event, callback) => {
|
|
136
|
-
if (event === 'error') callback({ target: { error: new Error('Transaction Error') } });
|
|
137
|
-
}),
|
|
138
|
-
})),
|
|
139
|
-
};
|
|
140
|
-
const clear_ctx: DashContext = { db: failingMockDb as IDBDatabase, on_success: mockSuccessCallback, on_error: mockErrorCallback };
|
|
141
|
-
|
|
142
|
-
storesMethods.clearAll(clear_ctx);
|
|
143
|
-
|
|
144
|
-
expect(mockErrorCallback).toHaveBeenCalled(); // Error callback should be called
|
|
145
|
-
expect(clear_ctx.error.message).toBe('Transaction Error');
|
|
146
|
-
});
|
|
147
|
-
});
|
|
148
|
-
});
|
|
@@ -1,48 +0,0 @@
|
|
|
1
|
-
import { clone } from '../../src/utilities';
|
|
2
|
-
|
|
3
|
-
describe('clone', () => {
|
|
4
|
-
it('should clone a simple object', () => {
|
|
5
|
-
const result = clone({ foo: "bar" });
|
|
6
|
-
expect(result).toBeDefined();
|
|
7
|
-
expect(result).toEqual({ foo: "bar" });
|
|
8
|
-
expect(result).not.toBe({ foo: "bar" }); // Ensure it's not the same reference
|
|
9
|
-
});
|
|
10
|
-
|
|
11
|
-
it('should deeply clone a nested object', () => {
|
|
12
|
-
const source = { foo: "bar", nested: { baz: 42 } };
|
|
13
|
-
const result = clone(source);
|
|
14
|
-
expect(result).toEqual(source);
|
|
15
|
-
expect(result).not.toBe(source); // Different reference
|
|
16
|
-
expect(result.nested).not.toBe(source.nested); // Nested object should also be cloned
|
|
17
|
-
});
|
|
18
|
-
|
|
19
|
-
it('should clone arrays correctly', () => {
|
|
20
|
-
const source = [1, 2, 3, { foo: "bar" }];
|
|
21
|
-
const result = clone(source);
|
|
22
|
-
expect(result).toEqual(source);
|
|
23
|
-
expect(result).not.toBe(source); // Ensure it's not the same reference
|
|
24
|
-
expect(result[3]).not.toBe(source[3]); // Nested objects in arrays should also be cloned
|
|
25
|
-
});
|
|
26
|
-
|
|
27
|
-
it('should handle cloning null', () => {
|
|
28
|
-
const result = clone(null);
|
|
29
|
-
expect(result).toBeNull();
|
|
30
|
-
});
|
|
31
|
-
|
|
32
|
-
it('should handle cloning undefined', () => {
|
|
33
|
-
const result = clone(undefined);
|
|
34
|
-
expect(result).toBeUndefined();
|
|
35
|
-
});
|
|
36
|
-
|
|
37
|
-
it('should handle cloning complex objects with functions', () => {
|
|
38
|
-
const source = {
|
|
39
|
-
foo: "bar",
|
|
40
|
-
method: function () {
|
|
41
|
-
return "test";
|
|
42
|
-
}
|
|
43
|
-
};
|
|
44
|
-
const result = clone(source);
|
|
45
|
-
expect(result).toEqual(source);
|
|
46
|
-
expect(result.method()).toBe("test"); // Functions should still work after cloning
|
|
47
|
-
});
|
|
48
|
-
});
|
|
@@ -1,33 +0,0 @@
|
|
|
1
|
-
import { cloneError } from '../../src/utilities';
|
|
2
|
-
|
|
3
|
-
describe('cloneError', () => {
|
|
4
|
-
it('should create a deep clone of an error object', () => {
|
|
5
|
-
const source = new Error('test');
|
|
6
|
-
const result = cloneError(source);
|
|
7
|
-
|
|
8
|
-
// Check that the result is defined and an instance of Error
|
|
9
|
-
expect(result).toBeDefined();
|
|
10
|
-
expect(result).toBeInstanceOf(Error);
|
|
11
|
-
|
|
12
|
-
// Ensure the cloned error has the same message and properties
|
|
13
|
-
expect(result.message).toBe(source.message);
|
|
14
|
-
|
|
15
|
-
// Optionally verify the stack if it's available
|
|
16
|
-
if (source.stack) {
|
|
17
|
-
expect(result.stack).toBe(source.stack); // Stack should be the same
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
// Ensure the result is a new object, not just a reference to the original
|
|
21
|
-
expect(result).not.toBe(source);
|
|
22
|
-
});
|
|
23
|
-
|
|
24
|
-
it('should handle custom error properties', () => {
|
|
25
|
-
const source = new Error('test') as any;
|
|
26
|
-
source.customProp = 'customValue';
|
|
27
|
-
const result = cloneError(source);
|
|
28
|
-
|
|
29
|
-
// Ensure the custom properties are cloned as well
|
|
30
|
-
expect((result as any).customProp).toBe(source.customProp);
|
|
31
|
-
expect(result).not.toBe(source); // Verify it's a new object
|
|
32
|
-
});
|
|
33
|
-
});
|
|
@@ -1,28 +0,0 @@
|
|
|
1
|
-
import { contains } from '../../src/utilities';
|
|
2
|
-
|
|
3
|
-
describe('contains', () => {
|
|
4
|
-
it('should return true if the substring exists in the string', () => {
|
|
5
|
-
const result = contains('hello world', 'world');
|
|
6
|
-
expect(result).toBe(true);
|
|
7
|
-
});
|
|
8
|
-
|
|
9
|
-
it('should return false if the substring does not exist in the string', () => {
|
|
10
|
-
const result = contains('hello world', 'moon');
|
|
11
|
-
expect(result).toBe(false);
|
|
12
|
-
});
|
|
13
|
-
|
|
14
|
-
it('should return false when the main string is empty', () => {
|
|
15
|
-
const result = contains('', 'hello');
|
|
16
|
-
expect(result).toBe(false);
|
|
17
|
-
});
|
|
18
|
-
|
|
19
|
-
it('should return true when the substring is empty', () => {
|
|
20
|
-
const result = contains('hello world', '');
|
|
21
|
-
expect(result).toBe(true); // An empty substring is technically in any string
|
|
22
|
-
});
|
|
23
|
-
|
|
24
|
-
it('should handle case sensitivity properly', () => {
|
|
25
|
-
const result = contains('hello world', 'World');
|
|
26
|
-
expect(result).toBe(false); // Case-sensitive
|
|
27
|
-
});
|
|
28
|
-
});
|
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
import { exists } from '../../src/utilities';
|
|
2
|
-
|
|
3
|
-
describe('exists', () => {
|
|
4
|
-
it('should return true for defined values', () => {
|
|
5
|
-
expect(exists(42)).toBe(true); // number
|
|
6
|
-
expect(exists('hello')).toBe(true); // non-empty string
|
|
7
|
-
expect(exists({})).toBe(true); // object
|
|
8
|
-
expect(exists([])).toBe(true); // array
|
|
9
|
-
expect(exists(false)).toBe(true); // boolean false
|
|
10
|
-
expect(exists(0)).toBe(true); // number 0
|
|
11
|
-
});
|
|
12
|
-
|
|
13
|
-
it('should return false for undefined or null values', () => {
|
|
14
|
-
expect(exists(undefined)).toBe(false); // undefined
|
|
15
|
-
expect(exists(null)).toBe(false); // null
|
|
16
|
-
});
|
|
17
|
-
|
|
18
|
-
it('should return true for empty string', () => {
|
|
19
|
-
expect(exists('')).toBe(true); // empty string is still a defined value
|
|
20
|
-
});
|
|
21
|
-
});
|
|
@@ -1,37 +0,0 @@
|
|
|
1
|
-
import { is } from '../../src/utilities';
|
|
2
|
-
|
|
3
|
-
describe('is', () => {
|
|
4
|
-
it('should return true for identical primitive values', () => {
|
|
5
|
-
expect(is(42, 42)).toBe(true); // number
|
|
6
|
-
expect(is('hello', 'hello')).toBe(true); // string
|
|
7
|
-
expect(is(true, true)).toBe(true); // boolean
|
|
8
|
-
});
|
|
9
|
-
|
|
10
|
-
it('should return true for objects with the same reference', () => {
|
|
11
|
-
const obj = { foo: 'bar' };
|
|
12
|
-
expect(is(obj, obj)).toBe(true); // Same reference
|
|
13
|
-
});
|
|
14
|
-
|
|
15
|
-
it('should return false for different objects even if they have the same structure', () => {
|
|
16
|
-
const obj1 = { foo: 'bar' };
|
|
17
|
-
const obj2 = { foo: 'bar' };
|
|
18
|
-
expect(is(obj1, obj2)).toBe(false); // Different references
|
|
19
|
-
});
|
|
20
|
-
|
|
21
|
-
it('should return true for identical arrays (by reference)', () => {
|
|
22
|
-
const arr = [1, 2, 3];
|
|
23
|
-
expect(is(arr, arr)).toBe(true); // Same array reference
|
|
24
|
-
});
|
|
25
|
-
|
|
26
|
-
it('should return false for different arrays with the same elements', () => {
|
|
27
|
-
expect(is([1, 2, 3], [1, 2, 3])).toBe(false); // Different array instances
|
|
28
|
-
});
|
|
29
|
-
|
|
30
|
-
it('should return true for null values compared to null', () => {
|
|
31
|
-
expect(is(null, null)).toBe(true); // null values
|
|
32
|
-
});
|
|
33
|
-
|
|
34
|
-
it('should return false when comparing null with undefined', () => {
|
|
35
|
-
expect(is(null, undefined)).toBe(false); // null vs undefined
|
|
36
|
-
});
|
|
37
|
-
});
|