Merge remote-tracking branch 'base-version/main' into dev
# Conflicts: # zt-dependencies/pom.xml
This commit is contained in:
@@ -0,0 +1,121 @@
|
||||
package com.zt.plat.module.system.service.integration.iwork.impl;
|
||||
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.zt.plat.module.system.controller.admin.integration.iwork.vo.IWorkOrgQueryReqVO;
|
||||
import com.zt.plat.module.system.controller.admin.integration.iwork.vo.IWorkOrgRespVO;
|
||||
import com.zt.plat.module.system.controller.admin.integration.iwork.vo.IWorkOrgSyncReqVO;
|
||||
import com.zt.plat.module.system.framework.integration.iwork.config.IWorkProperties;
|
||||
import com.zt.plat.module.system.service.integration.iwork.IWorkOrgRestService;
|
||||
import okhttp3.mockwebserver.MockResponse;
|
||||
import okhttp3.mockwebserver.MockWebServer;
|
||||
import okhttp3.mockwebserver.RecordedRequest;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.util.DigestUtils;
|
||||
|
||||
import java.net.URLDecoder;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.time.Clock;
|
||||
import java.time.Duration;
|
||||
import java.time.Instant;
|
||||
import java.time.ZoneOffset;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
class IWorkOrgRestServiceImplTest {
|
||||
|
||||
private MockWebServer mockWebServer;
|
||||
private IWorkOrgRestService service;
|
||||
private IWorkProperties properties;
|
||||
private Clock fixedClock;
|
||||
|
||||
@BeforeEach
|
||||
void setUp() throws Exception {
|
||||
mockWebServer = new MockWebServer();
|
||||
mockWebServer.start();
|
||||
|
||||
properties = buildProperties();
|
||||
fixedClock = Clock.fixed(Instant.ofEpochMilli(1_672_531_200_000L), ZoneOffset.UTC);
|
||||
service = new IWorkOrgRestServiceImpl(properties, new ObjectMapper(), fixedClock);
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
void tearDown() throws Exception {
|
||||
mockWebServer.shutdown();
|
||||
}
|
||||
|
||||
@Test
|
||||
void shouldListSubcompanies() throws Exception {
|
||||
mockWebServer.enqueue(jsonResponse("{\"code\":\"1\",\"data\":{\"page\":1}}"));
|
||||
|
||||
IWorkOrgQueryReqVO reqVO = new IWorkOrgQueryReqVO();
|
||||
reqVO.setParams(Map.of("curpage", 1));
|
||||
IWorkOrgRespVO respVO = service.listSubcompanies(reqVO);
|
||||
|
||||
assertThat(respVO.isSuccess()).isTrue();
|
||||
assertThat(respVO.getPayload()).containsEntry("page", 1);
|
||||
|
||||
RecordedRequest request = mockWebServer.takeRequest();
|
||||
assertThat(request.getPath()).isEqualTo(properties.getOrg().getPaths().getSubcompanyPage());
|
||||
String decoded = URLDecoder.decode(request.getBody().readUtf8(), StandardCharsets.UTF_8);
|
||||
assertThat(decoded).contains("params={\"curpage\":1}");
|
||||
String tokenJson = extractField(decoded, "token");
|
||||
assertThat(tokenJson).isNotBlank();
|
||||
assertThat(tokenJson).contains("\"ts\":\"1672531200000\"");
|
||||
String expectedKey = DigestUtils.md5DigestAsHex("test-seed1672531200000".getBytes(StandardCharsets.UTF_8)).toUpperCase();
|
||||
assertThat(tokenJson).contains("\"key\":\"" + expectedKey + "\"");
|
||||
}
|
||||
|
||||
@Test
|
||||
void shouldSyncDepartments() throws Exception {
|
||||
mockWebServer.enqueue(jsonResponse("{\"code\":\"1\",\"result\":{}}"));
|
||||
|
||||
IWorkOrgSyncReqVO reqVO = new IWorkOrgSyncReqVO();
|
||||
reqVO.setData(List.of(Map.of("@action", "add", "code", "demo")));
|
||||
IWorkOrgRespVO respVO = service.syncDepartments(reqVO);
|
||||
|
||||
assertThat(respVO.isSuccess()).isTrue();
|
||||
assertThat(respVO.getPayload()).containsKey("result");
|
||||
|
||||
RecordedRequest request = mockWebServer.takeRequest();
|
||||
assertThat(request.getPath()).isEqualTo(properties.getOrg().getPaths().getSyncDepartment());
|
||||
String decoded = URLDecoder.decode(request.getBody().readUtf8(), StandardCharsets.UTF_8);
|
||||
assertThat(decoded).contains("data=[{\"@action\":\"add\",\"code\":\"demo\"}]");
|
||||
}
|
||||
|
||||
private MockResponse jsonResponse(String body) {
|
||||
return new MockResponse()
|
||||
.setHeader("Content-Type", "application/json")
|
||||
.setBody(body);
|
||||
}
|
||||
|
||||
private String extractField(String decoded, String key) {
|
||||
return Arrays.stream(decoded.split("&"))
|
||||
.filter(part -> part.startsWith(key + "="))
|
||||
.map(part -> part.substring(key.length() + 1))
|
||||
.findFirst()
|
||||
.orElse("");
|
||||
}
|
||||
|
||||
private IWorkProperties buildProperties() {
|
||||
IWorkProperties properties = new IWorkProperties();
|
||||
properties.setBaseUrl(mockWebServer.url("/").toString());
|
||||
properties.getClient().setConnectTimeout(Duration.ofSeconds(5));
|
||||
properties.getClient().setResponseTimeout(Duration.ofSeconds(5));
|
||||
properties.getOrg().setTokenSeed("test-seed");
|
||||
IWorkProperties.OrgPaths paths = properties.getOrg().getPaths();
|
||||
paths.setSubcompanyPage("/api/hrm/resful/getHrmsubcompanyWithPage");
|
||||
paths.setDepartmentPage("/api/hrm/resful/getHrmdepartmentWithPage");
|
||||
paths.setJobTitlePage("/api/hrm/resful/getJobtitleInfoWithPage");
|
||||
paths.setUserPage("/api/hrm/resful/getHrmUserInfoWithPage");
|
||||
paths.setSyncSubcompany("/api/hrm/resful/synSubcompany");
|
||||
paths.setSyncDepartment("/api/hrm/resful/synDepartment");
|
||||
paths.setSyncJobTitle("/api/hrm/resful/synJobtitle");
|
||||
paths.setSyncUser("/api/hrm/resful/synHrmresource");
|
||||
return properties;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,85 @@
|
||||
package com.zt.plat.module.system.service.sso;
|
||||
|
||||
import com.zt.plat.module.system.framework.sso.config.ExternalSsoProperties;
|
||||
import com.zt.plat.module.system.service.logger.LoginLogService;
|
||||
import com.zt.plat.module.system.service.logger.OperateLogService;
|
||||
import com.zt.plat.module.system.service.oauth2.OAuth2TokenService;
|
||||
import com.zt.plat.module.system.service.sso.strategy.ExternalSsoStrategy;
|
||||
import com.zt.plat.module.system.service.user.AdminUserService;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.test.util.ReflectionTestUtils;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
class ExternalSsoServiceImplTest {
|
||||
|
||||
@Test
|
||||
void selectStrategy_returnsExactMatch_whenStrategySupportsSource() {
|
||||
ExternalSsoStrategy exactStrategy = mock(ExternalSsoStrategy.class);
|
||||
ExternalSsoStrategy fallbackStrategy = mock(ExternalSsoStrategy.class);
|
||||
when(exactStrategy.supports("BRMS")).thenReturn(true);
|
||||
|
||||
ExternalSsoServiceImpl service = newService(List.of(exactStrategy, fallbackStrategy));
|
||||
|
||||
ExternalSsoStrategy selected = invokeSelectStrategy(service, "BRMS");
|
||||
assertThat(selected).isSameAs(exactStrategy);
|
||||
}
|
||||
|
||||
@Test
|
||||
void selectStrategy_returnsWildcardStrategy_whenNoExactMatch() {
|
||||
ExternalSsoStrategy strictStrategy = mock(ExternalSsoStrategy.class);
|
||||
ExternalSsoStrategy wildcardStrategy = mock(ExternalSsoStrategy.class);
|
||||
when(strictStrategy.supports("ERP")).thenReturn(false);
|
||||
when(strictStrategy.supports(null)).thenReturn(false);
|
||||
when(wildcardStrategy.supports("ERP")).thenReturn(false);
|
||||
when(wildcardStrategy.supports(null)).thenReturn(true);
|
||||
|
||||
ExternalSsoServiceImpl service = newService(List.of(strictStrategy, wildcardStrategy));
|
||||
|
||||
ExternalSsoStrategy selected = invokeSelectStrategy(service, "ERP");
|
||||
assertThat(selected).isSameAs(wildcardStrategy);
|
||||
}
|
||||
|
||||
@Test
|
||||
void selectStrategy_returnsNull_whenNoStrategyAvailable() {
|
||||
ExternalSsoServiceImpl service = newService(Collections.emptyList());
|
||||
|
||||
ExternalSsoStrategy selected = invokeSelectStrategy(service, "ANY");
|
||||
assertThat(selected).isNull();
|
||||
}
|
||||
|
||||
@Test
|
||||
void selectStrategy_skipsStrategy_whenSupportsThrowsException() {
|
||||
ExternalSsoStrategy unstableStrategy = mock(ExternalSsoStrategy.class);
|
||||
ExternalSsoStrategy fallbackStrategy = mock(ExternalSsoStrategy.class);
|
||||
when(unstableStrategy.supports("CRM")).thenThrow(new IllegalStateException("boom"));
|
||||
when(unstableStrategy.supports(null)).thenReturn(false);
|
||||
when(fallbackStrategy.supports("CRM")).thenReturn(false);
|
||||
when(fallbackStrategy.supports(null)).thenReturn(true);
|
||||
|
||||
ExternalSsoServiceImpl service = newService(List.of(unstableStrategy, fallbackStrategy));
|
||||
|
||||
ExternalSsoStrategy selected = invokeSelectStrategy(service, "CRM");
|
||||
assertThat(selected).isSameAs(fallbackStrategy);
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
private ExternalSsoStrategy invokeSelectStrategy(ExternalSsoServiceImpl service, String sourceSystem) {
|
||||
return ReflectionTestUtils.invokeMethod(service, "selectStrategy", sourceSystem);
|
||||
}
|
||||
|
||||
private ExternalSsoServiceImpl newService(List<ExternalSsoStrategy> strategies) {
|
||||
ExternalSsoProperties properties = new ExternalSsoProperties();
|
||||
AdminUserService adminUserService = mock(AdminUserService.class);
|
||||
LoginLogService loginLogService = mock(LoginLogService.class);
|
||||
OAuth2TokenService oauth2TokenService = mock(OAuth2TokenService.class);
|
||||
OperateLogService operateLogService = mock(OperateLogService.class);
|
||||
return new ExternalSsoServiceImpl(properties, strategies, adminUserService,
|
||||
loginLogService, oauth2TokenService, operateLogService);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user