├── .gitignore ├── LICENSE ├── README.adoc ├── README.md ├── advanced ├── README.md ├── build.gradle ├── gatewayV7 │ ├── README.md │ ├── gateway.properties │ ├── london │ │ └── locator.properties │ ├── ny │ │ └── locator.properties │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── GatewayExample.java │ │ │ ├── London.java │ │ │ └── NewYork.java │ │ └── resources │ │ ├── log4j.properties │ │ ├── london │ │ └── cache-config.xml │ │ └── ny │ │ └── cache-config.xml └── locator-failover │ ├── README.md │ └── src │ └── main │ ├── java │ └── org │ │ └── springframework │ │ └── data │ │ └── gemfire │ │ └── examples │ │ ├── Client.java │ │ └── Server.java │ └── resources │ ├── client │ └── cache-config.xml │ └── server │ └── cache-config.xml ├── basic ├── README.md ├── annotated-function │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── Client.java │ │ │ ├── Server.java │ │ │ ├── client │ │ │ ├── ClientConfig.java │ │ │ └── SalesCalculator.java │ │ │ └── server │ │ │ ├── SalesFunctions.java │ │ │ └── ServerConfig.java │ │ └── resources │ │ ├── client │ │ └── cache-config.xml │ │ ├── log4j.properties │ │ └── server │ │ └── cache-config.xml ├── build.gradle ├── cq-with-javaconfig │ ├── README.md │ └── src │ │ └── main │ │ └── java │ │ └── org │ │ └── springframework │ │ └── data │ │ └── gemfire │ │ └── examples │ │ ├── client │ │ └── Client.java │ │ └── server │ │ └── Server.java ├── function │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── CalculateTotalSalesForProduct.java │ │ │ ├── CalculateTotalSalesForProductInvoker.java │ │ │ ├── Client.java │ │ │ └── Server.java │ │ └── resources │ │ ├── client │ │ └── cache-config.xml │ │ └── server │ │ └── cache-config.xml ├── java-config │ ├── README.md │ └── src │ │ ├── main │ │ └── java │ │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ └── SpringJavaBasedContainerGemFireConfiguration.java │ │ └── test │ │ └── java │ │ └── org │ │ └── springframework │ │ └── data │ │ └── gemfire │ │ └── examples │ │ └── SpringJavaBasedContainerGemFireConfigurationTest.java ├── partitioned │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── Client.java │ │ │ ├── OrderKey.java │ │ │ ├── PartitionedOrderKey.java │ │ │ └── Server.java │ │ └── resources │ │ ├── client │ │ └── cache-config.xml │ │ └── server │ │ └── cache-config.xml ├── persistence │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ └── Main.java │ │ └── resources │ │ └── cache-config.xml ├── replicated-cs │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── Client.java │ │ │ └── Server.java │ │ └── resources │ │ ├── client │ │ └── cache-config.xml │ │ └── server │ │ └── cache-config.xml ├── replicated │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── Consumer.java │ │ │ └── Producer.java │ │ └── resources │ │ ├── consumer │ │ └── cache-config.xml │ │ └── producer │ │ └── cache-config.xml └── write-through │ ├── README.md │ └── src │ └── main │ ├── java │ └── org │ │ └── springframework │ │ └── data │ │ └── gemfire │ │ └── examples │ │ ├── Main.java │ │ ├── ProductDBLoader.java │ │ ├── ProductDBWriter.java │ │ └── repository │ │ └── ProductRepository.java │ └── resources │ ├── app-context.xml │ ├── cache-config.xml │ ├── db-config.xml │ └── db │ ├── schema.sql │ └── test-data.sql ├── build.gradle ├── gradle.properties ├── gradle └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradlew ├── gradlew.bat ├── quickstart ├── README.md ├── build.gradle ├── cq │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── CQListener.java │ │ │ ├── Client.java │ │ │ └── Server.java │ │ └── resources │ │ ├── client │ │ └── cache-config.xml │ │ ├── log4j.properties │ │ └── server │ │ └── cache-config.xml ├── gemfire-template │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── CustomerDao.java │ │ │ ├── CustomerService.java │ │ │ ├── GemfireTemplateCustomerDao.java │ │ │ ├── GemfireTemplateOrderDao.java │ │ │ ├── Main.java │ │ │ ├── OrderDao.java │ │ │ ├── OrderExample.java │ │ │ └── OrderService.java │ │ └── resources │ │ ├── app-context.xml │ │ ├── cache-config.xml │ │ └── log4j.properties ├── json │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── JSONCustomerExample.java │ │ │ └── Main.java │ │ └── resources │ │ ├── app-context.xml │ │ ├── cache-config.xml │ │ └── log4j.properties ├── repository │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── ApplicationConfig.java │ │ │ ├── CustomerService.java │ │ │ ├── Main.java │ │ │ ├── OrderExample.java │ │ │ ├── OrderService.java │ │ │ ├── ProductService.java │ │ │ └── repository │ │ │ ├── CustomerRepository.java │ │ │ ├── OrderRepository.java │ │ │ └── ProductRepository.java │ │ └── resources │ │ ├── cache-config.xml │ │ └── log4j.properties ├── spring-cache │ ├── README.md │ └── src │ │ └── main │ │ ├── java │ │ └── org │ │ │ └── springframework │ │ │ └── data │ │ │ └── gemfire │ │ │ └── examples │ │ │ ├── CustomerDao.java │ │ │ ├── CustomerService.java │ │ │ ├── HashMapCustomerDao.java │ │ │ └── Main.java │ │ └── resources │ │ ├── app-context.xml │ │ └── cache-context.xml └── transaction │ ├── README.md │ └── src │ └── main │ ├── java │ └── org │ │ └── springframework │ │ └── data │ │ └── gemfire │ │ └── examples │ │ ├── ApplicationConfig.java │ │ ├── CustomerService.java │ │ ├── Main.java │ │ └── repository │ │ └── CustomerRepository.java │ └── resources │ ├── cache-config.xml │ └── log4j.properties ├── settings.gradle └── spring-gemfire-examples-common └── src └── main ├── java └── org │ └── springframework │ └── data │ └── gemfire │ └── examples │ ├── GenericServer.java │ ├── Locator.java │ ├── LocatorCommandParser.java │ ├── domain │ ├── AbstractPersistentEntity.java │ ├── Address.java │ ├── Customer.java │ ├── EmailAddress.java │ ├── LineItem.java │ ├── Order.java │ └── Product.java │ └── util │ ├── LoggingCacheListener.java │ ├── ServerPortGenerator.java │ └── Version.java └── resources └── log4j.properties /.gitignore: -------------------------------------------------------------------------------- 1 | locator1*/ 2 | .settings 3 | .project 4 | .classpath 5 | .idea 6 | .springBeans 7 | .gradle 8 | #Compile source# 9 | *.class 10 | *.lk 11 | *.if 12 | build 13 | vf.* 14 | bin 15 | *.iml 16 | BACKUP* 17 | #Packages# 18 | ############ 19 | # it's better to unpack these files and commit the raw source 20 | # git has its own built in compression methods 21 | *.7z 22 | *.dmg 23 | *.gz 24 | *.iso 25 | *.rar 26 | *.tar 27 | *.zip 28 | target/ 29 | 30 | # Logs and databases # 31 | ###################### 32 | *.log 33 | *.sqlite 34 | *.state 35 | *.lock 36 | *.crf 37 | *.drf 38 | 39 | 40 | # OS generated files # 41 | ###################### 42 | .DS_Store* 43 | ehthumbs.db 44 | Icon? 45 | Thumbs.db 46 | -------------------------------------------------------------------------------- /README.adoc: -------------------------------------------------------------------------------- 1 | # spring-gemfire-examples is no longer actively maintained by VMware, Inc. 2 | 3 | -------------------------------------------------------------------------------- /advanced/README.md: -------------------------------------------------------------------------------- 1 | Spring Data GemFire - Advanced Examples 2 | ======================================== 3 | 4 | These examples demonstrate additional GemFire features and require a full installation of GemFire. A trial version may be obtained [here](https://www.vmware.com/products/application-platform/vfabric-gemfire/overview.html). 5 | 6 | 7 | #Starting and Stopping Locators 8 | 9 | These examples require GemFire locators to be running. The locator is used to discover distributed system members and used to obtain member network addresses. For example, in a client-server topology locator addresses are known to the client and servers. The client pool uses the locator to obtain server connections on start up. Typically there are two locators for each distributed system, a primary and backup locator. 10 | 11 | The spring-gemfire-examples-common project includes a Locator utility to start and stop locators on localhost. It is required that you defing an environment variable GEMFIRE_HOME, set to the location of the GemFire product installation. Alternatively you can pass this location as a parameter to the locator utility. 12 | 13 | ## Starting a Locator 14 | 15 | Open a command window or terminal session, navigate to the examples directory and type 16 | 17 | gradle -q start-locator- 18 | 19 | For example, to start two locators with GEMFIRE_HOME set: 20 | 21 | gradle -q start-locator-10334 22 | gradle -q start-locator-10335 23 | 24 | ## Stopping a Locator 25 | 26 | gradle -q stop-locator-10334 27 | gradle -q stop-locator-10335 28 | 29 | By default, each locator instance keeps runtime files, e.g., logs in a directory location ./locator. Review the contents of these logs, especially if you are unable to start or stop a locator. You may also pass a command line parameter to specify an alternate working directory for a locator but you must create the directory first: 30 | 31 | gradle -q start-locator-10334 -Pdir=/foo/bar 32 | 33 | ## Running the Locator utility from the IDE 34 | 35 | Import the spring-gemfire-examples-common project into your IDE. From there you should be able to run the Locator utility as a Java program, providing appropriate command line options, e.g., 36 | 37 | --start --port 10334 --gemfire_home /foo/bar 38 | 39 | If you run it with no options you will get a help message. 40 | -------------------------------------------------------------------------------- /advanced/build.gradle: -------------------------------------------------------------------------------- 1 | description = 'Spring Data GemFire Advanced Examples' 2 | 3 | project('gatewayV7') { 4 | 5 | description = 'Spring Data GemFire Gateway (Version 7) Example' 6 | 7 | dependencies { 8 | compile project(':spring-gemfire-examples-common') 9 | } 10 | } 11 | 12 | project('locator-failover') { 13 | 14 | description = 'Spring Data GemFire Locator Failover Example' 15 | 16 | dependencies { 17 | compile project(':spring-gemfire-examples-common') 18 | } 19 | } 20 | 21 | 22 | project('server-failover') { 23 | 24 | description = 'Spring Data GemFire Server Failover Example' 25 | 26 | dependencies { 27 | compile project(':spring-gemfire-examples-common') 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /advanced/gatewayV7/README.md: -------------------------------------------------------------------------------- 1 | Spring Data GemFire - Gateway V7 Example 2 | ===================================== 3 | 4 | See the [README](..README.md) in the advanced root directory for information about locators. 5 | 6 | Note: This example requires a valid [GemFire license key](https://pubs.vmware.com/vfabric51/topic/com.vmware.vfabric.gemfire.6.6/deploying/licensing/licensing.html?resultof=%22%6c%69%63%65%6e%73%69%6e%67%22%20%22%6c%69%63%65%6e%73%22%20) for a Data Management Node. GemFire checks for a valid license before starting a gateway. 7 | 8 | If you have downloaded the trial version, you will need to obtain a key from GemFire sales. Edit gateway.properties to set the license key: 9 | 10 | gemfire.license.key=my license key 11 | 12 | To run this example, Open a command window and start two locators: 13 | 14 | ./gradlew -q start-locator-10334 -Pprops=advanced/gatewayV7/london/locator.properties 15 | ./gradlew -q start-locator-10335 -Pprops=advanced/gatewayV7/ny/locator.properties 16 | 17 | Each properties file declares the other locator as a remote locator and identifies the remote system Id. 18 | 19 | 20 | Start one of the processes: 21 | 22 | ./gradlew -q run-gatewayV7 -Pmain=NewYork 23 | 24 | In another command window, run: 25 | 26 | ./gradlew -q run-gatewayV7 -Pmain=London 27 | 28 | Each of these initializes an Order region which is gateway enabled and a gateway hub. Since each process uses a different locator, and multicast is disabled (mcast-port=0), each cache runs in a separate Distributed System, simulating two remote installations. Both processes will prompt you to press ENTER to update the region. Wait for both processes to start first. You should see a log message from the remote process's LoggingCacheListener indicating the remote region was updated. Press ENTER a second time to terminate the process. 29 | -------------------------------------------------------------------------------- /advanced/gatewayV7/gateway.properties: -------------------------------------------------------------------------------- 1 | gemfire.license.key=81083-4WY42-48948-0YM00-8J425,Y10AA-N0JDJ-J8R8T-07CFK-34RPC 2 | #gemfire.license.key=Y10AA-N0JDJ-J8R8T-07CFK-34RPC //WAN Upgrade 3 | #gemfire.license.key=W109C-00113-H888J-03FVP-3FMPF -------------------------------------------------------------------------------- /advanced/gatewayV7/london/locator.properties: -------------------------------------------------------------------------------- 1 | remote-locators=localhost[10335] 2 | distributed-system-id=1 -------------------------------------------------------------------------------- /advanced/gatewayV7/ny/locator.properties: -------------------------------------------------------------------------------- 1 | remote-locators=localhost[10334] 2 | distributed-system-id=2 -------------------------------------------------------------------------------- /advanced/gatewayV7/src/main/java/org/springframework/data/gemfire/examples/GatewayExample.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples; 18 | 19 | import java.io.File; 20 | import java.io.IOException; 21 | 22 | import org.springframework.context.ApplicationContext; 23 | import org.springframework.context.support.ClassPathXmlApplicationContext; 24 | import org.springframework.data.gemfire.examples.domain.Address; 25 | import org.springframework.data.gemfire.examples.domain.Order; 26 | 27 | import org.apache.geode.cache.Cache; 28 | import org.apache.geode.cache.Region; 29 | import org.apache.geode.cache.wan.GatewayReceiver; 30 | 31 | /** 32 | * @author David Turanski 33 | */ 34 | public class GatewayExample { 35 | 36 | @SuppressWarnings({ "deprecation", "unchecked" }) 37 | public static void run(String location, long id) { 38 | 39 | File diskStoreDirectory = new File(location); 40 | if (!diskStoreDirectory.exists()) { 41 | diskStoreDirectory.mkdir(); 42 | } 43 | 44 | ApplicationContext context = new ClassPathXmlApplicationContext( 45 | location + "/cache-config.xml"); 46 | Cache cache = context.getBean(Cache.class); 47 | GatewayReceiver receiver = cache.getGatewayReceivers().iterator().next(); 48 | if (receiver.isRunning()) { 49 | System.out.println("gateway reveiver is running on " + receiver.getPort()); 50 | } else { 51 | System.out.println("gateway receiver is not started"); 52 | } 53 | 54 | Region region = context.getBean(Region.class); 55 | 56 | try { 57 | System.out.println("Press to update region " + region.getName()); 58 | System.in.read(); 59 | region.put(id, new Order(1L, 1L, new Address("street", "city", 60 | "country"))); 61 | System.out.println("Press to quit"); 62 | System.in.read(); 63 | } catch (IOException e) { 64 | // TODO Auto-generated catch block 65 | e.printStackTrace(); 66 | } 67 | System.exit(0); 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /advanced/gatewayV7/src/main/java/org/springframework/data/gemfire/examples/London.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | 19 | /** 20 | * @author David Turanski 21 | * 22 | */ 23 | public class London { 24 | public static void main(String args[]) { 25 | GatewayExample.run("london",2); 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /advanced/gatewayV7/src/main/java/org/springframework/data/gemfire/examples/NewYork.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | /** 19 | * @author David Turanski 20 | * 21 | */ 22 | public class NewYork { 23 | public static void main(String args[]) { 24 | GatewayExample.run("ny", 1); 25 | } 26 | 27 | } 28 | -------------------------------------------------------------------------------- /advanced/gatewayV7/src/main/resources/log4j.properties: -------------------------------------------------------------------------------- 1 | log4j.rootCategory=WARN, stdout 2 | 3 | log4j.appender.stdout=org.apache.log4j.ConsoleAppender 4 | log4j.appender.stdout.layout=org.apache.log4j.PatternLayout 5 | log4j.appender.stdout.layout.ConversionPattern=%p [%t] [%C{1}] - %m%n 6 | 7 | #log4j.category.org.springframework.data.gemfire.examples=DEBUG 8 | log4j.category.org.springframework=DEBUG 9 | -------------------------------------------------------------------------------- /advanced/gatewayV7/src/main/resources/london/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | 12 | 13 | 0 14 | localhost[10334] 15 | 1 16 | info 17 | ${gemfire.license.key} 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 27 | 28 | 29 | 30 | 31 | 33 | 34 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | -------------------------------------------------------------------------------- /advanced/gatewayV7/src/main/resources/ny/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | 14 | 15 | 0 16 | localhost[10335] 17 | localhost[10334] 18 | 2 19 | info 20 | ${gemfire.license.key} 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | -------------------------------------------------------------------------------- /advanced/locator-failover/README.md: -------------------------------------------------------------------------------- 1 | Spring Data GemFire - Locator Failover Example 2 | ============================================== 3 | 4 | See the [README](..README.md) in the advanced root directory for information about locators. 5 | 6 | This example creates simple a client server system to demonstrate what happens when the primary locator is down either after initialization or before initialization. 7 | 8 | # Scenario 1 - Locator Down After Initialization 9 | 10 | Start two locators: 11 | 12 | ./gradlew -q start-locator-10334 13 | ./gradlew -q start-locator-10335 14 | 15 | Start the server: 16 | 17 | ./gradlew -q run-locator-failover -Pmain=Server 18 | 19 | Start the client: 20 | 21 | ./gradlew -q run-locator-failover -Pmain=Client 22 | 23 | 24 | The client will create two Customer entries which will be indicated by Server log messages. 25 | 26 | When prompted in the client, stop the primary locator: 27 | 28 | ./gradlew -q stop-locator-10334 29 | 30 | The client will create two more Customer entries. 31 | 32 | You should see some warning messages in the Server process like: 33 | 34 | Could not connect to distribution locator localhost:10334: java.net.ConnectException: Connection refused 35 | 36 | But everything should still work. In this case, the client already has a connection to the server so the locator is not used. 37 | 38 | 39 | #Scenario 2 - Locator Down Before Initialization 40 | 41 | Following scenario 1, the primary locator (port 10334) is stopped and the secondary locator (port 10335) is running. You may also leave the Server running or restart it. When the Client starts, you will see an info log message something like: 42 | 43 | [info ... EDT tid=0x17] locator localhost/127.0.0.1:10334 is not running. 44 | java.net.ConnectException: Connection refused ... (stack trace follows) 45 | 46 | The secondary locator will take over and the application will run as before. 47 | 48 | 49 | 50 | -------------------------------------------------------------------------------- /advanced/locator-failover/src/main/java/org/springframework/data/gemfire/examples/Client.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.io.IOException; 19 | 20 | import org.springframework.context.ApplicationContext; 21 | import org.springframework.context.support.ClassPathXmlApplicationContext; 22 | import org.springframework.data.gemfire.examples.domain.Customer; 23 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 24 | 25 | import org.apache.geode.cache.Region; 26 | 27 | public class Client { 28 | 29 | @SuppressWarnings("unchecked") 30 | public static void main(String args[]) throws IOException { 31 | 32 | System.out.println("Start locators on ports 10334 and 10335 and the Server. Press to continue"); 33 | System.in.read(); 34 | 35 | ApplicationContext context = new ClassPathXmlApplicationContext("client/cache-config.xml"); 36 | Region region = context.getBean(Region.class); 37 | 38 | 39 | Customer dave = new Customer(1L,new EmailAddress("dave@matthews.com"),"Dave","Matthews"); 40 | Customer alicia = new Customer(2L,new EmailAddress("alicia@keys.com"),"Alicia","Keys"); 41 | region.put(dave.getId(),dave); 42 | region.put(alicia.getId(),alicia); 43 | 44 | System.out.println("Stop the primary locator on port 10334. Press to continue"); 45 | System.in.read(); 46 | 47 | Customer john = new Customer(3L,new EmailAddress("john@mayer.com"),"John","Mayer"); 48 | Customer gwen = new Customer(4L,new EmailAddress("gwen@stefani.com"),"Gwen","Stefani"); 49 | region.put(john.getId(),john); 50 | region.put(gwen.getId(),gwen); 51 | 52 | System.exit(0); 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /advanced/locator-failover/src/main/java/org/springframework/data/gemfire/examples/Server.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.io.IOException; 19 | 20 | import org.springframework.context.support.ClassPathXmlApplicationContext; 21 | 22 | public class Server { 23 | public static void main(String args[]) throws IOException { 24 | 25 | System.out 26 | .println("Start locators on 10334 and 10335 and Press to continue"); 27 | System.in.read(); 28 | 29 | new ClassPathXmlApplicationContext("server/cache-config.xml"); 30 | 31 | System.out.println("Press to terminate the server"); 32 | System.in.read(); 33 | System.exit(0); 34 | } 35 | 36 | } 37 | -------------------------------------------------------------------------------- /advanced/locator-failover/src/main/resources/client/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | 0 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /advanced/locator-failover/src/main/resources/server/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | localhost[10334],localhost[10335] 14 | 0 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | -------------------------------------------------------------------------------- /basic/README.md: -------------------------------------------------------------------------------- 1 | Spring GemFire Basic Examples 2 | ============================= 3 | 4 | This project contains a number of examples demonstrating the basic use Spring Data GemFire to 5 | configure GemFire components such as Caches and Regions. 6 | -------------------------------------------------------------------------------- /basic/annotated-function/README.md: -------------------------------------------------------------------------------- 1 | Spring Data Annotated Function Execution Example 2 | ============================================== 3 | 4 | This example demonstrates the use of Annotation Driven Function Execution configured with Spring Data GemFire. The example is functionally equivalent to the [function](../basic/function) example and requires Spring Data GemFire 1.3.0 or above. The example includes a Server process which registers a function to calculate total $ales for a given product from cached orders. This requires searching all order line items for those containing the given product and computing the grand total. It is much more efficient to do this work at the server than to retrieve all orders over the network. 5 | 6 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 7 | 8 | ./gradlew -q run-annotated-function -Pmain=Server 9 | 10 | Open a second command window, and type: 11 | 12 | ./gradlew -q run-annotated-function -Pmain=Client 13 | 14 | Or to run from your IDE, execute one of the following tasks once. 15 | 16 | ./gradlew eclipse 17 | ./gradlew idea 18 | 19 | Then import the project into your IDE and run the above. 20 | 21 | # Details 22 | The Spring configuration files, *client/cache-config.xml* and *server/cache-config.xml* contain the core gemfire cache configurations respectively. These are imported by the corresponding Spring Configuration classes, *ClientConfig* and *ServerConfig*. 23 | 24 | The server hosts a Product Region and Order Region and registers the function with the id with a fun id *totalSalesForProduct* as implemented by the *totalSalesForProduct* method in the *SalesFunction.java* which is a normal Spring bean. The function is registered and wrapped in a GemFire Function by processing the *@GemfireFunction* annotation on the method. This processing is enabled via the *@EnableGemfireFunctions* annotation in *ServerConfig.java*. 25 | 26 | The client invokes the function remotely using the *SalesCalculator* interface. This interface is annotated with *OnServer* which implies that all supported methods will be invoked as a Server Execution. Note that it is not necessary for the function implementation to implement this interface as long as the implementation method defines a similar argument list. The client side behavior is enabled via the *@EnableGemfireFunctionExecutions* annotation in *ClientConfig.java*. This sets up a classpath scanner to discover annotated interfaces. 27 | 28 | Note that the server generates random orders so the totals will be different every time you start the Server. -------------------------------------------------------------------------------- /basic/annotated-function/src/main/java/org/springframework/data/gemfire/examples/Client.java: -------------------------------------------------------------------------------- 1 | package org.springframework.data.gemfire.examples; 2 | /* 3 | * Copyright 2012 the original author or authors. 4 | * 5 | * Licensed under the Apache License, Version 2.0 (the "License"); 6 | * you may not use this file except in compliance with the License. 7 | * You may obtain a copy of the License at 8 | * 9 | * https://www.apache.org/licenses/LICENSE-2.0 10 | * 11 | * Unless required by applicable law or agreed to in writing, software 12 | * distributed under the License is distributed on an "AS IS" BASIS, 13 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 | * See the License for the specific language governing permissions and 15 | * limitations under the License. 16 | */ 17 | 18 | 19 | import java.io.IOException; 20 | import java.math.BigDecimal; 21 | 22 | import org.apache.commons.logging.Log; 23 | import org.apache.commons.logging.LogFactory; 24 | import org.springframework.context.ApplicationContext; 25 | import org.springframework.context.annotation.AnnotationConfigApplicationContext; 26 | import org.springframework.data.gemfire.examples.client.ClientConfig; 27 | import org.springframework.data.gemfire.examples.client.SalesCalculator; 28 | 29 | public class Client { 30 | 31 | public static void main(String args[]) throws IOException { 32 | Log log = LogFactory.getLog(Client.class); 33 | ApplicationContext context = new AnnotationConfigApplicationContext(ClientConfig.class); 34 | 35 | SalesCalculator salesCalculator = context.getBean(SalesCalculator.class); 36 | 37 | String[] products = new String[]{"Apple iPad","Apple iPod","Apple macBook"}; 38 | 39 | for (String productName: products){ 40 | BigDecimal total = salesCalculator.totalSalesForProduct(productName); 41 | log.info("total sales for " + productName + " = $" + total); 42 | } 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /basic/annotated-function/src/main/java/org/springframework/data/gemfire/examples/client/ClientConfig.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2002-2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with 5 | * the License. You may obtain a copy of the License at 6 | * 7 | * https://www.apache.org/licenses/LICENSE-2.0 8 | * 9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on 10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the 11 | * specific language governing permissions and limitations under the License. 12 | */ 13 | package org.springframework.data.gemfire.examples.client; 14 | 15 | import org.springframework.context.annotation.Configuration; 16 | import org.springframework.context.annotation.ImportResource; 17 | import org.springframework.data.gemfire.function.config.EnableGemfireFunctionExecutions; 18 | 19 | /** 20 | * @author David Turanski 21 | * 22 | */ 23 | @ImportResource("client/cache-config.xml") 24 | @EnableGemfireFunctionExecutions(basePackages="org.springframework.data.gemfire.examples.client") 25 | @Configuration 26 | public class ClientConfig { 27 | 28 | } 29 | -------------------------------------------------------------------------------- /basic/annotated-function/src/main/java/org/springframework/data/gemfire/examples/client/SalesCalculator.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2002-2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with 5 | * the License. You may obtain a copy of the License at 6 | * 7 | * https://www.apache.org/licenses/LICENSE-2.0 8 | * 9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on 10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the 11 | * specific language governing permissions and limitations under the License. 12 | */ 13 | package org.springframework.data.gemfire.examples.client; 14 | 15 | import java.math.BigDecimal; 16 | 17 | import org.springframework.data.gemfire.function.annotation.OnServer; 18 | 19 | 20 | 21 | /** 22 | * @author David Turanski 23 | * 24 | 25 | * By default this will run on a server connected to the default client cache. e.g., the declaration is equivalent to 26 | * 27 | * @OnServer(id="totalSalesForProduct",cache="gemfireCache") 28 | * 29 | * 30 | * Also since the interface is a singleton, the method invocation is associated with the function with the same Id. 31 | * 32 | */ 33 | @OnServer 34 | public interface SalesCalculator { 35 | public BigDecimal totalSalesForProduct(String productName); 36 | } 37 | -------------------------------------------------------------------------------- /basic/annotated-function/src/main/java/org/springframework/data/gemfire/examples/server/SalesFunctions.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples.server; 17 | 18 | import java.math.BigDecimal; 19 | 20 | import javax.annotation.Resource; 21 | 22 | import org.apache.commons.logging.Log; 23 | import org.apache.commons.logging.LogFactory; 24 | import org.springframework.data.gemfire.GemfireTemplate; 25 | import org.springframework.data.gemfire.examples.domain.LineItem; 26 | import org.springframework.data.gemfire.examples.domain.Order; 27 | import org.springframework.data.gemfire.examples.domain.Product; 28 | import org.springframework.data.gemfire.function.annotation.GemfireFunction; 29 | 30 | import org.springframework.stereotype.Component; 31 | 32 | import org.apache.geode.cache.Region; 33 | import org.apache.geode.cache.execute.Function; 34 | import org.apache.geode.cache.query.SelectResults; 35 | 36 | 37 | /** 38 | * A function for aggregating and calculating results on the cache server. * 39 | * 40 | * @author David Turanski 41 | * 42 | */ 43 | 44 | @Component 45 | public class SalesFunctions { 46 | private static Log log = LogFactory.getLog(SalesFunctions.class); 47 | 48 | @Resource(name="productTemplate") 49 | private GemfireTemplate productTemplate; 50 | @Resource(name="Order") 51 | private Region orderRegion; 52 | 53 | 54 | /** 55 | * This method computes total sales for a given product. The @GemfireFunction 56 | * annotation allows this function to be wrapped in a GemFire {@link Function} and registered with the given 57 | * id. 58 | * 59 | * @param productName 60 | * @return 61 | */ 62 | @GemfireFunction 63 | public BigDecimal totalSalesForProduct(String productName) { 64 | 65 | log.debug("searching for product name '" + productName + "'"); 66 | 67 | SelectResults results = productTemplate.query("name = '" + productName + "'"); 68 | 69 | if (results.isEmpty()) { 70 | log.warn("cannot find product '" + productName + "'"); 71 | return new BigDecimal(0.0); 72 | } 73 | 74 | Product product = results.asList().get(0); 75 | 76 | long productId = product.getId(); 77 | 78 | BigDecimal total = new BigDecimal(0.0); 79 | 80 | for (Order order: orderRegion.values()) { 81 | for (LineItem lineItem: order.getLineItems()) { 82 | if (lineItem.getProductId() == productId) { 83 | total = total.add(lineItem.getTotal()); 84 | } 85 | } 86 | } 87 | 88 | return total.setScale(2,BigDecimal.ROUND_CEILING); 89 | } 90 | } 91 | -------------------------------------------------------------------------------- /basic/annotated-function/src/main/java/org/springframework/data/gemfire/examples/server/ServerConfig.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2002-2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with 5 | * the License. You may obtain a copy of the License at 6 | * 7 | * https://www.apache.org/licenses/LICENSE-2.0 8 | * 9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on 10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the 11 | * specific language governing permissions and limitations under the License. 12 | */ 13 | package org.springframework.data.gemfire.examples.server; 14 | 15 | import org.springframework.context.annotation.Bean; 16 | import org.springframework.context.annotation.Configuration; 17 | import org.springframework.context.annotation.ImportResource; 18 | import org.springframework.data.gemfire.examples.util.LoggingCacheListener; 19 | import org.springframework.data.gemfire.function.config.EnableGemfireFunctions; 20 | 21 | /** 22 | * @author David Turanski 23 | * 24 | */ 25 | @ImportResource("server/cache-config.xml") 26 | @EnableGemfireFunctions 27 | @Configuration 28 | public class ServerConfig { 29 | 30 | @Bean 31 | SalesFunctions salesFunctions() { 32 | return new SalesFunctions(); 33 | } 34 | 35 | @Bean 36 | LoggingCacheListener loggingCacheListener() { 37 | return new LoggingCacheListener(); 38 | } 39 | } 40 | -------------------------------------------------------------------------------- /basic/annotated-function/src/main/resources/client/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /basic/annotated-function/src/main/resources/log4j.properties: -------------------------------------------------------------------------------- 1 | log4j.rootCategory=WARN, stdout 2 | 3 | log4j.appender.stdout=org.apache.log4j.ConsoleAppender 4 | log4j.appender.stdout.layout=org.apache.log4j.PatternLayout 5 | log4j.appender.stdout.layout.ConversionPattern=%p [%t] [%C{1}] - %m%n 6 | 7 | log4j.category.org.springframework.data.gemfire=DEBUG 8 | -------------------------------------------------------------------------------- /basic/annotated-function/src/main/resources/server/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | 12 | warning 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | -------------------------------------------------------------------------------- /basic/build.gradle: -------------------------------------------------------------------------------- 1 | description = 'Spring Data GemFire Basic Examples' 2 | 3 | project('replicated') { 4 | 5 | description = 'Spring Data GemFire Replicated Region (p2p) Example' 6 | 7 | dependencies { 8 | compile project(':spring-gemfire-examples-common') 9 | } 10 | } 11 | 12 | project('replicated-cs') { 13 | 14 | description = 'Spring Data GemFire Replicated Region (Client Server) Example' 15 | 16 | dependencies { 17 | compile project(':spring-gemfire-examples-common') 18 | } 19 | } 20 | 21 | 22 | project('partitioned') { 23 | 24 | description = 'Spring Data GemFire Partitioned Region Example' 25 | 26 | dependencies { 27 | compile project(':spring-gemfire-examples-common') 28 | compile "org.springframework:spring-aop:$springVersion" 29 | compile "org.springframework:spring-context-support:$springVersion" 30 | compile "org.springframework:spring-tx:$springVersion" 31 | } 32 | } 33 | 34 | project('persistence') { 35 | 36 | description = 'Spring Data GemFire Persistence Example' 37 | 38 | dependencies { 39 | compile project(':spring-gemfire-examples-common') 40 | compile "org.springframework:spring-aop:$springVersion" 41 | compile "org.springframework:spring-context-support:$springVersion" 42 | compile "org.springframework:spring-tx:$springVersion" 43 | } 44 | } 45 | 46 | project('write-through') { 47 | 48 | description = 'Spring Data GemFire Write Through Example' 49 | 50 | dependencies { 51 | compile project(':spring-gemfire-examples-common') 52 | compile "org.springframework:spring-aop:$springVersion" 53 | compile "org.springframework:spring-context-support:$springVersion" 54 | compile "org.springframework:spring-jdbc:$springVersion" 55 | compile "org.springframework:spring-tx:$springVersion" 56 | compile "org.springframework.data:spring-data-jpa:1.2.0.BUILD-SNAPSHOT" 57 | runtime "com.h2database:h2:1.3.168" 58 | compile "org.hibernate:hibernate-entitymanager:4.1.6.Final" 59 | compile "org.hibernate:hibernate-core:4.1.6.Final" 60 | compile "org.hibernate:hibernate-validator:4.3.0.Final" 61 | } 62 | } 63 | 64 | project('function') { 65 | 66 | description = 'Spring Data GemFire Function Execution Example' 67 | 68 | dependencies { 69 | compile project(':spring-gemfire-examples-common') 70 | compile "org.springframework:spring-aop:$springVersion" 71 | compile "org.springframework:spring-context-support:$springVersion" 72 | compile "org.springframework:spring-tx:$springVersion" 73 | } 74 | } 75 | 76 | project('annotated-function') { 77 | 78 | description = 'Spring Data GemFire Function Execution with Annotations Example' 79 | 80 | dependencies { 81 | compile project(':spring-gemfire-examples-common') 82 | compile "org.springframework:spring-aop:$springVersion" 83 | compile "org.springframework:spring-context-support:$springVersion" 84 | compile "org.springframework:spring-tx:$springVersion" 85 | } 86 | } 87 | 88 | project('java-config') { 89 | 90 | description = 'Spring Data GemFire Configuration Example using Spring Java-based Container Configuration' 91 | 92 | dependencies { 93 | compile project(':spring-gemfire-examples-common') 94 | compile "org.springframework:spring-aop:$springVersion" 95 | compile "org.springframework:spring-context-support:$springVersion" 96 | compile "org.springframework:spring-tx:$springVersion" 97 | } 98 | } 99 | 100 | project('cq-with-javaconfig') { 101 | 102 | description = 'Continuous Query example using the Spring Data GemFire ContinuousQueryListenerContainer configured with JavaConfig' 103 | 104 | dependencies { 105 | compile project(':spring-gemfire-examples-common') 106 | compile "org.springframework:spring-aop:$springVersion" 107 | compile "org.springframework:spring-context-support:$springVersion" 108 | compile "org.springframework:spring-tx:$springVersion" 109 | compile ("org.springframework.boot:spring-boot-starter:$springBootVersion") { 110 | exclude group: "ch.qos.logback", module: "logback-classic" 111 | } 112 | } 113 | } 114 | -------------------------------------------------------------------------------- /basic/cq-with-javaconfig/README.md: -------------------------------------------------------------------------------- 1 | GemFire Continuous Query (CQ) Configured with Spring JavaConfig 2 | =============================================================== 3 | 4 | This example demonstrates GemFire's [Continuous Query (CQ)](https://gemfire.docs.pivotal.io/geode/developing/continuous_querying/chapter_overview.html) functionality. 5 | Specifically, this example shows how to use _Spring's_ [Java-based Container Configuration](https://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#beans-java) 6 | along with _Spring Data GemFire's_ [ContinuousQueryListenerContainer](https://docs.spring.io/spring-data-gemfire/docs/current/reference/html/#apis:cq-container) 7 | declared in JavaConfig to define cache client _Continuous Queries_ (CQ), 8 | register for notifications and process CQ events. 9 | 10 | This examples uses GemFire's [client/server](https://gemfire.docs.pivotal.io/geode/topologies_and_comm/cs_configuration/chapter_overview.html) 11 | topology. 12 | 13 | The `Server` class in this example is a _Spring Boot_ application that bootstraps 14 | an embedded GemFire Server (peer cache member of the GemFire cluster/distributed system) 15 | and starts a GemFire `CacheServer` allowing cache clients to connect. 16 | In addition, it also creates a `/Orders` _Region_ in which `Orders` 17 | will be placed and CQ events generated. 18 | 19 | The application simulates `Orders` from `Customers` using _Spring's_ [scheduling infrastructure](https://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#scheduling), 20 | placing `Orders` into the `/Orders` _Region_. 21 | 22 | The `Client` class in this example is also a _Spring Boot_ application 23 | as well as a GemFire cache client. It connects to the GemFire `CacheServer` directly 24 | using the default `CacheServer's` host and port (i.e. 40404). 25 | 26 | The client registers 2 CQs, 1 to capture events for `Orders` under $1000 27 | and another for `Orders` over $2000. Both the client and server log 28 | the entries in the `/Orders` _Region_. The `Server` does so with 29 | a `CacheListener` and the client does so using a SDG `ContinuousQueryListener`. 30 | 31 | To run this example, open a command window, go to the the `spring-gemfire-examples` root directory, and type: 32 | 33 | ./gradlew -q run-cq-with-javaconfig -Pmain=server.Server 34 | 35 | In another window, type: 36 | 37 | ./gradlew -q run-cq-with-javaconfig -Pmain=client.Client 38 | 39 | Or, to run from your IDE, execute one of the following tasks once: 40 | 41 | ./gradlew eclipse 42 | ./gradlew idea 43 | 44 | Then import the project into your IDE and run the above classes. 45 | 46 | # Additional Details 47 | 48 | An implementation of SDG's `ContinuousQueryListener` is a POJO (albeit dependent only on the GemFire type `CQEvent`). 49 | It is not required to implement any specific interfaces, but it must provide appropriate method signatures 50 | so the `ConitnuousQueryListenerContainer` can delegate `CQEvents` to it. 51 | 52 | Additionally, the cache client, _Spring Boot_ application's `Pool` 53 | must be configured with `subscription-enabled='true'`. 54 | -------------------------------------------------------------------------------- /basic/function/README.md: -------------------------------------------------------------------------------- 1 | Spring Data GemFire Function Execution Example 2 | ============================================== 3 | 4 | This example demonstrates the use of GemFire's Function Execution Service configured with Spring Data GemFire. The example contains a Server which registers a function to calculate total $ales for a given product from orders in cache. This requires searching all order line items for the given product and computing the grand total. It is much more efficient to do this work at the server than to retrieve all orders over the network. 5 | 6 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 7 | 8 | ./gradlew -q run-function -Pmain=Server 9 | 10 | Open a second command window, and type: 11 | 12 | ./gradlew -q run-function -Pmain=Client 13 | 14 | Or to run from your IDE, execute one of the following tasks once. 15 | 16 | ./gradlew eclipse 17 | ./gradlew idea 18 | 19 | Then import the project into your IDE and run the above. 20 | 21 | # Details 22 | The Spring configuration files, client/cache-config.xml and server/cache-config.xml contain the respective configurations. The client is configured with a client pool. The server hosts a Product Region and Order Region and uses the FunctionService to register a function CalculateTotalSalesForProduct. This is a Spring bean that implements GemFire's Function interface. The client invokes the function remotely using CalculateTotalSalesForProductInvoker. Note that the server generates random orders so the totals will be different every time you start the Server. 23 | 24 | Also Note that since the client and the server side components are all in the same classpath, Spring's compont scanner includes filters to ensure client side beans are not registered in the server application context, and vice versa. In a real application, it would be better to package server side functions in a separate jar and deploy that to the server. 25 | -------------------------------------------------------------------------------- /basic/function/src/main/java/org/springframework/data/gemfire/examples/CalculateTotalSalesForProduct.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.math.BigDecimal; 19 | 20 | import javax.annotation.Resource; 21 | 22 | import org.apache.commons.logging.Log; 23 | import org.apache.commons.logging.LogFactory; 24 | import org.springframework.data.gemfire.GemfireTemplate; 25 | import org.springframework.data.gemfire.examples.domain.LineItem; 26 | import org.springframework.data.gemfire.examples.domain.Product; 27 | import org.springframework.data.gemfire.examples.domain.Order; 28 | import org.springframework.stereotype.Component; 29 | 30 | import org.apache.geode.cache.Region; 31 | import org.apache.geode.cache.execute.FunctionAdapter; 32 | import org.apache.geode.cache.execute.FunctionContext; 33 | import org.apache.geode.cache.execute.ResultSender; 34 | import org.apache.geode.cache.query.SelectResults; 35 | 36 | 37 | /** 38 | * A GemFire Function for aggregating and calculating results on the cache server. 39 | * 40 | * This function computes the total sales for a given product. 41 | * 42 | * @author David Turanski 43 | * 44 | */ 45 | @SuppressWarnings("serial") 46 | @Component 47 | public class CalculateTotalSalesForProduct extends FunctionAdapter { 48 | private static Log log = LogFactory.getLog(CalculateTotalSalesForProduct.class); 49 | 50 | @Resource(name="productTemplate") 51 | private GemfireTemplate productTemplate; 52 | @Resource(name="Order") 53 | private Region orderRegion; 54 | 55 | /* (non-Javadoc) 56 | * @see org.apache.geode.cache.execute.FunctionAdapter#execute(org.apache.geode.cache.execute.FunctionContext) 57 | */ 58 | @Override 59 | public void execute(FunctionContext functionContext) { 60 | ResultSender resultSender = functionContext.getResultSender(); 61 | 62 | String productName = (String)functionContext.getArguments(); 63 | 64 | log.debug("searching for product name '" + productName + "'"); 65 | 66 | SelectResults results = productTemplate.query("name = '" + productName + "'"); 67 | 68 | if (results.isEmpty()) { 69 | log.warn("cannot find product '" + productName + "'"); 70 | resultSender.lastResult(new BigDecimal(0.0)); 71 | return; 72 | } 73 | 74 | Product product = results.asList().get(0); 75 | 76 | long productId = product.getId(); 77 | 78 | BigDecimal total = new BigDecimal(0.0); 79 | 80 | for (Order order: orderRegion.values()) { 81 | for (LineItem lineItem: order.getLineItems()) { 82 | if (lineItem.getProductId() == productId) { 83 | total = total.add(lineItem.getTotal()); 84 | } 85 | } 86 | } 87 | 88 | resultSender.lastResult(total.setScale(2,BigDecimal.ROUND_CEILING)); 89 | } 90 | 91 | /* (non-Javadoc) 92 | * @see org.apache.geode.cache.execute.FunctionAdapter#getId() 93 | */ 94 | @Override 95 | public String getId() { 96 | return getClass().getSimpleName(); 97 | } 98 | } 99 | -------------------------------------------------------------------------------- /basic/function/src/main/java/org/springframework/data/gemfire/examples/CalculateTotalSalesForProductInvoker.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.math.BigDecimal; 19 | import java.util.List; 20 | 21 | import javax.annotation.Resource; 22 | 23 | import org.springframework.stereotype.Component; 24 | 25 | import org.apache.geode.cache.client.Pool; 26 | import org.apache.geode.cache.execute.Execution; 27 | import org.apache.geode.cache.execute.FunctionService; 28 | import org.apache.geode.cache.execute.ResultCollector; 29 | 30 | /** 31 | * Invokes a registered function using GemFire's {@link FunctionService} 32 | * @author David Turanski 33 | * 34 | */ 35 | @Component 36 | public class CalculateTotalSalesForProductInvoker { 37 | @Resource(name="gemfirePool") 38 | private Pool pool; 39 | 40 | /** 41 | * Calculate total sales for the given product 42 | * @param productName the name of the product 43 | * @return 44 | */ 45 | public BigDecimal forProduct(String productName) { 46 | 47 | Execution functionExecution = FunctionService.onServer(pool) 48 | .withArgs(productName); 49 | 50 | ResultCollector results = functionExecution.execute("CalculateTotalSalesForProduct"); 51 | 52 | List list = (List)results.getResult(); 53 | 54 | return ((BigDecimal)list.get(0)); 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /basic/function/src/main/java/org/springframework/data/gemfire/examples/Client.java: -------------------------------------------------------------------------------- 1 | package org.springframework.data.gemfire.examples; 2 | /* 3 | * Copyright 2012 the original author or authors. 4 | * 5 | * Licensed under the Apache License, Version 2.0 (the "License"); 6 | * you may not use this file except in compliance with the License. 7 | * You may obtain a copy of the License at 8 | * 9 | * https://www.apache.org/licenses/LICENSE-2.0 10 | * 11 | * Unless required by applicable law or agreed to in writing, software 12 | * distributed under the License is distributed on an "AS IS" BASIS, 13 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 | * See the License for the specific language governing permissions and 15 | * limitations under the License. 16 | */ 17 | 18 | 19 | import java.io.IOException; 20 | import java.math.BigDecimal; 21 | 22 | import org.apache.commons.logging.Log; 23 | import org.apache.commons.logging.LogFactory; 24 | import org.springframework.context.ApplicationContext; 25 | import org.springframework.context.support.ClassPathXmlApplicationContext; 26 | 27 | public class Client { 28 | 29 | public static void main(String args[]) throws IOException { 30 | Log log = LogFactory.getLog(Client.class); 31 | ApplicationContext context = new ClassPathXmlApplicationContext("client/cache-config.xml"); 32 | 33 | CalculateTotalSalesForProductInvoker calculateTotalForProduct = context.getBean(CalculateTotalSalesForProductInvoker.class); 34 | 35 | String[] products = new String[]{"Apple iPad","Apple iPod","Apple macBook"}; 36 | 37 | for (String productName: products){ 38 | BigDecimal total = calculateTotalForProduct.forProduct(productName); 39 | log.info("total sales for " + productName + " = $" + total); 40 | } 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /basic/function/src/main/java/org/springframework/data/gemfire/examples/Server.java: -------------------------------------------------------------------------------- 1 | package org.springframework.data.gemfire.examples; 2 | /* 3 | * Copyright 2012 the original author or authors. 4 | * 5 | * Licensed under the Apache License, Version 2.0 (the "License"); 6 | * you may not use this file except in compliance with the License. 7 | * You may obtain a copy of the License at 8 | * 9 | * https://www.apache.org/licenses/LICENSE-2.0 10 | * 11 | * Unless required by applicable law or agreed to in writing, software 12 | * distributed under the License is distributed on an "AS IS" BASIS, 13 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 | * See the License for the specific language governing permissions and 15 | * limitations under the License. 16 | */ 17 | 18 | 19 | import java.io.IOException; 20 | import java.math.BigDecimal; 21 | import java.net.ServerSocket; 22 | import java.util.Date; 23 | import java.util.Random; 24 | 25 | import org.apache.commons.logging.Log; 26 | import org.apache.commons.logging.LogFactory; 27 | import org.springframework.context.ApplicationContext; 28 | import org.springframework.context.support.ClassPathXmlApplicationContext; 29 | import org.springframework.data.gemfire.examples.domain.Address; 30 | import org.springframework.data.gemfire.examples.domain.LineItem; 31 | import org.springframework.data.gemfire.examples.domain.Order; 32 | import org.springframework.data.gemfire.examples.domain.Product; 33 | import org.springframework.data.gemfire.examples.util.ServerPortGenerator; 34 | 35 | import org.apache.geode.cache.Region; 36 | 37 | public class Server { 38 | private static Log log = LogFactory.getLog(Server.class); 39 | 40 | @SuppressWarnings("unchecked") 41 | public static void main(String args[]) throws IOException { 42 | /* 43 | * Check if port is open. Currently the client pool is hard coded to look for a server on 40404, the default. If already taken, 44 | * this process will wait for a while so this forces an immediate exit if the port is in use. There are better ways to handle this 45 | * situation, but hey, this is sample code. 46 | */ 47 | try { 48 | new ServerPortGenerator().bind(new ServerSocket(), 40404,1); 49 | } catch (IOException e) { 50 | System.out.println("Sorry port 40404 is in use. Do you have another cache server process already running?"); 51 | System.exit(1); 52 | 53 | } 54 | 55 | ApplicationContext context = new ClassPathXmlApplicationContext("server/cache-config.xml"); 56 | 57 | Region productRegion = context.getBean("Product",Region.class); 58 | Region orderRegion = context.getBean("Order",Region.class); 59 | //create some products 60 | 61 | Product ipod = new Product(1L,"Apple iPod",new BigDecimal(99.99),"An Apple portable music player"); 62 | Product ipad = new Product(2L,"Apple iPad",new BigDecimal(499.99),"An Apple tablet device"); 63 | Product macbook = new Product(3L,"Apple macBook",new BigDecimal(899.99),"An Apple notebook computer"); 64 | macbook.setAttribute("warantee","included"); 65 | 66 | productRegion.put(ipad.getId(), ipad); 67 | productRegion.put(ipod.getId(), ipod); 68 | productRegion.put(macbook.getId(), macbook); 69 | 70 | 71 | //Write some random orders 72 | 73 | Random random = new Random(new Date().getTime()); 74 | Address address = new Address("it","doesnt","matter"); 75 | for (long orderId = 1; orderId <= 100; orderId ++) { 76 | 77 | Order order = new Order(orderId,0L,address); 78 | int nLineItems = random.nextInt(3) + 1; 79 | for (int i = 0; i to terminate the server"); 89 | System.in.read(); 90 | System.exit(0); 91 | } 92 | 93 | 94 | } 95 | -------------------------------------------------------------------------------- /basic/function/src/main/resources/client/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /basic/function/src/main/resources/server/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | warning 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | -------------------------------------------------------------------------------- /basic/java-config/README.md: -------------------------------------------------------------------------------- 1 | GemFire Configuration Using Spring Java-based Container Configuration 2 | ===================================================================== 3 | 4 | This example demonstrates how to configure a GemFire Server (data node) using _Spring's_ [Java-based Container Configuration](https://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#beans-java) 5 | along with _Spring Data GemFire's_ custom [GemFire FactoryBean components and classes](https://github.com/spring-projects/spring-data-gemfire/tree/master/src/main/java/org/springframework/data/gemfire). 6 | 7 | After reviewing this example, a developer should gain a general understanding of how to configure a single GemFire Server 8 | instance using _Spring's_ _Java-based Container Configuration_ with _Spring Data GemFire's_ API. The `@Configuration` class 9 | declares bean definitions for the GemFire Cache and creates a PARTITION Region with basic configuration, such as Eviction 10 | and entry TTI (Idle-Timeout) as well as TTL (Time-To-Live), along with PARTITION attributes for setting the 11 | local and total max memory used by the Region in addition to setting its level of redundancy. 12 | 13 | The example primarily consists of a _Spring_ Java-based Container Configuration class, [SpringJavaBasedContainerGemFireConfiguration](https://github.com/spring-projects/spring-gemfire-examples/blob/master/basic/java-config/src/main/java/org/springframework/data/gemfire/example/SpringJavaBasedContainerGemFireConfiguration.java) 14 | and a corresponding test suite class, [SpringJavaBasedContainerGemFireConfigurationTest](https://github.com/spring-projects/spring-gemfire-examples/blob/master/basic/java-config/src/test/java/org/springframework/data/gemfire/example/SpringJavaBasedContainerGemFireConfigurationTest.java) 15 | to verify the proper configuration of the GemFire Server with JavaConfig. 16 | 17 | To run this example, execute the following... 18 | 19 | $gradlew :basic:java-config:test 20 | 21 | You can then open the test report file to review the results... 22 | 23 | file:////spring-gemfire-examples/basic/java-config/build/reports/tests/packages/org.springframework.data.gemfire.example.html 24 | 25 | Make sure to substitute "" with the absolute file system path of your cloned copy of the *spring-gemfire-examples* project. 26 | -------------------------------------------------------------------------------- /basic/partitioned/README.md: -------------------------------------------------------------------------------- 1 | Partitioned Region Example 2 | ========================== 3 | 4 | This demonstrates using Spring Data GemFire to create a partitioned region. The demonstration contains a Client and a Server. The partitioned region will cause entries to be distributed among the active servers. This demonstration is designed for two server instances. 5 | 6 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 7 | 8 | ./gradlew -q run-partitioned -Pmain=Server 9 | 10 | Open a second command window and repeat the above command 11 | 12 | When both servers are running, open a third window, and type: 13 | ./gradlew -q run-partitioned -Pmain=Client 14 | 15 | Or to run from your IDE, execute one of the following tasks once. 16 | 17 | ./gradlew eclipse 18 | ./gradlew idea 19 | 20 | Then import the project into your IDE and run the above classes 21 | 22 | # Details 23 | 24 | When the Client runs, it will create 100 Orders. These will be evenly distributed across the two servers as indicated by the log messages. Notice the key values for each entry show a more or less random pattern. 25 | 26 | # Custom Partitioning 27 | 28 | The example also demonstrates the use of a custom PartitionResolver that allows the application to control how entries are co-located. In this example, the order shipping address is either in the US or the UK. To enable partitioning by country, an alternate implementation of the key class (OrderKey) that implements PartitionResolver replaces the normal key class. 29 | 30 | Run the the client again, adding an argument: 31 | 32 | ./gradlew -q run-partitioned -Pmain=Client -Pargs=partitionByCountry 33 | 34 | This time, observe that the server console log indicates orders are partitioned by country. 35 | -------------------------------------------------------------------------------- /basic/partitioned/src/main/java/org/springframework/data/gemfire/examples/Client.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.io.IOException; 19 | import java.util.Date; 20 | import java.util.Random; 21 | 22 | import org.apache.commons.logging.Log; 23 | import org.apache.commons.logging.LogFactory; 24 | import org.springframework.context.ApplicationContext; 25 | import org.springframework.context.support.ClassPathXmlApplicationContext; 26 | import org.springframework.data.gemfire.examples.domain.Address; 27 | import org.springframework.data.gemfire.examples.domain.Order; 28 | 29 | import org.apache.geode.cache.Region; 30 | 31 | public class Client { 32 | private static Log log = LogFactory.getLog(Client.class); 33 | private static boolean partitionByCountry; 34 | @SuppressWarnings("unchecked") 35 | 36 | public static void main(String args[]) throws IOException { 37 | if (args.length >= 1 && args[0].equalsIgnoreCase("partitionByCountry")) { 38 | log.debug("partitioning by country"); 39 | partitionByCountry = true; 40 | } 41 | 42 | @SuppressWarnings("resource") 43 | ApplicationContext context = new ClassPathXmlApplicationContext("client/cache-config.xml"); 44 | Region region = context.getBean(Region.class); 45 | 46 | //Create some orders 47 | Random rand = new Random(new Date().getTime()); 48 | for (long orderId = 1; orderId <= 100; orderId++) { 49 | Address shipTo = new Address("Some Street","Some City",(orderId%3 == 0)?"UK":"US"); 50 | Order order = new Order(orderId, (new Long(rand.nextInt(100)+1)),shipTo); 51 | OrderKey orderKey = getOrderKey(orderId,shipTo.getCountry()); 52 | region.put(orderKey, order); 53 | } 54 | } 55 | 56 | private static OrderKey getOrderKey(Long id, String countryCode) { 57 | if (partitionByCountry) { 58 | return new PartitionedOrderKey(id, countryCode); 59 | } 60 | return new OrderKey(id, countryCode); 61 | } 62 | } 63 | -------------------------------------------------------------------------------- /basic/partitioned/src/main/java/org/springframework/data/gemfire/examples/OrderKey.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2002-2013 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with 5 | * the License. You may obtain a copy of the License at 6 | * 7 | * https://www.apache.org/licenses/LICENSE-2.0 8 | * 9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on 10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the 11 | * specific language governing permissions and limitations under the License. 12 | */ 13 | package org.springframework.data.gemfire.examples; 14 | 15 | import java.io.Serializable; 16 | 17 | /** 18 | * @author David Turanski 19 | * 20 | */ 21 | @SuppressWarnings("serial") 22 | public class OrderKey implements Serializable { 23 | final String countryCode; 24 | final Long id; 25 | 26 | public OrderKey(Long id, String countryCode) { 27 | this.id = id; 28 | this.countryCode = countryCode; 29 | } 30 | 31 | public int hashCode() { 32 | return id.hashCode(); 33 | } 34 | 35 | public boolean equals(Object other) { 36 | if (!(other instanceof OrderKey)) { 37 | return false; 38 | } 39 | return ((OrderKey)other).id.equals(this.id); 40 | } 41 | 42 | public String toString() { 43 | return id + ":" + countryCode; 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /basic/partitioned/src/main/java/org/springframework/data/gemfire/examples/PartitionedOrderKey.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2002-2013 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with 5 | * the License. You may obtain a copy of the License at 6 | * 7 | * https://www.apache.org/licenses/LICENSE-2.0 8 | * 9 | * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on 10 | * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the 11 | * specific language governing permissions and limitations under the License. 12 | */ 13 | package org.springframework.data.gemfire.examples; 14 | 15 | import org.apache.geode.cache.EntryOperation; 16 | import org.apache.geode.cache.PartitionResolver; 17 | 18 | /** 19 | * @author David Turanski 20 | * 21 | */ 22 | @SuppressWarnings({ "rawtypes", "serial" }) 23 | public class PartitionedOrderKey extends OrderKey implements PartitionResolver { 24 | 25 | 26 | public PartitionedOrderKey(Long id, String countryCode) { 27 | super(id,countryCode); 28 | } 29 | @Override 30 | public void close() { 31 | } 32 | 33 | /* (non-Javadoc) 34 | * @see org.apache.geode.cache.PartitionResolver#getName() 35 | */ 36 | @Override 37 | public String getName() { 38 | return this.getClass().getName(); 39 | } 40 | 41 | /* (non-Javadoc) 42 | * @see org.apache.geode.cache.PartitionResolver#getRoutingObject(org.apache.geode.cache.EntryOperation) 43 | */ 44 | @Override 45 | public Object getRoutingObject(EntryOperation op) { 46 | return this.countryCode; 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /basic/partitioned/src/main/java/org/springframework/data/gemfire/examples/Server.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples; 18 | 19 | import java.io.IOException; 20 | 21 | import org.springframework.context.ApplicationContext; 22 | import org.springframework.context.support.ClassPathXmlApplicationContext; 23 | 24 | import org.apache.commons.logging.Log; 25 | import org.apache.commons.logging.LogFactory; 26 | import org.apache.geode.cache.server.CacheServer; 27 | 28 | public class Server { 29 | 30 | private static Log log = LogFactory.getLog(Server.class); 31 | 32 | public static void main(String args[]) throws IOException { 33 | 34 | ApplicationContext context = new ClassPathXmlApplicationContext("server/cache-config.xml"); 35 | 36 | CacheServer server = context.getBean(CacheServer.class); 37 | 38 | System.out.println("server running on port " + server.getPort()); 39 | System.out.println("Press to terminate the server"); 40 | System.in.read(); 41 | 42 | System.exit(0); 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /basic/partitioned/src/main/resources/client/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | config 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /basic/partitioned/src/main/resources/server/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | config 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /basic/persistence/README.md: -------------------------------------------------------------------------------- 1 | Persistent Regions Example 2 | ========================== 3 | 4 | This demonstrates using Spring Data GemFire to create persistent regions. Persistent regions back up entries to disk and are initialized with persistent data. Initially there is no data stored on disk. After running the application once, it will create some data which GemFire will persist in its disk stores. Each time you run the application you will be prompted to delete the disk stores or not. If you do not delete the disk files, the last created entries will still be available. 5 | 6 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 7 | 8 | ./gradlew -q run-persistence 9 | 10 | Or to run from your IDE, execute one of the following tasks once. 11 | 12 | ./gradlew eclipse 13 | ./gradlew idea 14 | 15 | Then import the project into your IDE and run Main.java 16 | 17 | # Details 18 | The cache-config.xml configures two persistent regions, one for Products and one for Orders. Order is configured for disk overflow with a maximum number of entries held in memory. Accessing this data is transparent to the application. Evicted entries are restored from disk when accessed via the Region apis. 19 | -------------------------------------------------------------------------------- /basic/persistence/src/main/resources/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | warning 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | -------------------------------------------------------------------------------- /basic/replicated-cs/README.md: -------------------------------------------------------------------------------- 1 | Replicated Region (Client Server) Example 2 | ========================================== 3 | 4 | This demonstrates using Spring Data GemFire to create a replicated region. The demonstration contains a Client and a Server that hosts a replicated region. 5 | 6 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 7 | 8 | ./gradlew -q run-replicate-cs -Pmain=Server 9 | 10 | Open a second command window, and type: 11 | 12 | ./gradlew -q run-replicate-cs -Pmain=Client 13 | 14 | Or to run from your IDE, execute one of the following tasks once. 15 | 16 | ./gradlew eclipse 17 | ./gradlew idea 18 | 19 | Then import the project into your IDE and run the above. 20 | 21 | # Details 22 | The Spring configuration files, client/cache-config.xml and server/cache-config.xml contain the respective configurations. The client is configured with a client region to access the same region hosted on the server. 23 | -------------------------------------------------------------------------------- /basic/replicated-cs/src/main/java/org/springframework/data/gemfire/examples/Client.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples; 18 | 19 | import java.io.IOException; 20 | 21 | import org.springframework.context.ApplicationContext; 22 | import org.springframework.context.support.ClassPathXmlApplicationContext; 23 | import org.springframework.data.gemfire.examples.domain.Customer; 24 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 25 | 26 | import org.apache.geode.cache.Region; 27 | 28 | public class Client { 29 | 30 | @SuppressWarnings("unchecked") 31 | public static void main(String args[]) throws IOException { 32 | 33 | ApplicationContext context = new ClassPathXmlApplicationContext("client/cache-config.xml"); 34 | 35 | Region region = context.getBean(Region.class); 36 | 37 | Customer dave = new Customer(1L, new EmailAddress("dave@matthews.com"), "Dave", "Matthews"); 38 | Customer alicia = new Customer(2L, new EmailAddress("alicia@keys.com"), "Alicia", "Keys"); 39 | 40 | region.put(dave.getId(), dave); 41 | region.put(alicia.getId(), alicia); 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /basic/replicated-cs/src/main/java/org/springframework/data/gemfire/examples/Server.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.io.IOException; 19 | import java.net.ServerSocket; 20 | 21 | import org.springframework.context.support.ClassPathXmlApplicationContext; 22 | import org.springframework.data.gemfire.examples.util.ServerPortGenerator; 23 | 24 | public class Server { 25 | public static void main(String args[]) throws IOException { 26 | 27 | /* 28 | * Check if port is open. Currently the client pool is hard coded to look for a server on 40404, the default. If already taken, 29 | * this process will wait for a while so this forces an immediate exit if the port is in use. There are better ways to handle this 30 | * situation, but hey, this is sample code. 31 | */ 32 | try { 33 | new ServerPortGenerator().bind(new ServerSocket(), 40404,1); 34 | } catch (IOException e) { 35 | System.out.println("Sorry port 40404 is in use. Do you have another cache server process already running?"); 36 | System.exit(1); 37 | 38 | } 39 | 40 | new ClassPathXmlApplicationContext("server/cache-config.xml"); 41 | 42 | System.out.println("Press to terminate the server"); 43 | System.in.read(); 44 | System.exit(0); 45 | } 46 | 47 | 48 | } 49 | -------------------------------------------------------------------------------- /basic/replicated-cs/src/main/resources/client/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /basic/replicated-cs/src/main/resources/server/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | warning 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /basic/replicated/README.md: -------------------------------------------------------------------------------- 1 | Replicated Region Example 2 | ========================== 3 | 4 | This demonstrates using Spring Data GemFire to create a replicated region. The demonstration contains a Producer and a Consumer that share a replicated region. 5 | 6 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 7 | 8 | ./gradlew -q run-replicate -Pmain=Consumer 9 | 10 | When instructed, open a second command window, and type: 11 | 12 | ./gradlew -q run-replicate -Pmain=Producer 13 | 14 | Or to run from your IDE, execute one of the following tasks once. 15 | 16 | ./gradlew eclipse 17 | ./gradlew idea 18 | 19 | Then import the project into your IDE and run the above classes 20 | 21 | # Details 22 | The Spring configuration files, consumer/cache-config.xml and producer/cache-config.xml are nearly identical. The main difference is that the Producer version has data-policy="empty" in the replicated-region configuration. This means that The Producer does not cache data but uses the region to write data which wil be shared with peers (Consumer in this case). The Consumer caches the data in its replica and may also create or update data but these changes won't be seen by the Producer. 23 | -------------------------------------------------------------------------------- /basic/replicated/src/main/java/org/springframework/data/gemfire/examples/Consumer.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples; 18 | 19 | import java.io.IOException; 20 | 21 | import org.springframework.context.ApplicationContext; 22 | import org.springframework.context.support.ClassPathXmlApplicationContext; 23 | import org.springframework.data.gemfire.examples.domain.Address; 24 | import org.springframework.data.gemfire.examples.domain.Customer; 25 | 26 | import org.apache.commons.logging.Log; 27 | import org.apache.commons.logging.LogFactory; 28 | import org.apache.geode.cache.Region; 29 | 30 | public class Consumer { 31 | 32 | private static Log log = LogFactory.getLog(Consumer.class); 33 | 34 | @SuppressWarnings("unchecked") 35 | public static void main(String args[]) throws IOException { 36 | 37 | ApplicationContext context = new ClassPathXmlApplicationContext("consumer/cache-config.xml"); 38 | Region region = context.getBean(Region.class); 39 | 40 | System.out.println("Please Start the Producer. Then press "); 41 | System.in.read(); 42 | 43 | Customer dave = region.get(1L); 44 | if (dave != null) { 45 | log.debug("retrieved " + dave.getFirstname() + " " + dave.getLastname()); 46 | } 47 | 48 | Customer alicia = region.get(2L); 49 | if (alicia !=null) { 50 | log.debug("retrieved " + alicia.getFirstname() + " " + alicia.getLastname()); 51 | alicia.add(new Address("Keys Street","Alicia","UK")); 52 | region.put(alicia.getId(), alicia); 53 | } 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /basic/replicated/src/main/java/org/springframework/data/gemfire/examples/Producer.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples; 18 | 19 | import java.io.IOException; 20 | 21 | import org.springframework.context.ApplicationContext; 22 | import org.springframework.context.support.ClassPathXmlApplicationContext; 23 | import org.springframework.data.gemfire.examples.domain.Customer; 24 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 25 | 26 | import org.apache.geode.cache.Region; 27 | 28 | public class Producer { 29 | 30 | @SuppressWarnings("unchecked") 31 | public static void main(String args[]) throws IOException { 32 | 33 | ApplicationContext context = new ClassPathXmlApplicationContext("producer/cache-config.xml"); 34 | 35 | Region region = context.getBean(Region.class); 36 | 37 | Customer dave = new Customer(1L,new EmailAddress("dave@matthews.com"),"Dave","Matthews"); 38 | Customer alicia = new Customer(2L,new EmailAddress("alicia@keys.com"),"Alicia","Keys"); 39 | 40 | region.put(dave.getId(),dave); 41 | region.put(alicia.getId(),alicia); 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /basic/replicated/src/main/resources/consumer/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | config 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /basic/replicated/src/main/resources/producer/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | config 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /basic/write-through/README.md: -------------------------------------------------------------------------------- 1 | Write Through Example 2 | ========================== 3 | 4 | This demonstrates using Spring Data GemFire to create a CacheLoader and CacheWriter to synchronize data with a relational database. Database synchronization 5 | may be done synchronously (write-through) or asynchronously (write-behind). 6 | 7 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 8 | 9 | ./gradlew -q run-write-through 10 | 11 | To demonstrate write-behind, pass an 'async' argument to the command line: 12 | 13 | ./gradlew -q run-write-through -Pargs=async 14 | 15 | Or to run from your IDE, execute one of the following tasks once. 16 | 17 | ./gradlew eclipse 18 | ./gradlew idea 19 | 20 | Then import the project into your IDE and run Main.java 21 | 22 | # Details 23 | The cache-config.xml configures A Product region with a CacheLoader (ProductDBLoader.java) and CacheWriter (ProductDBWriter.java). An embedded H2 database is initialized with a corresponding Product table with 3 rows. The example accesses this data using via the cache and the entries are lazily loaded from the database. Any updates are written to the database. 24 | 25 | A Spring Data JPA Repository is used to access the database. The 'async' command line argument enables the 'async' Spring profile which enables the asynchronous behavior in ProductDBWriter. You can verify this by the thread names shown in the log messages (e.g. 'main' and 'SimpleAsyncTaskExecutor-#'). 26 | -------------------------------------------------------------------------------- /basic/write-through/src/main/java/org/springframework/data/gemfire/examples/Main.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples; 18 | 19 | import java.math.BigDecimal; 20 | 21 | import org.springframework.context.ApplicationContext; 22 | import org.springframework.context.support.ClassPathXmlApplicationContext; 23 | import org.springframework.data.gemfire.examples.domain.Product; 24 | import org.springframework.data.gemfire.examples.repository.ProductRepository; 25 | 26 | import org.apache.commons.logging.Log; 27 | import org.apache.commons.logging.LogFactory; 28 | import org.apache.geode.cache.Region; 29 | 30 | /** 31 | * @author David Turanski 32 | * 33 | */ 34 | public class Main { 35 | 36 | private static Log log = LogFactory.getLog(Main.class); 37 | 38 | @SuppressWarnings("unchecked") 39 | public static void main(String[] args) throws InterruptedException { 40 | 41 | if (args.length >= 1) { 42 | log.debug("Setting the spring profile to " + args[0]); 43 | System.setProperty("spring.profiles.active", args[0]); 44 | } 45 | 46 | ApplicationContext context = new ClassPathXmlApplicationContext( 47 | "app-context.xml"); 48 | 49 | Region region = context.getBean(Region.class); 50 | ProductRepository productRepository = context.getBean(ProductRepository.class); 51 | 52 | for (long i = 1; i<=3; i++){ 53 | Product p = region.get(i); 54 | log.debug("Retrieved product " + p.getName() + " from cache"); 55 | } 56 | 57 | //Let's try this again 58 | 59 | log.debug("2nd pass...This time the CacheLoader is not called since items are already cached"); 60 | for (long i = 1; i<=3; i++){ 61 | Product p = region.get(i); 62 | log.debug("Retrieved product " + p.getName() + " from cache"); 63 | } 64 | 65 | //Create a new product 66 | log.debug("Adding a new product to the cache..."); 67 | 68 | Product iphone = new Product(4L, "Apple IPhone", new BigDecimal(299.99),"Smart phone"); 69 | region.put(iphone.getId(), iphone); 70 | 71 | while (productRepository.count() == 3) { 72 | log.debug("Product repository still has : " + productRepository.count() + " rows"); 73 | Thread.sleep(10); 74 | } 75 | log.debug("Product repository now has : " + productRepository.count() + " rows"); 76 | 77 | log.debug("Removing a product from the cache..."); 78 | region.destroy(4L); 79 | 80 | while (productRepository.count() == 4) { 81 | log.debug("Product repository still has : " + productRepository.count() + " rows"); 82 | Thread.sleep(10); 83 | } 84 | log.debug("Product repository now has : " + productRepository.count() + " rows"); 85 | } 86 | } 87 | -------------------------------------------------------------------------------- /basic/write-through/src/main/java/org/springframework/data/gemfire/examples/ProductDBLoader.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples; 18 | 19 | import org.springframework.beans.factory.annotation.Autowired; 20 | import org.springframework.data.gemfire.examples.domain.Product; 21 | import org.springframework.data.gemfire.examples.repository.ProductRepository; 22 | import org.springframework.stereotype.Component; 23 | 24 | import org.apache.commons.logging.Log; 25 | import org.apache.commons.logging.LogFactory; 26 | import org.apache.geode.cache.CacheLoader; 27 | import org.apache.geode.cache.CacheLoaderException; 28 | import org.apache.geode.cache.LoaderHelper; 29 | 30 | /** 31 | * A cache loader that loads Product entries from a backing store using a Spring Data Repository 32 | * 33 | * @author David Turanski 34 | */ 35 | @Component 36 | public class ProductDBLoader implements CacheLoader { 37 | 38 | @Autowired 39 | private ProductRepository productRepository; 40 | 41 | private static Log log = LogFactory.getLog(ProductDBLoader.class); 42 | 43 | /* (non-Javadoc) 44 | * @see org.apache.geode.cache.CacheCallback#close() 45 | */ 46 | @Override 47 | public void close() { 48 | // TODO Auto-generated method stub 49 | 50 | } 51 | 52 | /* (non-Javadoc) 53 | * @see org.apache.geode.cache.CacheLoader#load(org.apache.geode.cache.LoaderHelper) 54 | */ 55 | @Override 56 | public Product load(LoaderHelper loadHelper) throws CacheLoaderException { 57 | Long id = Long.parseLong(String.valueOf(loadHelper.getKey())); 58 | log.debug("loading product id " + id + " from the database"); 59 | return productRepository.findById(id).orElse(null); 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /basic/write-through/src/main/java/org/springframework/data/gemfire/examples/repository/ProductRepository.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples.repository; 17 | 18 | import org.springframework.data.gemfire.examples.domain.Product; 19 | import org.springframework.data.repository.CrudRepository; 20 | 21 | /** 22 | * A Product Repository to perform simple CRUD operations 23 | * 24 | * @author David Turanski 25 | * 26 | */ 27 | public interface ProductRepository extends CrudRepository { 28 | 29 | } 30 | -------------------------------------------------------------------------------- /basic/write-through/src/main/resources/app-context.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /basic/write-through/src/main/resources/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | warning 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /basic/write-through/src/main/resources/db-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /basic/write-through/src/main/resources/db/schema.sql: -------------------------------------------------------------------------------- 1 | CREATE TABLE Product ( 2 | id NUMBER(11,0) PRIMARY KEY, 3 | name VARCHAR(50) NOT NULL, 4 | price NUMBER(7,2) NOT NULL, 5 | description VARCHAR(120) NULL 6 | ); -------------------------------------------------------------------------------- /basic/write-through/src/main/resources/db/test-data.sql: -------------------------------------------------------------------------------- 1 | INSERT INTO PRODUCT (id, name, price,description) VALUES (1, 'iPod', 99.99,'a portable media player'); 2 | INSERT INTO PRODUCT (id, name, price,description) VALUES (2, 'iPad', 699.99,'a tablet computer'); 3 | INSERT INTO PRODUCT (id, name, price,description) VALUES (3, 'macBook', 999.99,'a notebook computer'); -------------------------------------------------------------------------------- /gradle.properties: -------------------------------------------------------------------------------- 1 | assertjVersion = 3.6.2 2 | junitVersion = 4.12 3 | log4jVersion = 1.2.17 4 | lombokVersion = 1.16.18 5 | mockitoVersion = 2.8.47 6 | slf4jVersion = 1.7.10 7 | springVersion = 5.0.0.RC3 8 | springBootVersion = 2.0.0.M3 9 | springShellVersion = 1.2.0.RELEASE 10 | version = 2.0.0.RC2 11 | -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/spring-attic/spring-gemfire-examples/25fb505b078293cd7751144587b5e1490c582fa6/gradle/wrapper/gradle-wrapper.jar -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.properties: -------------------------------------------------------------------------------- 1 | #Wed Aug 16 21:12:23 PDT 2017 2 | distributionBase=GRADLE_USER_HOME 3 | distributionPath=wrapper/dists 4 | zipStoreBase=GRADLE_USER_HOME 5 | zipStorePath=wrapper/dists 6 | distributionUrl=https\://services.gradle.org/distributions/gradle-3.5-all.zip 7 | -------------------------------------------------------------------------------- /gradlew.bat: -------------------------------------------------------------------------------- 1 | @if "%DEBUG%" == "" @echo off 2 | @rem ########################################################################## 3 | @rem 4 | @rem Gradle startup script for Windows 5 | @rem 6 | @rem ########################################################################## 7 | 8 | @rem Set local scope for the variables with windows NT shell 9 | if "%OS%"=="Windows_NT" setlocal 10 | 11 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. 12 | set DEFAULT_JVM_OPTS= 13 | 14 | set DIRNAME=%~dp0 15 | if "%DIRNAME%" == "" set DIRNAME=. 16 | set APP_BASE_NAME=%~n0 17 | set APP_HOME=%DIRNAME% 18 | 19 | @rem Find java.exe 20 | if defined JAVA_HOME goto findJavaFromJavaHome 21 | 22 | set JAVA_EXE=java.exe 23 | %JAVA_EXE% -version >NUL 2>&1 24 | if "%ERRORLEVEL%" == "0" goto init 25 | 26 | echo. 27 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 28 | echo. 29 | echo Please set the JAVA_HOME variable in your environment to match the 30 | echo location of your Java installation. 31 | 32 | goto fail 33 | 34 | :findJavaFromJavaHome 35 | set JAVA_HOME=%JAVA_HOME:"=% 36 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe 37 | 38 | if exist "%JAVA_EXE%" goto init 39 | 40 | echo. 41 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% 42 | echo. 43 | echo Please set the JAVA_HOME variable in your environment to match the 44 | echo location of your Java installation. 45 | 46 | goto fail 47 | 48 | :init 49 | @rem Get command-line arguments, handling Windowz variants 50 | 51 | if not "%OS%" == "Windows_NT" goto win9xME_args 52 | if "%@eval[2+2]" == "4" goto 4NT_args 53 | 54 | :win9xME_args 55 | @rem Slurp the command line arguments. 56 | set CMD_LINE_ARGS= 57 | set _SKIP=2 58 | 59 | :win9xME_args_slurp 60 | if "x%~1" == "x" goto execute 61 | 62 | set CMD_LINE_ARGS=%* 63 | goto execute 64 | 65 | :4NT_args 66 | @rem Get arguments from the 4NT Shell from JP Software 67 | set CMD_LINE_ARGS=%$ 68 | 69 | :execute 70 | @rem Setup the command line 71 | 72 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar 73 | 74 | @rem Execute Gradle 75 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS% 76 | 77 | :end 78 | @rem End local scope for the variables with windows NT shell 79 | if "%ERRORLEVEL%"=="0" goto mainEnd 80 | 81 | :fail 82 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of 83 | rem the _cmd.exe /c_ return code! 84 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 85 | exit /b 1 86 | 87 | :mainEnd 88 | if "%OS%"=="Windows_NT" endlocal 89 | 90 | :omega 91 | -------------------------------------------------------------------------------- /quickstart/README.md: -------------------------------------------------------------------------------- 1 | Quick Start Examples 2 | ==================== 3 | The examples in this section focus on developing Java applications with Spring Data GemFire. 4 | They demonstrate aspects of the Spring programming model using very basic cache configurations. 5 | 6 | -------------------------------------------------------------------------------- /quickstart/build.gradle: -------------------------------------------------------------------------------- 1 | description = 'Spring Data GemFire Quickstart Examples' 2 | 3 | project('spring-cache') { 4 | 5 | description = 'Spring Cache with GemFire Example' 6 | 7 | dependencies { 8 | compile project(':spring-gemfire-examples-common') 9 | } 10 | } 11 | 12 | project('repository') { 13 | 14 | description = 'Spring Data Gemfire Repository Example' 15 | 16 | dependencies { 17 | compile project(':spring-gemfire-examples-common') 18 | } 19 | } 20 | 21 | 22 | project('gemfire-template') { 23 | 24 | description = 'Spring Data Gemfire GemfireTemplate Example' 25 | 26 | dependencies { 27 | compile project(':spring-gemfire-examples-common') 28 | compile "org.springframework:spring-aop:$springVersion" 29 | compile "org.springframework:spring-context-support:$springVersion" 30 | compile "org.springframework:spring-tx:$springVersion" 31 | } 32 | } 33 | 34 | project('cq') { 35 | 36 | description = 'Spring Data GemFire Continuous Query Example' 37 | 38 | dependencies { 39 | compile project(':spring-gemfire-examples-common') 40 | compile "org.springframework:spring-aop:$springVersion" 41 | compile "org.springframework:spring-context-support:$springVersion" 42 | compile "org.springframework:spring-tx:$springVersion" 43 | } 44 | } 45 | 46 | project('transaction') { 47 | 48 | description = 'Spring Data GemFire Transaction Example' 49 | 50 | dependencies { 51 | compile project(':spring-gemfire-examples-common') 52 | compile "org.springframework:spring-aop:$springVersion" 53 | compile "org.springframework:spring-context-support:$springVersion" 54 | compile "org.springframework:spring-tx:$springVersion" 55 | } 56 | } 57 | 58 | project('json') { 59 | 60 | description = 'Spring Data GemFire JSON Example' 61 | 62 | dependencies { 63 | compile project(':spring-gemfire-examples-common') 64 | compile "org.springframework:spring-aop:$springVersion" 65 | compile "org.springframework:spring-context-support:$springVersion" 66 | compile "org.springframework:spring-tx:$springVersion" 67 | } 68 | } 69 | -------------------------------------------------------------------------------- /quickstart/cq/README.md: -------------------------------------------------------------------------------- 1 | Spring Continuous Query Example 2 | =============================== 3 | 4 | This example demonstrates how to process *Continuous Queries* (QQ) using _Spring Data GemFire's+_ 5 | `ContinuousQueryListenerContainer`. 6 | 7 | This example requires a GemFire client/server configuration. The `CacheServer` starts a cache server 8 | and updates the Region. The `CacheClient` configures a CQ Listener which handles CQ Events received. 9 | 10 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 11 | 12 | ./gradlew -q run-cq -Pmain=Server 13 | 14 | In another window, type: 15 | 16 | ./gradlew -q run-cq -Pmain=Client 17 | 18 | Or to run from your IDE, execute one of the following tasks once. 19 | 20 | ./gradlew eclipse 21 | ./gradlew idea 22 | 23 | Then import the project into your IDE and run the above classes. 24 | 25 | # Details 26 | 27 | Note that `ContinuousQueryListener` is a POJO (albeit dependent on the GemFire type `CQEvent`). It is not required 28 | to implement any specific interface, but it must provide appropriate method signatures so the `ConitnuousQueryListenerContainer` 29 | can delegate `CQEvents` to it. The `CacheClient's` Pool must be configured with `subscription-enabled='true'`. 30 | 31 | When the `CacheServer` starts, you will be prompted to update the cache. This will create three entries in the 'Order' Region. 32 | You must start the cache client before doing this since the client is not configured as a durable subscription. Upon updating 33 | the cache, the client should receive two order events matching the CQ criteria. 34 | -------------------------------------------------------------------------------- /quickstart/cq/src/main/java/org/springframework/data/gemfire/examples/CQListener.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.apache.commons.logging.Log; 19 | import org.apache.commons.logging.LogFactory; 20 | 21 | import org.apache.geode.cache.query.CqEvent; 22 | /** 23 | * A simple CQ listener 24 | * @author David Turanski 25 | * 26 | */ 27 | public class CQListener { 28 | 29 | private static Log log = LogFactory.getLog(CQListener.class); 30 | 31 | public void handleEvent(CqEvent event) { 32 | log.info("Received a CQ event " + event); 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /quickstart/cq/src/main/java/org/springframework/data/gemfire/examples/Client.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.io.IOException; 19 | 20 | import org.springframework.context.support.ClassPathXmlApplicationContext; 21 | 22 | /** 23 | * Creates a cache client 24 | * 25 | * @author David Turanski 26 | * 27 | */ 28 | public class Client { 29 | 30 | public static void main(String args[]) throws IOException { 31 | new ClassPathXmlApplicationContext("client/cache-config.xml"); 32 | System.out.println("Press to quit"); 33 | System.in.read(); 34 | System.exit(0); 35 | } 36 | 37 | } 38 | -------------------------------------------------------------------------------- /quickstart/cq/src/main/resources/client/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 20 | 21 | 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /quickstart/cq/src/main/resources/log4j.properties: -------------------------------------------------------------------------------- 1 | log4j.rootCategory=WARN, stdout 2 | 3 | log4j.appender.stdout=org.apache.log4j.ConsoleAppender 4 | log4j.appender.stdout.layout=org.apache.log4j.PatternLayout 5 | log4j.appender.stdout.layout.ConversionPattern=%p [%C{1}] - %m%n 6 | 7 | log4j.category.org.springframework.data.gemfire.examples=DEBUG 8 | -------------------------------------------------------------------------------- /quickstart/cq/src/main/resources/server/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 15 | 16 | 17 | 18 | 19 | 20 | warning 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | -------------------------------------------------------------------------------- /quickstart/gemfire-template/README.md: -------------------------------------------------------------------------------- 1 | Spring GemfireTemplate Example 2 | ============================== 3 | 4 | This demonstrates Spring Framework's GemfireTemplate to access the Gemfire cache. 5 | 6 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 7 | 8 | ./gradlew -q run-gemfire-template 9 | 10 | Or to run from your IDE, run the following command once for all projects. 11 | 12 | ./gradlew eclipse 13 | ./gradlew idea 14 | 15 | Then import the project into your IDE and run Main.java 16 | 17 | #Details 18 | 19 | This example demonstrates the use of GemfireTemplate to perform region data access. GemfireTemplate wraps the native 20 | GemFire Region and translates GemFire checked exceptions and native runtime exceptions to Spring's DataAccessException 21 | RuntimeException hierarchy. This plays well with Spring's [declarative transaction management] 22 | (https://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/spring-framework-reference.html#transaction). 23 | The CustomerService class includes a deleteCustomer(...) method which deletes a Customer from the Customer Region and also deletes any of that 24 | customer's orders from the Order region. This is an atomic unit of work, enclosed in a transaction by the 25 | [GemfireTransactionManager](https://docs.spring.io/spring-data/geode/docs/current/reference/html/#apis:transaction-management) 26 | using @Transactional. 27 | 28 | -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/java/org/springframework/data/gemfire/examples/CustomerDao.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.springframework.data.gemfire.examples.domain.Customer; 19 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 20 | 21 | /** 22 | * Interface for Customer data access 23 | * @author David Turanski 24 | * 25 | */ 26 | public interface CustomerDao { 27 | 28 | /** 29 | * Delete a customer by ID 30 | * @param id 31 | */ 32 | public abstract void delete(long id); 33 | 34 | /** 35 | * Save a customer 36 | * @param customer 37 | * @return 38 | */ 39 | public abstract Customer save(Customer customer); 40 | 41 | /** 42 | * Retrieve a customer by ID 43 | * @param id 44 | * @return 45 | */ 46 | public abstract Customer get(long id); 47 | 48 | /** 49 | * Find a Customer by email address 50 | * @param emailAddress 51 | * @return 52 | */ 53 | public abstract Customer findByEmailAddress(EmailAddress emailAddress); 54 | 55 | } -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/java/org/springframework/data/gemfire/examples/CustomerService.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.apache.commons.logging.Log; 19 | import org.apache.commons.logging.LogFactory; 20 | import org.springframework.beans.factory.annotation.Autowired; 21 | import org.springframework.data.gemfire.examples.domain.Customer; 22 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 23 | import org.springframework.data.gemfire.examples.domain.Order; 24 | import org.springframework.stereotype.Component; 25 | import org.springframework.transaction.annotation.Transactional; 26 | import org.springframework.util.Assert; 27 | 28 | /** 29 | * A simple Customer service implementation 30 | * @author David Turanski 31 | * 32 | */ 33 | @Component 34 | public class CustomerService { 35 | private static Log log = LogFactory.getLog(CustomerService.class); 36 | @Autowired 37 | CustomerDao customerDao; 38 | @Autowired 39 | OrderDao orderDao; 40 | 41 | /** 42 | * Delete Customer and any customer orders. This runs in a transaction 43 | * 44 | * @param customerId 45 | */ 46 | @Transactional("gemfireTransactionManager") 47 | public void deleteCustomer(long customerId) { 48 | log.debug("deleting customer ID " + customerId); 49 | customerDao.delete(customerId); 50 | for (Order order: orderDao.findCustomerOrders(customerId)) { 51 | orderDao.delete(order.getId()); 52 | } 53 | log.debug("deleted customer ID " + customerId); 54 | } 55 | 56 | /** 57 | * Create a customer 58 | * @param customer 59 | * @return 60 | */ 61 | public Customer createCustomer(Customer customer) { 62 | Assert.notNull(customer,"customer cannot be null"); 63 | Assert.notNull(customer.getId(), "customer ID cannot be null"); 64 | Assert.hasText(customer.getLastname(),"customer last name cannot be empty"); 65 | Assert.hasText(customer.getFirstname(),"customer first name cannot be empty"); 66 | Assert.notNull(customer.getEmailAddress(),"customer email address cannot be null"); 67 | 68 | log.debug("saving customer ID:" + customer.getId() + " " + customer.getFirstname() + " " + customer.getLastname()); 69 | 70 | return customerDao.save(customer); 71 | } 72 | 73 | /** 74 | * Find a customer by email address 75 | * @param emailAddress 76 | * @return 77 | */ 78 | public Customer findByEmailAddress(String emailAddress) { 79 | Assert.hasText(emailAddress,"email address cannot be null or blank"); 80 | return customerDao.findByEmailAddress(new EmailAddress(emailAddress)); 81 | } 82 | 83 | } 84 | -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/java/org/springframework/data/gemfire/examples/GemfireTemplateCustomerDao.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.springframework.beans.factory.annotation.Autowired; 19 | import org.springframework.data.gemfire.GemfireTemplate; 20 | import org.springframework.data.gemfire.examples.domain.Customer; 21 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 22 | import org.springframework.stereotype.Repository; 23 | 24 | import org.apache.geode.cache.query.SelectResults; 25 | 26 | /** 27 | * An Implementation of {@link CustomerDao} using {@link GemfireTemplate} 28 | * @author David Turanski 29 | * 30 | */ 31 | @Repository 32 | public class GemfireTemplateCustomerDao implements CustomerDao { 33 | @Autowired 34 | GemfireTemplate customerTemplate; 35 | 36 | /* (non-Javadoc) 37 | * @see org.springframework.data.gemfire.examples.CustomerDao#delete(long) 38 | */ 39 | @Override 40 | public void delete(long id) { 41 | customerTemplate.remove(id); 42 | } 43 | 44 | /* (non-Javadoc) 45 | * @see org.springframework.data.gemfire.examples.CustomerDao#save(org.springframework.data.gemfire.examples.domain.Customer) 46 | */ 47 | @Override 48 | public Customer save(Customer customer) { 49 | return customerTemplate.put(customer.getId(),customer); 50 | } 51 | 52 | @Override 53 | public Customer get(long id) { 54 | return customerTemplate.get(id); 55 | } 56 | 57 | @Override 58 | public Customer findByEmailAddress(EmailAddress emailAddress) { 59 | SelectResults customers = customerTemplate.find("SELECT * from /Customer WHERE emailAddress=$1",emailAddress); 60 | return customers.isEmpty()? null: customers.asList().get(0); 61 | } 62 | 63 | } 64 | -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/java/org/springframework/data/gemfire/examples/GemfireTemplateOrderDao.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.util.List; 19 | 20 | import org.springframework.beans.factory.annotation.Autowired; 21 | import org.springframework.data.gemfire.GemfireTemplate; 22 | import org.springframework.data.gemfire.examples.domain.Order; 23 | import org.springframework.stereotype.Repository; 24 | 25 | import org.apache.geode.cache.query.SelectResults; 26 | 27 | /** 28 | * An implementation of {@link OrderDao} using {@link GemfireTemplate} 29 | * @author David Turanski 30 | * 31 | */ 32 | @Repository 33 | public class GemfireTemplateOrderDao implements OrderDao { 34 | @Autowired 35 | GemfireTemplate orderTemplate; 36 | 37 | /* (non-Javadoc) 38 | * @see org.springframework.data.gemfire.examples.OrderDao#findCustomerOrders(long) 39 | */ 40 | @Override 41 | public List findCustomerOrders(long customerId) { 42 | SelectResults orders = orderTemplate.find("SELECT * from /Order WHERE customerId = $1", customerId); 43 | return (orders == null)?null : orders.asList(); 44 | } 45 | 46 | /* (non-Javadoc) 47 | * @see org.springframework.data.gemfire.examples.OrderDao#delete(long) 48 | */ 49 | @Override 50 | public void delete(long id) { 51 | orderTemplate.remove(id); 52 | } 53 | 54 | /* (non-Javadoc) 55 | * @see org.springframework.data.gemfire.examples.OrderDao#save(org.springframework.data.gemfire.examples.domain.Order) 56 | */ 57 | @Override 58 | public Order save(Order order) { 59 | return orderTemplate.put(order.getId(), order); 60 | } 61 | 62 | @Override 63 | public Order get(long id) { 64 | return orderTemplate.get(id); 65 | } 66 | } 67 | -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/java/org/springframework/data/gemfire/examples/Main.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.springframework.context.ApplicationContext; 19 | import org.springframework.context.support.ClassPathXmlApplicationContext; 20 | 21 | public class Main { 22 | 23 | public static void main(String args[]) { 24 | ApplicationContext context = new ClassPathXmlApplicationContext("app-context.xml"); 25 | OrderExample example = context.getBean(OrderExample.class); 26 | example.run(); 27 | } 28 | 29 | } 30 | -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/java/org/springframework/data/gemfire/examples/OrderDao.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.util.List; 19 | 20 | import org.springframework.data.gemfire.examples.domain.Order; 21 | /** 22 | * Interface for Order data access 23 | * @author David Turanski 24 | * 25 | */ 26 | public interface OrderDao { 27 | 28 | /** 29 | * find all orders for a customer 30 | * @param customerId 31 | * @return 32 | */ 33 | public abstract List findCustomerOrders(long customerId); 34 | 35 | /** 36 | * Delete an order 37 | * @param id 38 | */ 39 | public abstract void delete(long id); 40 | 41 | /** 42 | * Save an order 43 | * @param order 44 | * @return 45 | */ 46 | public abstract Order save(Order order); 47 | 48 | /** 49 | * Retrieve an order by ID 50 | * @param id 51 | * @return 52 | */ 53 | public abstract Order get(long id); 54 | 55 | } -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/java/org/springframework/data/gemfire/examples/OrderService.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.apache.commons.logging.Log; 19 | import org.apache.commons.logging.LogFactory; 20 | import org.springframework.beans.factory.annotation.Autowired; 21 | import org.springframework.data.gemfire.examples.domain.Order; 22 | import org.springframework.stereotype.Component; 23 | import org.springframework.util.Assert; 24 | 25 | /** 26 | * A simple Order service 27 | * @author David Turanski 28 | * 29 | */ 30 | @Component 31 | public class OrderService { 32 | private static Log log = LogFactory.getLog(OrderService.class); 33 | 34 | @Autowired OrderDao orderDao; 35 | 36 | /** 37 | * Create an order 38 | * @param order 39 | * @return 40 | */ 41 | public Order createOrder(Order order) { 42 | Assert.notNull(order, "order cannot be null"); 43 | Assert.notNull(order.getId(),"order id cannot be null"); 44 | Assert.notNull(order.getCustomerId(), "order customer ID cannot be null"); 45 | Assert.notEmpty(order.getLineItems(),"order must contain at least one line item"); 46 | 47 | log.debug("creating order ID:" + order.getId() ); 48 | return orderDao.save(order); 49 | 50 | } 51 | 52 | /** 53 | * Get an Order by ID 54 | * @param id 55 | * @return 56 | */ 57 | public Order getOrder(long id) { 58 | return orderDao.get(id); 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/resources/app-context.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/resources/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | warning 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /quickstart/gemfire-template/src/main/resources/log4j.properties: -------------------------------------------------------------------------------- 1 | log4j.rootCategory=WARN, stdout 2 | 3 | log4j.appender.stdout=org.apache.log4j.ConsoleAppender 4 | log4j.appender.stdout.layout=org.apache.log4j.PatternLayout 5 | log4j.appender.stdout.layout.ConversionPattern=%p [%C{1}] - %m%n 6 | 7 | log4j.category.org.springframework.data.gemfire=DEBUG 8 | -------------------------------------------------------------------------------- /quickstart/json/README.md: -------------------------------------------------------------------------------- 1 | Spring Data Gemfire JSON Example 2 | ================================ 3 | 4 | This demonstrates Spring Framework's GemfireTemplate to access the Gemfire cache with automatic JSON conversion. 5 | 6 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 7 | 8 | ./gradlew -q run-json 9 | 10 | Or to run from your IDE, run the following command once for all projects. 11 | 12 | ./gradlew eclipse 13 | ./gradlew idea 14 | 15 | Then import the project into your IDE and run Main.java 16 | 17 | #Details 18 | 19 | This simple example demonstrates the use of GemfireTemplate to perform region data access for data stored as JSON. Spring converts objects to GemFire's internal JSON representation before writing then to the cache. This feature is enabled in src/main/resources/cache-config with the following configuration: 20 | 21 | 22 | 23 | This enables Spring AOP to add advise around appropriate read and write operations on Region and GemfireTemplate to perform the necessary conversions. *Note that target regions and/or GemfireTemplates must be declared as Spring beans for this to work.* 24 | 25 | -------------------------------------------------------------------------------- /quickstart/json/src/main/java/org/springframework/data/gemfire/examples/JSONCustomerExample.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.apache.commons.logging.Log; 19 | import org.apache.commons.logging.LogFactory; 20 | import org.springframework.beans.factory.annotation.Autowired; 21 | import org.springframework.beans.factory.annotation.Qualifier; 22 | import org.springframework.data.gemfire.GemfireOperations; 23 | import org.springframework.data.gemfire.examples.domain.Customer; 24 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 25 | import org.springframework.stereotype.Component; 26 | 27 | import org.apache.geode.cache.query.SelectResults; 28 | /** 29 | * Sample application demonstrating JSON support 30 | * @author David Turanski 31 | * 32 | */ 33 | @Component 34 | public class JSONCustomerExample { 35 | private static Log log = LogFactory.getLog(JSONCustomerExample.class); 36 | @Autowired 37 | @Qualifier("customerTemplate") 38 | GemfireOperations customerTemplate; 39 | /** 40 | * run the example 41 | */ 42 | public void run() { 43 | createCustomers(); 44 | searchCustomers(); 45 | deleteCustomers(); 46 | } 47 | 48 | /* 49 | * create some customers 50 | */ 51 | private void createCustomers() { 52 | Customer dave = new Customer(1L,new EmailAddress("dave@matthews.com"),"Dave","Matthews"); 53 | Customer alicia = new Customer(2L,new EmailAddress("alicia@keys.com"),"Alicia","Keys"); 54 | customerTemplate.put(1L,dave); 55 | customerTemplate.put(2l, alicia); 56 | } 57 | 58 | /* 59 | * Retrieve customers 60 | */ 61 | private void searchCustomers() { 62 | String jSonDave = (String) customerTemplate.findUnique("select * from /Customer where emailAddress.value=$1","dave@matthews.com"); 63 | log.info(jSonDave); 64 | 65 | SelectResults results = customerTemplate.find("select * from /Customer where emailAddress.value=$1", "alicia@keys.com"); 66 | String jSonAlicia = results.iterator().next(); 67 | log.info(jSonAlicia); 68 | } 69 | 70 | /* 71 | * Delete customers 72 | */ 73 | private void deleteCustomers() { 74 | customerTemplate.remove(1L); 75 | customerTemplate.remove(2L); 76 | } 77 | } 78 | -------------------------------------------------------------------------------- /quickstart/json/src/main/java/org/springframework/data/gemfire/examples/Main.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.springframework.context.ApplicationContext; 19 | import org.springframework.context.support.ClassPathXmlApplicationContext; 20 | 21 | public class Main { 22 | 23 | public static void main(String args[]) { 24 | @SuppressWarnings("resource") 25 | ApplicationContext context = new ClassPathXmlApplicationContext("app-context.xml"); 26 | JSONCustomerExample example = context.getBean(JSONCustomerExample.class); 27 | example.run(); 28 | } 29 | 30 | } 31 | -------------------------------------------------------------------------------- /quickstart/json/src/main/resources/app-context.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /quickstart/json/src/main/resources/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 13 | 14 | 15 | warning 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /quickstart/json/src/main/resources/log4j.properties: -------------------------------------------------------------------------------- 1 | log4j.rootCategory=WARN, stdout 2 | 3 | log4j.appender.stdout=org.apache.log4j.ConsoleAppender 4 | log4j.appender.stdout.layout=org.apache.log4j.PatternLayout 5 | log4j.appender.stdout.layout.ConversionPattern=%p [%C{1}] - %m%n 6 | 7 | log4j.category.org.springframework.data.gemfire=DEBUG 8 | -------------------------------------------------------------------------------- /quickstart/repository/README.md: -------------------------------------------------------------------------------- 1 | Spring Data GemFire Repository Example 2 | ===================================== 3 | 4 | This example demonstrates how to use Spring Data Gemfire Repositories. The Spring configuration uses environment profiles to 5 | allow you to run this example with or without PDX serialization enabled. 6 | 7 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 8 | 9 | ./gradlew -q run-repository 10 | 11 | To run with PDX, supply a command line argument, which is done in ./gradlew as follows: 12 | 13 | ./gradlew -q run-repository -Pargs=pdx 14 | 15 | If pdx is enabled you will see some files created in the 'pdx' folder. 16 | 17 | Or to run from your IDE, run one of the following commands once. 18 | 19 | ./gradlew eclipse 20 | ./gradlew idea 21 | 22 | Then import the project into your IDE and run Main.java 23 | 24 | # Details 25 | 26 | The example application code is contained in OrderExample.java. This class depends on 3 service components, CustomerService, 27 | ProductService, and OrderService. Each of these is wired with the corresponding GemFire Repository associated to a domain object. 28 | (NOTE: The source code for the domain classes is found in the 'spring-gemfire-examples-common' project). 29 | 30 | For example, CustomerRepository is used to access instances of Customer. Customer is bound to a GemFire Region via the @Region 31 | annotation. By default the Region name is the same as the simple class name, but may be overridden in the annotation value. 32 | 33 | The Repositories are simply interface definitions. These are discovered using Spring Java config in this case, using the @EnableGemfireRepositories 34 | annotation. This can be found in the ApplicationConfig class. Note that even though the application uses Java config, it is still 35 | inherently simpler to use the Spring Data GemFire XML namespace to configure GemFire components. The XML location is also loaded by the configuration 36 | class. The Spring Data Repository framework creates proxies for each repository to implement the repository methods. 37 | 38 | NOTE: This example uses a very simple GemFire configuration appropriate for unit testing. Data is held in a local region, 39 | backed by a local cache and is not persisted. 40 | 41 | In practice, GemFire should be configured so that the Repository region is distributed and replicated across multiple nodes. Disk 42 | persistence is also available if needed. Refer to the GemFire [documentation] (https://www.vmware.com/support/pubs/vfabric-gemfire.html) 43 | for more information. Also see the [spring data] (https://www.springsource.org/spring-data) project page for further details about Spring Data. 44 | -------------------------------------------------------------------------------- /quickstart/repository/src/main/java/org/springframework/data/gemfire/examples/ApplicationConfig.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.springframework.context.annotation.Bean; 19 | import org.springframework.context.annotation.Configuration; 20 | import org.springframework.context.annotation.ImportResource; 21 | import org.springframework.data.gemfire.repository.config.EnableGemfireRepositories; 22 | 23 | /** 24 | * Spring JavaConfig configuration class to setup a Spring container and infrastructure components. 25 | * 26 | * @author Oliver Gierke 27 | * @author David Turanski 28 | */ 29 | @Configuration 30 | @ImportResource("classpath:cache-config.xml") 31 | @EnableGemfireRepositories 32 | public class ApplicationConfig { 33 | 34 | @Bean CustomerService customerService() { 35 | return new CustomerService(); 36 | } 37 | 38 | @Bean OrderService orderService() { 39 | return new OrderService(); 40 | } 41 | 42 | @Bean ProductService productService() { 43 | return new ProductService(); 44 | } 45 | 46 | @Bean OrderExample orderExample() { 47 | return new OrderExample(customerService(), productService(), orderService()); 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /quickstart/repository/src/main/java/org/springframework/data/gemfire/examples/Main.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.io.File; 19 | 20 | import org.apache.commons.logging.Log; 21 | import org.apache.commons.logging.LogFactory; 22 | import org.springframework.context.annotation.AnnotationConfigApplicationContext; 23 | 24 | public class Main { 25 | private static Log log = LogFactory.getLog(Main.class); 26 | private static boolean usePdx; 27 | public static void main(String args[]) { 28 | 29 | usePdx = args.length > 0 && args[0].toUpperCase().contains("PDX"); 30 | 31 | AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(); 32 | if (usePdx) { 33 | log.info("PDX is enabled"); 34 | File pdxDir = new File("pdx"); 35 | if (!pdxDir.exists()){ 36 | new File("pdx").mkdir(); 37 | } 38 | context.getEnvironment().setActiveProfiles("pdx"); 39 | } 40 | 41 | context.scan("org.springframework.data.gemfire.examples"); 42 | context.refresh(); 43 | 44 | OrderExample orderExample = context.getBean(OrderExample.class); 45 | orderExample.run(); 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /quickstart/repository/src/main/java/org/springframework/data/gemfire/examples/OrderService.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples; 18 | 19 | import java.util.ArrayList; 20 | import java.util.Collections; 21 | import java.util.List; 22 | 23 | import org.springframework.beans.factory.annotation.Autowired; 24 | import org.springframework.data.gemfire.examples.domain.Order; 25 | import org.springframework.data.gemfire.examples.repository.OrderRepository; 26 | import org.springframework.util.Assert; 27 | 28 | import org.apache.commons.logging.Log; 29 | import org.apache.commons.logging.LogFactory; 30 | 31 | 32 | /** 33 | * A simple Order service 34 | * 35 | * @author David Turanski 36 | */ 37 | public class OrderService { 38 | 39 | private static Log log = LogFactory.getLog(OrderService.class); 40 | 41 | @Autowired 42 | OrderRepository orderRepository; 43 | 44 | /** 45 | * Create an order 46 | */ 47 | public Order createOrder(Order order) { 48 | 49 | Assert.notNull(order, "order cannot be null"); 50 | Assert.notNull(order.getId(), "order ID cannot be null"); 51 | Assert.notNull(order.getCustomerId(), "order customer ID cannot be null"); 52 | Assert.notEmpty(order.getLineItems(), "order must contain at least one line item"); 53 | Assert.notNull(order.getBillingAddress(), "order billing address cannot be null"); 54 | 55 | log.debug("creating new order " + order.getId()); 56 | 57 | return orderRepository.save(order); 58 | } 59 | 60 | /** 61 | * Delete an order 62 | */ 63 | public boolean deleteOrder(long id) { 64 | 65 | Order order = orderRepository.findById(id).orElse(null); 66 | 67 | if (order != null) { 68 | orderRepository.delete(order); 69 | log.debug("deleted order :" + order.getId()); 70 | return true; 71 | } 72 | 73 | log.debug("cannot find order for id " + id); 74 | 75 | return false; 76 | } 77 | 78 | /** 79 | * Delete an order 80 | */ 81 | public boolean deleteOrder(Order order) { 82 | Assert.notNull(order, "order cannot be null"); 83 | Assert.notNull(order.getId(), "order ID cannot be null"); 84 | return deleteOrder(order.getId()); 85 | } 86 | 87 | /** 88 | * Find all orders for a customer 89 | */ 90 | public List findOrdersByCustomerId(long customerId) { 91 | return orderRepository.findByCustomerId(customerId); 92 | } 93 | 94 | 95 | /** 96 | * Find all orders 97 | */ 98 | public List findAllOrders() { 99 | List orders = new ArrayList(); 100 | for (Order order : orderRepository.findAll()) { 101 | orders.add(order); 102 | } 103 | return Collections.unmodifiableList(orders); 104 | } 105 | } 106 | -------------------------------------------------------------------------------- /quickstart/repository/src/main/java/org/springframework/data/gemfire/examples/ProductService.java: -------------------------------------------------------------------------------- 1 | package org.springframework.data.gemfire.examples; 2 | 3 | import java.util.ArrayList; 4 | import java.util.Collections; 5 | import java.util.List; 6 | 7 | import org.springframework.beans.factory.annotation.Autowired; 8 | import org.springframework.data.gemfire.examples.domain.Product; 9 | import org.springframework.data.gemfire.examples.repository.ProductRepository; 10 | import org.springframework.util.Assert; 11 | 12 | import org.apache.commons.logging.Log; 13 | import org.apache.commons.logging.LogFactory; 14 | 15 | /** 16 | * @author David Turanski 17 | */ 18 | public class ProductService { 19 | 20 | private static Log log = LogFactory.getLog(ProductService.class); 21 | @Autowired 22 | ProductRepository productRepository; 23 | 24 | /** 25 | * Create a new product 26 | */ 27 | public Product createProduct(Product product) { 28 | Assert.notNull(product, "product cannot be null"); 29 | Assert.notNull(product.getId(), "product ID cannot be null"); 30 | Assert.hasText(product.getName(), "product name must contain text"); 31 | 32 | log.debug("creating new product " + product.getId() + " " + product.getName()); 33 | return productRepository.save(product); 34 | } 35 | 36 | /** 37 | * Delete a product for a given id 38 | */ 39 | public boolean deleteProduct(long id) { 40 | 41 | Product product = productRepository.findById(id).orElse(null); 42 | 43 | if (product != null) { 44 | productRepository.delete(product); 45 | log.debug("deleted product " + product.getId() + ":" + product.getName()); 46 | return true; 47 | } 48 | 49 | log.warn("product not found for id " + id); 50 | 51 | return false; 52 | } 53 | 54 | /** 55 | * Delete a product 56 | */ 57 | public boolean deleteProduct(Product product) { 58 | Assert.notNull(product, "product cannot be null"); 59 | Assert.notNull(product.getId(), "product ID cannot be null"); 60 | return deleteProduct(product.getId()); 61 | } 62 | 63 | /** 64 | * return a list of products containing a description 65 | */ 66 | public List findProductsByDescription(String description) { 67 | return productRepository.findByDescriptionContaining(description); 68 | } 69 | 70 | /** 71 | * return a list of products with the given name 72 | */ 73 | public List findProductsByName(String name) { 74 | return productRepository.findByName(name); 75 | } 76 | 77 | /** 78 | * return a list of products with a given attribute value 79 | * 80 | * @param key - the attribute name 81 | * @param value - the value 82 | */ 83 | public List findProductsByAttribute(String key, String value) { 84 | return productRepository.findByAttributes(key, value); 85 | } 86 | 87 | /** 88 | * Return all products 89 | */ 90 | public List findAllProducts() { 91 | List products = new ArrayList(); 92 | for (Product p : productRepository.findAll()) { 93 | products.add(p); 94 | } 95 | return Collections.unmodifiableList(products); 96 | } 97 | } 98 | 99 | -------------------------------------------------------------------------------- /quickstart/repository/src/main/java/org/springframework/data/gemfire/examples/repository/CustomerRepository.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples.repository; 17 | 18 | import java.util.List; 19 | 20 | import org.springframework.data.gemfire.examples.domain.Customer; 21 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 22 | import org.springframework.data.gemfire.repository.GemfireRepository; 23 | 24 | /** 25 | * Repository interface to access {@link Customer}s. 26 | * 27 | * @author Oliver Gierke 28 | * @author David Turanski 29 | */ 30 | 31 | public interface CustomerRepository extends GemfireRepository { 32 | 33 | /** 34 | * Returns all {@link Customer}s. 35 | * 36 | * @return 37 | */ 38 | List findAll(); 39 | 40 | /** 41 | * Finds all {@link Customer}s with the given lastname. 42 | * 43 | * @param lastname 44 | * @return 45 | */ 46 | List findByLastname(String lastname); 47 | 48 | /** 49 | * Finds the Customer with the given {@link EmailAddress}. 50 | * 51 | * @param emailAddress 52 | * @return 53 | */ 54 | Customer findByEmailAddress(EmailAddress emailAddress); 55 | } 56 | -------------------------------------------------------------------------------- /quickstart/repository/src/main/java/org/springframework/data/gemfire/examples/repository/OrderRepository.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples.repository; 17 | 18 | import java.util.List; 19 | 20 | import org.springframework.data.gemfire.examples.domain.Order; 21 | import org.springframework.data.repository.CrudRepository; 22 | 23 | /** 24 | * @author Oliver Gierke 25 | * @author David Turanski 26 | */ 27 | public interface OrderRepository extends CrudRepository { 28 | List findByCustomerId(Long customerId); 29 | } 30 | -------------------------------------------------------------------------------- /quickstart/repository/src/main/java/org/springframework/data/gemfire/examples/repository/ProductRepository.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples.repository; 17 | 18 | import java.util.List; 19 | 20 | import org.springframework.data.gemfire.examples.domain.Product; 21 | import org.springframework.data.gemfire.repository.Query; 22 | import org.springframework.data.repository.CrudRepository; 23 | 24 | 25 | /** 26 | * Repository interface to access {@link Product}s. 27 | * 28 | * @author Oliver Gierke 29 | * @author David Turanski 30 | */ 31 | public interface ProductRepository extends CrudRepository { 32 | 33 | /** 34 | * Returns a list of {@link Product}s having a description which contains the given snippet. 35 | * @param the search string 36 | * @return 37 | */ 38 | 39 | List findByDescriptionContaining(String description); 40 | 41 | /** 42 | * Returns all {@link Product}s having the given attribute value. 43 | * @param attribute 44 | * @param value 45 | * @return 46 | */ 47 | @Query("SELECT * FROM /Product where attributes[$1] = $2") 48 | List findByAttributes(String key, String value); 49 | 50 | List findByName(String name); 51 | } 52 | -------------------------------------------------------------------------------- /quickstart/repository/src/main/resources/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /quickstart/repository/src/main/resources/log4j.properties: -------------------------------------------------------------------------------- 1 | log4j.rootCategory=WARN, stdout 2 | 3 | log4j.appender.stdout=org.apache.log4j.ConsoleAppender 4 | log4j.appender.stdout.layout=org.apache.log4j.PatternLayout 5 | log4j.appender.stdout.layout.ConversionPattern=%p [%C{1}] - %m%n 6 | 7 | log4j.category.org.springframework.data.gemfire.examples=DEBUG 8 | -------------------------------------------------------------------------------- /quickstart/spring-cache/README.md: -------------------------------------------------------------------------------- 1 | Spring Cache Example 2 | ==================== 3 | 4 | This demonstrates Spring Framework's @Cacheable annotation backed by GemFire. 5 | 6 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 7 | 8 | ./gradlew -q run-spring-cache 9 | 10 | Or to run from your IDE, execute one of the following tasks once. 11 | 12 | ./gradlew eclipse 13 | ./gradlew idea 14 | 15 | Then import the project into your IDE and run Main.java 16 | 17 | # Details 18 | The CustomerService uses a CustomerDao to retrieve customer data. To improve performance, customer data is cached so if the same customer is 19 | retrieved again the cached instance will be returned. 20 | 21 | The method CustomerService.findCustomer() is annotated with @Cacheable("Customer"), which refers to a GemFire Region named 'Customer'. 22 | The GemFire cache and region are configured in cache-context.xml and the cacheManager are Spring beans configured in app-context.xml 23 | 24 | See [This section of the Spring Reference](https://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/spring-framework-reference.html#new-in-3.1-cache-abstraction) 25 | for more information. 26 | 27 | -------------------------------------------------------------------------------- /quickstart/spring-cache/src/main/java/org/springframework/data/gemfire/examples/CustomerDao.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.springframework.data.gemfire.examples.domain.Customer; 19 | 20 | /** 21 | * Customer data access interface 22 | * @author David Turanski 23 | * 24 | */ 25 | public interface CustomerDao { 26 | 27 | /** 28 | * Get a Customer by ID 29 | * @param id 30 | * @return 31 | */ 32 | public abstract Customer get(long id); 33 | 34 | } -------------------------------------------------------------------------------- /quickstart/spring-cache/src/main/java/org/springframework/data/gemfire/examples/CustomerService.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.apache.commons.logging.Log; 19 | import org.apache.commons.logging.LogFactory; 20 | import org.springframework.beans.factory.annotation.Autowired; 21 | import org.springframework.cache.annotation.Cacheable; 22 | import org.springframework.data.gemfire.examples.domain.Customer; 23 | import org.springframework.stereotype.Component; 24 | 25 | @Component 26 | /** 27 | * A Service for accessing Customer Data 28 | * @author "David Turanski" 29 | * 30 | */ 31 | public class CustomerService { 32 | private static Log log = LogFactory.getLog(CustomerService.class); 33 | @Autowired 34 | CustomerDao customerDao; 35 | 36 | @Cacheable("Customer") 37 | public Customer findCustomer(long id) { 38 | log.info("Retrieving a customer instance from the data store on a cache miss. The return value will be cached"); 39 | return customerDao.get(id); 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /quickstart/spring-cache/src/main/java/org/springframework/data/gemfire/examples/HashMapCustomerDao.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import java.util.HashMap; 19 | import java.util.Map; 20 | 21 | import org.springframework.data.gemfire.examples.domain.Customer; 22 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 23 | import org.springframework.stereotype.Component; 24 | 25 | /** 26 | * Retrieve Customer data from a simulated data store 27 | * @author David Turanski 28 | * 29 | */ 30 | @Component 31 | public class HashMapCustomerDao implements CustomerDao { 32 | private Map customerData; 33 | 34 | public HashMapCustomerDao() { 35 | customerData = new HashMap(); 36 | Customer dave = new Customer(1L,new EmailAddress("dave@matthews.com"),"Dave","Matthews"); 37 | Customer alicia = new Customer(2L,new EmailAddress("alicia@keys.com"),"Alicia","Keys"); 38 | customerData.put(dave.getId(),dave); 39 | customerData.put(alicia.getId(), alicia); 40 | } 41 | 42 | /* (non-Javadoc) 43 | * @see org.springframework.data.gemfire.examples.CustomerDao#get(long) 44 | */ 45 | @Override 46 | public Customer get(long id){ 47 | return customerData.get(id); 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /quickstart/spring-cache/src/main/java/org/springframework/data/gemfire/examples/Main.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.apache.commons.logging.Log; 19 | import org.apache.commons.logging.LogFactory; 20 | import org.springframework.context.ApplicationContext; 21 | import org.springframework.context.support.ClassPathXmlApplicationContext; 22 | import org.springframework.data.gemfire.examples.domain.Customer; 23 | 24 | public class Main { 25 | private static Log log = LogFactory.getLog(Main.class); 26 | 27 | public static void main(String args[]) { 28 | 29 | ApplicationContext context = new ClassPathXmlApplicationContext("app-context.xml"); 30 | 31 | CustomerService customerService = context.getBean(CustomerService.class); 32 | 33 | log.info("Retrieving objects not in cache..."); 34 | for (long i = 1; i<=2; i++) { 35 | log.info("Retrieving object with id: " + i); 36 | Customer c = customerService.findCustomer(i); 37 | log.info("Retrieved " + c.getFirstname()+ " " + c.getLastname()); 38 | } 39 | 40 | log.info("Retrieving the same objects again. This time, the target method is not actually invoked!"); 41 | log.info("@Cacheable causes Spring to wrap CustomerService in a proxy: " + customerService.getClass().getName()); 42 | 43 | for (int i = 1; i<=2; i++) { 44 | log.info("Retrieving object with id: " + i); 45 | Customer c = customerService.findCustomer(i); 46 | log.info("Retrieved " + c.getFirstname()+ " " + c.getLastname()); 47 | } 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /quickstart/spring-cache/src/main/resources/app-context.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /quickstart/spring-cache/src/main/resources/cache-context.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | warning 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /quickstart/transaction/README.md: -------------------------------------------------------------------------------- 1 | Spring Data Gemfire Transaction Example 2 | ======================================= 3 | 4 | This example demonstrates how to use Spring's declarative transaction management using the GemfireTransactionManager and Spring Data Gemfire Repositories. The example creates 5 | a customer in the Customer region and then performs an update which throws an exception after the cache entry is updated, triggering a rollback. 6 | 7 | To run this example, open a command window, go to the the spring-gemfire-examples root directory, and type: 8 | 9 | ./gradlew -q run-transaction 10 | 11 | Or to run from your IDE, run one of the following commands once. 12 | 13 | ./gradlew eclipse 14 | ./gradlew idea 15 | 16 | Then import the project into your IDE and run Main.java 17 | 18 | # Details 19 | 20 | The CustomerService uses CustomerRepository to perform CRUD operations on the Customer region. The CustomerService.updateCustomer() method is annoted with 21 | @Transactional to wrap each method invocation in a GemFire transaction. The method has a boolean argument that, if set to true, will throw an exception after 22 | the repository operation completes. This simulates an exception that could occur during some subsequent step that must be performed within the same transaction. 23 | 24 | The application configuration uses Java configuration. The configuration class is ApplicationConfig.java. 25 | -------------------------------------------------------------------------------- /quickstart/transaction/src/main/java/org/springframework/data/gemfire/examples/ApplicationConfig.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.springframework.context.annotation.Bean; 19 | import org.springframework.context.annotation.Configuration; 20 | import org.springframework.context.annotation.ImportResource; 21 | import org.springframework.data.gemfire.repository.config.EnableGemfireRepositories; 22 | import org.springframework.transaction.annotation.EnableTransactionManagement; 23 | 24 | /** 25 | * @author David Turanski 26 | * 27 | */ 28 | @Configuration 29 | @ImportResource("cache-config.xml") 30 | @EnableTransactionManagement 31 | @EnableGemfireRepositories 32 | public class ApplicationConfig { 33 | 34 | @Bean 35 | CustomerService customerService() { 36 | return new CustomerService(); 37 | } 38 | 39 | } 40 | -------------------------------------------------------------------------------- /quickstart/transaction/src/main/java/org/springframework/data/gemfire/examples/CustomerService.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.springframework.beans.factory.annotation.Autowired; 19 | import org.springframework.data.gemfire.examples.domain.Customer; 20 | import org.springframework.data.gemfire.examples.repository.CustomerRepository; 21 | import org.springframework.transaction.annotation.Transactional; 22 | 23 | /** 24 | * @author David Turanski 25 | */ 26 | public class CustomerService { 27 | 28 | @Autowired 29 | CustomerRepository customerRepository; 30 | 31 | /** 32 | * @param customer 33 | * @param fail - set to true to simulate some downstream processing that throws an exception which should trigger a rollback 34 | */ 35 | @Transactional("gemfireTransactionManager") 36 | public void updateCustomer(Customer customer, boolean fail) { 37 | customerRepository.save(customer); 38 | if (fail) { 39 | throw new RuntimeException("Updated failed - should trigger a rollback."); 40 | } 41 | } 42 | 43 | public Customer getCustomer(long id) { 44 | return customerRepository.findById(id).orElse(null); 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /quickstart/transaction/src/main/java/org/springframework/data/gemfire/examples/Main.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples; 17 | 18 | import org.apache.commons.logging.Log; 19 | import org.apache.commons.logging.LogFactory; 20 | import org.springframework.context.ApplicationContext; 21 | import org.springframework.context.annotation.AnnotationConfigApplicationContext; 22 | import org.springframework.data.gemfire.examples.domain.Customer; 23 | import org.springframework.data.gemfire.examples.domain.EmailAddress; 24 | import org.springframework.util.Assert; 25 | 26 | /** 27 | * @author David Turanski 28 | * 29 | */ 30 | public class Main { 31 | private static Log log = LogFactory.getLog(Main.class); 32 | private static CustomerService customerService; 33 | 34 | public static void main(String[] args) { 35 | ApplicationContext context = new AnnotationConfigApplicationContext(ApplicationConfig.class); 36 | 37 | customerService = context.getBean(CustomerService.class); 38 | 39 | Customer customer = new Customer(1L,new EmailAddress("customer@customer.com"),"First","Last"); 40 | log.debug("creating a Customer with last name " + customer.getLastname()); 41 | 42 | customerService.updateCustomer(customer,false); 43 | 44 | customer = customerService.getCustomer(1L); 45 | 46 | customer.setLastname("Newname"); 47 | 48 | try { 49 | log.debug("changing customer last name to " + customer.getLastname()); 50 | customerService.updateCustomer(customer,true); 51 | 52 | } catch (Exception e) { 53 | customer = customerService.getCustomer(1L); 54 | Assert.isTrue(customer.getLastname().equals("Last"), "No rollback - customer last name is " + customer.getLastname()); 55 | log.debug(e.getMessage() + " Customer last name is still '" + customer.getLastname()+"'"); 56 | } 57 | } 58 | } 59 | 60 | 61 | -------------------------------------------------------------------------------- /quickstart/transaction/src/main/java/org/springframework/data/gemfire/examples/repository/CustomerRepository.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples.repository; 17 | 18 | import org.springframework.data.gemfire.examples.domain.Customer; 19 | import org.springframework.data.gemfire.repository.GemfireRepository; 20 | 21 | /** 22 | * @author David Turanski 23 | * 24 | */ 25 | public interface CustomerRepository extends GemfireRepository { 26 | } 27 | -------------------------------------------------------------------------------- /quickstart/transaction/src/main/resources/cache-config.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 13 | warning 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /quickstart/transaction/src/main/resources/log4j.properties: -------------------------------------------------------------------------------- 1 | log4j.rootCategory=WARN, stdout 2 | 3 | log4j.appender.stdout=org.apache.log4j.ConsoleAppender 4 | log4j.appender.stdout.layout=org.apache.log4j.PatternLayout 5 | log4j.appender.stdout.layout.ConversionPattern=%p [%t] [%C{1}] - %m%n 6 | 7 | log4j.category.org.springframework.data.gemfire.GemfireTransactionManager=DEBUG 8 | log4j.category.org.springframework.data.gemfire.examples=DEBUG 9 | -------------------------------------------------------------------------------- /settings.gradle: -------------------------------------------------------------------------------- 1 | rootProject.name = 'spring-gemfire-examples' 2 | 3 | include ':spring-gemfire-examples-common' 4 | include ':quickstart:spring-cache', ':quickstart:repository', ':quickstart:gemfire-template',':quickstart:cq',':quickstart:transaction','quickstart:json' 5 | include ':basic:replicated',':basic:replicated-cs',':basic:partitioned',':basic:write-through',':basic:function',':basic:persistence',':basic:annotated-function',":basic:java-config",':basic:cq-with-javaconfig' 6 | include ':advanced:gatewayV7',':advanced:locator-failover',':advanced:server-failover' 7 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/GenericServer.java: -------------------------------------------------------------------------------- 1 | package org.springframework.data.gemfire.examples; 2 | 3 | import java.io.IOException; 4 | 5 | import org.apache.commons.logging.Log; 6 | import org.apache.commons.logging.LogFactory; 7 | import org.springframework.context.support.FileSystemXmlApplicationContext; 8 | 9 | public class GenericServer { 10 | 11 | private static Log log = LogFactory.getLog(GenericServer.class); 12 | public static void main(String args[]) throws IOException { 13 | if (args.length >= 1) { 14 | log.debug("initializing application context from Spring bean definition file " + args[0]); 15 | } else { 16 | System.out.println("usage: GenericServer "); 17 | System.exit(1); 18 | } 19 | 20 | new FileSystemXmlApplicationContext(args[0]); 21 | 22 | System.out.println("Press to terminate"); 23 | System.in.read(); 24 | System.exit(0); 25 | 26 | 27 | } 28 | } 29 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/LocatorCommandParser.java: -------------------------------------------------------------------------------- 1 | package org.springframework.data.gemfire.examples; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | import org.apache.commons.cli.BasicParser; 7 | import org.apache.commons.cli.CommandLine; 8 | import org.apache.commons.cli.HelpFormatter; 9 | import org.apache.commons.cli.Options; 10 | import org.apache.commons.cli.ParseException; 11 | 12 | public class LocatorCommandParser { 13 | private static Options options = new Options(); 14 | private static void initOptions() { 15 | options.addOption("start", false, "Start the locator"); 16 | options.addOption("stop", false, "Stop the locator"); 17 | options.addOption("status", false, "Check locator status"); 18 | options.addOption("port", true, "the locator port"); 19 | options.addOption("dir", true, "the locator working directory"); 20 | options.addOption("properties", true, "a gemfire properties file"); 21 | options.addOption("help", false, "display this message"); 22 | } 23 | 24 | public static Map parseOptions(String [] args) { 25 | initOptions(); 26 | HashMap optionsMap = new HashMap(); 27 | BasicParser parser = new BasicParser(); 28 | 29 | try { 30 | CommandLine cl = parser.parse(options, args); 31 | if (cl.hasOption("help")){ 32 | usage("help"); 33 | return null; 34 | } 35 | 36 | String command = getCommand(cl); 37 | 38 | if (command==null){ 39 | return null; 40 | } 41 | 42 | optionsMap.put("command",command); 43 | 44 | if (cl.hasOption("port")){ 45 | optionsMap.put("port",Integer.parseInt(cl.getOptionValue("port"))); 46 | } 47 | 48 | if (cl.hasOption("dir")){ 49 | optionsMap.put("dir",cl.getOptionValue("dir")); 50 | } 51 | 52 | if (cl.hasOption("properties")){ 53 | optionsMap.put("properties",cl.getOptionValue("properties")); 54 | } 55 | } 56 | 57 | catch (ParseException e) { 58 | usage(e.getMessage()); 59 | return null; 60 | } 61 | 62 | return optionsMap; 63 | 64 | } 65 | 66 | private static String getCommand(CommandLine cl) { 67 | String command = null; 68 | if(cl.hasOption("start")){ 69 | command = "start"; 70 | } 71 | 72 | if(cl.hasOption("stop")){ 73 | if (command == null){ 74 | command = "stop"; 75 | } else { 76 | usage("ERROR: Invalid command option: 'stop'. Command already provided '" + command + "'." ); 77 | return null; 78 | } 79 | } 80 | 81 | if (command==null){ 82 | usage("ERROR: No command option provided. One of 'start', 'stop' or 'status' is required."); 83 | } 84 | 85 | return command; 86 | } 87 | 88 | private static void usage(String msg){ 89 | HelpFormatter f = new HelpFormatter(); 90 | f.printHelp(msg, options); 91 | } 92 | 93 | } 94 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/domain/AbstractPersistentEntity.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | package org.springframework.data.gemfire.examples.domain; 17 | 18 | import java.io.Serializable; 19 | 20 | import javax.persistence.MappedSuperclass; 21 | 22 | import org.springframework.data.annotation.Id; 23 | 24 | /** 25 | * Base class for persistent classes. 26 | * 27 | * @author Oliver Gierke 28 | * @author David Turanski 29 | */ 30 | @SuppressWarnings("serial") 31 | @MappedSuperclass 32 | public class AbstractPersistentEntity implements Serializable { 33 | 34 | @Id 35 | @javax.persistence.Id 36 | private final Long id; 37 | 38 | /** 39 | * Returns the identifier of the entity. 40 | * 41 | * @return the id 42 | */ 43 | public Long getId() { 44 | return id; 45 | } 46 | 47 | protected AbstractPersistentEntity(Long id) { 48 | this.id = id; 49 | } 50 | 51 | protected AbstractPersistentEntity() { 52 | this.id = null; 53 | } 54 | 55 | 56 | /* 57 | * (non-Javadoc) 58 | * @see java.lang.Object#equals(java.lang.Object) 59 | */ 60 | @Override 61 | public boolean equals(Object obj) { 62 | 63 | if (this == obj) { 64 | return true; 65 | } 66 | 67 | if (this.id == null || obj == null || !(this.getClass().equals(obj.getClass()))) { 68 | return false; 69 | } 70 | 71 | AbstractPersistentEntity that = (AbstractPersistentEntity) obj; 72 | 73 | return this.id.equals(that.getId()); 74 | } 75 | 76 | /* 77 | * (non-Javadoc) 78 | * @see java.lang.Object#hashCode() 79 | */ 80 | @Override 81 | public int hashCode() { 82 | return id == null ? 0 : id.hashCode(); 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/domain/Address.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples.domain; 18 | 19 | import java.io.Serializable; 20 | 21 | import org.springframework.util.Assert; 22 | 23 | /** 24 | * An address. 25 | * 26 | * @author Oliver Gierke 27 | */ 28 | public class Address implements Serializable { 29 | 30 | private static final long serialVersionUID = -2639944658538569230L; 31 | 32 | private final String street, city, country; 33 | 34 | /** 35 | * Creates a new {@link Address} from the given street, city and country. 36 | * 37 | * @param street must not be {@literal null} or empty. 38 | * @param city must not be {@literal null} or empty. 39 | * @param country must not be {@literal null} or empty. 40 | */ 41 | public Address(String street, String city, String country) { 42 | 43 | Assert.hasText(street, "Street is required"); 44 | Assert.hasText(city, "City is required"); 45 | Assert.hasText(country, "Country is required"); 46 | 47 | this.street = street; 48 | this.city = city; 49 | this.country = country; 50 | } 51 | 52 | /** 53 | * Returns a copy of the current {@link Address} instance which is a new entity in terms of persistence. 54 | * 55 | * @return 56 | */ 57 | public Address getCopy() { 58 | return new Address(this.street, this.city, this.country); 59 | } 60 | 61 | /** 62 | * Returns the street. 63 | * 64 | * @return 65 | */ 66 | public String getStreet() { 67 | return street; 68 | } 69 | 70 | /** 71 | * Returns the city. 72 | * 73 | * @return 74 | */ 75 | public String getCity() { 76 | return city; 77 | } 78 | 79 | /** 80 | * Returns the country. 81 | * 82 | * @return 83 | */ 84 | public String getCountry() { 85 | return country; 86 | } 87 | 88 | @Override 89 | public String toString() { 90 | return String.format("%1$s, %2$s - %3$s", getStreet(), getCity(), getCountry()); 91 | } 92 | } 93 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/domain/EmailAddress.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples.domain; 18 | 19 | import java.io.Serializable; 20 | import java.util.regex.Pattern; 21 | 22 | import org.springframework.core.convert.converter.Converter; 23 | import org.springframework.stereotype.Component; 24 | import org.springframework.util.Assert; 25 | import org.springframework.util.StringUtils; 26 | 27 | /** 28 | * Value object to represent email addresses. 29 | * 30 | * @author Oliver Gierke 31 | */ 32 | public final class EmailAddress implements Serializable { 33 | 34 | private static final long serialVersionUID = -2990839949384592331L; 35 | 36 | private static final String EMAIL_REGEX = 37 | "^[_A-Za-z0-9-]+(\\.[_A-Za-z0-9-]+)*@[A-Za-z0-9]+(\\.[A-Za-z0-9]+)*(\\.[A-Za-z]{2,})$"; 38 | 39 | private static final Pattern PATTERN = Pattern.compile(EMAIL_REGEX); 40 | 41 | private final String value; 42 | 43 | /** 44 | * Creates a new {@link EmailAddress} from the given {@link String} representation. 45 | * 46 | * @param emailAddress must not be {@literal null} or empty. 47 | */ 48 | public EmailAddress(String emailAddress) { 49 | 50 | Assert.isTrue(isValid(emailAddress), "Invalid email address!"); 51 | 52 | this.value = emailAddress; 53 | } 54 | 55 | /** 56 | * Returns whether the given value is a valid {@link EmailAddress}. 57 | * 58 | * @param source must not be {@literal null} or empty. 59 | * @return 60 | */ 61 | public static boolean isValid(String source) { 62 | 63 | Assert.hasText(source, "Source is required"); 64 | 65 | return PATTERN.matcher(source).matches(); 66 | } 67 | 68 | public String getValue() { 69 | return value; 70 | } 71 | 72 | /* 73 | * (non-Javadoc) 74 | * @see java.lang.Object#toString() 75 | */ 76 | @Override 77 | public String toString() { 78 | return value; 79 | } 80 | 81 | /* 82 | * (non-Javadoc) 83 | * @see java.lang.Object#equals(java.lang.Object) 84 | */ 85 | @Override 86 | public boolean equals(Object obj) { 87 | 88 | if (this == obj) { 89 | return true; 90 | } 91 | 92 | if (!(obj instanceof EmailAddress)) { 93 | return false; 94 | } 95 | 96 | EmailAddress that = (EmailAddress) obj; 97 | return this.value.equals(that.value); 98 | } 99 | 100 | /* 101 | * (non-Javadoc) 102 | * @see java.lang.Object#hashCode() 103 | */ 104 | @Override 105 | public int hashCode() { 106 | return value.hashCode(); 107 | } 108 | 109 | @Component 110 | static class EmailAddressToStringConverter implements Converter { 111 | 112 | /* 113 | * (non-Javadoc) 114 | * @see org.springframework.core.convert.converter.Converter#convert(java.lang.Object) 115 | */ 116 | @Override 117 | public String convert(EmailAddress source) { 118 | return source == null ? null : source.value; 119 | } 120 | } 121 | 122 | @Component 123 | static class StringToEmailAddressConverter implements Converter { 124 | 125 | /* 126 | * (non-Javadoc) 127 | * @see org.springframework.core.convert.converter.Converter#convert(java.lang.Object) 128 | */ 129 | public EmailAddress convert(String source) { 130 | return StringUtils.hasText(source) ? new EmailAddress(source) : null; 131 | } 132 | } 133 | } 134 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/domain/LineItem.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples.domain; 18 | 19 | import java.io.Serializable; 20 | import java.math.BigDecimal; 21 | 22 | import org.springframework.util.Assert; 23 | 24 | /** 25 | * @author Oliver Gierke 26 | */ 27 | public class LineItem implements Serializable { 28 | 29 | private static final long serialVersionUID = 6571108615511329726L; 30 | 31 | private int amount; 32 | 33 | private BigDecimal price; 34 | 35 | private Long productId; 36 | 37 | private String productName; 38 | 39 | /** 40 | * Creates a new {@link LineItem} for the given {@link Product}. 41 | * @param product must not be {@literal null}. 42 | */ 43 | public LineItem(Product product) { 44 | this(product,1); 45 | } 46 | 47 | /** 48 | * Constructs a new {@link LineItem} for the given {@link Product} and amount. 49 | * 50 | * @param product must not be {@literal null}. 51 | * @param amount the number of {@link Product Products} purchased. 52 | */ 53 | public LineItem(Product product, int amount) { 54 | 55 | Assert.notNull(product, "Product is required"); 56 | Assert.isTrue(amount > 0, "The amount of Products to be bought must be greater than 0"); 57 | 58 | this.productId = product.getId(); 59 | this.productName = product.getName(); 60 | this.amount = amount; 61 | this.price = product.getPrice(); 62 | } 63 | 64 | /** 65 | * Returns the id of the {@link Product} the {@link LineItem} refers to. 66 | * 67 | * @return 68 | */ 69 | public Long getProductId() { 70 | return productId; 71 | } 72 | 73 | /** 74 | * Returns the {@link String name} of the {@link Product} that this {@link LineItem} refers to. 75 | * 76 | * @return the {@link String name} of the {@link Product} that this {@link LineItem} refers to. 77 | */ 78 | public String getProductName() { 79 | return productName; 80 | } 81 | 82 | /** 83 | * Returns the amount of {@link Product}s to be ordered. 84 | * 85 | * @return 86 | */ 87 | public int getAmount() { 88 | return amount; 89 | } 90 | 91 | /** 92 | * Returns the price a single unit of the {@link LineItem}'s product. 93 | * 94 | * @return the price 95 | */ 96 | public BigDecimal getUnitPrice() { 97 | return price; 98 | } 99 | 100 | /** 101 | * Returns the total for the {@link LineItem}. 102 | * 103 | * @return 104 | */ 105 | public BigDecimal getTotal() { 106 | return price.multiply(BigDecimal.valueOf(amount)); 107 | } 108 | 109 | @Override 110 | public String toString() { 111 | return String.format("Purchased [%d] of Product [%s] at [%s] for total of [%s]", 112 | getAmount(), getProductName(), getUnitPrice(), getTotal()); 113 | } 114 | } 115 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/domain/Order.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples.domain; 18 | 19 | import java.math.BigDecimal; 20 | import java.util.Collections; 21 | import java.util.HashSet; 22 | import java.util.Iterator; 23 | import java.util.Set; 24 | 25 | import org.springframework.data.gemfire.mapping.annotation.Region; 26 | import org.springframework.util.Assert; 27 | 28 | /** 29 | * @author Oliver Gierke 30 | * @author David Turanski 31 | */ 32 | @Region 33 | public class Order extends AbstractPersistentEntity implements Iterable { 34 | 35 | private static final long serialVersionUID = -3779061453639083037L; 36 | 37 | private Address billingAddress; 38 | private Address shippingAddress; 39 | 40 | private Long customerId; 41 | 42 | private Set lineItems = new HashSet<>(); 43 | 44 | /** 45 | * Creates a new {@link Order} for the given {@link Customer}. 46 | * 47 | * @param customer must not be {@literal null}. 48 | */ 49 | public Order(Long id, Long customerId, Address billingAddress) { 50 | 51 | super(id); 52 | 53 | Assert.notNull(customerId, "Customer ID must not be null"); 54 | Assert.notNull(billingAddress, "Billing Address must not be null"); 55 | 56 | this.customerId = customerId; 57 | this.billingAddress = billingAddress; 58 | this.shippingAddress = billingAddress; 59 | } 60 | 61 | /** 62 | * Adds the given {@link LineItem} to the {@link Order}. 63 | * 64 | * @param lineItem 65 | */ 66 | public void add(LineItem lineItem) { 67 | this.lineItems.add(lineItem); 68 | } 69 | 70 | /** 71 | * Returns the billing {@link Address} for this order. 72 | * 73 | * @return 74 | */ 75 | public Address getBillingAddress() { 76 | return billingAddress; 77 | } 78 | 79 | /** 80 | * Returns the id of the {@link Customer} who placed the {@link Order}. 81 | * 82 | * @return 83 | */ 84 | public Long getCustomerId() { 85 | return customerId; 86 | } 87 | 88 | /** 89 | * Returns all {@link LineItem}s currently belonging to the {@link Order}. 90 | * 91 | * @return 92 | */ 93 | public Set getLineItems() { 94 | return Collections.unmodifiableSet(lineItems); 95 | } 96 | 97 | /** 98 | * Returns the shipping {@link Address} for this order; 99 | * 100 | * @return 101 | */ 102 | public Address getShippingAddress() { 103 | return shippingAddress; 104 | } 105 | 106 | /** 107 | * Returns the total of the {@link Order}. 108 | * 109 | * @return 110 | */ 111 | public BigDecimal getTotal() { 112 | 113 | BigDecimal total = BigDecimal.ZERO; 114 | 115 | for (LineItem item : this) { 116 | total = total.add(item.getTotal()); 117 | } 118 | 119 | return total; 120 | } 121 | 122 | @Override 123 | public Iterator iterator() { 124 | return getLineItems().iterator(); 125 | } 126 | 127 | @Override 128 | public String toString() { 129 | return String.valueOf(getId()); 130 | } 131 | } 132 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/domain/Product.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples.domain; 18 | 19 | import java.math.BigDecimal; 20 | import java.util.Collections; 21 | import java.util.HashMap; 22 | import java.util.Map; 23 | 24 | import org.springframework.data.annotation.PersistenceConstructor; 25 | import org.springframework.data.gemfire.mapping.annotation.Region; 26 | import org.springframework.util.Assert; 27 | 28 | /** 29 | * A product. 30 | * 31 | * @author Oliver Gierke 32 | * @author David Turanski 33 | */ 34 | @Region 35 | @javax.persistence.Entity 36 | public class Product extends AbstractPersistentEntity { 37 | 38 | private static final long serialVersionUID = 831295555713696643L; 39 | 40 | private BigDecimal price; 41 | 42 | @javax.persistence.Transient 43 | private Map attributes = new HashMap<>(); 44 | 45 | private String name, description; 46 | 47 | /** 48 | * Creates a new {@link Product} with the given name. 49 | * @param id a unique Id 50 | * @param name must not be {@literal null} or empty. 51 | * @param price must not be {@literal null} or less than or equal to zero. 52 | */ 53 | public Product(Long id, String name, BigDecimal price) { 54 | this(id, name, price, null); 55 | } 56 | 57 | /** 58 | * Creates a new {@link Product} from the given name and description. 59 | * @param id a unique Id 60 | * @param name must not be {@literal null} or empty. 61 | * @param price must not be {@literal null} or less than or equal to zero. 62 | * @param description 63 | */ 64 | @PersistenceConstructor 65 | public Product(Long id, String name, BigDecimal price, String description) { 66 | 67 | super(id); 68 | 69 | Assert.hasText(name, "Name must not be null or empty"); 70 | Assert.isTrue(BigDecimal.ZERO.compareTo(price) < 0, "Price must be greater than zero"); 71 | 72 | this.name = name; 73 | this.price = price; 74 | this.description = description; 75 | } 76 | 77 | /** 78 | * Sets the attribute with the given name to the given value. 79 | * 80 | * @param name must not be {@literal null} or empty. 81 | * @param value 82 | */ 83 | public void setAttribute(String name, String value) { 84 | 85 | Assert.hasText(name, "Name is required"); 86 | 87 | if (value == null) { 88 | this.attributes.remove(value); 89 | } 90 | else { 91 | this.attributes.put(name, value); 92 | } 93 | } 94 | 95 | /** 96 | * Returns the {@link Product}'s name. 97 | * 98 | * @return 99 | */ 100 | public String getName() { 101 | return name; 102 | } 103 | 104 | /** 105 | * Returns the {@link Product}'s description. 106 | * 107 | * @return 108 | */ 109 | public String getDescription() { 110 | return description; 111 | } 112 | 113 | /** 114 | * Returns all the custom attributes of the {@link Product}. 115 | * 116 | * @return 117 | */ 118 | public Map getAttributes() { 119 | return Collections.unmodifiableMap(attributes); 120 | } 121 | 122 | /** 123 | * Returns the price of the {@link Product}. 124 | * 125 | * @return 126 | */ 127 | public BigDecimal getPrice() { 128 | return price; 129 | } 130 | 131 | @Override 132 | public String toString() { 133 | return getName(); 134 | } 135 | } 136 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/util/LoggingCacheListener.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2012 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples.util; 18 | 19 | import org.springframework.stereotype.Component; 20 | 21 | import org.apache.commons.logging.Log; 22 | import org.apache.commons.logging.LogFactory; 23 | import org.apache.geode.cache.EntryEvent; 24 | import org.apache.geode.cache.util.CacheListenerAdapter; 25 | 26 | /** 27 | * A simple CacheListener to log cache events 28 | * @author David Turanski 29 | */ 30 | @Component 31 | @SuppressWarnings("rawtypes") 32 | public class LoggingCacheListener extends CacheListenerAdapter { 33 | 34 | private static Log log = LogFactory.getLog(LoggingCacheListener.class); 35 | 36 | @Override 37 | public void afterCreate(EntryEvent event) { 38 | final String regionName = event.getRegion().getName(); 39 | final Object key = event.getKey(); 40 | final Object newValue = event.getNewValue(); 41 | log.info("In region [" + regionName + "] created key [" + key 42 | + "] value [" + newValue + "]"); 43 | } 44 | 45 | @Override 46 | public void afterDestroy(EntryEvent event) { 47 | final String regionName = event.getRegion().getName(); 48 | final Object key = event.getKey(); 49 | log.info("In region [" + regionName + "] destroyed key [" + key 50 | + "]"); 51 | } 52 | 53 | @Override 54 | public void afterUpdate(EntryEvent event) { 55 | final String regionName = event.getRegion().getName(); 56 | final Object key = event.getKey(); 57 | final Object newValue = event.getNewValue(); 58 | final Object oldValue = event.getOldValue(); 59 | log.info("In region [" + regionName + "] updated key [" + key 60 | + "] [oldValue [" + oldValue + "] new value [" + newValue +"]"); 61 | } 62 | } 63 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/util/ServerPortGenerator.java: -------------------------------------------------------------------------------- 1 | /* Copyright 2012 the original author or authors. 2 | * 3 | * Licensed under the Apache License, Version 2.0 (the "License"); 4 | * you may not use this file except in compliance with the License. 5 | * You may obtain a copy of the License at 6 | * 7 | * https://www.apache.org/licenses/LICENSE-2.0 8 | * 9 | * Unless required by applicable law or agreed to in writing, software 10 | * distributed under the License is distributed on an "AS IS" BASIS, 11 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 | * See the License for the specific language governing permissions and 13 | * limitations under the License. 14 | */ 15 | 16 | package org.springframework.data.gemfire.examples.util; 17 | 18 | import java.io.IOException; 19 | import java.net.InetSocketAddress; 20 | import java.net.ServerSocket; 21 | import java.security.SecureRandom; 22 | 23 | /** 24 | * @author Wayne Lund 25 | * @author David Turanski 26 | */ 27 | public class ServerPortGenerator { 28 | 29 | public int generatePort() { 30 | SecureRandom random = new SecureRandom(); 31 | int port = random.nextInt(10000); 32 | port += 40000; 33 | // implement a check to make sure port is not used. 34 | // on bind exception try again 35 | System.err.println("Server Port:" + port); 36 | return port; 37 | } 38 | 39 | public int generatePort(int min, int max) throws IOException { 40 | ServerSocket socket = new ServerSocket(); 41 | int port = bind(socket, min, max - min); 42 | if (port > 0) { 43 | socket.close(); 44 | return port; 45 | } else { 46 | throw new IOException("Unable to bind on to a port between " + min + " and " + max); 47 | } 48 | 49 | } 50 | 51 | public int bind(ServerSocket socket, int portstart, int retries) throws IOException { 52 | InetSocketAddress addr = null; 53 | int port = portstart; 54 | while (retries > 0) { 55 | try { 56 | addr = new InetSocketAddress(port); 57 | socket.bind(addr); 58 | retries = 0; 59 | return port; 60 | } catch (IOException x) { 61 | retries--; 62 | if (retries <= 0) { 63 | throw x; 64 | } 65 | port++; 66 | } 67 | } 68 | return -1; 69 | } 70 | } 71 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/java/org/springframework/data/gemfire/examples/util/Version.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright 2017 the original author or authors. 3 | * 4 | * Licensed under the Apache License, Version 2.0 (the "License"); 5 | * you may not use this file except in compliance with the License. 6 | * You may obtain a copy of the License at 7 | * 8 | * https://www.apache.org/licenses/LICENSE-2.0 9 | * 10 | * Unless required by applicable law or agreed to in writing, software 11 | * distributed under the License is distributed on an "AS IS" BASIS, 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | * See the License for the specific language governing permissions and 14 | * limitations under the License. 15 | */ 16 | 17 | package org.springframework.data.gemfire.examples.util; 18 | 19 | import java.io.File; 20 | import java.io.FileReader; 21 | import java.io.IOException; 22 | import java.time.LocalDate; 23 | import java.util.Optional; 24 | import java.util.Properties; 25 | 26 | /** 27 | * The {@link Version} class outputs the current version of the Spring GemFire Examples project to Standard Out. 28 | * 29 | * @author John Blum 30 | * @see java.io.File 31 | * @see java.util.Properties 32 | * @since 2.0.0 33 | */ 34 | public class Version { 35 | 36 | private static final String DEFAULT_VERSION = "2.0.0.RC2"; 37 | private static final String GRADLE_PROPERTIES_FILE_NAME = "gradle.properties"; 38 | private static final String VERSION_PROPERTY = "version"; 39 | 40 | public static void main(String[] args) { 41 | System.out.printf("Spring GemFire Examples version %s%n; Copyright (c) %d", 42 | resolveVersion(), LocalDate.now().getYear()); 43 | } 44 | 45 | private static String resolveVersion() { 46 | 47 | return Optional.of(new File(GRADLE_PROPERTIES_FILE_NAME)) 48 | .filter(File::exists) 49 | .map(file -> { 50 | try { 51 | Properties properties = new Properties(); 52 | properties.load(new FileReader(file)); 53 | return properties.getProperty(VERSION_PROPERTY); 54 | } 55 | catch (IOException ignore) { 56 | return null; 57 | } 58 | }) 59 | .orElse(DEFAULT_VERSION); 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /spring-gemfire-examples-common/src/main/resources/log4j.properties: -------------------------------------------------------------------------------- 1 | log4j.rootCategory=WARN, stdout 2 | 3 | log4j.appender.stdout=org.apache.log4j.ConsoleAppender 4 | log4j.appender.stdout.layout=org.apache.log4j.PatternLayout 5 | log4j.appender.stdout.layout.ConversionPattern=%p [%t] [%C{1}] - %m%n 6 | 7 | log4j.category.org.springframework.data.gemfire.examples=DEBUG 8 | --------------------------------------------------------------------------------