From 2e0a5f4c1368993c8cf71b9f4b59273a323b9aff Mon Sep 17 00:00:00 2001 From: antelder Date: Thu, 28 Jul 2011 11:07:25 +0000 Subject: Recreate 2.0-Beta3 branch from current trunk git-svn-id: http://svn.us.apache.org/repos/asf/tuscany@1151792 13f79535-47bb-0310-9956-ffa450edef68 --- .../binding-websocket/autocomplete-webapp/README | 67 +++++++ .../binding-websocket/autocomplete-webapp/pom.xml | 61 ++++++ .../src/main/java/sample/Country.java | 40 ++++ .../src/main/java/sample/CountryRepository.java | 30 +++ .../main/java/sample/CountryRepositoryImpl.java | 80 ++++++++ .../src/main/java/sample/CountryService.java | 30 +++ .../src/main/java/sample/CountryServiceImpl.java | 36 ++++ .../src/main/resources/countries.txt | 211 +++++++++++++++++++++ .../src/main/webapp/META-INF/MANIFEST.MF | 2 + .../src/main/webapp/WEB-INF/web.composite | 40 ++++ .../src/main/webapp/WEB-INF/web.xml | 34 ++++ .../autocomplete-webapp/src/main/webapp/index.html | 64 +++++++ .../binding-websocket/chat-webapp/README | 88 +++++++++ .../binding-websocket/chat-webapp/pom.xml | 67 +++++++ .../src/main/java/sample/ChatService.java | 36 ++++ .../src/main/java/sample/ChatServiceImpl.java | 58 ++++++ .../src/main/webapp/META-INF/MANIFEST.MF | 2 + .../src/main/webapp/WEB-INF/web.composite | 37 ++++ .../chat-webapp/src/main/webapp/WEB-INF/web.xml | 34 ++++ .../chat-webapp/src/main/webapp/index.html | 99 ++++++++++ .../learning-more/binding-websocket/pom.xml | 47 +++++ .../binding-websocket/pubsub-webapp/README | 93 +++++++++ .../binding-websocket/pubsub-webapp/pom.xml | 67 +++++++ .../pubsub-webapp/src/main/java/sample/Event.java | 51 +++++ .../src/main/java/sample/EventProcessor.java | 104 ++++++++++ .../java/sample/EventProcessorConsumerService.java | 37 ++++ .../java/sample/EventProcessorProducerService.java | 28 +++ .../src/main/java/sample/Producer.java | 75 ++++++++ .../src/main/webapp/META-INF/MANIFEST.MF | 2 + .../src/main/webapp/WEB-INF/web.composite | 60 ++++++ .../pubsub-webapp/src/main/webapp/WEB-INF/web.xml | 34 ++++ .../pubsub-webapp/src/main/webapp/index.html | 96 ++++++++++ .../binding-websocket/weather-webapp/README | 89 +++++++++ .../binding-websocket/weather-webapp/pom.xml | 60 ++++++ .../src/main/java/sample/Helper.java | 34 ++++ .../src/main/java/sample/HumidityService.java | 36 ++++ .../src/main/java/sample/PrecipitationService.java | 36 ++++ .../main/java/sample/PrecipitationServiceImpl.java | 57 ++++++ .../sample/TemperatureHumidityServiceImpl.java | 77 ++++++++ .../src/main/java/sample/TemperatureService.java | 36 ++++ .../src/main/java/sample/model/Location.java | 43 +++++ .../src/main/java/sample/model/Response.java | 45 +++++ .../src/main/webapp/META-INF/MANIFEST.MF | 2 + .../src/main/webapp/WEB-INF/web.composite | 57 ++++++ .../weather-webapp/src/main/webapp/WEB-INF/web.xml | 34 ++++ .../weather-webapp/src/main/webapp/index.html | 114 +++++++++++ 46 files changed, 2530 insertions(+) create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/README create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/pom.xml create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/Country.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryRepository.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryRepositoryImpl.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryService.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryServiceImpl.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/resources/countries.txt create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/META-INF/MANIFEST.MF create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/WEB-INF/web.composite create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/WEB-INF/web.xml create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/index.html create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/README create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/pom.xml create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/java/sample/ChatService.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/java/sample/ChatServiceImpl.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/META-INF/MANIFEST.MF create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/WEB-INF/web.composite create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/WEB-INF/web.xml create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/index.html create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pom.xml create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/README create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/pom.xml create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/Event.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessor.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessorConsumerService.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessorProducerService.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/Producer.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/META-INF/MANIFEST.MF create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/WEB-INF/web.composite create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/WEB-INF/web.xml create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/index.html create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/README create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/pom.xml create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/Helper.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/HumidityService.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/PrecipitationService.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/PrecipitationServiceImpl.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/TemperatureHumidityServiceImpl.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/TemperatureService.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/model/Location.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/model/Response.java create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/META-INF/MANIFEST.MF create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/WEB-INF/web.composite create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/WEB-INF/web.xml create mode 100644 sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/index.html (limited to 'sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket') diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/README b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/README new file mode 100644 index 0000000000..a0b90cdf2f --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/README @@ -0,0 +1,67 @@ +Tuscany - Learning More - Binding Websocket - Autocomplete Webapp +----------------------------------------------------------------- + +This sample demonstrates how Tuscany can expose services via websockets as well +as how to interact with them using Tuscany's javascript API. + +This project contains a service (CountryService) that handles requests asking +for country names starting with a certain prefix. The service implementation +uses a country repository to fetch the necessary data. + +By adding to a service definition, the +Tuscany runtime will start a websocket server listening for requests coming +in for the exposed service at the specified port. If no port is specified, the +runtime will use port 9000 as a default. + +The websocket binding uses embedded Jetty instances as websocket servers. At the +moment, Jetty 8.0.0-M3 is used which has support for the 00, 01, 06 and 07 +versions of the websocket protocol drafts. + +IN ORDER TO RUN THIS SAMPLE SUCCESSFULLY PLEASE CHECK IF YOUR BROWSER SUPPORTS +THE ABOVE WEBSOCKET PROTOCOL VERSIONS AND THAT THE WEBSOCKET SUPPORT IS ENABLED. + +The websocket binding also features a javascript API to simulate SCA in the +browser. In order to use it, the following script has to be included in the +client page: + + +This will inject proxies for all services defined in the composite that are +using binding.websocket. All invocation and connection management is handled +under the hood so in order to invoke a websocket service, the following should +be called: + Tuscany.WebsocketComponentContext...(); + +Given the asynchornous nature of websockets, a function should be defined in +order to handle responses received for a certain service operation. This should +be done as follows: + Tuscany.WebsocketComponentContext....responseHandler = function(response) { + // handle response + }; + +Note that the data exchange is automatically handled by the binding, so the +parameters should have the same structure as the data types defined in the method +definition. Also, the response will have the same data type as the return type of +the service method. Objects are passed over the wire in JSON format. + +Another detail worth mentioning is that the binding will use a single websocket +connection to handle communication between a browser client and all services +defined using binding.websocket on the same port. Requests and responses will get +multiplexed via the same channel and get routed to the appropriate service +implementation, respectively javascript function. + +In order to run the sample, you can execute "mvn jetty:run" which will start a Jetty +instance automatically or use "mvn package" and deploy the resulting war to the +application server of your choice. + +Next, point your browser at + http://localhost:8080/sample-binding-websocket-autocomplete-webapp/ + +You can see how suggestions are being received in real time when characters are +entered in the text field. You can see the persistent websocket connection using +the developer tools provided by your browser. + +The websocket binding is an experimental binding so community feedback is much +appreciated. Feel free to send comments or suggestions on the Apache Tuscany +dev mailing list (dev@tuscany.apache.org). \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/pom.xml b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/pom.xml new file mode 100644 index 0000000000..42356da09d --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/pom.xml @@ -0,0 +1,61 @@ + + + + 4.0.0 + + org.apache.tuscany.sca.samples + tuscany-samples-binding-websocket + 2.0-Beta3-SNAPSHOT + ../pom.xml + + + sample-binding-websocket-autocomplete-webapp + war + 2.0-Beta3-SNAPSHOT + Apache Tuscany SCA Sample binding.websocket Autocomplete Webapp + + + + org.apache.tuscany.sca + tuscany-binding-websocket + 2.0-Beta3-SNAPSHOT + + + org.apache.tuscany.sca + tuscany-base-runtime-pom + 2.0-Beta3-SNAPSHOT + pom + compile + + + + + + + org.mortbay.jetty + maven-jetty-plugin + 6.1.26 + + + + + + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/Country.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/Country.java new file mode 100644 index 0000000000..931e205dd7 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/Country.java @@ -0,0 +1,40 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +import java.io.Serializable; + +public class Country implements Serializable { + + private String name; + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + @Override + public String toString() { + return name; + } + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryRepository.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryRepository.java new file mode 100644 index 0000000000..eb30e6f36a --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryRepository.java @@ -0,0 +1,30 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +import java.util.List; + +import org.oasisopen.sca.annotation.Remotable; + +@Remotable +public interface CountryRepository { + + List findStartingWith(String text); + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryRepositoryImpl.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryRepositoryImpl.java new file mode 100644 index 0000000000..17ce39a10e --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryRepositoryImpl.java @@ -0,0 +1,80 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +import java.io.BufferedReader; +import java.io.FileNotFoundException; +import java.io.IOException; +import java.io.InputStreamReader; +import java.util.ArrayList; +import java.util.List; + +import org.oasisopen.sca.annotation.Constructor; +import org.oasisopen.sca.annotation.EagerInit; +import org.oasisopen.sca.annotation.Init; +import org.oasisopen.sca.annotation.Property; +import org.oasisopen.sca.annotation.Scope; +import org.oasisopen.sca.annotation.Service; + +@EagerInit +@Scope("COMPOSITE") +@Service(CountryRepository.class) +public class CountryRepositoryImpl implements CountryRepository { + + private String fileName; + private List countries; + + @Constructor + public CountryRepositoryImpl(@Property(name = "fileName") String fileName) { + this.fileName = fileName; + countries = new ArrayList(); + } + + @Init + public void start() { + try { + BufferedReader reader = new BufferedReader(new InputStreamReader(getClass().getClassLoader() + .getResourceAsStream(fileName))); + String line; + while ((line = reader.readLine()) != null) { + if (!line.startsWith("#")) { + Country c = new Country(); + c.setName(line); + countries.add(c); + } + } + } catch (FileNotFoundException e) { + e.printStackTrace(); + } catch (IOException e) { + e.printStackTrace(); + } + } + + @Override + public List findStartingWith(String text) { + List result = new ArrayList(); + for (Country c : countries) { + if (c.getName().toLowerCase().startsWith(text.toLowerCase())) { + result.add(c); + } + } + return result; + } + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryService.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryService.java new file mode 100644 index 0000000000..40212d5ba5 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryService.java @@ -0,0 +1,30 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +import java.util.List; + +import org.oasisopen.sca.annotation.Remotable; + +@Remotable +public interface CountryService { + + List getCountriesStartingWith(String text); + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryServiceImpl.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryServiceImpl.java new file mode 100644 index 0000000000..20ceacd5f0 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/java/sample/CountryServiceImpl.java @@ -0,0 +1,36 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +import java.util.List; + +import org.oasisopen.sca.annotation.Reference; +import org.oasisopen.sca.annotation.Service; + +@Service(CountryService.class) +public class CountryServiceImpl implements CountryService { + + @Reference + protected CountryRepository repository; + + @Override + public List getCountriesStartingWith(String text) { + return repository.findStartingWith(text); + } +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/resources/countries.txt b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/resources/countries.txt new file mode 100644 index 0000000000..0ce76f8167 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/resources/countries.txt @@ -0,0 +1,211 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. +Afghanistan +Albania +Algeria +Andorra +Angola +Antigua & Barbuda +Argentina +Armenia +Australia +Austria +Azerbaijan +Bahamas +Bahrain +Bangladesh +Barbados +Belarus +Belgium +Belize +Benin +Bhutan +Bolivia +Bosnia & Herzegovina +Botswana +Brazil +Brunei +Bulgaria +Burkina Faso +Burundi +Cambodia +Cameroon +Canada +Cape Verde +Central African Republic +Chad +Chile +China +Colombia +Comoros +Congo +Congo Democratic Republic of +Costa Rica +Cote d'Ivoire +Croatia +Cuba +Cyprus +Czech Republic +Denmark +Djibouti +Dominica +Dominican Republic +Ecuador +East Timor +Egypt +El Salvador +Equatorial Guinea +Eritrea +Estonia +Ethiopia +Fiji +Finland +France +Gabon +Gambia +Georgia +Germany +Ghana +Greece +Grenada +Guatemala +Guinea +Guinea-Bissau +Guyana +Haiti +Honduras +Hungary +Iceland +India +Indonesia +Iran +Iraq +Ireland +Israel +Italy +Jamaica +Japan +Jordan +Kazakhstan +Kenya +Kiribati +Korea North +Korea South +Kosovo +Kuwait +Kyrgyzstan +Laos +Latvia +Lebanon +Lesotho +Liberia +Libya +Liechtenstein +Lithuania +Luxembourg +Macedonia +Madagascar +Malawi +Malaysia +Maldives +Mali +Malta +Marshall Islands +Mauritania +Mauritius +Mexico +Micronesia +Moldova +Monaco +Mongolia +Montenegro +Morocco +Mozambique +Myanmar (Burma) +Namibia +Nauru +Nepal +The Netherlands +New Zealand +Nicaragua +Niger +Nigeria +Norway +Oman +Pakistan +Palau +Palestinian State* +Panama +Papua New Guinea +Paraguay +Peru +The Philippines +Poland +Portugal +Qatar +Romania +Russia +Rwanda +St. Kitts & Nevis +St. Lucia +St. Vincent & The Grenadines +Samoa +San Marino +Sao Tome & Principe +Saudi Arabia +Senegal +Serbia +Seychelles +Sierra Leone +Singapore +Slovakia +Slovenia +Solomon Islands +Somalia +South Africa +Spain +Sri Lanka +Sudan +Suriname +Swaziland +Sweden +Switzerland +Syria +Taiwan +Tajikistan +Tanzania +Thailand +Togo +Tonga +Trinidad & Tobago +Tunisia +Turkey +Turkmenistan +Tuvalu +Uganda +Ukraine +United Arab Emirates +United Kingdom +United States of America +Uruguay +Uzbekistan +Vanuatu +Vatican City (Holy See) +Venezuela +Yemen +Zambia +Zimbabwe diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/META-INF/MANIFEST.MF b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/META-INF/MANIFEST.MF new file mode 100644 index 0000000000..58630c02ef --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/META-INF/MANIFEST.MF @@ -0,0 +1,2 @@ +Manifest-Version: 1.0 + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/WEB-INF/web.composite b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/WEB-INF/web.composite new file mode 100644 index 0000000000..fc1c177e9b --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/WEB-INF/web.composite @@ -0,0 +1,40 @@ + + + + + + + + + + + + + + + + countries.txt + + + \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/WEB-INF/web.xml b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/WEB-INF/web.xml new file mode 100644 index 0000000000..25b06c457a --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/WEB-INF/web.xml @@ -0,0 +1,34 @@ + + + + Apache Tuscany Stock Comet Sample + + tuscany + org.apache.tuscany.sca.host.webapp.TuscanyServletFilter + true + + + tuscany + /* + + + index.html + + \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/index.html b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/index.html new file mode 100644 index 0000000000..618c772eb6 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/autocomplete-webapp/src/main/webapp/index.html @@ -0,0 +1,64 @@ + + + + Apache Tuscany Websocket Sample + + + + + +

