@progressive-development/pd-provider-mock 0.9.0
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/dist/MockAuthProvider.d.ts +47 -0
- package/dist/MockAuthProvider.d.ts.map +1 -0
- package/dist/MockAuthProvider.js +161 -0
- package/dist/MockDatabaseProvider.d.ts +44 -0
- package/dist/MockDatabaseProvider.d.ts.map +1 -0
- package/dist/MockDatabaseProvider.js +196 -0
- package/dist/MockFunctionProvider.d.ts +43 -0
- package/dist/MockFunctionProvider.d.ts.map +1 -0
- package/dist/MockFunctionProvider.js +108 -0
- package/dist/MockStorageProvider.d.ts +43 -0
- package/dist/MockStorageProvider.d.ts.map +1 -0
- package/dist/MockStorageProvider.js +172 -0
- package/dist/createMockProvider.d.ts +87 -0
- package/dist/createMockProvider.d.ts.map +1 -0
- package/dist/createMockProvider.js +89 -0
- package/dist/example-fixtures.d.ts +38 -0
- package/dist/example-fixtures.d.ts.map +1 -0
- package/dist/example-fixtures.js +116 -0
- package/dist/fixtures.d.ts +142 -0
- package/dist/fixtures.d.ts.map +1 -0
- package/dist/fixtures.js +46 -0
- package/dist/index.d.ts +10 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +7 -0
- package/package.json +39 -0
|
@@ -0,0 +1,172 @@
|
|
|
1
|
+
class MockStorageProvider {
|
|
2
|
+
constructor(fixtures = [], config = {}) {
|
|
3
|
+
/** In-memory storage for uploaded files */
|
|
4
|
+
this.uploadedFiles = /* @__PURE__ */ new Map();
|
|
5
|
+
this.fixtures = fixtures;
|
|
6
|
+
this.config = config;
|
|
7
|
+
}
|
|
8
|
+
async uploadFile(request) {
|
|
9
|
+
this.log(`Uploading file: ${request.fileName} to ${request.storageName}/${request.referenceKey}`);
|
|
10
|
+
await this.delay();
|
|
11
|
+
const filePath = this.buildFilePath(
|
|
12
|
+
request.storageName,
|
|
13
|
+
request.referenceKey,
|
|
14
|
+
request.fileName,
|
|
15
|
+
request.subFolderName
|
|
16
|
+
);
|
|
17
|
+
const document = {
|
|
18
|
+
storageName: request.storageName,
|
|
19
|
+
refKey: request.referenceKey,
|
|
20
|
+
fileName: request.fileName,
|
|
21
|
+
filePath,
|
|
22
|
+
subFolderName: request.subFolderName,
|
|
23
|
+
description: request.description,
|
|
24
|
+
descriptionName: request.descriptionName,
|
|
25
|
+
creation: /* @__PURE__ */ new Date(),
|
|
26
|
+
readonly: request.readonly
|
|
27
|
+
};
|
|
28
|
+
this.uploadedFiles.set(filePath, {
|
|
29
|
+
document,
|
|
30
|
+
content: request.base64DataURL
|
|
31
|
+
});
|
|
32
|
+
this.log(`File uploaded: ${filePath}`);
|
|
33
|
+
return {
|
|
34
|
+
fullPath: filePath,
|
|
35
|
+
downloadURL: `mock://storage/${filePath}`
|
|
36
|
+
};
|
|
37
|
+
}
|
|
38
|
+
async downloadFile(options) {
|
|
39
|
+
this.log(`Downloading file: ${options.fileName}`);
|
|
40
|
+
await this.delay();
|
|
41
|
+
const filePath = this.buildFilePath(
|
|
42
|
+
options.storageName,
|
|
43
|
+
options.referenceKey,
|
|
44
|
+
options.fileName,
|
|
45
|
+
options.subFolderName
|
|
46
|
+
);
|
|
47
|
+
const uploaded = this.uploadedFiles.get(filePath);
|
|
48
|
+
if (uploaded?.content) {
|
|
49
|
+
return uploaded.content;
|
|
50
|
+
}
|
|
51
|
+
const file = this.findFileInFixtures(options);
|
|
52
|
+
if (file?.content) {
|
|
53
|
+
return file.content;
|
|
54
|
+
}
|
|
55
|
+
return `mock://storage/${filePath}`;
|
|
56
|
+
}
|
|
57
|
+
async deleteFile(options) {
|
|
58
|
+
this.log(`Deleting file: ${options.fileName}`);
|
|
59
|
+
await this.delay();
|
|
60
|
+
const filePath = this.buildFilePath(
|
|
61
|
+
options.storageName,
|
|
62
|
+
options.referenceKey,
|
|
63
|
+
options.fileName,
|
|
64
|
+
options.subFolderName
|
|
65
|
+
);
|
|
66
|
+
this.uploadedFiles.delete(filePath);
|
|
67
|
+
this.log(`File deleted: ${filePath}`);
|
|
68
|
+
}
|
|
69
|
+
async listFiles(options) {
|
|
70
|
+
this.log(`Listing files: ${options.storageName}/${options.referenceKey}`);
|
|
71
|
+
await this.delay();
|
|
72
|
+
const result = [];
|
|
73
|
+
const fixture = this.fixtures.find(
|
|
74
|
+
(f) => f.storageName === options.storageName && f.referenceKey === options.referenceKey
|
|
75
|
+
);
|
|
76
|
+
if (fixture) {
|
|
77
|
+
for (const file of fixture.files) {
|
|
78
|
+
if (options.subFolderName && file.document.subFolderName !== options.subFolderName) {
|
|
79
|
+
continue;
|
|
80
|
+
}
|
|
81
|
+
result.push(file.document);
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
for (const [, file] of this.uploadedFiles) {
|
|
85
|
+
if (file.document.storageName === options.storageName && file.document.refKey === options.referenceKey) {
|
|
86
|
+
if (!options.subFolderName || file.document.subFolderName === options.subFolderName) {
|
|
87
|
+
result.push(file.document);
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
this.log(`Found ${result.length} files`);
|
|
92
|
+
return result;
|
|
93
|
+
}
|
|
94
|
+
async getFile(options) {
|
|
95
|
+
this.log(`Getting file: ${options.fileName}`);
|
|
96
|
+
await this.delay();
|
|
97
|
+
const filePath = this.buildFilePath(
|
|
98
|
+
options.storageName,
|
|
99
|
+
options.referenceKey,
|
|
100
|
+
options.fileName,
|
|
101
|
+
options.subFolderName
|
|
102
|
+
);
|
|
103
|
+
const uploaded = this.uploadedFiles.get(filePath);
|
|
104
|
+
if (uploaded) {
|
|
105
|
+
return uploaded.document;
|
|
106
|
+
}
|
|
107
|
+
const file = this.findFileInFixtures(options);
|
|
108
|
+
return file?.document ?? null;
|
|
109
|
+
}
|
|
110
|
+
// -------------------------------------------------------------------------
|
|
111
|
+
// Mock-specific Methods
|
|
112
|
+
// -------------------------------------------------------------------------
|
|
113
|
+
/**
|
|
114
|
+
* Add a storage fixture at runtime
|
|
115
|
+
*/
|
|
116
|
+
addFixture(fixture) {
|
|
117
|
+
this.fixtures.push(fixture);
|
|
118
|
+
}
|
|
119
|
+
/**
|
|
120
|
+
* Clear all uploaded files (in-memory)
|
|
121
|
+
*/
|
|
122
|
+
clearUploads() {
|
|
123
|
+
this.uploadedFiles.clear();
|
|
124
|
+
}
|
|
125
|
+
/**
|
|
126
|
+
* Get all uploaded files
|
|
127
|
+
*/
|
|
128
|
+
getUploadedFiles() {
|
|
129
|
+
return new Map(this.uploadedFiles);
|
|
130
|
+
}
|
|
131
|
+
/**
|
|
132
|
+
* Set fixtures (replace all)
|
|
133
|
+
*/
|
|
134
|
+
setFixtures(fixtures) {
|
|
135
|
+
this.fixtures = fixtures;
|
|
136
|
+
}
|
|
137
|
+
// -------------------------------------------------------------------------
|
|
138
|
+
// Private Helpers
|
|
139
|
+
// -------------------------------------------------------------------------
|
|
140
|
+
buildFilePath(storageName, referenceKey, fileName, subFolderName) {
|
|
141
|
+
const parts = [storageName, referenceKey];
|
|
142
|
+
if (subFolderName) {
|
|
143
|
+
parts.push(subFolderName);
|
|
144
|
+
}
|
|
145
|
+
parts.push(fileName);
|
|
146
|
+
return parts.join("/");
|
|
147
|
+
}
|
|
148
|
+
findFileInFixtures(options) {
|
|
149
|
+
const fixture = this.fixtures.find(
|
|
150
|
+
(f) => f.storageName === options.storageName && f.referenceKey === options.referenceKey
|
|
151
|
+
);
|
|
152
|
+
if (!fixture) {
|
|
153
|
+
return void 0;
|
|
154
|
+
}
|
|
155
|
+
return fixture.files.find(
|
|
156
|
+
(f) => f.document.fileName === options.fileName && (!options.subFolderName || f.document.subFolderName === options.subFolderName)
|
|
157
|
+
);
|
|
158
|
+
}
|
|
159
|
+
async delay() {
|
|
160
|
+
const delayMs = this.config.defaultDelay ?? 200;
|
|
161
|
+
if (delayMs > 0) {
|
|
162
|
+
await new Promise((resolve) => setTimeout(resolve, delayMs));
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
log(message) {
|
|
166
|
+
if (this.config.logging) {
|
|
167
|
+
console.log(`[MockStorage] ${message}`);
|
|
168
|
+
}
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
export { MockStorageProvider };
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
import { ServiceProvider } from '@progressive-development/pd-provider-interfaces';
|
|
2
|
+
import { MockAuthProvider } from './MockAuthProvider.js';
|
|
3
|
+
import { MockFunctionProvider } from './MockFunctionProvider.js';
|
|
4
|
+
import { MockStorageProvider } from './MockStorageProvider.js';
|
|
5
|
+
import { MockDatabaseProvider } from './MockDatabaseProvider.js';
|
|
6
|
+
import { MockProviderConfig } from './fixtures.js';
|
|
7
|
+
/**
|
|
8
|
+
* Extended ServiceProvider with mock-specific access
|
|
9
|
+
*/
|
|
10
|
+
export interface MockServiceProvider extends ServiceProvider {
|
|
11
|
+
/** Get typed auth provider */
|
|
12
|
+
readonly mockAuth: MockAuthProvider;
|
|
13
|
+
/** Get typed function provider */
|
|
14
|
+
readonly mockFunctions: MockFunctionProvider;
|
|
15
|
+
/** Get typed storage provider */
|
|
16
|
+
readonly mockStorage: MockStorageProvider;
|
|
17
|
+
/** Get typed database provider */
|
|
18
|
+
readonly mockDatabase: MockDatabaseProvider;
|
|
19
|
+
/** Switch to a different scenario */
|
|
20
|
+
switchScenario(scenarioName: string): void;
|
|
21
|
+
/** Get current scenario name */
|
|
22
|
+
getCurrentScenario(): string | undefined;
|
|
23
|
+
/** Get available scenario names */
|
|
24
|
+
getAvailableScenarios(): string[];
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Create a mock service provider
|
|
28
|
+
*
|
|
29
|
+
* @example
|
|
30
|
+
* ```typescript
|
|
31
|
+
* // Simple usage with inline fixtures
|
|
32
|
+
* const provider = createMockProvider({
|
|
33
|
+
* fixtures: {
|
|
34
|
+
* users: [
|
|
35
|
+
* { email: "test@example.com", password: "test123", user: { uid: "1", email: "test@example.com", emailVerified: true } }
|
|
36
|
+
* ],
|
|
37
|
+
* functions: [
|
|
38
|
+
* { name: "getData", response: { result: { statusCode: 200, resultData: { items: [] } } } }
|
|
39
|
+
* ]
|
|
40
|
+
* },
|
|
41
|
+
* defaultDelay: 500,
|
|
42
|
+
* logging: true,
|
|
43
|
+
* });
|
|
44
|
+
*
|
|
45
|
+
* services.initialize(provider);
|
|
46
|
+
* ```
|
|
47
|
+
*
|
|
48
|
+
* @example
|
|
49
|
+
* ```typescript
|
|
50
|
+
* // Usage with scenarios
|
|
51
|
+
* const provider = createMockProvider({
|
|
52
|
+
* scenarios: [
|
|
53
|
+
* {
|
|
54
|
+
* name: "happy-path",
|
|
55
|
+
* fixtures: {
|
|
56
|
+
* users: [{ email: "user@test.com", password: "pass", user: { uid: "1", email: "user@test.com", emailVerified: true } }],
|
|
57
|
+
* functions: [{ name: "submit", response: { result: { statusCode: 200, resultData: "ok" } } }]
|
|
58
|
+
* }
|
|
59
|
+
* },
|
|
60
|
+
* {
|
|
61
|
+
* name: "error-scenario",
|
|
62
|
+
* fixtures: {
|
|
63
|
+
* users: [{ email: "user@test.com", password: "pass", user: { uid: "1", email: "user@test.com", emailVerified: true } }],
|
|
64
|
+
* functions: [{ name: "submit", response: { result: { statusCode: -1, resultData: null }, error: { message: "Server error" } } }]
|
|
65
|
+
* }
|
|
66
|
+
* }
|
|
67
|
+
* ],
|
|
68
|
+
* activeScenario: "happy-path",
|
|
69
|
+
* });
|
|
70
|
+
*
|
|
71
|
+
* // Later: switch scenario
|
|
72
|
+
* provider.switchScenario("error-scenario");
|
|
73
|
+
* ```
|
|
74
|
+
*/
|
|
75
|
+
export declare function createMockProvider(config?: MockProviderConfig): MockServiceProvider;
|
|
76
|
+
/**
|
|
77
|
+
* Create a minimal mock provider for quick testing
|
|
78
|
+
*
|
|
79
|
+
* Provides a single test user and empty fixtures
|
|
80
|
+
*/
|
|
81
|
+
export declare function createQuickMockProvider(options?: {
|
|
82
|
+
email?: string;
|
|
83
|
+
password?: string;
|
|
84
|
+
delay?: number;
|
|
85
|
+
logging?: boolean;
|
|
86
|
+
}): MockServiceProvider;
|
|
87
|
+
//# sourceMappingURL=createMockProvider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"createMockProvider.d.ts","sourceRoot":"","sources":["../src/createMockProvider.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,iDAAiD,CAAC;AAEvF,OAAO,EAAE,gBAAgB,EAAE,MAAM,uBAAuB,CAAC;AACzD,OAAO,EAAE,oBAAoB,EAAE,MAAM,2BAA2B,CAAC;AACjE,OAAO,EAAE,mBAAmB,EAAE,MAAM,0BAA0B,CAAC;AAC/D,OAAO,EAAE,oBAAoB,EAAE,MAAM,2BAA2B,CAAC;AACjE,OAAO,KAAK,EACV,kBAAkB,EAGnB,MAAM,eAAe,CAAC;AAEvB;;GAEG;AACH,MAAM,WAAW,mBAAoB,SAAQ,eAAe;IAC1D,8BAA8B;IAC9B,QAAQ,CAAC,QAAQ,EAAE,gBAAgB,CAAC;IACpC,kCAAkC;IAClC,QAAQ,CAAC,aAAa,EAAE,oBAAoB,CAAC;IAC7C,iCAAiC;IACjC,QAAQ,CAAC,WAAW,EAAE,mBAAmB,CAAC;IAC1C,kCAAkC;IAClC,QAAQ,CAAC,YAAY,EAAE,oBAAoB,CAAC;IAC5C,qCAAqC;IACrC,cAAc,CAAC,YAAY,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3C,gCAAgC;IAChC,kBAAkB,IAAI,MAAM,GAAG,SAAS,CAAC;IACzC,mCAAmC;IACnC,qBAAqB,IAAI,MAAM,EAAE,CAAC;CACnC;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAgDG;AACH,wBAAgB,kBAAkB,CAChC,MAAM,GAAE,kBAAuB,GAC9B,mBAAmB,CAiFrB;AAED;;;;GAIG;AACH,wBAAgB,uBAAuB,CACrC,OAAO,GAAE;IACP,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,OAAO,CAAC,EAAE,OAAO,CAAC;CACd,GACL,mBAAmB,CAuBrB"}
|
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
import { MockAuthProvider } from './MockAuthProvider.js';
|
|
2
|
+
import { MockFunctionProvider } from './MockFunctionProvider.js';
|
|
3
|
+
import { MockStorageProvider } from './MockStorageProvider.js';
|
|
4
|
+
import { MockDatabaseProvider } from './MockDatabaseProvider.js';
|
|
5
|
+
|
|
6
|
+
function createMockProvider(config = {}) {
|
|
7
|
+
let activeFixtures = config.fixtures || {};
|
|
8
|
+
let activeScenarioName = config.activeScenario;
|
|
9
|
+
if (config.scenarios && config.scenarios.length > 0) {
|
|
10
|
+
const scenario = config.activeScenario ? config.scenarios.find((s) => s.name === config.activeScenario) : config.scenarios[0];
|
|
11
|
+
if (scenario) {
|
|
12
|
+
activeFixtures = scenario.fixtures;
|
|
13
|
+
activeScenarioName = scenario.name;
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
const auth = new MockAuthProvider(activeFixtures.users || [], config);
|
|
17
|
+
const functions = new MockFunctionProvider(activeFixtures.functions || [], config);
|
|
18
|
+
const storage = new MockStorageProvider(activeFixtures.storage || [], config);
|
|
19
|
+
const database = new MockDatabaseProvider(activeFixtures.database || [], config);
|
|
20
|
+
const provider = {
|
|
21
|
+
auth,
|
|
22
|
+
functions,
|
|
23
|
+
storage,
|
|
24
|
+
database,
|
|
25
|
+
get mockAuth() {
|
|
26
|
+
return auth;
|
|
27
|
+
},
|
|
28
|
+
get mockFunctions() {
|
|
29
|
+
return functions;
|
|
30
|
+
},
|
|
31
|
+
get mockStorage() {
|
|
32
|
+
return storage;
|
|
33
|
+
},
|
|
34
|
+
get mockDatabase() {
|
|
35
|
+
return database;
|
|
36
|
+
},
|
|
37
|
+
switchScenario(scenarioName) {
|
|
38
|
+
if (!config.scenarios) {
|
|
39
|
+
throw new Error("No scenarios configured");
|
|
40
|
+
}
|
|
41
|
+
const scenario = config.scenarios.find((s) => s.name === scenarioName);
|
|
42
|
+
if (!scenario) {
|
|
43
|
+
throw new Error(`Scenario not found: ${scenarioName}`);
|
|
44
|
+
}
|
|
45
|
+
functions.setFixtures(scenario.fixtures.functions || []);
|
|
46
|
+
storage.setFixtures(scenario.fixtures.storage || []);
|
|
47
|
+
database.clearAllCollections();
|
|
48
|
+
for (const collection of scenario.fixtures.database || []) {
|
|
49
|
+
database.addCollection(collection.path, collection.documents);
|
|
50
|
+
}
|
|
51
|
+
activeScenarioName = scenarioName;
|
|
52
|
+
if (config.logging) {
|
|
53
|
+
console.log(`[MockProvider] Switched to scenario: ${scenarioName}`);
|
|
54
|
+
}
|
|
55
|
+
},
|
|
56
|
+
getCurrentScenario() {
|
|
57
|
+
return activeScenarioName;
|
|
58
|
+
},
|
|
59
|
+
getAvailableScenarios() {
|
|
60
|
+
return (config.scenarios || []).map((s) => s.name);
|
|
61
|
+
}
|
|
62
|
+
};
|
|
63
|
+
return provider;
|
|
64
|
+
}
|
|
65
|
+
function createQuickMockProvider(options = {}) {
|
|
66
|
+
const email = options.email || "test@example.com";
|
|
67
|
+
const password = options.password || "test123";
|
|
68
|
+
return createMockProvider({
|
|
69
|
+
fixtures: {
|
|
70
|
+
users: [
|
|
71
|
+
{
|
|
72
|
+
email,
|
|
73
|
+
password,
|
|
74
|
+
user: {
|
|
75
|
+
uid: `mock-${Date.now()}`,
|
|
76
|
+
email,
|
|
77
|
+
emailVerified: true,
|
|
78
|
+
displayName: email.split("@")[0]
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
]
|
|
82
|
+
},
|
|
83
|
+
defaultDelay: options.delay ?? 200,
|
|
84
|
+
logging: options.logging ?? false,
|
|
85
|
+
persistAuth: true
|
|
86
|
+
});
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
export { createMockProvider, createQuickMockProvider };
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import { MockFixtures, MockScenario } from './fixtures.js';
|
|
2
|
+
/**
|
|
3
|
+
* Default test user
|
|
4
|
+
*/
|
|
5
|
+
export declare const DEFAULT_TEST_USER: import('./fixtures.js').MockUserFixture;
|
|
6
|
+
/**
|
|
7
|
+
* Admin test user
|
|
8
|
+
*/
|
|
9
|
+
export declare const ADMIN_TEST_USER: import('./fixtures.js').MockUserFixture;
|
|
10
|
+
/**
|
|
11
|
+
* Basic fixtures for simple testing
|
|
12
|
+
*/
|
|
13
|
+
export declare const BASIC_FIXTURES: MockFixtures;
|
|
14
|
+
/**
|
|
15
|
+
* Fixtures with multiple users
|
|
16
|
+
*/
|
|
17
|
+
export declare const MULTI_USER_FIXTURES: MockFixtures;
|
|
18
|
+
/**
|
|
19
|
+
* Happy path scenario - everything works
|
|
20
|
+
*/
|
|
21
|
+
export declare const HAPPY_PATH_SCENARIO: MockScenario;
|
|
22
|
+
/**
|
|
23
|
+
* Auth error scenario - login failures
|
|
24
|
+
*/
|
|
25
|
+
export declare const AUTH_ERROR_SCENARIO: MockScenario;
|
|
26
|
+
/**
|
|
27
|
+
* Network error scenario - function calls fail
|
|
28
|
+
*/
|
|
29
|
+
export declare const NETWORK_ERROR_SCENARIO: MockScenario;
|
|
30
|
+
/**
|
|
31
|
+
* Slow network scenario - operations have long delays
|
|
32
|
+
*/
|
|
33
|
+
export declare const SLOW_NETWORK_SCENARIO: MockScenario;
|
|
34
|
+
/**
|
|
35
|
+
* All example scenarios combined
|
|
36
|
+
*/
|
|
37
|
+
export declare const ALL_EXAMPLE_SCENARIOS: MockScenario[];
|
|
38
|
+
//# sourceMappingURL=example-fixtures.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"example-fixtures.d.ts","sourceRoot":"","sources":["../src/example-fixtures.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,YAAY,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAGhE;;GAEG;AACH,eAAO,MAAM,iBAAiB,yCAI7B,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,eAAe,yCAI3B,CAAC;AAGF;;GAEG;AACH,eAAO,MAAM,cAAc,EAAE,YAK5B,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,mBAAmB,EAAE,YAUjC,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,mBAAmB,EAAE,YAwCjC,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,mBAAmB,EAAE,YASjC,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,sBAAsB,EAAE,YAYpC,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,qBAAqB,EAAE,YAYnC,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,qBAAqB,EAAE,YAAY,EAK/C,CAAC"}
|
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
import { createUserFixture, createFunctionSuccess, createFunctionError } from './fixtures.js';
|
|
2
|
+
|
|
3
|
+
const DEFAULT_TEST_USER = createUserFixture(
|
|
4
|
+
"test@example.com",
|
|
5
|
+
"test123",
|
|
6
|
+
{ displayName: "Test User" }
|
|
7
|
+
);
|
|
8
|
+
const ADMIN_TEST_USER = createUserFixture(
|
|
9
|
+
"admin@example.com",
|
|
10
|
+
"admin123",
|
|
11
|
+
{ displayName: "Admin User" }
|
|
12
|
+
);
|
|
13
|
+
ADMIN_TEST_USER.claims = { admin: true, role: "admin" };
|
|
14
|
+
const BASIC_FIXTURES = {
|
|
15
|
+
users: [DEFAULT_TEST_USER],
|
|
16
|
+
functions: [],
|
|
17
|
+
storage: [],
|
|
18
|
+
database: []
|
|
19
|
+
};
|
|
20
|
+
const MULTI_USER_FIXTURES = {
|
|
21
|
+
users: [
|
|
22
|
+
DEFAULT_TEST_USER,
|
|
23
|
+
ADMIN_TEST_USER,
|
|
24
|
+
createUserFixture("user2@example.com", "pass2"),
|
|
25
|
+
createUserFixture("user3@example.com", "pass3")
|
|
26
|
+
],
|
|
27
|
+
functions: [],
|
|
28
|
+
storage: [],
|
|
29
|
+
database: []
|
|
30
|
+
};
|
|
31
|
+
const HAPPY_PATH_SCENARIO = {
|
|
32
|
+
name: "happy-path",
|
|
33
|
+
description: "All operations succeed with realistic data",
|
|
34
|
+
fixtures: {
|
|
35
|
+
users: [DEFAULT_TEST_USER, ADMIN_TEST_USER],
|
|
36
|
+
functions: [
|
|
37
|
+
createFunctionSuccess("getData", { items: [], total: 0 }, 200, 300),
|
|
38
|
+
createFunctionSuccess("saveData", { success: true }, 200, 500),
|
|
39
|
+
createFunctionSuccess("deleteData", { deleted: true }, 200, 300)
|
|
40
|
+
],
|
|
41
|
+
storage: [
|
|
42
|
+
{
|
|
43
|
+
storageName: "documents",
|
|
44
|
+
referenceKey: "uploads",
|
|
45
|
+
files: [
|
|
46
|
+
{
|
|
47
|
+
document: {
|
|
48
|
+
storageName: "documents",
|
|
49
|
+
refKey: "uploads",
|
|
50
|
+
fileName: "example.pdf",
|
|
51
|
+
filePath: "documents/uploads/example.pdf",
|
|
52
|
+
documentType: "application/pdf",
|
|
53
|
+
description: "Example document",
|
|
54
|
+
creation: /* @__PURE__ */ new Date("2024-01-15"),
|
|
55
|
+
size: 1024
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
]
|
|
59
|
+
}
|
|
60
|
+
],
|
|
61
|
+
database: [
|
|
62
|
+
{
|
|
63
|
+
path: "users",
|
|
64
|
+
documents: [
|
|
65
|
+
{ id: "user1", data: { name: "John", email: "john@example.com" } },
|
|
66
|
+
{ id: "user2", data: { name: "Jane", email: "jane@example.com" } }
|
|
67
|
+
]
|
|
68
|
+
}
|
|
69
|
+
]
|
|
70
|
+
}
|
|
71
|
+
};
|
|
72
|
+
const AUTH_ERROR_SCENARIO = {
|
|
73
|
+
name: "auth-error",
|
|
74
|
+
description: "Authentication fails",
|
|
75
|
+
fixtures: {
|
|
76
|
+
users: [],
|
|
77
|
+
// No valid users - all logins will fail
|
|
78
|
+
functions: [],
|
|
79
|
+
storage: [],
|
|
80
|
+
database: []
|
|
81
|
+
}
|
|
82
|
+
};
|
|
83
|
+
const NETWORK_ERROR_SCENARIO = {
|
|
84
|
+
name: "network-error",
|
|
85
|
+
description: "Network/API calls fail",
|
|
86
|
+
fixtures: {
|
|
87
|
+
users: [DEFAULT_TEST_USER],
|
|
88
|
+
functions: [
|
|
89
|
+
createFunctionError("getData", "Network error", "network/unavailable", 1e3),
|
|
90
|
+
createFunctionError("saveData", "Server unavailable", "server/unavailable", 1e3)
|
|
91
|
+
],
|
|
92
|
+
storage: [],
|
|
93
|
+
database: []
|
|
94
|
+
}
|
|
95
|
+
};
|
|
96
|
+
const SLOW_NETWORK_SCENARIO = {
|
|
97
|
+
name: "slow-network",
|
|
98
|
+
description: "Operations succeed but with significant delays",
|
|
99
|
+
fixtures: {
|
|
100
|
+
users: [DEFAULT_TEST_USER],
|
|
101
|
+
functions: [
|
|
102
|
+
createFunctionSuccess("getData", { items: [], total: 0 }, 200, 3e3),
|
|
103
|
+
createFunctionSuccess("saveData", { success: true }, 200, 5e3)
|
|
104
|
+
],
|
|
105
|
+
storage: [],
|
|
106
|
+
database: []
|
|
107
|
+
}
|
|
108
|
+
};
|
|
109
|
+
const ALL_EXAMPLE_SCENARIOS = [
|
|
110
|
+
HAPPY_PATH_SCENARIO,
|
|
111
|
+
AUTH_ERROR_SCENARIO,
|
|
112
|
+
NETWORK_ERROR_SCENARIO,
|
|
113
|
+
SLOW_NETWORK_SCENARIO
|
|
114
|
+
];
|
|
115
|
+
|
|
116
|
+
export { ADMIN_TEST_USER, ALL_EXAMPLE_SCENARIOS, AUTH_ERROR_SCENARIO, BASIC_FIXTURES, DEFAULT_TEST_USER, HAPPY_PATH_SCENARIO, MULTI_USER_FIXTURES, NETWORK_ERROR_SCENARIO, SLOW_NETWORK_SCENARIO };
|
|
@@ -0,0 +1,142 @@
|
|
|
1
|
+
import { AuthUser, FunctionResult, StorageDocument } from '@progressive-development/pd-provider-interfaces';
|
|
2
|
+
/**
|
|
3
|
+
* Mock user definition with credentials
|
|
4
|
+
*/
|
|
5
|
+
export interface MockUserFixture {
|
|
6
|
+
/** User credentials */
|
|
7
|
+
email: string;
|
|
8
|
+
password: string;
|
|
9
|
+
/** User profile data */
|
|
10
|
+
user: AuthUser;
|
|
11
|
+
/** Custom claims for the user */
|
|
12
|
+
claims?: Record<string, unknown>;
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Mock function response definition
|
|
16
|
+
*/
|
|
17
|
+
export interface MockFunctionResponse {
|
|
18
|
+
/** Response data */
|
|
19
|
+
result: FunctionResult;
|
|
20
|
+
/** Optional delay in ms before responding */
|
|
21
|
+
delay?: number;
|
|
22
|
+
/** Optional error to throw instead of returning result */
|
|
23
|
+
error?: {
|
|
24
|
+
message: string;
|
|
25
|
+
code?: string;
|
|
26
|
+
};
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Function fixture - maps function calls to responses
|
|
30
|
+
*/
|
|
31
|
+
export interface MockFunctionFixture {
|
|
32
|
+
/** Function name */
|
|
33
|
+
name: string;
|
|
34
|
+
/** Input matcher - if provided, only match when input matches */
|
|
35
|
+
inputMatcher?: Record<string, unknown>;
|
|
36
|
+
/** Response to return */
|
|
37
|
+
response: MockFunctionResponse;
|
|
38
|
+
}
|
|
39
|
+
/**
|
|
40
|
+
* Mock file in storage
|
|
41
|
+
*/
|
|
42
|
+
export interface MockStorageFile {
|
|
43
|
+
/** File metadata */
|
|
44
|
+
document: StorageDocument;
|
|
45
|
+
/** Base64 content (optional - for download simulation) */
|
|
46
|
+
content?: string;
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Storage fixture - predefined files
|
|
50
|
+
*/
|
|
51
|
+
export interface MockStorageFixture {
|
|
52
|
+
/** Storage bucket name */
|
|
53
|
+
storageName: string;
|
|
54
|
+
/** Reference key */
|
|
55
|
+
referenceKey: string;
|
|
56
|
+
/** Files in this location */
|
|
57
|
+
files: MockStorageFile[];
|
|
58
|
+
}
|
|
59
|
+
/**
|
|
60
|
+
* Mock document in database
|
|
61
|
+
*/
|
|
62
|
+
export interface MockDatabaseDocument<T = unknown> {
|
|
63
|
+
/** Document ID */
|
|
64
|
+
id: string;
|
|
65
|
+
/** Document data */
|
|
66
|
+
data: T;
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* Database collection fixture
|
|
70
|
+
*/
|
|
71
|
+
export interface MockDatabaseCollection<T = unknown> {
|
|
72
|
+
/** Collection path */
|
|
73
|
+
path: string;
|
|
74
|
+
/** Documents in the collection */
|
|
75
|
+
documents: MockDatabaseDocument<T>[];
|
|
76
|
+
}
|
|
77
|
+
/**
|
|
78
|
+
* Complete mock fixture configuration
|
|
79
|
+
*
|
|
80
|
+
* Can be loaded from JSON files or defined programmatically
|
|
81
|
+
*/
|
|
82
|
+
export interface MockFixtures {
|
|
83
|
+
/** Available mock users */
|
|
84
|
+
users?: MockUserFixture[];
|
|
85
|
+
/** Function responses */
|
|
86
|
+
functions?: MockFunctionFixture[];
|
|
87
|
+
/** Storage files */
|
|
88
|
+
storage?: MockStorageFixture[];
|
|
89
|
+
/** Database collections */
|
|
90
|
+
database?: MockDatabaseCollection[];
|
|
91
|
+
}
|
|
92
|
+
/**
|
|
93
|
+
* Mock scenario - a named configuration for specific test cases
|
|
94
|
+
*/
|
|
95
|
+
export interface MockScenario {
|
|
96
|
+
/** Scenario name (e.g., "happy-path", "auth-error", "network-error") */
|
|
97
|
+
name: string;
|
|
98
|
+
/** Scenario description */
|
|
99
|
+
description?: string;
|
|
100
|
+
/** Fixtures for this scenario */
|
|
101
|
+
fixtures: MockFixtures;
|
|
102
|
+
}
|
|
103
|
+
/**
|
|
104
|
+
* Mock provider configuration
|
|
105
|
+
*/
|
|
106
|
+
export interface MockProviderConfig {
|
|
107
|
+
/** Fixtures to use */
|
|
108
|
+
fixtures?: MockFixtures;
|
|
109
|
+
/** Named scenarios (can switch between them) */
|
|
110
|
+
scenarios?: MockScenario[];
|
|
111
|
+
/** Active scenario name */
|
|
112
|
+
activeScenario?: string;
|
|
113
|
+
/** Default delay for all operations (ms) */
|
|
114
|
+
defaultDelay?: number;
|
|
115
|
+
/** Use localStorage for auth persistence */
|
|
116
|
+
persistAuth?: boolean;
|
|
117
|
+
/** LocalStorage key for auth persistence */
|
|
118
|
+
persistAuthKey?: string;
|
|
119
|
+
/** Enable console logging */
|
|
120
|
+
logging?: boolean;
|
|
121
|
+
}
|
|
122
|
+
/**
|
|
123
|
+
* Merge multiple fixture configurations
|
|
124
|
+
*/
|
|
125
|
+
export declare function mergeFixtures(...fixtures: MockFixtures[]): MockFixtures;
|
|
126
|
+
/**
|
|
127
|
+
* Create a simple user fixture
|
|
128
|
+
* @param email - User's email address
|
|
129
|
+
* @param password - User's password
|
|
130
|
+
* @param overrides - Optional overrides for AuthUser properties
|
|
131
|
+
* @param claims - Optional custom claims (for role-based access)
|
|
132
|
+
*/
|
|
133
|
+
export declare function createUserFixture(email: string, password: string, overrides?: Partial<AuthUser>, claims?: Record<string, unknown>): MockUserFixture;
|
|
134
|
+
/**
|
|
135
|
+
* Create a function fixture with success response
|
|
136
|
+
*/
|
|
137
|
+
export declare function createFunctionSuccess(name: string, resultData: unknown, statusCode?: number, delay?: number): MockFunctionFixture;
|
|
138
|
+
/**
|
|
139
|
+
* Create a function fixture with error response
|
|
140
|
+
*/
|
|
141
|
+
export declare function createFunctionError(name: string, errorMessage: string, errorCode?: string, delay?: number): MockFunctionFixture;
|
|
142
|
+
//# sourceMappingURL=fixtures.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"fixtures.d.ts","sourceRoot":"","sources":["../src/fixtures.ts"],"names":[],"mappings":"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"}
|