From 11a6e4b69380521f41d4b807efb217c3683381b1 Mon Sep 17 00:00:00 2001 From: Oliver Gierke Date: Tue, 9 Sep 2014 08:56:15 -0500 Subject: [PATCH] #7 - Added sample for Spring Data REST ALPS support and excerpt projections. --- rest/pom.xml | 1 + rest/projections/pom.xml | 29 ++++++++++ .../src/main/java/example/orders/Address.java | 52 ++++++++++++++++++ .../main/java/example/orders/Application.java | 54 +++++++++++++++++++ .../main/java/example/orders/Customer.java | 52 ++++++++++++++++++ .../java/example/orders/CustomerExcerpt.java | 33 ++++++++++++ .../example/orders/CustomerRepository.java | 27 ++++++++++ .../main/java/example/orders/LineItem.java | 43 +++++++++++++++ .../src/main/java/example/orders/Order.java | 51 ++++++++++++++++++ .../java/example/orders/OrderRepository.java | 25 +++++++++ .../orders/ApplicationIntegrationTests.java | 45 ++++++++++++++++ rest/starbucks/pom.xml | 1 - 12 files changed, 412 insertions(+), 1 deletion(-) create mode 100644 rest/projections/pom.xml create mode 100644 rest/projections/src/main/java/example/orders/Address.java create mode 100644 rest/projections/src/main/java/example/orders/Application.java create mode 100644 rest/projections/src/main/java/example/orders/Customer.java create mode 100644 rest/projections/src/main/java/example/orders/CustomerExcerpt.java create mode 100644 rest/projections/src/main/java/example/orders/CustomerRepository.java create mode 100644 rest/projections/src/main/java/example/orders/LineItem.java create mode 100644 rest/projections/src/main/java/example/orders/Order.java create mode 100644 rest/projections/src/main/java/example/orders/OrderRepository.java create mode 100644 rest/projections/src/test/java/example/orders/ApplicationIntegrationTests.java diff --git a/rest/pom.xml b/rest/pom.xml index 4b28962e..2db81ded 100644 --- a/rest/pom.xml +++ b/rest/pom.xml @@ -17,6 +17,7 @@ starbucks multi-store + projections diff --git a/rest/projections/pom.xml b/rest/projections/pom.xml new file mode 100644 index 00000000..80ac096b --- /dev/null +++ b/rest/projections/pom.xml @@ -0,0 +1,29 @@ + + 4.0.0 + + spring-data-rest-projections + + Spring Data REST - Projections Example + + + org.springframework.data.examples + spring-data-rest-examples + 1.0.0.BUILD-SNAPSHOT + + + + + + org.springframework.boot + spring-boot-starter-data-jpa + + + + org.hsqldb + hsqldb + + + + + \ No newline at end of file diff --git a/rest/projections/src/main/java/example/orders/Address.java b/rest/projections/src/main/java/example/orders/Address.java new file mode 100644 index 00000000..7b2d4e8a --- /dev/null +++ b/rest/projections/src/main/java/example/orders/Address.java @@ -0,0 +1,52 @@ +/* + * Copyright 2014 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package example.orders; + +import javax.persistence.Entity; +import javax.persistence.GeneratedValue; +import javax.persistence.Id; + +import lombok.Data; +import lombok.RequiredArgsConstructor; + +/** + * @author Oliver Gierke + */ +@Entity +@Data +@RequiredArgsConstructor +public class Address { + + @GeneratedValue @Id// + private Long id; + private final String street, zipCode, city, state; + + Address() { + + this.street = null; + this.zipCode = null; + this.city = null; + this.state = null; + } + + /* + * (non-Javadoc) + * @see java.lang.Object#toString() + */ + public String toString() { + return String.format("%s, %s %s, %s", street, zipCode, city, state); + } +} diff --git a/rest/projections/src/main/java/example/orders/Application.java b/rest/projections/src/main/java/example/orders/Application.java new file mode 100644 index 00000000..5e4a8bf8 --- /dev/null +++ b/rest/projections/src/main/java/example/orders/Application.java @@ -0,0 +1,54 @@ +/* + * Copyright 2014 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package example.orders; + +import java.math.BigDecimal; + +import javax.annotation.PostConstruct; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.EnableAutoConfiguration; + +import example.orders.Customer.Gender; + +/** + * @author Oliver Gierke + */ +@EnableAutoConfiguration +public class Application { + + @Autowired CustomerRepository customers; + @Autowired OrderRepository orders; + + public static void main(String... args) { + SpringApplication.run(Application.class, args); + } + + @PostConstruct + public void init() { + + Customer dave = customers.save(new Customer("Dave", "Matthews", Gender.MALE, // + new Address("4711 Some Place", "54321", "Charlottesville", "VA"))); + + Order order = new Order(); + + order.setCustomer(dave); + order.add(new LineItem("Lakewood guitar", new BigDecimal(1299.0))); + + orders.save(order); + } +} diff --git a/rest/projections/src/main/java/example/orders/Customer.java b/rest/projections/src/main/java/example/orders/Customer.java new file mode 100644 index 00000000..93aa9902 --- /dev/null +++ b/rest/projections/src/main/java/example/orders/Customer.java @@ -0,0 +1,52 @@ +/* + * Copyright 2014 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package example.orders; + +import javax.persistence.CascadeType; +import javax.persistence.Entity; +import javax.persistence.GeneratedValue; +import javax.persistence.Id; +import javax.persistence.OneToOne; + +import lombok.Data; +import lombok.RequiredArgsConstructor; + +/** + * @author Oliver Gierke + */ +@Entity +@Data +@RequiredArgsConstructor +public class Customer { + + private @GeneratedValue @Id Long id; + private final String firstname, lastname; + private final Gender gender; + + @OneToOne(cascade = CascadeType.ALL, orphanRemoval = true)// + private final Address address; + + Customer() { + this.firstname = null; + this.lastname = null; + this.address = null; + this.gender = null; + } + + static enum Gender { + MALE, FEMALE; + } +} diff --git a/rest/projections/src/main/java/example/orders/CustomerExcerpt.java b/rest/projections/src/main/java/example/orders/CustomerExcerpt.java new file mode 100644 index 00000000..8ff68fcd --- /dev/null +++ b/rest/projections/src/main/java/example/orders/CustomerExcerpt.java @@ -0,0 +1,33 @@ +/* + * Copyright 2014 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package example.orders; + +import org.springframework.beans.factory.annotation.Value; +import org.springframework.data.rest.core.config.Projection; + +/** + * @author Oliver Gierke + */ +@Projection(name = "excerpt", types = Customer.class) +public interface CustomerExcerpt { + + String getFirstname(); + + String getLastname(); + + @Value("#{target.address.toString()}") + String getAddress(); +} diff --git a/rest/projections/src/main/java/example/orders/CustomerRepository.java b/rest/projections/src/main/java/example/orders/CustomerRepository.java new file mode 100644 index 00000000..46195a22 --- /dev/null +++ b/rest/projections/src/main/java/example/orders/CustomerRepository.java @@ -0,0 +1,27 @@ +/* + * Copyright 2014 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package example.orders; + +import org.springframework.data.repository.CrudRepository; +import org.springframework.data.rest.core.annotation.RepositoryRestResource; + +/** + * @author Oliver Gierke + */ +@RepositoryRestResource(excerptProjection = CustomerExcerpt.class) +public interface CustomerRepository extends CrudRepository { + +} diff --git a/rest/projections/src/main/java/example/orders/LineItem.java b/rest/projections/src/main/java/example/orders/LineItem.java new file mode 100644 index 00000000..9efbf9b2 --- /dev/null +++ b/rest/projections/src/main/java/example/orders/LineItem.java @@ -0,0 +1,43 @@ +/* + * Copyright 2014 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package example.orders; + +import java.math.BigDecimal; + +import javax.persistence.Entity; +import javax.persistence.GeneratedValue; +import javax.persistence.Id; + +import lombok.Data; +import lombok.RequiredArgsConstructor; + +/** + * @author Oliver Gierke + */ +@Entity +@Data +@RequiredArgsConstructor +public class LineItem { + + private @GeneratedValue @Id Long id; + private final String description; + private final BigDecimal price; + + LineItem() { + this.description = null; + this.price = null; + } +} diff --git a/rest/projections/src/main/java/example/orders/Order.java b/rest/projections/src/main/java/example/orders/Order.java new file mode 100644 index 00000000..c4d2a29e --- /dev/null +++ b/rest/projections/src/main/java/example/orders/Order.java @@ -0,0 +1,51 @@ +/* + * Copyright 2014 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package example.orders; + +import java.util.ArrayList; +import java.util.List; + +import javax.persistence.CascadeType; +import javax.persistence.Entity; +import javax.persistence.GeneratedValue; +import javax.persistence.Id; +import javax.persistence.ManyToOne; +import javax.persistence.OneToMany; + +import lombok.Data; + +/** + * @author Oliver Gierke + */ +@Entity(name = "SampleOrder") +@Data +public class Order { + + @Id @GeneratedValue// + private Long id; + + @OneToMany(cascade = CascadeType.ALL, orphanRemoval = true)// + private List items = new ArrayList<>(); + + @ManyToOne// + private Customer customer; + + public Order add(LineItem item) { + + this.items.add(item); + return this; + } +} diff --git a/rest/projections/src/main/java/example/orders/OrderRepository.java b/rest/projections/src/main/java/example/orders/OrderRepository.java new file mode 100644 index 00000000..523b85c3 --- /dev/null +++ b/rest/projections/src/main/java/example/orders/OrderRepository.java @@ -0,0 +1,25 @@ +/* + * Copyright 2014 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package example.orders; + +import org.springframework.data.repository.CrudRepository; + +/** + * @author Oliver Gierke + */ +public interface OrderRepository extends CrudRepository { + +} diff --git a/rest/projections/src/test/java/example/orders/ApplicationIntegrationTests.java b/rest/projections/src/test/java/example/orders/ApplicationIntegrationTests.java new file mode 100644 index 00000000..9a653db1 --- /dev/null +++ b/rest/projections/src/test/java/example/orders/ApplicationIntegrationTests.java @@ -0,0 +1,45 @@ +/* + * Copyright 2014 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package example.orders; + +import static org.hamcrest.Matchers.*; +import static org.junit.Assert.*; + +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.test.SpringApplicationConfiguration; +import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; + +/** + * Integration tests to bootstrap the application. + * + * @author Oliver Gierke + */ +@RunWith(SpringJUnit4ClassRunner.class) +@SpringApplicationConfiguration(classes = Application.class) +public class ApplicationIntegrationTests { + + @Autowired OrderRepository repository; + + @Test + public void initializesRepositoryWithSampleData() { + + Iterable result = repository.findAll(); + + assertThat(result, is(iterableWithSize(1))); + } +} diff --git a/rest/starbucks/pom.xml b/rest/starbucks/pom.xml index b9ca5f06..0df9cf7c 100644 --- a/rest/starbucks/pom.xml +++ b/rest/starbucks/pom.xml @@ -27,7 +27,6 @@ com.jayway.jsonpath json-path - 0.9.1 runtime