Apache Tuscany Websocket Sample

+

Real-time suggestions

+ + + + + +
Enter a country name
+ +
+
+ + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/README b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/README new file mode 100644 index 0000000000..5a9381f980 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/README @@ -0,0 +1,88 @@ +Tuscany - Learning More - Binding Websocket - Chat Webapp +----------------------------------------------------------------- + +This sample demonstrates how Tuscany can expose services via websockets as well +as how to interact with them using Tuscany's javascript API. It also demonstrates +how to push multiple responses from the server to the client for a single request +using SCA callbacks. + +This project contains a service (ChatService) that handles chat operations like +register and postMessage. Once a client is registered it will receive messages +that are sent to the chat room. + +By adding to a service definition, the +Tuscany runtime will start a websocket server listening for requests coming +in for the exposed service at the specified port. If no port is specified, the +runtime will use port 9000 as a default. + +The websocket binding uses embedded Jetty instances as websocket servers. At the +moment, Jetty 8.0.0-M3 is used which has support for the 00, 01, 06 and 07 +versions of the websocket protocol drafts. + +IN ORDER TO RUN THIS SAMPLE SUCCESSFULLY PLEASE CHECK IF YOUR BROWSER SUPPORTS +THE ABOVE WEBSOCKET PROTOCOL VERSIONS AND THAT THE WEBSOCKET SUPPORT IS ENABLED. + +In order to enable callbacks to push multiple responses, you need to declare the +WebsocketBindingCallback in the service definition as follows: + + + + + + + +The callback object has methods that facilitate sending messages back to the +calling client. It can be injected in the service implementation using the @Callback +annotation. However, the service implementation for this sample has the COMPOSITE +scope so the callback reference has to be obtained from the ComponentContext. + +One requirement that service methods have to meet to enable multiple response +support is that they have to be annotated with @OneWay to enable non-blocking +support. Without it, methods are treated synchronously sending a single response +which is the object returned by the method call. + +The websocket binding also features a javascript API to simulate SCA in the +browser. In order to use it, the following script has to be included in the +client page: + + +This will inject proxies for all services defined in the composite that are +using binding.websocket. All invocation and connection management is handled +under the hood so in order to invoke a websocket service, the following should +be called: + Tuscany.WebsocketComponentContext...(); + +Given the asynchornous nature of websockets, a function should be defined in +order to handle responses received for a certain service operation. This should +be done as follows: + Tuscany.WebsocketComponentContext....responseHandler = function(response) { + // handle response + }; + +Note that the data exchange is automatically handled by the binding, so parameters +will be mapped to the data types defined in the method definition. Also, the response +will have the same data type as the server side object used to wrap the response. +Objects are passed over the wire in JSON format. + +Another detail worth mentioning is that the binding will use a single persistent +websocket connection to handle communication between a browser client and all services +defined using binding.websocket on the same port. Requests and responses will get +multiplexed via the same channel and get routed to the appropriate service +implementation, respectively javascript function. + +In order to run the sample, you can execute "mvn jetty:run" which will start a Jetty +instance automatically or use "mvn package" and deploy the resulting war to the +application server of your choice. + +Next, point your browser at + http://localhost:8080/sample-binding-websocket-chat-webapp/ + +You can now chat using multiple tabs or browsers. You can see the persistent websocket +connection using the developer tools provided by your browser. + +The websocket binding is an experimental binding so community feedback is much +appreciated. Feel free to send comments or suggestions on the Apache Tuscany +dev mailing list (dev@tuscany.apache.org). \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/pom.xml b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/pom.xml new file mode 100644 index 0000000000..04dee5ac19 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/pom.xml @@ -0,0 +1,67 @@ + + + + 4.0.0 + + org.apache.tuscany.sca.samples + tuscany-samples-binding-websocket + 2.0-Beta3-SNAPSHOT + ../pom.xml + + + sample-binding-websocket-chat-webapp + war + 2.0-Beta3-SNAPSHOT + Apache Tuscany SCA Sample binding.websocket Chat Webapp + + + + org.apache.tuscany.sca + tuscany-binding-websocket + 2.0-Beta3-SNAPSHOT + + + org.apache.tuscany.sca + tuscany-base-runtime-pom + 2.0-Beta3-SNAPSHOT + pom + compile + + + com.google.guava + guava + r09 + jar + compile + + + + + + + org.mortbay.jetty + maven-jetty-plugin + 6.1.26 + + + + + + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/java/sample/ChatService.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/java/sample/ChatService.java new file mode 100644 index 0000000000..7ec6a547a9 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/java/sample/ChatService.java @@ -0,0 +1,36 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketBindingCallback; +import org.oasisopen.sca.annotation.Callback; +import org.oasisopen.sca.annotation.OneWay; +import org.oasisopen.sca.annotation.Remotable; + +@Callback(WebsocketBindingCallback.class) +@Remotable +public interface ChatService { + + @OneWay + void register(); + + @OneWay + void postMessage(String user, String message); + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/java/sample/ChatServiceImpl.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/java/sample/ChatServiceImpl.java new file mode 100644 index 0000000000..6fd4455ba9 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/java/sample/ChatServiceImpl.java @@ -0,0 +1,58 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +import java.util.ArrayList; +import java.util.concurrent.CopyOnWriteArrayList; + +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketBindingCallback; +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketStatus; +import org.oasisopen.sca.ComponentContext; +import org.oasisopen.sca.annotation.Context; +import org.oasisopen.sca.annotation.Scope; +import org.oasisopen.sca.annotation.Service; + +@Service(ChatService.class) +@Scope("COMPOSITE") +public class ChatServiceImpl implements ChatService { + + @Context + protected ComponentContext context; + + private CopyOnWriteArrayList clients = new CopyOnWriteArrayList(); + + @Override + public void postMessage(String user, String message) { + for (WebsocketBindingCallback callback : new ArrayList(clients)) { + WebsocketStatus status = callback.sendMessage(user + ": " + message); + if (status == WebsocketStatus.CLOSED) { + clients.remove(callback); + } + } + } + + @Override + public void register() { + // saving the callback object during register() method so it will push + // data back to the client + // using the callback method defined for the register operation in the + // js when used + clients.add(context.getRequestContext(). getCallback()); + } +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/META-INF/MANIFEST.MF b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/META-INF/MANIFEST.MF new file mode 100644 index 0000000000..58630c02ef --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/META-INF/MANIFEST.MF @@ -0,0 +1,2 @@ +Manifest-Version: 1.0 + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/WEB-INF/web.composite b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/WEB-INF/web.composite new file mode 100644 index 0000000000..4e83fee9e8 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/WEB-INF/web.composite @@ -0,0 +1,37 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/WEB-INF/web.xml b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/WEB-INF/web.xml new file mode 100644 index 0000000000..25b06c457a --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/WEB-INF/web.xml @@ -0,0 +1,34 @@ + + + + Apache Tuscany Stock Comet Sample + + tuscany + org.apache.tuscany.sca.host.webapp.TuscanyServletFilter + true + + + tuscany + /* + + + index.html + + \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/index.html b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/index.html new file mode 100644 index 0000000000..2309be8533 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/chat-webapp/src/main/webapp/index.html @@ -0,0 +1,99 @@ + + + + Apache Tuscany Websocket Sample + + + + + +

