Merge branch 'master' of https://github.com/eugenp/tutorials into BAEL-10982
This commit is contained in:
commit
8f7bc84798
|
@ -9,7 +9,7 @@ public interface IOperations<T extends Serializable> {
|
||||||
|
|
||||||
// read - one
|
// read - one
|
||||||
|
|
||||||
T findOne(final long id);
|
T findById(final long id);
|
||||||
|
|
||||||
// read - all
|
// read - all
|
||||||
|
|
||||||
|
|
|
@ -18,9 +18,8 @@ public abstract class AbstractService<T extends Serializable> implements IOperat
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@Transactional(readOnly = true)
|
@Transactional(readOnly = true)
|
||||||
public T findOne(final long id) {
|
public T findById(final long id) {
|
||||||
return getDao().findById(id)
|
return getDao().findById(id).orElse(null);
|
||||||
.get();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// read - all
|
// read - all
|
||||||
|
|
|
@ -55,7 +55,7 @@ public class WebConfig implements WebMvcConfigurer {
|
||||||
@Bean
|
@Bean
|
||||||
public FilterRegistrationBean<ShallowEtagHeaderFilter> shallowEtagHeaderFilter() {
|
public FilterRegistrationBean<ShallowEtagHeaderFilter> shallowEtagHeaderFilter() {
|
||||||
FilterRegistrationBean<ShallowEtagHeaderFilter> filterRegistrationBean = new FilterRegistrationBean<>( new ShallowEtagHeaderFilter());
|
FilterRegistrationBean<ShallowEtagHeaderFilter> filterRegistrationBean = new FilterRegistrationBean<>( new ShallowEtagHeaderFilter());
|
||||||
filterRegistrationBean.addUrlPatterns("/auth/foos/*");
|
filterRegistrationBean.addUrlPatterns("/foos/*");
|
||||||
filterRegistrationBean.setName("etagFilter");
|
filterRegistrationBean.setName("etagFilter");
|
||||||
return filterRegistrationBean;
|
return filterRegistrationBean;
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,6 +20,7 @@ import org.springframework.web.bind.annotation.RequestMapping;
|
||||||
import org.springframework.web.bind.annotation.RequestParam;
|
import org.springframework.web.bind.annotation.RequestParam;
|
||||||
import org.springframework.web.bind.annotation.ResponseStatus;
|
import org.springframework.web.bind.annotation.ResponseStatus;
|
||||||
import org.springframework.web.bind.annotation.RestController;
|
import org.springframework.web.bind.annotation.RestController;
|
||||||
|
import org.springframework.web.server.ResponseStatusException;
|
||||||
import org.springframework.web.util.UriComponentsBuilder;
|
import org.springframework.web.util.UriComponentsBuilder;
|
||||||
|
|
||||||
import com.baeldung.persistence.model.Foo;
|
import com.baeldung.persistence.model.Foo;
|
||||||
|
@ -32,7 +33,7 @@ import com.baeldung.web.util.RestPreconditions;
|
||||||
import com.google.common.base.Preconditions;
|
import com.google.common.base.Preconditions;
|
||||||
|
|
||||||
@RestController
|
@RestController
|
||||||
@RequestMapping(value = "/auth/foos")
|
@RequestMapping(value = "/foos")
|
||||||
public class FooController {
|
public class FooController {
|
||||||
|
|
||||||
@Autowired
|
@Autowired
|
||||||
|
@ -51,22 +52,29 @@ public class FooController {
|
||||||
@GetMapping(value = "/{id}/custom-etag")
|
@GetMapping(value = "/{id}/custom-etag")
|
||||||
public ResponseEntity<Foo> findByIdWithCustomEtag(@PathVariable("id") final Long id,
|
public ResponseEntity<Foo> findByIdWithCustomEtag(@PathVariable("id") final Long id,
|
||||||
final HttpServletResponse response) {
|
final HttpServletResponse response) {
|
||||||
final Foo resourceById = RestPreconditions.checkFound(service.findOne(id));
|
final Foo foo = RestPreconditions.checkFound(service.findById(id));
|
||||||
|
|
||||||
eventPublisher.publishEvent(new SingleResourceRetrievedEvent(this, response));
|
eventPublisher.publishEvent(new SingleResourceRetrievedEvent(this, response));
|
||||||
return ResponseEntity.ok()
|
return ResponseEntity.ok()
|
||||||
.eTag(Long.toString(resourceById.getVersion()))
|
.eTag(Long.toString(foo.getVersion()))
|
||||||
.body(resourceById);
|
.body(foo);
|
||||||
}
|
}
|
||||||
|
|
||||||
// read - one
|
// read - one
|
||||||
|
|
||||||
@GetMapping(value = "/{id}")
|
@GetMapping(value = "/{id}")
|
||||||
public Foo findById(@PathVariable("id") final Long id, final HttpServletResponse response) {
|
public Foo findById(@PathVariable("id") final Long id, final HttpServletResponse response) {
|
||||||
final Foo resourceById = RestPreconditions.checkFound(service.findOne(id));
|
try {
|
||||||
|
final Foo resourceById = RestPreconditions.checkFound(service.findById(id));
|
||||||
|
|
||||||
|
eventPublisher.publishEvent(new SingleResourceRetrievedEvent(this, response));
|
||||||
|
return resourceById;
|
||||||
|
}
|
||||||
|
catch (MyResourceNotFoundException exc) {
|
||||||
|
throw new ResponseStatusException(
|
||||||
|
HttpStatus.NOT_FOUND, "Foo Not Found", exc);
|
||||||
|
}
|
||||||
|
|
||||||
eventPublisher.publishEvent(new SingleResourceRetrievedEvent(this, response));
|
|
||||||
return resourceById;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// read - all
|
// read - all
|
||||||
|
@ -120,7 +128,7 @@ public class FooController {
|
||||||
@ResponseStatus(HttpStatus.OK)
|
@ResponseStatus(HttpStatus.OK)
|
||||||
public void update(@PathVariable("id") final Long id, @RequestBody final Foo resource) {
|
public void update(@PathVariable("id") final Long id, @RequestBody final Foo resource) {
|
||||||
Preconditions.checkNotNull(resource);
|
Preconditions.checkNotNull(resource);
|
||||||
RestPreconditions.checkFound(service.findOne(resource.getId()));
|
RestPreconditions.checkFound(service.findById(resource.getId()));
|
||||||
service.update(resource);
|
service.update(resource);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -7,34 +7,28 @@ import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
import org.springframework.http.HttpStatus;
|
import org.springframework.http.HttpStatus;
|
||||||
import org.springframework.stereotype.Controller;
|
import org.springframework.stereotype.Controller;
|
||||||
import org.springframework.web.bind.annotation.RequestMapping;
|
import org.springframework.web.bind.annotation.GetMapping;
|
||||||
import org.springframework.web.bind.annotation.RequestMethod;
|
|
||||||
import org.springframework.web.bind.annotation.ResponseStatus;
|
import org.springframework.web.bind.annotation.ResponseStatus;
|
||||||
import org.springframework.web.util.UriTemplate;
|
import org.springframework.web.util.UriTemplate;
|
||||||
|
|
||||||
import com.baeldung.web.util.LinkUtil;
|
import com.baeldung.web.util.LinkUtil;
|
||||||
|
|
||||||
@Controller
|
@Controller
|
||||||
@RequestMapping(value = "/auth/")
|
|
||||||
public class RootController {
|
public class RootController {
|
||||||
|
|
||||||
public RootController() {
|
|
||||||
super();
|
|
||||||
}
|
|
||||||
|
|
||||||
// API
|
// API
|
||||||
|
|
||||||
// discover
|
// discover
|
||||||
|
|
||||||
@RequestMapping(value = "admin", method = RequestMethod.GET)
|
@GetMapping("/")
|
||||||
@ResponseStatus(value = HttpStatus.NO_CONTENT)
|
@ResponseStatus(value = HttpStatus.NO_CONTENT)
|
||||||
public void adminRoot(final HttpServletRequest request, final HttpServletResponse response) {
|
public void adminRoot(final HttpServletRequest request, final HttpServletResponse response) {
|
||||||
final String rootUri = request.getRequestURL()
|
final String rootUri = request.getRequestURL()
|
||||||
.toString();
|
.toString();
|
||||||
|
|
||||||
final URI fooUri = new UriTemplate("{rootUri}/{resource}").expand(rootUri, "foo");
|
final URI fooUri = new UriTemplate("{rootUri}{resource}").expand(rootUri, "foos");
|
||||||
final String linkToFoo = LinkUtil.createLinkHeader(fooUri.toASCIIString(), "collection");
|
final String linkToFoos = LinkUtil.createLinkHeader(fooUri.toASCIIString(), "collection");
|
||||||
response.addHeader("Link", linkToFoo);
|
response.addHeader("Link", linkToFoos);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -115,7 +115,7 @@ class PaginatedResultsRetrievedDiscoverabilityListener implements ApplicationLis
|
||||||
protected void plural(final UriComponentsBuilder uriBuilder, final Class clazz) {
|
protected void plural(final UriComponentsBuilder uriBuilder, final Class clazz) {
|
||||||
final String resourceName = clazz.getSimpleName()
|
final String resourceName = clazz.getSimpleName()
|
||||||
.toLowerCase() + "s";
|
.toLowerCase() + "s";
|
||||||
uriBuilder.path("/auth/" + resourceName);
|
uriBuilder.path("/" + resourceName);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
server.port=8082
|
|
||||||
server.servlet.context-path=/spring-boot-rest
|
server.servlet.context-path=/spring-boot-rest
|
||||||
|
|
||||||
### Spring Boot default error handling configurations
|
### Spring Boot default error handling configurations
|
||||||
#server.error.whitelabel.enabled=false
|
#server.error.whitelabel.enabled=false
|
||||||
#server.error.include-stacktrace=always
|
#server.error.include-stacktrace=always
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
package com.baeldung;
|
package com.baeldung;
|
||||||
|
|
||||||
public interface Consts {
|
public interface Consts {
|
||||||
int APPLICATION_PORT = 8082;
|
int APPLICATION_PORT = 8080;
|
||||||
}
|
}
|
||||||
|
|
|
@ -59,7 +59,7 @@ public abstract class AbstractLiveTest<T extends Serializable> {
|
||||||
//
|
//
|
||||||
|
|
||||||
protected String getURL() {
|
protected String getURL() {
|
||||||
return "http://localhost:" + APPLICATION_PORT + "/spring-boot-rest/auth/foos";
|
return "http://localhost:" + APPLICATION_PORT + "/spring-boot-rest/foos";
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -27,7 +27,7 @@ public class FooControllerAppIntegrationTest {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void whenFindPaginatedRequest_thenEmptyResponse() throws Exception {
|
public void whenFindPaginatedRequest_thenEmptyResponse() throws Exception {
|
||||||
this.mockMvc.perform(get("/auth/foos").param("page", "0")
|
this.mockMvc.perform(get("/foos").param("page", "0")
|
||||||
.param("size", "2"))
|
.param("size", "2"))
|
||||||
.andExpect(status().isOk())
|
.andExpect(status().isOk())
|
||||||
.andExpect(content().json("[]"));
|
.andExpect(content().json("[]"));
|
||||||
|
|
|
@ -29,7 +29,7 @@ public class FooControllerCustomEtagIntegrationTest {
|
||||||
@Autowired
|
@Autowired
|
||||||
private MockMvc mvc;
|
private MockMvc mvc;
|
||||||
|
|
||||||
private String FOOS_ENDPOINT = "/auth/foos/";
|
private String FOOS_ENDPOINT = "/foos/";
|
||||||
private String CUSTOM_ETAG_ENDPOINT_SUFFIX = "/custom-etag";
|
private String CUSTOM_ETAG_ENDPOINT_SUFFIX = "/custom-etag";
|
||||||
|
|
||||||
private static String serializeFoo(Foo foo) throws Exception {
|
private static String serializeFoo(Foo foo) throws Exception {
|
||||||
|
|
|
@ -51,7 +51,7 @@ public class FooControllerWebLayerIntegrationTest {
|
||||||
doNothing().when(publisher)
|
doNothing().when(publisher)
|
||||||
.publishEvent(any(PaginatedResultsRetrievedEvent.class));
|
.publishEvent(any(PaginatedResultsRetrievedEvent.class));
|
||||||
|
|
||||||
this.mockMvc.perform(get("/auth/foos").param("page", "0")
|
this.mockMvc.perform(get("/foos").param("page", "0")
|
||||||
.param("size", "2"))
|
.param("size", "2"))
|
||||||
.andExpect(status().isOk())
|
.andExpect(status().isOk())
|
||||||
.andExpect(jsonPath("$",Matchers.hasSize(1)));
|
.andExpect(jsonPath("$",Matchers.hasSize(1)));
|
||||||
|
|
|
@ -74,7 +74,7 @@ public class FooPageableLiveTest extends AbstractBasicLiveTest<Foo> {
|
||||||
}
|
}
|
||||||
|
|
||||||
protected String getPageableURL() {
|
protected String getPageableURL() {
|
||||||
return "http://localhost:" + APPLICATION_PORT + "/spring-boot-rest/auth/foos/pageable";
|
return "http://localhost:" + APPLICATION_PORT + "/spring-boot-rest/foos/pageable";
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,15 +42,14 @@
|
||||||
"raw": "{\n \"name\": \"Transformers\"\n}"
|
"raw": "{\n \"name\": \"Transformers\"\n}"
|
||||||
},
|
},
|
||||||
"url": {
|
"url": {
|
||||||
"raw": "http://localhost:8082/spring-boot-rest/auth/foos",
|
"raw": "http://localhost:8080/spring-boot-rest/foos",
|
||||||
"protocol": "http",
|
"protocol": "http",
|
||||||
"host": [
|
"host": [
|
||||||
"localhost"
|
"localhost"
|
||||||
],
|
],
|
||||||
"port": "8082",
|
"port": "8080",
|
||||||
"path": [
|
"path": [
|
||||||
"spring-boot-rest",
|
"spring-boot-rest",
|
||||||
"auth",
|
|
||||||
"foos"
|
"foos"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
@ -85,15 +84,14 @@
|
||||||
"raw": ""
|
"raw": ""
|
||||||
},
|
},
|
||||||
"url": {
|
"url": {
|
||||||
"raw": "http://localhost:8082/spring-boot-rest/auth/foos/{{id}}",
|
"raw": "http://localhost:8080/spring-boot-rest/foos/{{id}}",
|
||||||
"protocol": "http",
|
"protocol": "http",
|
||||||
"host": [
|
"host": [
|
||||||
"localhost"
|
"localhost"
|
||||||
],
|
],
|
||||||
"port": "8082",
|
"port": "8080",
|
||||||
"path": [
|
"path": [
|
||||||
"spring-boot-rest",
|
"spring-boot-rest",
|
||||||
"auth",
|
|
||||||
"foos",
|
"foos",
|
||||||
"{{id}}"
|
"{{id}}"
|
||||||
]
|
]
|
||||||
|
@ -123,15 +121,14 @@
|
||||||
"raw": ""
|
"raw": ""
|
||||||
},
|
},
|
||||||
"url": {
|
"url": {
|
||||||
"raw": "http://localhost:8082/spring-boot-rest/auth/foos/{{id}}",
|
"raw": "http://localhost:8080/spring-boot-rest/foos/{{id}}",
|
||||||
"protocol": "http",
|
"protocol": "http",
|
||||||
"host": [
|
"host": [
|
||||||
"localhost"
|
"localhost"
|
||||||
],
|
],
|
||||||
"port": "8082",
|
"port": "8080",
|
||||||
"path": [
|
"path": [
|
||||||
"spring-boot-rest",
|
"spring-boot-rest",
|
||||||
"auth",
|
|
||||||
"foos",
|
"foos",
|
||||||
"{{id}}"
|
"{{id}}"
|
||||||
]
|
]
|
||||||
|
@ -164,15 +161,14 @@
|
||||||
"raw": ""
|
"raw": ""
|
||||||
},
|
},
|
||||||
"url": {
|
"url": {
|
||||||
"raw": "http://localhost:8082/spring-boot-rest/auth/foos/{{id}}",
|
"raw": "http://localhost:8080/spring-boot-rest/foos/{{id}}",
|
||||||
"protocol": "http",
|
"protocol": "http",
|
||||||
"host": [
|
"host": [
|
||||||
"localhost"
|
"localhost"
|
||||||
],
|
],
|
||||||
"port": "8082",
|
"port": "8080",
|
||||||
"path": [
|
"path": [
|
||||||
"spring-boot-rest",
|
"spring-boot-rest",
|
||||||
"auth",
|
|
||||||
"foos",
|
"foos",
|
||||||
"{{id}}"
|
"{{id}}"
|
||||||
]
|
]
|
||||||
|
|
|
@ -8,16 +8,30 @@
|
||||||
|
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>com.baeldung</groupId>
|
<groupId>com.baeldung</groupId>
|
||||||
<artifactId>parent-java</artifactId>
|
<artifactId>parent-boot-2</artifactId>
|
||||||
<version>0.0.1-SNAPSHOT</version>
|
<version>0.0.1-SNAPSHOT</version>
|
||||||
<relativePath>../../parent-java</relativePath>
|
<relativePath>../../parent-boot-2</relativePath>
|
||||||
|
<!-- lookup parent from repository -->
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<dependencies>
|
<dependencies>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-web</artifactId>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-test</artifactId>
|
||||||
|
<scope>test</scope>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.google.guava</groupId>
|
||||||
|
<artifactId>guava</artifactId>
|
||||||
|
<version>${guava.version}</version>
|
||||||
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>javax.servlet</groupId>
|
<groupId>javax.servlet</groupId>
|
||||||
<artifactId>javax.servlet-api</artifactId>
|
<artifactId>javax.servlet-api</artifactId>
|
||||||
<version>${javax.servlet-api.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>javax.servlet</groupId>
|
<groupId>javax.servlet</groupId>
|
||||||
|
@ -27,49 +41,40 @@
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-security</artifactId>
|
<artifactId>jetty-security</artifactId>
|
||||||
<version>${jetty.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-servlet</artifactId>
|
<artifactId>jetty-servlet</artifactId>
|
||||||
<version>${jetty.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-servlets</artifactId>
|
<artifactId>jetty-servlets</artifactId>
|
||||||
<version>${jetty.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-io</artifactId>
|
<artifactId>jetty-io</artifactId>
|
||||||
<version>${jetty.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-http</artifactId>
|
<artifactId>jetty-http</artifactId>
|
||||||
<version>${jetty.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-server</artifactId>
|
<artifactId>jetty-server</artifactId>
|
||||||
<version>${jetty.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-util</artifactId>
|
<artifactId>jetty-util</artifactId>
|
||||||
<version>${jetty.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.apache.httpcomponents</groupId>
|
<groupId>org.apache.httpcomponents</groupId>
|
||||||
<artifactId>httpcore</artifactId>
|
<artifactId>httpcore</artifactId>
|
||||||
<version>${httpcore.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.apache.commons</groupId>
|
<groupId>org.apache.commons</groupId>
|
||||||
<artifactId>commons-lang3</artifactId>
|
<artifactId>commons-lang3</artifactId>
|
||||||
<version>${commons-lang3.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
|
@ -92,19 +97,16 @@
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>joda-time</groupId>
|
<groupId>joda-time</groupId>
|
||||||
<artifactId>joda-time</artifactId>
|
<artifactId>joda-time</artifactId>
|
||||||
<version>${joda-time.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.fasterxml.jackson.core</groupId>
|
<groupId>com.fasterxml.jackson.core</groupId>
|
||||||
<artifactId>jackson-annotations</artifactId>
|
<artifactId>jackson-annotations</artifactId>
|
||||||
<version>${jackson.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.fasterxml.jackson.core</groupId>
|
<groupId>com.fasterxml.jackson.core</groupId>
|
||||||
<artifactId>jackson-databind</artifactId>
|
<artifactId>jackson-databind</artifactId>
|
||||||
<version>${jackson.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
|
@ -128,7 +130,6 @@
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.apache.httpcomponents</groupId>
|
<groupId>org.apache.httpcomponents</groupId>
|
||||||
<artifactId>httpclient</artifactId>
|
<artifactId>httpclient</artifactId>
|
||||||
<version>${httpclient.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
|
@ -145,13 +146,11 @@
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>io.rest-assured</groupId>
|
<groupId>io.rest-assured</groupId>
|
||||||
<artifactId>rest-assured</artifactId>
|
<artifactId>rest-assured</artifactId>
|
||||||
<version>${rest-assured.version}</version>
|
|
||||||
<scope>test</scope>
|
<scope>test</scope>
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>io.rest-assured</groupId>
|
<groupId>io.rest-assured</groupId>
|
||||||
<artifactId>json-schema-validator</artifactId>
|
<artifactId>json-schema-validator</artifactId>
|
||||||
<version>${rest-assured-json-schema-validator.version}</version>
|
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.github.fge</groupId>
|
<groupId>com.github.fge</groupId>
|
||||||
|
@ -171,6 +170,7 @@
|
||||||
</dependencies>
|
</dependencies>
|
||||||
|
|
||||||
<properties>
|
<properties>
|
||||||
|
<guava.version>18.0</guava.version>
|
||||||
<jackson.version>2.9.7</jackson.version>
|
<jackson.version>2.9.7</jackson.version>
|
||||||
<jackson-coreutils.version>1.8</jackson-coreutils.version>
|
<jackson-coreutils.version>1.8</jackson-coreutils.version>
|
||||||
<guava.version>19.0</guava.version>
|
<guava.version>19.0</guava.version>
|
||||||
|
|
|
@ -0,0 +1,13 @@
|
||||||
|
package com.baeldung.restassured;
|
||||||
|
|
||||||
|
import org.springframework.boot.SpringApplication;
|
||||||
|
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||||
|
|
||||||
|
@SpringBootApplication
|
||||||
|
public class Application {
|
||||||
|
|
||||||
|
public static void main(String[] args) {
|
||||||
|
SpringApplication.run(Application.class, args);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,100 @@
|
||||||
|
package com.baeldung.restassured.controller;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.FileInputStream;
|
||||||
|
import java.io.FileNotFoundException;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.UUID;
|
||||||
|
|
||||||
|
import javax.servlet.http.Cookie;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.core.io.InputStreamResource;
|
||||||
|
import org.springframework.core.io.Resource;
|
||||||
|
import org.springframework.http.HttpHeaders;
|
||||||
|
import org.springframework.http.HttpStatus;
|
||||||
|
import org.springframework.http.MediaType;
|
||||||
|
import org.springframework.http.ResponseEntity;
|
||||||
|
import org.springframework.web.bind.annotation.GetMapping;
|
||||||
|
import org.springframework.web.bind.annotation.PathVariable;
|
||||||
|
import org.springframework.web.bind.annotation.PostMapping;
|
||||||
|
import org.springframework.web.bind.annotation.RequestBody;
|
||||||
|
import org.springframework.web.bind.annotation.ResponseStatus;
|
||||||
|
import org.springframework.web.bind.annotation.RestController;
|
||||||
|
|
||||||
|
import com.baeldung.restassured.model.Movie;
|
||||||
|
import com.baeldung.restassured.service.AppService;
|
||||||
|
|
||||||
|
@RestController
|
||||||
|
public class AppController {
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
AppService appService;
|
||||||
|
|
||||||
|
@GetMapping("/movies")
|
||||||
|
public ResponseEntity<?> getMovies() {
|
||||||
|
|
||||||
|
Set<Movie> result = appService.getAll();
|
||||||
|
|
||||||
|
return ResponseEntity.ok()
|
||||||
|
.body(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
@PostMapping("/movie")
|
||||||
|
@ResponseStatus(HttpStatus.CREATED)
|
||||||
|
public Movie addMovie(@RequestBody Movie movie) {
|
||||||
|
|
||||||
|
appService.add(movie);
|
||||||
|
return movie;
|
||||||
|
}
|
||||||
|
|
||||||
|
@GetMapping("/movie/{id}")
|
||||||
|
public ResponseEntity<?> getMovie(@PathVariable int id) {
|
||||||
|
|
||||||
|
Movie movie = appService.findMovie(id);
|
||||||
|
if (movie == null) {
|
||||||
|
return ResponseEntity.badRequest()
|
||||||
|
.body("Invalid movie id");
|
||||||
|
}
|
||||||
|
|
||||||
|
return ResponseEntity.ok(movie);
|
||||||
|
}
|
||||||
|
|
||||||
|
@GetMapping("/welcome")
|
||||||
|
public ResponseEntity<?> welcome(HttpServletResponse response) {
|
||||||
|
|
||||||
|
HttpHeaders headers = new HttpHeaders();
|
||||||
|
headers.add(HttpHeaders.CONTENT_TYPE, "application/json; charset=UTF-8");
|
||||||
|
headers.add("sessionId", UUID.randomUUID()
|
||||||
|
.toString());
|
||||||
|
|
||||||
|
Cookie cookie = new Cookie("token", "some-token");
|
||||||
|
cookie.setDomain("localhost");
|
||||||
|
|
||||||
|
response.addCookie(cookie);
|
||||||
|
|
||||||
|
return ResponseEntity.noContent()
|
||||||
|
.headers(headers)
|
||||||
|
.build();
|
||||||
|
}
|
||||||
|
|
||||||
|
@GetMapping("/download/{id}")
|
||||||
|
public ResponseEntity<Resource> getFile(@PathVariable int id) throws FileNotFoundException {
|
||||||
|
|
||||||
|
File file = appService.getFile(id);
|
||||||
|
|
||||||
|
if (file == null) {
|
||||||
|
return ResponseEntity.notFound()
|
||||||
|
.build();
|
||||||
|
}
|
||||||
|
|
||||||
|
InputStreamResource resource = new InputStreamResource(new FileInputStream(file));
|
||||||
|
|
||||||
|
return ResponseEntity.ok()
|
||||||
|
.contentLength(file.length())
|
||||||
|
.contentType(MediaType.parseMediaType("application/octet-stream"))
|
||||||
|
.body(resource);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,58 @@
|
||||||
|
package com.baeldung.restassured.model;
|
||||||
|
|
||||||
|
public class Movie {
|
||||||
|
|
||||||
|
private Integer id;
|
||||||
|
|
||||||
|
private String name;
|
||||||
|
|
||||||
|
private String synopsis;
|
||||||
|
|
||||||
|
public Movie() {
|
||||||
|
}
|
||||||
|
|
||||||
|
public Movie(Integer id, String name, String synopsis) {
|
||||||
|
super();
|
||||||
|
this.id = id;
|
||||||
|
this.name = name;
|
||||||
|
this.synopsis = synopsis;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Integer getId() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getSynopsis() {
|
||||||
|
return synopsis;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
final int prime = 31;
|
||||||
|
int result = 1;
|
||||||
|
result = prime * result + ((id == null) ? 0 : id.hashCode());
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object obj) {
|
||||||
|
if (this == obj)
|
||||||
|
return true;
|
||||||
|
if (obj == null)
|
||||||
|
return false;
|
||||||
|
if (getClass() != obj.getClass())
|
||||||
|
return false;
|
||||||
|
Movie other = (Movie) obj;
|
||||||
|
if (id == null) {
|
||||||
|
if (other.id != null)
|
||||||
|
return false;
|
||||||
|
} else if (!id.equals(other.id))
|
||||||
|
return false;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,45 @@
|
||||||
|
package com.baeldung.restassured.service;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
|
import org.springframework.core.io.ClassPathResource;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
import com.baeldung.restassured.model.Movie;
|
||||||
|
|
||||||
|
@Service
|
||||||
|
public class AppService {
|
||||||
|
|
||||||
|
private Set<Movie> movieSet = new HashSet<>();
|
||||||
|
|
||||||
|
public Set<Movie> getAll() {
|
||||||
|
return movieSet;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void add(Movie movie) {
|
||||||
|
movieSet.add(movie);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Movie findMovie(int id) {
|
||||||
|
return movieSet.stream()
|
||||||
|
.filter(movie -> movie.getId()
|
||||||
|
.equals(id))
|
||||||
|
.findFirst()
|
||||||
|
.orElse(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public File getFile(int id) {
|
||||||
|
File file = null;
|
||||||
|
try {
|
||||||
|
file = new ClassPathResource(String.valueOf(id)).getFile();
|
||||||
|
} catch (IOException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
|
||||||
|
return file;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1 @@
|
||||||
|
File 1
|
|
@ -0,0 +1 @@
|
||||||
|
File 2
|
|
@ -0,0 +1,149 @@
|
||||||
|
package com.baeldung.restassured.controller;
|
||||||
|
|
||||||
|
import static io.restassured.RestAssured.get;
|
||||||
|
import static io.restassured.RestAssured.given;
|
||||||
|
import static org.assertj.core.api.Assertions.assertThat;
|
||||||
|
import static org.hamcrest.CoreMatchers.equalTo;
|
||||||
|
import static org.hamcrest.CoreMatchers.is;
|
||||||
|
import static org.hamcrest.CoreMatchers.notNullValue;
|
||||||
|
import static org.mockito.Mockito.when;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
|
import javax.annotation.PostConstruct;
|
||||||
|
|
||||||
|
import org.junit.jupiter.api.Test;
|
||||||
|
import org.junit.runner.RunWith;
|
||||||
|
import org.springframework.boot.test.context.SpringBootTest;
|
||||||
|
import org.springframework.boot.test.context.SpringBootTest.WebEnvironment;
|
||||||
|
import org.springframework.boot.test.mock.mockito.MockBean;
|
||||||
|
import org.springframework.boot.web.server.LocalServerPort;
|
||||||
|
import org.springframework.core.io.ClassPathResource;
|
||||||
|
import org.springframework.http.HttpStatus;
|
||||||
|
import org.springframework.test.context.junit4.SpringRunner;
|
||||||
|
|
||||||
|
import com.baeldung.restassured.model.Movie;
|
||||||
|
import com.baeldung.restassured.service.AppService;
|
||||||
|
|
||||||
|
import io.restassured.response.Response;
|
||||||
|
|
||||||
|
@RunWith(SpringRunner.class)
|
||||||
|
@SpringBootTest(webEnvironment = WebEnvironment.RANDOM_PORT)
|
||||||
|
public class AppControllerIntegrationTest {
|
||||||
|
|
||||||
|
@LocalServerPort
|
||||||
|
private int port;
|
||||||
|
|
||||||
|
private String uri;
|
||||||
|
|
||||||
|
@PostConstruct
|
||||||
|
public void init() {
|
||||||
|
uri = "http://localhost:" + port;
|
||||||
|
}
|
||||||
|
|
||||||
|
@MockBean
|
||||||
|
AppService appService;
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void givenMovieId_whenMakingGetRequestToMovieEndpoint_thenReturnMovie() {
|
||||||
|
|
||||||
|
Movie testMovie = new Movie(1, "movie1", "summary1");
|
||||||
|
when(appService.findMovie(1)).thenReturn(testMovie);
|
||||||
|
|
||||||
|
get(uri + "/movie/" + testMovie.getId()).then()
|
||||||
|
.assertThat()
|
||||||
|
.statusCode(HttpStatus.OK.value())
|
||||||
|
.body("id", equalTo(testMovie.getId()))
|
||||||
|
.body("name", equalTo(testMovie.getName()))
|
||||||
|
.body("synopsis", notNullValue());
|
||||||
|
|
||||||
|
Movie result = get(uri + "/movie/" + testMovie.getId()).then()
|
||||||
|
.assertThat()
|
||||||
|
.statusCode(HttpStatus.OK.value())
|
||||||
|
.extract()
|
||||||
|
.as(Movie.class);
|
||||||
|
assertThat(result).isEqualTo(testMovie);
|
||||||
|
|
||||||
|
String responseString = get(uri + "/movie/" + testMovie.getId()).then()
|
||||||
|
.assertThat()
|
||||||
|
.statusCode(HttpStatus.OK.value())
|
||||||
|
.extract()
|
||||||
|
.asString();
|
||||||
|
assertThat(responseString).isNotEmpty();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void whenCallingMoviesEndpoint_thenReturnAllMovies() {
|
||||||
|
|
||||||
|
Set<Movie> movieSet = new HashSet<>();
|
||||||
|
movieSet.add(new Movie(1, "movie1", "summary1"));
|
||||||
|
movieSet.add(new Movie(2, "movie2", "summary2"));
|
||||||
|
when(appService.getAll()).thenReturn(movieSet);
|
||||||
|
|
||||||
|
get(uri + "/movies").then()
|
||||||
|
.statusCode(HttpStatus.OK.value())
|
||||||
|
.assertThat()
|
||||||
|
.body("size()", is(2));
|
||||||
|
|
||||||
|
Movie[] movies = get(uri + "/movies").then()
|
||||||
|
.statusCode(200)
|
||||||
|
.extract()
|
||||||
|
.as(Movie[].class);
|
||||||
|
assertThat(movies.length).isEqualTo(2);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void givenMovie_whenMakingPostRequestToMovieEndpoint_thenCorrect() {
|
||||||
|
|
||||||
|
Map<String, String> request = new HashMap<>();
|
||||||
|
request.put("id", "11");
|
||||||
|
request.put("name", "movie1");
|
||||||
|
request.put("synopsis", "summary1");
|
||||||
|
|
||||||
|
int movieId = given().contentType("application/json")
|
||||||
|
.body(request)
|
||||||
|
.when()
|
||||||
|
.post(uri + "/movie")
|
||||||
|
.then()
|
||||||
|
.assertThat()
|
||||||
|
.statusCode(HttpStatus.CREATED.value())
|
||||||
|
.extract()
|
||||||
|
.path("id");
|
||||||
|
assertThat(movieId).isEqualTo(11);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void whenCallingWelcomeEndpoint_thenCorrect() {
|
||||||
|
|
||||||
|
get(uri + "/welcome").then()
|
||||||
|
.assertThat()
|
||||||
|
.header("sessionId", notNullValue())
|
||||||
|
.cookie("token", notNullValue());
|
||||||
|
|
||||||
|
Response response = get(uri + "/welcome");
|
||||||
|
|
||||||
|
String headerName = response.getHeader("sessionId");
|
||||||
|
String cookieValue = response.getCookie("token");
|
||||||
|
assertThat(headerName).isNotBlank();
|
||||||
|
assertThat(cookieValue).isNotBlank();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void givenId_whenCallingDowloadEndpoint_thenCorrect() throws IOException {
|
||||||
|
|
||||||
|
File file = new ClassPathResource("test.txt").getFile();
|
||||||
|
long fileSize = file.length();
|
||||||
|
when(appService.getFile(1)).thenReturn(file);
|
||||||
|
|
||||||
|
byte[] result = get(uri + "/download/1").asByteArray();
|
||||||
|
|
||||||
|
assertThat(result.length).isEqualTo(fileSize);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1 @@
|
||||||
|
Test file
|
Loading…
Reference in New Issue