From a17deb9b7f207fe71b60a968da293b9412310144 Mon Sep 17 00:00:00 2001 From: vsxd Date: Fri, 20 Mar 2026 11:25:50 +0800 Subject: [PATCH] test(app): cover missing query context paths --- .../JpaGovernanceQueryRepositoryTest.java | 38 +++++++++++++++++++ .../JpaMySkillQueryRepositoryTest.java | 23 +++++++++++ .../JpaProfileReviewQueryRepositoryTest.java | 24 ++++++++++++ .../auth/oauth/OAuthLoginFlowServiceTest.java | 17 +++++++++ 4 files changed, 102 insertions(+) diff --git a/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaGovernanceQueryRepositoryTest.java b/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaGovernanceQueryRepositoryTest.java index 197264d7..beb53df9 100644 --- a/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaGovernanceQueryRepositoryTest.java +++ b/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaGovernanceQueryRepositoryTest.java @@ -145,6 +145,44 @@ class JpaGovernanceQueryRepositoryTest { assertThat(responses.get(0).subtitle()).isEqualTo("Spam"); } + @Test + void getReviewInboxItems_toleratesMissingVersionContext() { + ReviewTask task = new ReviewTask(101L, 11L, "submitter"); + setField(task, "id", 4L); + setField(task, "submittedAt", Instant.parse("2026-03-20T04:00:00Z")); + + given(skillVersionRepository.findByIdIn(List.of(101L))).willReturn(List.of()); + + var responses = repository.getReviewInboxItems(List.of(task)); + + assertThat(responses).hasSize(1); + assertThat(responses.get(0).type()).isEqualTo("REVIEW"); + assertThat(responses.get(0).title()).isEqualTo("Unknown target"); + assertThat(responses.get(0).namespace()).isNull(); + assertThat(responses.get(0).skillSlug()).isNull(); + assertThat(responses.get(0).subtitle()).isEqualTo("Pending review"); + } + + @Test + void getPromotionInboxItems_toleratesMissingSourceAndTargetContext() { + PromotionRequest request = new PromotionRequest(201L, 101L, 12L, "submitter"); + setField(request, "id", 5L); + setField(request, "submittedAt", Instant.parse("2026-03-20T05:00:00Z")); + + given(skillRepository.findByIdIn(List.of(201L))).willReturn(List.of()); + given(skillVersionRepository.findByIdIn(List.of(101L))).willReturn(List.of()); + given(namespaceRepository.findByIdIn(List.of(12L))).willReturn(List.of()); + + var responses = repository.getPromotionInboxItems(List.of(request)); + + assertThat(responses).hasSize(1); + assertThat(responses.get(0).type()).isEqualTo("PROMOTION"); + assertThat(responses.get(0).title()).isEqualTo("Unknown target"); + assertThat(responses.get(0).namespace()).isNull(); + assertThat(responses.get(0).skillSlug()).isNull(); + assertThat(responses.get(0).subtitle()).isEqualTo("Pending promotion"); + } + private void setField(Object target, String fieldName, Object value) { try { java.lang.reflect.Field field = target.getClass().getDeclaredField(fieldName); diff --git a/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaMySkillQueryRepositoryTest.java b/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaMySkillQueryRepositoryTest.java index 5e288671..48e05639 100644 --- a/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaMySkillQueryRepositoryTest.java +++ b/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaMySkillQueryRepositoryTest.java @@ -109,4 +109,27 @@ class JpaMySkillQueryRepositoryTest { assertThat(responses.get(0).ownerPreviewVersion()).isNull(); assertThat(responses.get(0).headlineVersion().status()).isEqualTo("PUBLISHED"); } + + @Test + void getSkillSummaries_disablesPromotionWhenNamespaceContextIsMissing() { + Skill skill = new Skill(101L, "orphan-skill", "user-1", SkillVisibility.PUBLIC); + skill.setDisplayName("Orphan Skill"); + ReflectionTestUtils.setField(skill, "id", 4L); + + SkillVersion publishedVersion = new SkillVersion(4L, "1.0.0", "user-1"); + publishedVersion.setStatus(SkillVersionStatus.PUBLISHED); + ReflectionTestUtils.setField(publishedVersion, "id", 44L); + ReflectionTestUtils.setField(publishedVersion, "createdAt", Instant.parse("2026-03-15T10:30:00Z")); + + given(namespaceRepository.findByIdIn(List.of(101L))).willReturn(List.of()); + given(skillVersionRepository.findBySkillIdAndStatus(4L, SkillVersionStatus.PUBLISHED)).willReturn(List.of(publishedVersion)); + given(skillVersionRepository.findBySkillId(4L)).willReturn(List.of(publishedVersion)); + + var responses = repository.getSkillSummaries(List.of(skill), "user-1"); + + assertThat(responses).hasSize(1); + assertThat(responses.get(0).namespace()).isNull(); + assertThat(responses.get(0).publishedVersion()).isNotNull(); + assertThat(responses.get(0).canSubmitPromotion()).isFalse(); + } } diff --git a/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaProfileReviewQueryRepositoryTest.java b/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaProfileReviewQueryRepositoryTest.java index eefb710b..ed8147a1 100644 --- a/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaProfileReviewQueryRepositoryTest.java +++ b/server/skillhub-app/src/test/java/com/iflytek/skillhub/repository/JpaProfileReviewQueryRepositoryTest.java @@ -81,4 +81,28 @@ class JpaProfileReviewQueryRepositoryTest { assertThat(response.get(0).currentDisplayName()).isNull(); assertThat(response.get(0).requestedDisplayName()).isEqualTo("NewName"); } + + @Test + void getProfileReviewSummaries_toleratesInvalidSnapshotJson() { + ProfileChangeRequest request = new ProfileChangeRequest( + "user-2", + "{invalid", + "{also-invalid", + ProfileChangeStatus.PENDING, + "PASS", + null + ); + ReflectionTestUtils.setField(request, "id", 3L); + ReflectionTestUtils.setField(request, "createdAt", Instant.parse("2026-03-19T08:00:00Z")); + + UserAccount submitter = new UserAccount("user-2", "Current Name", "user2@example.com", null); + given(userAccountRepository.findByIdIn(List.of("user-2"))).willReturn(List.of(submitter)); + + var response = repository.getProfileReviewSummaries(List.of(request)); + + assertThat(response).hasSize(1); + assertThat(response.get(0).username()).isEqualTo("Current Name"); + assertThat(response.get(0).currentDisplayName()).isEqualTo("Current Name"); + assertThat(response.get(0).requestedDisplayName()).isNull(); + } } diff --git a/server/skillhub-auth/src/test/java/com/iflytek/skillhub/auth/oauth/OAuthLoginFlowServiceTest.java b/server/skillhub-auth/src/test/java/com/iflytek/skillhub/auth/oauth/OAuthLoginFlowServiceTest.java index 6278d548..029ec294 100644 --- a/server/skillhub-auth/src/test/java/com/iflytek/skillhub/auth/oauth/OAuthLoginFlowServiceTest.java +++ b/server/skillhub-auth/src/test/java/com/iflytek/skillhub/auth/oauth/OAuthLoginFlowServiceTest.java @@ -47,4 +47,21 @@ class OAuthLoginFlowServiceTest { assertThat(redirect).isEqualTo("/access-denied"); } + + @Test + void consumeReturnTo_clearsUnsafeSessionValue() { + OAuthLoginFlowService service = new OAuthLoginFlowService( + List.of(), + mock(AccessPolicy.class), + mock(IdentityBindingService.class) + ); + MockHttpServletRequest request = new MockHttpServletRequest(); + HttpSession session = request.getSession(true); + session.setAttribute(OAuthLoginRedirectSupport.SESSION_RETURN_TO_ATTRIBUTE, "https://evil.example"); + + String returnTo = service.consumeReturnTo(session); + + assertThat(returnTo).isNull(); + assertThat(session.getAttribute(OAuthLoginRedirectSupport.SESSION_RETURN_TO_ATTRIBUTE)).isNull(); + } }