SAPUI5 Mockserver 始终生成相同的随机 ID
SAPUI5 Mockserver always generate same random ids
我有一个 UI5
应用程序,我 运行 它带有 UI5
用于测试的标准内置模拟服务器。
这是 mockserver.js 中由 Web IDE
自动生成的代码:
sap.ui.define([
"sap/ui/core/util/MockServer",
"sap/ui/model/json/JSONModel",
"sap/base/util/UriParameters",
"sap/base/Log"
], function (MockServer, JSONModel, UriParameters, Log) {
"use strict";
var oMockServer,
_sAppPath = "de/cimt/test/",
_sJsonFilesPath = _sAppPath + "localService/mockdata";
var oMockServerInterface = {
/**
* Initializes the mock server asynchronously.
* You can configure the delay with the URL parameter "serverDelay".
* The local mock data in this folder is returned instead of the real data for testing.
* @protected
* @param {object} [oOptionsParameter] init parameters for the mockserver
* @returns{Promise} a promise that is resolved when the mock server has been started
*/
init : function (oOptionsParameter) {
var oOptions = oOptionsParameter || {};
return new Promise(function(fnResolve, fnReject) {
var sManifestUrl = sap.ui.require.toUrl(_sAppPath + "manifest.json"),
oManifestModel = new JSONModel(sManifestUrl);
oManifestModel.attachRequestCompleted(function () {
var oUriParameters = new UriParameters(window.location.href),
// parse manifest for local metatadata URI
sJsonFilesUrl = sap.ui.require.toUrl(_sJsonFilesPath),
oMainDataSource = oManifestModel.getProperty("/sap.app/dataSources/mainService"),
sMetadataUrl = sap.ui.require.toUrl(_sAppPath + oMainDataSource.settings.localUri),
// ensure there is a trailing slash
sMockServerUrl = /.*\/$/.test(oMainDataSource.uri) ? oMainDataSource.uri : oMainDataSource.uri + "/";
// ensure the URL to be relative to the application
sMockServerUrl = sMockServerUrl && new URI(sMockServerUrl).absoluteTo(sap.ui.require.toUrl(_sAppPath)).toString();
// create a mock server instance or stop the existing one to reinitialize
if (!oMockServer) {
oMockServer = new MockServer({
rootUri: sMockServerUrl
});
} else {
oMockServer.stop();
}
// configure mock server with the given options or a default delay of 0.5s
MockServer.config({
autoRespond : true,
autoRespondAfter : (oOptions.delay || oUriParameters.get("serverDelay") || 500)
});
// simulate all requests using mock data
oMockServer.simulate(sMetadataUrl, {
sMockdataBaseUrl : sJsonFilesUrl,
bGenerateMissingMockData : true
});
var aRequests = oMockServer.getRequests();
// compose an error response for each request
var fnResponse = function (iErrCode, sMessage, aRequest) {
aRequest.response = function(oXhr){
oXhr.respond(iErrCode, {"Content-Type": "text/plain;charset=utf-8"}, sMessage);
};
};
// simulate metadata errors
if (oOptions.metadataError || oUriParameters.get("metadataError")) {
aRequests.forEach(function (aEntry) {
if (aEntry.path.toString().indexOf("$metadata") > -1) {
fnResponse(500, "metadata Error", aEntry);
}
});
}
// simulate request errors
var sErrorParam = oOptions.errorType || oUriParameters.get("errorType"),
iErrorCode = sErrorParam === "badRequest" ? 400 : 500;
if (sErrorParam) {
aRequests.forEach(function (aEntry) {
fnResponse(iErrorCode, sErrorParam, aEntry);
});
}
// custom mock behaviour may be added here
// set requests and start the server
oMockServer.setRequests(aRequests);
oMockServer.start();
Log.info("Running the app with mock data");
fnResolve();
});
oManifestModel.attachRequestFailed(function () {
var sError = "Failed to load application manifest";
Log.error(sError);
fnReject(new Error(sError));
});
});
},
/**
* @public returns the mockserver of the app, should be used in integration tests
* @returns {sap.ui.core.util.MockServer} the mockserver instance
*/
getMockServer : function () {
return oMockServer;
}
};
return oMockServerInterface;
});
我的 oData 元数据中的所有集合都具有 ID
整数类型! (真实网关服务器自动增量)
有趣的是,当我创建一个集合的新对象时,它将分配 9
作为第一次创建的对象的 id,而第二个创建的对象将是 416
等等。
很明显,内置模拟服务器使用随机生成算法,不带或带静态种子。这就是它会为我的元数据模型中的每个集合生成始终相同的 ID 链的原因。
现在我的问题是如何更改 UI5 模拟服务器的这种行为?
换句话说,我如何设置一个随机数作为模拟服务器的种子,或者我如何强制它对 ID 使用增量行为。
生成 9, 416, 6671, 2631, ...
作为 id 的 UI5 默认行为的问题是当其中一个集合已经有一个带有 id 9
的项目时!然后通过创建一个新项目,我的列表中将有两个具有相同 ID(即 9)的项目!
查看UI5 mock server的source code,随机种子好像没有public setter
如果要模拟顺序ID的生成,可以在mock server处理完请求后使用MockServer#attachAfter()改变生成的值,像这样:
oMockServer.attachAfter("POST", oEvent => {
oEvent.getParameter("oEntity").Id = generateId()
}, "<your entity set name>")
如果您需要完全控制模拟服务器如何响应请求,您也可以 override its behavior per request。
我有一个 UI5
应用程序,我 运行 它带有 UI5
用于测试的标准内置模拟服务器。
这是 mockserver.js 中由 Web IDE
自动生成的代码:
sap.ui.define([
"sap/ui/core/util/MockServer",
"sap/ui/model/json/JSONModel",
"sap/base/util/UriParameters",
"sap/base/Log"
], function (MockServer, JSONModel, UriParameters, Log) {
"use strict";
var oMockServer,
_sAppPath = "de/cimt/test/",
_sJsonFilesPath = _sAppPath + "localService/mockdata";
var oMockServerInterface = {
/**
* Initializes the mock server asynchronously.
* You can configure the delay with the URL parameter "serverDelay".
* The local mock data in this folder is returned instead of the real data for testing.
* @protected
* @param {object} [oOptionsParameter] init parameters for the mockserver
* @returns{Promise} a promise that is resolved when the mock server has been started
*/
init : function (oOptionsParameter) {
var oOptions = oOptionsParameter || {};
return new Promise(function(fnResolve, fnReject) {
var sManifestUrl = sap.ui.require.toUrl(_sAppPath + "manifest.json"),
oManifestModel = new JSONModel(sManifestUrl);
oManifestModel.attachRequestCompleted(function () {
var oUriParameters = new UriParameters(window.location.href),
// parse manifest for local metatadata URI
sJsonFilesUrl = sap.ui.require.toUrl(_sJsonFilesPath),
oMainDataSource = oManifestModel.getProperty("/sap.app/dataSources/mainService"),
sMetadataUrl = sap.ui.require.toUrl(_sAppPath + oMainDataSource.settings.localUri),
// ensure there is a trailing slash
sMockServerUrl = /.*\/$/.test(oMainDataSource.uri) ? oMainDataSource.uri : oMainDataSource.uri + "/";
// ensure the URL to be relative to the application
sMockServerUrl = sMockServerUrl && new URI(sMockServerUrl).absoluteTo(sap.ui.require.toUrl(_sAppPath)).toString();
// create a mock server instance or stop the existing one to reinitialize
if (!oMockServer) {
oMockServer = new MockServer({
rootUri: sMockServerUrl
});
} else {
oMockServer.stop();
}
// configure mock server with the given options or a default delay of 0.5s
MockServer.config({
autoRespond : true,
autoRespondAfter : (oOptions.delay || oUriParameters.get("serverDelay") || 500)
});
// simulate all requests using mock data
oMockServer.simulate(sMetadataUrl, {
sMockdataBaseUrl : sJsonFilesUrl,
bGenerateMissingMockData : true
});
var aRequests = oMockServer.getRequests();
// compose an error response for each request
var fnResponse = function (iErrCode, sMessage, aRequest) {
aRequest.response = function(oXhr){
oXhr.respond(iErrCode, {"Content-Type": "text/plain;charset=utf-8"}, sMessage);
};
};
// simulate metadata errors
if (oOptions.metadataError || oUriParameters.get("metadataError")) {
aRequests.forEach(function (aEntry) {
if (aEntry.path.toString().indexOf("$metadata") > -1) {
fnResponse(500, "metadata Error", aEntry);
}
});
}
// simulate request errors
var sErrorParam = oOptions.errorType || oUriParameters.get("errorType"),
iErrorCode = sErrorParam === "badRequest" ? 400 : 500;
if (sErrorParam) {
aRequests.forEach(function (aEntry) {
fnResponse(iErrorCode, sErrorParam, aEntry);
});
}
// custom mock behaviour may be added here
// set requests and start the server
oMockServer.setRequests(aRequests);
oMockServer.start();
Log.info("Running the app with mock data");
fnResolve();
});
oManifestModel.attachRequestFailed(function () {
var sError = "Failed to load application manifest";
Log.error(sError);
fnReject(new Error(sError));
});
});
},
/**
* @public returns the mockserver of the app, should be used in integration tests
* @returns {sap.ui.core.util.MockServer} the mockserver instance
*/
getMockServer : function () {
return oMockServer;
}
};
return oMockServerInterface;
});
我的 oData 元数据中的所有集合都具有 ID
整数类型! (真实网关服务器自动增量)
有趣的是,当我创建一个集合的新对象时,它将分配 9
作为第一次创建的对象的 id,而第二个创建的对象将是 416
等等。
很明显,内置模拟服务器使用随机生成算法,不带或带静态种子。这就是它会为我的元数据模型中的每个集合生成始终相同的 ID 链的原因。
现在我的问题是如何更改 UI5 模拟服务器的这种行为?
换句话说,我如何设置一个随机数作为模拟服务器的种子,或者我如何强制它对 ID 使用增量行为。
生成 9, 416, 6671, 2631, ...
作为 id 的 UI5 默认行为的问题是当其中一个集合已经有一个带有 id 9
的项目时!然后通过创建一个新项目,我的列表中将有两个具有相同 ID(即 9)的项目!
查看UI5 mock server的source code,随机种子好像没有public setter
如果要模拟顺序ID的生成,可以在mock server处理完请求后使用MockServer#attachAfter()改变生成的值,像这样:
oMockServer.attachAfter("POST", oEvent => {
oEvent.getParameter("oEntity").Id = generateId()
}, "<your entity set name>")
如果您需要完全控制模拟服务器如何响应请求,您也可以 override its behavior per request。