ftmocks-utils 1.0.0 → 1.0.2

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/package.json CHANGED
@@ -1,10 +1,10 @@
1
1
  {
2
2
  "name": "ftmocks-utils",
3
- "version": "1.0.0",
3
+ "version": "1.0.2",
4
4
  "description": "Util functions for FtMocks",
5
5
  "main": "src/index.js",
6
6
  "scripts": {
7
- "test": "node test.js"
7
+ "test": "node tests/test.js"
8
8
  },
9
9
  "repository": {
10
10
  "type": "git",
package/src/index.js CHANGED
@@ -1,5 +1,105 @@
1
+ import fs from 'fs';
2
+ import path from 'path';
3
+
4
+ export const nameToFolder = name => {
5
+ return name.replaceAll(' ', '_');
6
+ };
7
+
8
+ const areJsonEqual = (jsonObj1, jsonObj2) => {
9
+ // Check if both are objects and not null
10
+ if (typeof jsonObj1 === 'object' && jsonObj1 !== null &&
11
+ typeof jsonObj2 === 'object' && jsonObj2 !== null) {
12
+
13
+ // Get the keys of both objects
14
+ const keys1 = Object.keys(jsonObj1);
15
+ const keys2 = Object.keys(jsonObj2);
16
+
17
+ // Check if the number of keys is different
18
+ if (keys1.length !== keys2.length) {
19
+ return false;
20
+ }
21
+
22
+ // Recursively check each key-value pair
23
+ for (let key of keys1) {
24
+ if (!keys2.includes(key) || !areJsonEqual(jsonObj1[key], jsonObj2[key])) {
25
+ return false;
26
+ }
27
+ }
28
+
29
+ return true;
30
+ } else {
31
+ // For non-object types, use strict equality comparison
32
+ return jsonObj1 === jsonObj2;
33
+ }
34
+ }
35
+
36
+ const getDefaultMockDataFromConfig = (testConfig) => {
37
+ const defaultPath = path.join(testConfig.MOCK_DIR, testConfig.MOCK_DEFAULT_FILE);
38
+
39
+ try {
40
+ const defaultData = fs.readFileSync(defaultPath, 'utf8');
41
+ let parsedData = JSON.parse(defaultData);
42
+
43
+ // Read and attach mock data for each entry in parsedData
44
+ parsedData.forEach(entry => {
45
+ const mockFilePath = path.join(testConfig.MOCK_DIR, testConfig.MOCK_DEFAULT_DIR, `mock_${entry.id}.json`);;
46
+ try {
47
+ const mockData = fs.readFileSync(mockFilePath, 'utf8');
48
+ entry.fileContent = JSON.parse(mockData);
49
+ } catch (error) {
50
+ console.error(`Error reading mock data for ${entry.path}:`, error);
51
+ return entry; // Return the original entry if there's an error
52
+ }
53
+ });
54
+ return parsedData;
55
+ } catch (error) {
56
+ console.error(`Error reading or parsing ${testConfig.MOCK_DEFAULT_FILE}:`, error);
57
+ return [];
58
+ }
59
+ }
60
+
1
61
  // src/index.js
62
+ const loadMockDataFromConfig = (testConfig, _testName) => {
63
+ try {
64
+ let testName = _testName;
65
+ if(!testName) {
66
+ // Read the test ID from mockServer.config.json
67
+ const configPath = path.join(testConfig.MOCK_DIR, 'mockServer.config.json');
68
+ const configData = fs.readFileSync(configPath, 'utf8');
69
+ const config = JSON.parse(configData);
70
+ testName = config.testName;
71
+ }
72
+ // Read the tests from testConfig.MOCK_TEST_FILE
73
+ const mocksPath = path.join(testConfig.MOCK_DIR, `test_${nameToFolder(testName)}`, '_mock_list.json');
74
+ const mocksData = fs.readFileSync(mocksPath, 'utf8');
75
+ const mocks = JSON.parse(mocksData);
2
76
 
77
+ mocks.forEach(mock => {
78
+ const fileContent = JSON.parse(fs.readFileSync(path.join(testConfig.MOCK_DIR, `test_${nameToFolder(testName)}`, `mock_${mock.id}.json`), 'utf8'));
79
+ mock.fileContent = fileContent;
80
+ });
81
+
82
+
83
+ return mocks;
84
+ } catch (error) {
85
+ console.debug('Error loading test data:', error.message);
86
+ return [];
87
+ }
88
+ };
89
+
90
+ const isSameRequest = (req1, req2) => {
91
+ let matched = true;
92
+ if(req1.url !== req2.url) {
93
+ matched = false;
94
+ } else if(req1.method !== req2.method) {
95
+ matched = false;
96
+ } else if((!req1.postData && req2.postData) || (req1.postData && !req2.postData)) {
97
+ matched = areJsonEqual(req1.postData || {} , req2.postData || {});
98
+ } else if(req1.postData && req2.postData && !areJsonEqual(req1.postData , req2.postData)) {
99
+ matched = false;
100
+ }
101
+ return matched;
102
+ }
3
103
 
4
104
  const processURL = (url, ignoreParams=[]) => {
5
105
  // Remove the hostname from the URL
@@ -27,8 +127,62 @@ function compareMockToRequest(mock, req) {
27
127
  });
28
128
  }
29
129
 
130
+ function compareMockToFetchRequest(mock, fetchReq) {
131
+ const mockURL = processURL(mock.fileContent.url, mock.fileContent.ignoreParams);
132
+ const reqURL = processURL(fetchReq.url, mock.fileContent.ignoreParams);
133
+ const postData = mock.fileContent.request?.postData?.text ? JSON.parse(mock.fileContent.request?.postData?.text) : mock.fileContent.request?.postData;
134
+ return isSameRequest({url: mockURL, method: mock.fileContent.method, postData}, {
135
+ method: fetchReq.options.method || 'GET',
136
+ postData: fetchReq.options.body?.length ? JSON.parse(fetchReq.options.body) : fetchReq.options.body,
137
+ url: reqURL,
138
+ });
139
+ }
140
+
141
+ function getMatchingMockData({testMockData, defaultMockData, url, options, testConfig, testName}) {
142
+ let served = false;
143
+ let matchedMocks = testMockData?.filter(mock => {
144
+ if (mock.fileContent.waitForPrevious && !served) {
145
+ return false;
146
+ }
147
+ served = mock.fileContent.served;
148
+ return compareMockToFetchRequest(mock, { url, options });
149
+ }) || [];
150
+ let foundMock = matchedMocks.find(mock => !mock.fileContent.served) ? matchedMocks.find(mock => !mock.fileContent.served) : matchedMocks[0];
151
+ // updating stats to mock file
152
+ if(foundMock) {
153
+ const mockFilePath = path.join(testConfig.MOCK_DIR, `test_${nameToFolder(testName)}`, `mock_${foundMock.id}.json`);
154
+ foundMock.fileContent.served = true;
155
+ fs.writeFileSync(mockFilePath, JSON.stringify(foundMock.fileContent, null, 2));
156
+ }
157
+
158
+ if(!foundMock) {
159
+ foundMock = defaultMockData.find(tm => compareMockToFetchRequest(tm, {
160
+ url,
161
+ options
162
+ }));
163
+ }
164
+ return foundMock ? foundMock.fileContent : null;
165
+ }
166
+
167
+ async function resetAllMockStats({testMockData, testConfig, testName}) {
168
+ for(let i=0; i<testMockData.length; i++) {
169
+ const tmd = testMockData[i];
170
+ const mockFilePath = path.join(testConfig.MOCK_DIR, `test_${nameToFolder(testName)}`, `mock_${tmd.id}.json`);
171
+ tmd.fileContent.served = false;
172
+ await fs.writeFileSync(mockFilePath, JSON.stringify(tmd.fileContent, null, 2));
173
+ }
174
+ }
175
+
176
+
30
177
  // Export functions as a module
31
178
  module.exports = {
32
179
  compareMockToRequest,
33
- processURL
180
+ processURL,
181
+ isSameRequest,
182
+ loadMockDataFromConfig,
183
+ getDefaultMockDataFromConfig,
184
+ nameToFolder,
185
+ compareMockToFetchRequest,
186
+ getMatchingMockData,
187
+ resetAllMockStats
34
188
  };
File without changes