在 java 中模拟功能接口调用
Mocking functional interface call in java
我有一个调用功能接口的方法实现 (Java 8),我正在尝试为其编写单元测试。这是我要测试的方法:
// Impl
public Optional<ExternalRelease> getStagedRelease(AccessParams accessParams) throws DigitalIngestionException {
String resourcesPath=getReleaseResourcesPath(accessParams).orElseThrow(() -> new ValidationException(WRONG_ACCESS_CONTEXT_EXCEPTION));
String ddexFilePath=getReleaseDdexPath(accessParams).get();
if( stageDataManager.directoryExists(resourcesPath) ) {
List<Track> tracks = getTracks(accessParams).
orElse(new ArrayList<>());
ExternalRelease externalRelease = null;
//Verify if lite XML already exists
if( stageDataManager.fileExists(ddexFilePath) ) {
//Load externalRelease values
String liteDdex = stageDataManager.loadFileContent(ddexFilePath).
orElseThrow(() -> new ProcessException("Lite DDEX content couldn't be read."));
externalRelease = ddexManagerExecutor( (ddexManager) -> ddexManager.getExternalReleaseFromLiteDdex(liteDdex) ).
orElseThrow(() -> new ProcessException("External release couldn't be parsed from Lite DDEX."));
externalRelease.setTracks(tracks);
return Optional.ofNullable(externalRelease);
} else {
//Create lite ddex if it doesn't exist
ExternalRelease releaseFromTracks=getReleaseFromTracks(tracks);
String liteDdex = ddexManagerExecutor( (ddexManager) -> ddexManager.getLiteDdexFromAccessParamsAndExternalRelease(accessParams, releaseFromTracks)).
orElseThrow(() -> new ProcessException("Lite DDEX content couldn't be generated."));
stageDataManager.writeStringInFile(ddexFilePath, liteDdex);
return Optional.ofNullable(releaseFromTracks);
}
} else {
return Optional.empty();
}
}
注意第二个 IF
中的行
externalRelease = ddexManagerExecutor( (ddexManager) -> ddexManager.getExternalReleaseFromLiteDdex(liteDdex) ).orElseThrow(() -> new ProcessException("External release couldn't be parsed from Lite DDEX."));`
ddexManagerExecutor 是一个功能接口,使用 java 8 个功能:
public interface ddexManagerConsumer<R> {
R process(DdexManager ddexManager) throws ProcessException;
}
private <R> R ddexManagerExecutor(ddexManagerConsumer<R> action) throws ProcessException {
DdexManager ddexManager = null;
try {
ddexManager = (DdexManager) ddexManagerPool.getTarget();
return action.process(ddexManager);
} catch (Exception e) {
throw new ProcessException("Error while accessing to ddexManager pool.");
} finally {
try {
ddexManagerPool.releaseTarget(ddexManager);
} catch (Exception e) {
log.error("Error while releasing ddexManager instance.", e);
}
}
}
所以在我的单元测试中,我正在尝试执行以下操作,
@Test
public void getStagedReleaseTest_whenFileDoesNoExist() throws Exception{
AccessParams accessParams = getDefaultAccessParams();
File file = new File("src/test/resources/testTrack.mp3");
String xml="<xml/>";
accessParams.setFileName("testTrack.mp3");
accessParams.setReleaseSlug("test-release-slug");
Optional<List<File>> mockFileList = Optional.of(Arrays.asList(file));
when(mockedStageDataManager.directoryExists(any())).thenReturn(true);
when(mockedStageDataManager.getResources(anyString(), any())).thenReturn(mockFileList);
when(mockedStageDataManager.fileExists(anyString())).thenReturn(false);
when(mockedStageDataManager.loadFileContent(anyString())).thenReturn(Optional.of(xml));
when(mockedDdexManager.getLiteDdexFromAccessParamsAndExternalRelease(any(), any())).thenReturn(Optional.of(xml));
DigitalIngestionServiceImpl serviceSpy = spy(service);
Optional<ExternalRelease> externalRelease = serviceSpy.getStagedRelease(accessParams);
Assert.assertNotNull(externalRelease);
}
这破坏了我的单元测试,因为我没有模拟对私有功能接口的调用。我只是在考虑嘲笑以下内线:
ddexManager.getExternalReleaseFromLiteDdex(liteDdex)
但是none对于调用上述方法的功能接口调用。任何线索如何实现这一目标?
您可以模拟 ddexManagerPool.getTarget()
以便 return 一个模拟的 DdexManager
将 return 您在调用 getExternalReleaseFromLiteDdex
时想要的结果
我有一个调用功能接口的方法实现 (Java 8),我正在尝试为其编写单元测试。这是我要测试的方法:
// Impl
public Optional<ExternalRelease> getStagedRelease(AccessParams accessParams) throws DigitalIngestionException {
String resourcesPath=getReleaseResourcesPath(accessParams).orElseThrow(() -> new ValidationException(WRONG_ACCESS_CONTEXT_EXCEPTION));
String ddexFilePath=getReleaseDdexPath(accessParams).get();
if( stageDataManager.directoryExists(resourcesPath) ) {
List<Track> tracks = getTracks(accessParams).
orElse(new ArrayList<>());
ExternalRelease externalRelease = null;
//Verify if lite XML already exists
if( stageDataManager.fileExists(ddexFilePath) ) {
//Load externalRelease values
String liteDdex = stageDataManager.loadFileContent(ddexFilePath).
orElseThrow(() -> new ProcessException("Lite DDEX content couldn't be read."));
externalRelease = ddexManagerExecutor( (ddexManager) -> ddexManager.getExternalReleaseFromLiteDdex(liteDdex) ).
orElseThrow(() -> new ProcessException("External release couldn't be parsed from Lite DDEX."));
externalRelease.setTracks(tracks);
return Optional.ofNullable(externalRelease);
} else {
//Create lite ddex if it doesn't exist
ExternalRelease releaseFromTracks=getReleaseFromTracks(tracks);
String liteDdex = ddexManagerExecutor( (ddexManager) -> ddexManager.getLiteDdexFromAccessParamsAndExternalRelease(accessParams, releaseFromTracks)).
orElseThrow(() -> new ProcessException("Lite DDEX content couldn't be generated."));
stageDataManager.writeStringInFile(ddexFilePath, liteDdex);
return Optional.ofNullable(releaseFromTracks);
}
} else {
return Optional.empty();
}
}
注意第二个 IF
中的行 externalRelease = ddexManagerExecutor( (ddexManager) -> ddexManager.getExternalReleaseFromLiteDdex(liteDdex) ).orElseThrow(() -> new ProcessException("External release couldn't be parsed from Lite DDEX."));`
ddexManagerExecutor 是一个功能接口,使用 java 8 个功能:
public interface ddexManagerConsumer<R> {
R process(DdexManager ddexManager) throws ProcessException;
}
private <R> R ddexManagerExecutor(ddexManagerConsumer<R> action) throws ProcessException {
DdexManager ddexManager = null;
try {
ddexManager = (DdexManager) ddexManagerPool.getTarget();
return action.process(ddexManager);
} catch (Exception e) {
throw new ProcessException("Error while accessing to ddexManager pool.");
} finally {
try {
ddexManagerPool.releaseTarget(ddexManager);
} catch (Exception e) {
log.error("Error while releasing ddexManager instance.", e);
}
}
}
所以在我的单元测试中,我正在尝试执行以下操作,
@Test
public void getStagedReleaseTest_whenFileDoesNoExist() throws Exception{
AccessParams accessParams = getDefaultAccessParams();
File file = new File("src/test/resources/testTrack.mp3");
String xml="<xml/>";
accessParams.setFileName("testTrack.mp3");
accessParams.setReleaseSlug("test-release-slug");
Optional<List<File>> mockFileList = Optional.of(Arrays.asList(file));
when(mockedStageDataManager.directoryExists(any())).thenReturn(true);
when(mockedStageDataManager.getResources(anyString(), any())).thenReturn(mockFileList);
when(mockedStageDataManager.fileExists(anyString())).thenReturn(false);
when(mockedStageDataManager.loadFileContent(anyString())).thenReturn(Optional.of(xml));
when(mockedDdexManager.getLiteDdexFromAccessParamsAndExternalRelease(any(), any())).thenReturn(Optional.of(xml));
DigitalIngestionServiceImpl serviceSpy = spy(service);
Optional<ExternalRelease> externalRelease = serviceSpy.getStagedRelease(accessParams);
Assert.assertNotNull(externalRelease);
}
这破坏了我的单元测试,因为我没有模拟对私有功能接口的调用。我只是在考虑嘲笑以下内线:
ddexManager.getExternalReleaseFromLiteDdex(liteDdex)
但是none对于调用上述方法的功能接口调用。任何线索如何实现这一目标?
您可以模拟 ddexManagerPool.getTarget()
以便 return 一个模拟的 DdexManager
将 return 您在调用 getExternalReleaseFromLiteDdex