Apache Tuscany Comet Sample

+

Chat

+

+

+ + + + + + +
Nickname
+
+
+

Server notifications

+ + + + + + +
+
+ + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pom.xml b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pom.xml new file mode 100644 index 0000000000..28f05a4fb9 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pom.xml @@ -0,0 +1,47 @@ + + + + 4.0.0 + + org.apache.tuscany.sca.samples + tuscany-samples-learning-more + 2.0-Beta3-SNAPSHOT + ../pom.xml + + + tuscany-samples-binding-websocket + pom + Apache Tuscany SCA Sample binding.websocket + + + + default + + true + + + autocomplete-webapp + weather-webapp + chat-webapp + pubsub-webapp + + + + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/README b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/README new file mode 100644 index 0000000000..1ec7d6b807 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/README @@ -0,0 +1,93 @@ +Tuscany - Learning More - Binding Websocket - PubSub Webapp +----------------------------------------------------------------- + +This sample demonstrates how Tuscany can expose services via websockets as well +as how to interact with them using Tuscany's javascript API. It also demonstrates +how to push multiple responses from the server to the client for a single request +using SCA callbacks. + +This project contains a component that registers browser clients' interest in a +certain event type. When an event of that type comes in, it notifies all registered +clients. The event processor exposes a service via the websocket binding which +enables server push to clients. Note that Tuscany 2.x doesn't have any conversational +support so this has to be handled at application level by passing ids back and forth +between the client and the server. + +By adding to a service definition, the +Tuscany runtime will start a websocket server listening for requests coming +in for the exposed service at the specified port. If no port is specified, the +runtime will use port 9000 as a default. + +The websocket binding uses embedded Jetty instances as websocket servers. At the +moment, Jetty 8.0.0-M3 is used which has support for the 00, 01, 06 and 07 +versions of the websocket protocol drafts. + +IN ORDER TO RUN THIS SAMPLE SUCCESSFULLY PLEASE CHECK IF YOUR BROWSER SUPPORTS +THE ABOVE WEBSOCKET PROTOCOL VERSIONS AND THAT THE WEBSOCKET SUPPORT IS ENABLED. + +In order to enable callbacks to push multiple responses, you need to declare the +WebsocketBindingCallback in the service definition as follows: + + + + + + + +The callback object has methods that facilitate sending messages back to the +calling client. It can be injected in the service implementation using the @Callback +annotation. However, the service implementation for this sample has the COMPOSITE +scope so the callback reference has to be obtained from the ComponentContext. + +One requirement that service methods have to meet to enable multiple response +support is that they have to be annotated with @OneWay to enable non-blocking +support. Without it, methods are treated synchronously sending a single response +which is the object returned by the method call. + +The websocket binding also features a javascript API to simulate SCA in the +browser. In order to use it, the following script has to be included in the +client page: + + +This will inject proxies for all services defined in the composite that are +using binding.websocket. All invocation and connection management is handled +under the hood so in order to invoke a websocket service, the following should +be called: + Tuscany.WebsocketComponentContext...(); + +Given the asynchornous nature of websockets, a function should be defined in +order to handle responses received for a certain service operation. This should +be done as follows: + Tuscany.WebsocketComponentContext....responseHandler = function(response) { + // handle response + }; + +Note that the data exchange is automatically handled by the binding, so parameters +will be mapped to the data types defined in the method definition. Also, the response +will have the same data type as the server side object used to wrap the response. +Objects are passed over the wire in JSON format. + +Another detail worth mentioning is that the binding will use a single persistent +websocket connection to handle communication between a browser client and all services +defined using binding.websocket on the same port. Requests and responses will get +multiplexed via the same channel and get routed to the appropriate service +implementation, respectively javascript function. + +In order to run the sample, you can execute "mvn jetty:run" which will start a Jetty +instance automatically or use "mvn package" and deploy the resulting war to the +application server of your choice. + +Next, point your browser at + http://localhost:8080/sample-binding-websocket-chat-webapp/ + +You can now register or unregister for any of a number of events. When an event is fired +on the server side, the browser client will receive a notification which will be displayed +in the page. You can see the persistent websocket connection using the developer tools +provided by your browser. + +The websocket binding is an experimental binding so community feedback is much +appreciated. Feel free to send comments or suggestions on the Apache Tuscany +dev mailing list (dev@tuscany.apache.org). \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/pom.xml b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/pom.xml new file mode 100644 index 0000000000..3c6c7e0ebd --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/pom.xml @@ -0,0 +1,67 @@ + + + + 4.0.0 + + org.apache.tuscany.sca.samples + tuscany-samples-binding-websocket + 2.0-Beta3-SNAPSHOT + ../pom.xml + + + sample-binding-websocket-pubsub-webapp + war + 2.0-Beta3-SNAPSHOT + Apache Tuscany SCA Sample binding.websocket PubSub Webapp + + + + org.apache.tuscany.sca + tuscany-binding-websocket + 2.0-Beta3-SNAPSHOT + + + org.apache.tuscany.sca + tuscany-base-runtime-pom + 2.0-Beta3-SNAPSHOT + pom + compile + + + com.google.guava + guava + r09 + jar + compile + + + + + + + org.mortbay.jetty + maven-jetty-plugin + 6.1.26 + + + + + + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/Event.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/Event.java new file mode 100644 index 0000000000..c9d9eb54c4 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/Event.java @@ -0,0 +1,51 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +public class Event { + + private String id; + private String name; + private String data; + + public String getId() { + return id; + } + + public void setId(String id) { + this.id = id; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getData() { + return data; + } + + public void setData(String data) { + this.data = data; + } + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessor.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessor.java new file mode 100644 index 0000000000..d289b361cf --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessor.java @@ -0,0 +1,104 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample; + +import java.util.ArrayList; +import java.util.Date; +import java.util.List; +import java.util.UUID; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; + +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketBindingCallback; +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketStatus; +import org.oasisopen.sca.ComponentContext; +import org.oasisopen.sca.annotation.Context; +import org.oasisopen.sca.annotation.Destroy; +import org.oasisopen.sca.annotation.Scope; +import org.oasisopen.sca.annotation.Service; + +import com.google.common.collect.HashMultimap; +import com.google.common.collect.Multimap; +import com.google.common.collect.Multimaps; + +@Service({ EventProcessorConsumerService.class, EventProcessorProducerService.class }) +@Scope("COMPOSITE") +public class EventProcessor implements EventProcessorConsumerService, EventProcessorProducerService { + + @Context + protected ComponentContext componentContext; + + private ConcurrentMap clients = new ConcurrentHashMap(); + private Multimap eventListeners = Multimaps.synchronizedMultimap(HashMultimap. create()); + + @Override + public void onEvent(String eventName, String eventData) { + List destinations = new ArrayList(); + synchronized (eventListeners) { + destinations.addAll(eventListeners.get(eventName)); + } + Event event = new Event(); + event.setName(eventName); + event.setData(eventData); + for (String registrationId : destinations) { + WebsocketBindingCallback client = clients.get(registrationId); + if (client == null) { + // client has unregistered from this event + synchronized (eventListeners) { + eventListeners.remove(eventName, registrationId); + } + } else { + WebsocketStatus status = client.sendMessage(event); + if (status == WebsocketStatus.CLOSED) { + unregister(registrationId); + } + } + } + } + + @Override + public void register(String eventName) { + String registrationId = UUID.randomUUID().toString(); + WebsocketBindingCallback callback = componentContext.getRequestContext().getCallback(); + clients.put(registrationId, callback); + synchronized (eventListeners) { + eventListeners.put(eventName, registrationId); + } + Event event = new Event(); + event.setId(registrationId); + event.setName(eventName); + event.setData(new Date().toString()); + callback.sendMessage(event); + } + + @Override + public void unregister(String registrationId) { + clients.remove(registrationId); + // unregistration from eventListeners done during onEvent + } + + @Destroy + public void shutdown() { + clients.clear(); + eventListeners.clear(); + clients = null; + eventListeners = null; + } +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessorConsumerService.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessorConsumerService.java new file mode 100644 index 0000000000..aa9156b088 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessorConsumerService.java @@ -0,0 +1,37 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample; + +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketBindingCallback; +import org.oasisopen.sca.annotation.Callback; +import org.oasisopen.sca.annotation.OneWay; +import org.oasisopen.sca.annotation.Remotable; + +@Callback(WebsocketBindingCallback.class) +@Remotable +public interface EventProcessorConsumerService { + + @OneWay + void register(String eventName); + + @OneWay + void unregister(String registrationId); + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessorProducerService.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessorProducerService.java new file mode 100644 index 0000000000..a9c80cc697 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/EventProcessorProducerService.java @@ -0,0 +1,28 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +import org.oasisopen.sca.annotation.Remotable; + +@Remotable +public interface EventProcessorProducerService { + + void onEvent(String eventName, String eventData); + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/Producer.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/Producer.java new file mode 100644 index 0000000000..88a214d843 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/java/sample/Producer.java @@ -0,0 +1,75 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package sample; + +import java.util.Date; +import java.util.Timer; +import java.util.TimerTask; + +import org.oasisopen.sca.annotation.Constructor; +import org.oasisopen.sca.annotation.Destroy; +import org.oasisopen.sca.annotation.EagerInit; +import org.oasisopen.sca.annotation.Init; +import org.oasisopen.sca.annotation.Property; +import org.oasisopen.sca.annotation.Reference; +import org.oasisopen.sca.annotation.Scope; + +@EagerInit +@Scope("COMPOSITE") +public class Producer { + + @Reference + protected EventProcessorProducerService eventProcessor; + + private String eventName; + private long frequency; + + private Timer timer = new Timer(); + private Object lock = new Object(); + + @Constructor + public Producer(@Property(name = "eventName") String eventName, @Property(name = "frequency") long frequency) { + System.out.println("Producer: In Constructor with eventName=" + eventName + " and frequency=" + frequency); + this.eventName = eventName; + this.frequency = frequency; + } + + @Init + public void start() { + System.out.println("Producer: In Init..."); + timer.schedule(new TimerTask() { + + @Override + public void run() { + synchronized (lock) { + eventProcessor.onEvent(Producer.this.eventName, "Event @ " + new Date()); + } + } + }, 0L, this.frequency); + } + + @Destroy + public void stop() { + synchronized (lock) { + timer.cancel(); + } + timer = null; + } + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/META-INF/MANIFEST.MF b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/META-INF/MANIFEST.MF new file mode 100644 index 0000000000..58630c02ef --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/META-INF/MANIFEST.MF @@ -0,0 +1,2 @@ +Manifest-Version: 1.0 + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/WEB-INF/web.composite b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/WEB-INF/web.composite new file mode 100644 index 0000000000..743e2b418e --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/WEB-INF/web.composite @@ -0,0 +1,60 @@ + + + + + + + + + + + + + + + + + + + + + + SLOW + 6000 + + + + + + MODERATE + 3000 + + + + + + FAST + 1000 + + + \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/WEB-INF/web.xml b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/WEB-INF/web.xml new file mode 100644 index 0000000000..25b06c457a --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/WEB-INF/web.xml @@ -0,0 +1,34 @@ + + + + Apache Tuscany Stock Comet Sample + + tuscany + org.apache.tuscany.sca.host.webapp.TuscanyServletFilter + true + + + tuscany + /* + + + index.html + + \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/index.html b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/index.html new file mode 100644 index 0000000000..bfacf28236 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/pubsub-webapp/src/main/webapp/index.html @@ -0,0 +1,96 @@ + + + + Apache Tuscany Websocket Sample + + + + + +

