Skip to content

Commit 73c555e

Browse files
Add missing unit tests for toc endpoint
RISDEV-6266
1 parent 8ed12e6 commit 73c555e

File tree

2 files changed

+195
-0
lines changed

2 files changed

+195
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,129 @@
1+
package de.bund.digitalservice.ris.norms.adapter.input.restapi.controller;
2+
3+
import static org.mockito.ArgumentMatchers.any;
4+
import static org.mockito.Mockito.when;
5+
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
6+
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.jsonPath;
7+
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
8+
9+
import de.bund.digitalservice.ris.norms.application.exception.RegelungstextNotFoundException;
10+
import de.bund.digitalservice.ris.norms.application.port.input.*;
11+
import de.bund.digitalservice.ris.norms.config.SecurityConfig;
12+
import de.bund.digitalservice.ris.norms.domain.entity.*;
13+
import de.bund.digitalservice.ris.norms.domain.entity.eli.DokumentExpressionEli;
14+
import java.util.Collections;
15+
import java.util.List;
16+
import org.junit.jupiter.api.Test;
17+
import org.springframework.beans.factory.annotation.Autowired;
18+
import org.springframework.boot.autoconfigure.security.oauth2.client.servlet.OAuth2ClientAutoConfiguration;
19+
import org.springframework.boot.test.autoconfigure.web.servlet.WebMvcTest;
20+
import org.springframework.http.MediaType;
21+
import org.springframework.security.test.context.support.WithMockUser;
22+
import org.springframework.test.context.bean.override.mockito.MockitoBean;
23+
import org.springframework.test.web.servlet.MockMvc;
24+
25+
/**
26+
* Not using SpringBootTest annotation to avoid needing a database connection. Using @Import to load
27+
* the {@link SecurityConfig} in order to avoid http 401 Unauthorised
28+
*/
29+
@WithMockUser
30+
@WebMvcTest(
31+
controllers = TableOfContentsController.class,
32+
excludeAutoConfiguration = OAuth2ClientAutoConfiguration.class
33+
)
34+
class TableOfContentsControllerTest {
35+
36+
@Autowired
37+
private MockMvc mockMvc;
38+
39+
@MockitoBean
40+
private LoadTocFromRegelungstextUseCase loadTocFromRegelungstextUseCase;
41+
42+
@Test
43+
void itReturnsTableOfContents() throws Exception {
44+
// Given
45+
var eli = DokumentExpressionEli.fromString(
46+
"eli/bund/bgbl-1/2017/s419/2017-03-15/1/deu/regelungstext-1"
47+
);
48+
final TableOfContentsItem childItem = new TableOfContentsItem(
49+
"child-id",
50+
"child-marker",
51+
"child-heading",
52+
"child-type",
53+
Collections.emptyList()
54+
);
55+
final TableOfContentsItem parentItem = new TableOfContentsItem(
56+
"parent-id",
57+
"parent-marker",
58+
"parent-heading",
59+
"parent-type",
60+
List.of(childItem)
61+
);
62+
when(loadTocFromRegelungstextUseCase.loadTocFromRegelungstext(any()))
63+
.thenReturn(List.of(parentItem));
64+
65+
// When // Then
66+
mockMvc
67+
.perform(get("/api/v1/norms/" + eli + "/toc").accept(MediaType.APPLICATION_JSON))
68+
.andExpect(status().isOk())
69+
.andExpect(jsonPath("$[0].id").value("parent-id"))
70+
.andExpect(jsonPath("$[0].marker").value("parent-marker"))
71+
.andExpect(jsonPath("$[0].heading").value("parent-heading"))
72+
.andExpect(jsonPath("$[0].type").value("parent-type"))
73+
.andExpect(jsonPath("$[0].children[0].id").value("child-id"))
74+
.andExpect(jsonPath("$[0].children[0].marker").value("child-marker"))
75+
.andExpect(jsonPath("$[0].children[0].heading").value("child-heading"))
76+
.andExpect(jsonPath("$[0].children[0].type").value("child-type"));
77+
}
78+
79+
@Test
80+
void itReturnsEmptyListWhenNoTableOfContentsExists() throws Exception {
81+
// Given
82+
var eli = DokumentExpressionEli.fromString(
83+
"eli/bund/bgbl-1/2017/s419/2017-03-15/1/deu/regelungstext-1"
84+
);
85+
when(loadTocFromRegelungstextUseCase.loadTocFromRegelungstext(any())).thenReturn(List.of());
86+
87+
// When // Then
88+
mockMvc
89+
.perform(get("/api/v1/norms/" + eli + "/toc").accept(MediaType.APPLICATION_JSON))
90+
.andExpect(status().isOk())
91+
.andExpect(jsonPath("$").isEmpty());
92+
}
93+
94+
@Test
95+
void return404IfRegelungstextNotFound() throws Exception {
96+
// given no norm
97+
var eli = DokumentExpressionEli.fromString(
98+
"eli/bund/NONEXISTENT_NORM/1964/s593/1964-08-05/1/deu/regelungstext-1"
99+
);
100+
101+
when(loadTocFromRegelungstextUseCase.loadTocFromRegelungstext(any()))
102+
.thenThrow(new RegelungstextNotFoundException(eli.toString()));
103+
104+
// when
105+
mockMvc
106+
.perform(get("/api/v1/norms/" + eli + "/toc").accept(MediaType.APPLICATION_JSON_VALUE))
107+
// then
108+
.andExpect(status().isNotFound())
109+
.andExpect(jsonPath("type").value("/errors/regelungstext-not-found"))
110+
.andExpect(jsonPath("title").value("Regelungstext not found"))
111+
.andExpect(jsonPath("status").value(404))
112+
.andExpect(
113+
jsonPath("detail")
114+
.value(
115+
"Regelungstext with eli eli/bund/NONEXISTENT_NORM/1964/s593/1964-08-05/1/deu/regelungstext-1 does not exist"
116+
)
117+
)
118+
.andExpect(
119+
jsonPath("instance")
120+
.value(
121+
"/api/v1/norms/eli/bund/NONEXISTENT_NORM/1964/s593/1964-08-05/1/deu/regelungstext-1/toc"
122+
)
123+
)
124+
.andExpect(
125+
jsonPath("eli")
126+
.value("eli/bund/NONEXISTENT_NORM/1964/s593/1964-08-05/1/deu/regelungstext-1")
127+
);
128+
}
129+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
package de.bund.digitalservice.ris.norms.adapter.input.restapi.mapper;
2+
3+
import static org.assertj.core.api.Assertions.assertThat;
4+
5+
import de.bund.digitalservice.ris.norms.adapter.input.restapi.schema.TableOfContentsResponseSchema;
6+
import de.bund.digitalservice.ris.norms.domain.entity.TableOfContentsItem;
7+
import java.util.Collections;
8+
import java.util.List;
9+
import org.junit.jupiter.api.Test;
10+
11+
class TableOfContentsResponseMapperTest {
12+
13+
@Test
14+
void shouldMapTableOfContentsItemsToResponseSchema() {
15+
// Given
16+
final TableOfContentsItem childItem = new TableOfContentsItem(
17+
"child-id",
18+
"child-marker",
19+
"child-heading",
20+
"child-type",
21+
Collections.emptyList()
22+
);
23+
final TableOfContentsItem parentItem = new TableOfContentsItem(
24+
"parent-id",
25+
"parent-marker",
26+
"parent-heading",
27+
"parent-type",
28+
List.of(childItem)
29+
);
30+
31+
final List<TableOfContentsItem> tableOfContents = List.of(parentItem);
32+
33+
// When
34+
final List<TableOfContentsResponseSchema> response =
35+
TableOfContentsResponseMapper.fromTableOfContents(tableOfContents);
36+
37+
// Then
38+
assertThat(response).hasSize(1);
39+
final TableOfContentsResponseSchema parentResponse = response.getFirst();
40+
assertThat(parentResponse.getId()).isEqualTo("parent-id");
41+
assertThat(parentResponse.getMarker()).isEqualTo("parent-marker");
42+
assertThat(parentResponse.getHeading()).isEqualTo("parent-heading");
43+
assertThat(parentResponse.getType()).isEqualTo("parent-type");
44+
assertThat(parentResponse.getChildren()).hasSize(1);
45+
46+
final TableOfContentsResponseSchema childResponse = parentResponse.getChildren().getFirst();
47+
assertThat(childResponse.getId()).isEqualTo("child-id");
48+
assertThat(childResponse.getMarker()).isEqualTo("child-marker");
49+
assertThat(childResponse.getHeading()).isEqualTo("child-heading");
50+
assertThat(childResponse.getType()).isEqualTo("child-type");
51+
assertThat(childResponse.getChildren()).isEmpty();
52+
}
53+
54+
@Test
55+
void shouldReturnEmptyListWhenTableOfContentsIsEmpty() {
56+
// Given
57+
final List<TableOfContentsItem> tableOfContents = List.of();
58+
59+
// When
60+
final List<TableOfContentsResponseSchema> response =
61+
TableOfContentsResponseMapper.fromTableOfContents(tableOfContents);
62+
63+
// Then
64+
assertThat(response).isEmpty();
65+
}
66+
}

0 commit comments

Comments
 (0)