Apache Tuscany Websocket Sample

+

PubSub for FAST, MODERATE and SLOW events

+

+ + + + + + + + + + + +
Event name + +
Event name + +
+

Server notifications

+ + + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/README b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/README new file mode 100644 index 0000000000..eb195bc4dc --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/README @@ -0,0 +1,89 @@ +Tuscany - Learning More - Binding Websocket - Weather Monitor Webapp +----------------------------------------------------------------- + +This sample demonstrates how Tuscany can expose services via websockets as well +as how to interact with them using Tuscany's javascript API. It also demonstrates +how to push multiple responses for a single request using SCA callbacks. + +This project contains multiple services that once called will push notifications +to the client regarding certain weather parameters according to the location of +the user. Of course, the service implementation is a mock that generates random +numbers at a fixed interval of time as weather parameters. + +By adding to a service definition, the +Tuscany runtime will start a websocket server listening for requests coming +in for the exposed service at the specified port. If no port is specified, the +runtime will use port 9000 as a default. + +The websocket binding uses embedded Jetty instances as websocket servers. At the +moment, Jetty 8.0.0-M3 is used which has support for the 00, 01, 06 and 07 +versions of the websocket protocol drafts. + +IN ORDER TO RUN THIS SAMPLE SUCCESSFULLY PLEASE CHECK IF YOUR BROWSER SUPPORTS +THE ABOVE WEBSOCKET PROTOCOL VERSIONS AND THAT THE WEBSOCKET SUPPORT IS ENABLED. + +In order to enable callbacks to push multiple responses, you need to declare the +WebsocketBindingCallback in the service definition as follows: + + + + + + + +The callback object has methods that facilitate sending messages back to the +calling client. It can be injected in the service implementation using the @Callback +annotation. + +One requirement that service methods have to meet to enable multiple response +support is that they have to be annotated with @OneWay to enable non-blocking +support. Without it, methods are treated synchronously sending a single response +which is the object returned by the method call. + +The websocket binding also features a javascript API to simulate SCA in the +browser. In order to use it, the following script has to be included in the +client page: + + +This will inject proxies for all services defined in the composite that are +using binding.websocket. All invocation and connection management is handled +under the hood so in order to invoke a websocket service, the following should +be called: + Tuscany.WebsocketComponentContext...(); + +Given the asynchornous nature of websockets, a function should be defined in +order to handle responses received for a certain service operation. This should +be done as follows: + Tuscany.WebsocketComponentContext....responseHandler = function(response) { + // handle response + }; + +Note that the data exchange is automatically handled by the binding, so parameters +will be mapped to the data types defined in the method definition. Also, the response +will have the same data type as the server side object used to wrap the response. +Objects are passed over the wire in JSON format. + +Another detail worth mentioning is that the binding will use a single persistent +websocket connection to handle communication between a browser client and all services +defined using binding.websocket on the same port. Requests and responses will get +multiplexed via the same channel and get routed to the appropriate service +implementation, respectively javascript function. + +In order to run the sample, you can execute "mvn jetty:run" which will start a Jetty +instance automatically or use "mvn package" and deploy the resulting war to the +application server of your choice. + +Next, point your browser at + http://localhost:8080/sample-binding-websocket-weather-webapp/ + +You can now set a location and register for various weather parameters. Notifications +will be pushed to the browser when weather parameters change. You can see the persistent +websocket connection handling all the communication using the developer tools provided +by your browser. + +The websocket binding is an experimental binding so community feedback is much +appreciated. Feel free to send comments or suggestions on the Apache Tuscany +dev mailing list (dev@tuscany.apache.org). \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/pom.xml b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/pom.xml new file mode 100644 index 0000000000..a130750acb --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/pom.xml @@ -0,0 +1,60 @@ + + + + 4.0.0 + + org.apache.tuscany.sca.samples + tuscany-samples-binding-websocket + 2.0-Beta3-SNAPSHOT + ../pom.xml + + + sample-binding-websocket-weather-webapp + war + 2.0-Beta3-SNAPSHOT + Apache Tuscany SCA Sample binding.websocket Weather Monitor Webapp + + + + org.apache.tuscany.sca + tuscany-binding-websocket + 2.0-Beta3-SNAPSHOT + + + org.apache.tuscany.sca + tuscany-base-runtime-pom + 2.0-Beta3-SNAPSHOT + pom + compile + + + + + + + org.mortbay.jetty + maven-jetty-plugin + 6.1.26 + + + + + + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/Helper.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/Helper.java new file mode 100644 index 0000000000..10b46cc55f --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/Helper.java @@ -0,0 +1,34 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample; + +import java.util.Date; +import java.util.Random; + +public final class Helper { + + public static int randomInt(final int max) { + return (new Random(new Date().getTime()).nextInt(100)); + } + + private Helper() { + } + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/HumidityService.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/HumidityService.java new file mode 100644 index 0000000000..7b38a098ac --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/HumidityService.java @@ -0,0 +1,36 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample; + +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketBindingCallback; +import org.oasisopen.sca.annotation.Callback; +import org.oasisopen.sca.annotation.OneWay; +import org.oasisopen.sca.annotation.Remotable; + +import sample.model.Location; + +@Remotable +@Callback(WebsocketBindingCallback.class) +public interface HumidityService { + + @OneWay + void getHumidity(Location location); + +} \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/PrecipitationService.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/PrecipitationService.java new file mode 100644 index 0000000000..14fcdfd8b3 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/PrecipitationService.java @@ -0,0 +1,36 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample; + +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketBindingCallback; +import org.oasisopen.sca.annotation.Callback; +import org.oasisopen.sca.annotation.OneWay; +import org.oasisopen.sca.annotation.Remotable; + +import sample.model.Location; + +@Remotable +@Callback(WebsocketBindingCallback.class) +public interface PrecipitationService { + + @OneWay + void getPrecipitation(Location location); + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/PrecipitationServiceImpl.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/PrecipitationServiceImpl.java new file mode 100644 index 0000000000..5d9575686b --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/PrecipitationServiceImpl.java @@ -0,0 +1,57 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample; + +import java.util.Date; +import java.util.Timer; +import java.util.TimerTask; + +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketBindingCallback; +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketStatus; +import org.oasisopen.sca.annotation.Callback; +import org.oasisopen.sca.annotation.Service; + +import sample.model.Location; +import sample.model.Response; + +@Service(PrecipitationService.class) +public class PrecipitationServiceImpl implements PrecipitationService { + + @Callback + protected WebsocketBindingCallback client; + + @Override + public void getPrecipitation(final Location location) { + new Timer().scheduleAtFixedRate(new TimerTask() { + + @Override + public void run() { + Response response = new Response(); + response.setDate(new Date()); + response.setData(Helper.randomInt(100) + "%"); + WebsocketStatus status = client.sendMessage(response); + if (status == WebsocketStatus.CLOSED) { + System.out.println("Client disconnected from PrecipitationService."); + this.cancel(); + } + } + }, 0L, 1000L); + } +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/TemperatureHumidityServiceImpl.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/TemperatureHumidityServiceImpl.java new file mode 100644 index 0000000000..e505167b3c --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/TemperatureHumidityServiceImpl.java @@ -0,0 +1,77 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample; + +import java.util.Date; +import java.util.Timer; +import java.util.TimerTask; + +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketBindingCallback; +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketStatus; +import org.oasisopen.sca.annotation.Callback; +import org.oasisopen.sca.annotation.Service; + +import sample.model.Location; +import sample.model.Response; + +@Service({ TemperatureService.class, HumidityService.class }) +public class TemperatureHumidityServiceImpl implements TemperatureService, HumidityService { + + @Callback + protected WebsocketBindingCallback callback; + + @Override + public void getHumidity(final Location location) { + new Timer().scheduleAtFixedRate(new TimerTask() { + + @Override + public void run() { + final Response response = new Response(); + response.setDate(new Date()); + response.setData(Helper.randomInt(90) + "%"); + WebsocketStatus status = callback.sendMessage(response); + if (status == WebsocketStatus.CLOSED) { + System.out.println("Client disconnected from HumidityService."); + this.cancel(); + } + } + }, 0L, 5000L); + } + + @Override + public void getTemperature(final Location location) { + new Timer().scheduleAtFixedRate(new TimerTask() { + + @Override + public void run() { + final Response response = new Response(); + response.setDate(new Date()); + final String data = "" + Helper.randomInt(40); + response.setData(data); + WebsocketStatus status = callback.sendMessage(response); + if (status == WebsocketStatus.CLOSED) { + System.out.println("Client disconnected from TemperatureService."); + this.cancel(); + } + } + }, 0L, 3000L); + } + +} \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/TemperatureService.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/TemperatureService.java new file mode 100644 index 0000000000..67318c67c7 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/TemperatureService.java @@ -0,0 +1,36 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample; + +import org.apache.tuscany.sca.binding.websocket.runtime.WebsocketBindingCallback; +import org.oasisopen.sca.annotation.Callback; +import org.oasisopen.sca.annotation.OneWay; +import org.oasisopen.sca.annotation.Remotable; + +import sample.model.Location; + +@Remotable +@Callback(WebsocketBindingCallback.class) +public interface TemperatureService { + + @OneWay + void getTemperature(Location location); + +} \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/model/Location.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/model/Location.java new file mode 100644 index 0000000000..67edc140f9 --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/model/Location.java @@ -0,0 +1,43 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample.model; + +public class Location { + + private String city; + private String country; + + public String getCity() { + return this.city; + } + + public void setCity(final String city) { + this.city = city; + } + + public String getCountry() { + return this.country; + } + + public void setCountry(final String country) { + this.country = country; + } + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/model/Response.java b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/model/Response.java new file mode 100644 index 0000000000..462af6d8ab --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/java/sample/model/Response.java @@ -0,0 +1,45 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package sample.model; + +import java.util.Date; + +public class Response { + + private Date date; + private String data; + + public Date getDate() { + return this.date; + } + + public void setDate(final Date date) { + this.date = date; + } + + public String getData() { + return this.data; + } + + public void setData(final String data) { + this.data = data; + } + +} diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/META-INF/MANIFEST.MF b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/META-INF/MANIFEST.MF new file mode 100644 index 0000000000..58630c02ef --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/META-INF/MANIFEST.MF @@ -0,0 +1,2 @@ +Manifest-Version: 1.0 + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/WEB-INF/web.composite b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/WEB-INF/web.composite new file mode 100644 index 0000000000..edf53fa76c --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/WEB-INF/web.composite @@ -0,0 +1,57 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/WEB-INF/web.xml b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/WEB-INF/web.xml new file mode 100644 index 0000000000..25b06c457a --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/WEB-INF/web.xml @@ -0,0 +1,34 @@ + + + + Apache Tuscany Stock Comet Sample + + tuscany + org.apache.tuscany.sca.host.webapp.TuscanyServletFilter + true + + + tuscany + /* + + + index.html + + \ No newline at end of file diff --git a/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/index.html b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/index.html new file mode 100644 index 0000000000..5d5ae2c1ca --- /dev/null +++ b/sca-java-2.x/branches/2.0-Beta3/samples/learning-more/binding-websocket/weather-webapp/src/main/webapp/index.html @@ -0,0 +1,114 @@ + + + + Apache Tuscany Websocket Sample + + + + + + + + -- cgit v1.2.3