- * Remote nodes should always be started with special configuration file which - * enables P2P class loading: {@code 'ignite.{sh|bat} examples/config/example-ignite.xml'}. - *
- * Alternatively you can run {@link ExampleNodeStartup} in another JVM which will - * start node with {@code examples/config/example-ignite.xml} configuration. - */ -object ScalarCacheEntryProcessorExample extends App { - /** Configuration file name. */ - private val CONFIG = "examples/config/example-ignite.xml" - - /** Name of cache. */ - private val CACHE_NAME = ScalarCacheEntryProcessorExample.getClass.getSimpleName - - /** Number of keys. */ - private val KEY_CNT = 20 - - /** Type alias. */ - type Cache = IgniteCache[String, Int] - - /* - * Note that in case of `LOCAL` configuration, - * since there is no distribution, values may come back as `nulls`. - */ - scalar(CONFIG) { - println() - println(">>> Entry processor example started.") - - val cache = createCache$[String, Int](CACHE_NAME) - - try { - populateEntriesWithInvoke(cache) - - checkEntriesInCache(cache) - - incrementEntriesWithInvoke(cache) - - checkEntriesInCache(cache) - } - finally { - cache.destroy() - } - } - - private def checkEntriesInCache(cache: Cache) { - println() - println(">>> Entries in the cache.") - - (0 until KEY_CNT).foreach(i => - println("Entry: " + cache.get(i.toString))) - } - - /** - * Runs jobs on primary nodes with {@link IgniteCache#invoke(Object, CacheEntryProcessor, Object...)} to create - * entries when they don't exist. - * - * @param cache Cache to populate. - */ - private def populateEntriesWithInvoke(cache: Cache) { - (0 until KEY_CNT).foreach(i => - cache.invoke(i.toString, - new EntryProcessor[String, Int, Object]() { - override def process(e: MutableEntry[String, Int], args: AnyRef*): Object = { - if (e.getValue == null) - e.setValue(i) - - null - } - } - ) - ) - } - - /** - * Runs jobs on primary nodes with {@link IgniteCache#invoke(Object, CacheEntryProcessor, Object...)} to increment - * entries values. - * - * @param cache Cache to populate. - */ - private def incrementEntriesWithInvoke(cache: Cache) { - println() - println(">>> Incrementing values.") - - (0 until KEY_CNT).foreach(i => - cache.invoke(i.toString, - new EntryProcessor[String, Int, Object]() { - override def process(e: MutableEntry[String, Int], args: AnyRef*): Object = { - Option(e.getValue) foreach (v => e.setValue(v + 1)) - - null - } - } - ) - ) - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCacheExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCacheExample.scala deleted file mode 100644 index 32afab228a312..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCacheExample.scala +++ /dev/null @@ -1,128 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import org.apache.ignite.events.Event -import org.apache.ignite.events.EventType._ -import org.apache.ignite.lang.IgnitePredicate -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ - -import scala.collection.JavaConversions._ - -/** - * Demonstrates basic In-Memory Data Ignite Cluster operations with Scalar. - *
- * Remote nodes should always be started with special configuration file which - * enables P2P class loading: `'ignite.{sh|bat} examples/config/example-ignite.xml'`. - * - * Alternatively you can run `ExampleNodeStartup` in another JVM which will - * start node with `examples/config/example-ignite.xml` configuration. - */ -object ScalarCacheExample extends App { - /** Configuration file name. */ - private val CONFIG = "examples/config/example-ignite.xml" - - /** Name of cache specified in spring configuration. */ - private val NAME = ScalarCacheExample.getClass.getSimpleName - - scalar(CONFIG) { - val cache = createCache$[String, Int](NAME) - - try { - registerListener() - - basicOperations() - } - catch { - case e: Throwable => - e.printStackTrace(); - } - finally { - cache.destroy() - } - } - - /** - * Demos basic cache operations. - */ - def basicOperations() { - val c = cache$[String, Int](NAME).get - - // Add few values. - c += (1.toString -> 1) - c += (2.toString -> 2) - - // Update values. - c += (1.toString -> 11) - c += (2.toString -> 22) - - c += (1.toString -> 31) - c += (2.toString -> 32) - c += ((2.toString, 32)) - - // Remove couple of keys (if any). - c -= (11.toString, 22.toString) - - // Put one more value. - c += (3.toString -> 11) - - try { - c.opt(44.toString) match { - case Some(v) => sys.error("Should never happen.") - case _ => println("Correct") - } - } - catch { - case e: Throwable => - e.printStackTrace() - } - - - // Print all values. - println("Print all values.") - c.iterator() foreach println - } - - /** - * This method will register listener for cache events on all nodes, - * so we can actually see what happens underneath locally and remotely. - */ - def registerListener() { - val g = ignite$ - - g *< (() => { - val lsnr = new IgnitePredicate[Event] { - override def apply(e: Event): Boolean = { - println(e.shortDisplay) - - true - } - } - - if (g.cluster().nodeLocalMap[String, AnyRef].putIfAbsent("lsnr", lsnr) == null) { - g.events().localListen(lsnr, - EVT_CACHE_OBJECT_PUT, - EVT_CACHE_OBJECT_READ, - EVT_CACHE_OBJECT_REMOVED) - - println("Listener is registered.") - } - }, null) - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCachePopularNumbersExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCachePopularNumbersExample.scala deleted file mode 100644 index d113297ac4d54..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCachePopularNumbersExample.scala +++ /dev/null @@ -1,151 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import java.lang.{Integer => JavaInt, Long => JavaLong} -import java.util -import java.util.Map.Entry -import java.util.Timer -import javax.cache.processor.{EntryProcessor, MutableEntry} - -import org.apache.ignite.cache.query.SqlFieldsQuery -import org.apache.ignite.internal.util.scala.impl -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ -import org.apache.ignite.stream.StreamReceiver -import org.apache.ignite.{IgniteCache, IgniteException} - -import scala.collection.JavaConversions._ -import scala.util.Random - -/** - * Real time popular number counter. - * - * Remote nodes should always be started with special configuration file which - * enables P2P class loading: `'ignite.{sh|bat} examples/config/example-ignite.xml'`. - * - * Alternatively you can run `ExampleNodeStartup` in another JVM which will - * start node with `examples/config/example-ignite.xml` configuration. - * - * The counts are kept in cache on all remote nodes. Top `10` counts from each node are then grabbed to produce - * an overall top `10` list within the ignite. - */ -object ScalarCachePopularNumbersExample extends App { - /** Configuration file name. */ - private val CONFIG = "examples/config/example-ignite.xml" - - /** Cache name. */ - private final val NAME = ScalarCachePopularNumbersExample.getClass.getSimpleName - - /** Count of most popular numbers to retrieve from cluster. */ - private final val POPULAR_NUMBERS_CNT = 10 - - /** Random number generator. */ - private final val RAND = new Random() - - /** Range within which to generate numbers. */ - private final val RANGE = 1000 - - /** Count of total numbers to generate. */ - private final val CNT = 1000000 - - scalar(CONFIG) { - val cache = createCache$[JavaInt, JavaLong](NAME, indexedTypes = Seq(classOf[JavaInt], classOf[JavaLong])) - - println() - println(">>> Cache popular numbers example started.") - - try { - val prj = ignite$.cluster().forCacheNodes(NAME) - - if (prj.nodes().isEmpty) - println("Ignite does not have cache configured: " + NAME) - else { - val popularNumbersQryTimer = new Timer("numbers-query-worker") - - try { - // Schedule queries to run every 3 seconds during populates cache phase. - popularNumbersQryTimer.schedule(timerTask(query(POPULAR_NUMBERS_CNT)), 3000, 3000) - - streamData() - - // Force one more run to get final counts. - query(POPULAR_NUMBERS_CNT) - } - finally { - popularNumbersQryTimer.cancel() - } - } - } - finally { - cache.destroy() - } - } - - /** - * Populates cache in real time with numbers and keeps count for every number. - * @throws IgniteException If failed. - */ - @throws[IgniteException] - def streamData() { - // Set larger per-node buffer size since our state is relatively small. - // Reduce parallel operations since we running the whole ignite cluster locally under heavy load. - val smtr = dataStreamer$[JavaInt, JavaLong](NAME, 2048) - - smtr.receiver(new IncrementingUpdater()) - - (0 until CNT) foreach (_ => smtr.addData(RAND.nextInt(RANGE), 1L)) - - smtr.close(false) - } - - /** - * Queries a subset of most popular numbers from in-memory data ignite cluster. - * - * @param cnt Number of most popular numbers to return. - */ - def query(cnt: Int) { - val results = cache$[JavaInt, JavaLong](NAME).get - .query(new SqlFieldsQuery("select _key, _val from Long order by _val desc, _key limit " + cnt)) - .getAll - - results.foreach(res => println(res.get(0) + "=" + res.get(1))) - - println("------------------") - } - - /** - * Increments value for key. - */ - private class IncrementingUpdater extends StreamReceiver[JavaInt, JavaLong] { - private[this] final val INC = new EntryProcessor[JavaInt, JavaLong, Object]() { - /** Process entries to increase value by entry key. */ - override def process(e: MutableEntry[JavaInt, JavaLong], args: AnyRef*): Object = { - e.setValue(Option(e.getValue) - .map(l => JavaLong.valueOf(l + 1)) - .getOrElse(JavaLong.valueOf(1L))) - - null - } - } - - @impl def receive(cache: IgniteCache[JavaInt, JavaLong], entries: util.Collection[Entry[JavaInt, JavaLong]]) { - entries.foreach(entry => cache.invoke(entry.getKey, INC)) - } - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCacheQueryExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCacheQueryExample.scala deleted file mode 100644 index 6d6c8c34af96c..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCacheQueryExample.scala +++ /dev/null @@ -1,152 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import java.lang.{Long => JLong} -import java.util._ - -import org.apache.ignite.cache.CacheMode._ -import org.apache.ignite.cache.affinity.AffinityKey -import org.apache.ignite.configuration.CacheConfiguration -import org.apache.ignite.examples.model.{Person, Organization} -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ -import org.apache.ignite.{Ignite, IgniteCache} - -import scala.collection.JavaConversions._ - -/** - * Demonstrates cache ad-hoc queries with Scalar. - * - * Remote nodes should be started using `ExampleNodeStartup` which will - * start node with `examples/config/example-ignite.xml` configuration. - */ -object ScalarCacheQueryExample { - /** Configuration file name. */ - private val CONFIG = "examples/config/example-ignite.xml" - - /** Cache name. */ - private val NAME = ScalarCacheQueryExample.getClass.getSimpleName - - /** - * Example entry point. No arguments required. - * - * @param args Command line arguments. None required. - */ - def main(args: Array[String]) { - scalar(CONFIG) { - val cache = createCache$(NAME, indexedTypes = Seq(classOf[JLong], classOf[Organization], - classOf[AffinityKey[_]], classOf[Person])) - - try { - example(ignite$) - } - finally { - cache.destroy() - } - } - } - - /** - * Runs the example. - * - * @param ignite Ignite instance to use. - */ - private def example(ignite: Ignite) { - // Populate cache. - initialize() - - // Cache instance shortcut. - val cache = mkCache[AffinityKey[JLong], Person] - - // Using distributed queries for partitioned cache and local queries for replicated cache. - // Since in replicated caches data is available on all nodes, including local one, - // it is enough to just query the local node. - val prj = if (cache.getConfiguration(classOf[CacheConfiguration[AffinityKey[JLong], Person]]).getCacheMode == PARTITIONED) - ignite.cluster().forRemotes() - else - ignite.cluster().forLocal() - - // Example for SQL-based querying employees based on salary ranges. - // Gets all persons with 'salary > 1000'. - print("People with salary more than 1000: ", cache.sql("salary > 1000").getAll.map(e => e.getValue)) - - // Example for TEXT-based querying for a given string in people resumes. - // Gets all persons with 'Bachelor' degree. - print("People with Bachelor degree: ", cache.text("Bachelor").getAll.map(e => e.getValue)) - } - - /** - * Gets instance of typed cache view to use. - * - * @return Cache to use. - */ - private def mkCache[K, V]: IgniteCache[K, V] = cache$[K, V](NAME).get - - /** - * Populates cache with test data. - */ - private def initialize() { - // Clean up caches on all nodes before run. - cache$(NAME).get.clear() - - // Organization cache projection. - val orgCache = mkCache[JLong, Organization] - - // Organizations. - val org1 = new Organization("Ignite") - val org2 = new Organization("Other") - - orgCache += (org1.id -> org1) - orgCache += (org2.id -> org2) - - // Person cache projection. - val prnCache = mkCache[AffinityKey[JLong], Person] - - // People. - val p1 = new Person(org1, "John", "Doe", 2000, "John Doe has Master Degree.") - val p2 = new Person(org1, "Jane", "Doe", 1000, "Jane Doe has Bachelor Degree.") - val p3 = new Person(org2, "John", "Smith", 1500, "John Smith has Bachelor Degree.") - val p4 = new Person(org2, "Jane", "Smith", 2500, "Jane Smith has Master Degree.") - - // Note that in this example we use custom affinity key for Person objects - // to ensure that all persons are collocated with their organizations. - prnCache += (p1.key -> p1) - prnCache += (p2.key -> p2) - prnCache += (p3.key -> p3) - prnCache += (p4.key -> p4) - } - - /** - * Prints object or collection of objects to standard out. - * - * @param msg Message to print before object is printed. - * @param o Object to print, can be `Iterable`. - */ - private def print(msg: String, o: Any) { - assert(msg != null) - assert(o != null) - - println(">>> " + msg) - - o match { - case it: Iterable[Any] => it.foreach(e => println(">>> " + e.toString)) - case _ => println(">>> " + o.toString) - } - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarClosureExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarClosureExample.scala deleted file mode 100644 index 719f216c62d67..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarClosureExample.scala +++ /dev/null @@ -1,100 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import org.apache.ignite.cluster.ClusterNode -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ - -/** - * Demonstrates various closure executions on the cloud using Scalar. - * - * Remote nodes should always be started with special configuration file which - * enables P2P class loading: `'ignite.{sh|bat} examples/config/example-ignite.xml'`. - * - * Alternatively you can run `ExampleNodeStartup` in another JVM which will - * start node with `examples/config/example-ignite.xml` configuration. - */ -object ScalarClosureExample extends App { - scalar("examples/config/example-ignite.xml") { - topology() - helloWorld() - helloWorld2() - broadcast() - greetRemotes() - greetRemotesAgain() - } - - /** - * Prints ignite topology. - */ - def topology() { - ignite$ foreach (n => println("Node: " + nid8$(n))) - } - - /** - * Obligatory example (2) - cloud enabled Hello World! - */ - def helloWorld2() { - // Notice the example usage of Java-side closure 'F.println(...)' and method 'scala' - // that explicitly converts Java side object to a proper Scala counterpart. - // This method is required since implicit conversion won't be applied here. - ignite$.run$(for (w <- "Hello World!".split(" ")) yield () => println(w), null) - } - - /** - * Obligatory example - cloud enabled Hello World! - */ - def helloWorld() { - ignite$.run$("HELLO WORLD!".split(" ") map (w => () => println(w)), null) - } - - /** - * One way to execute closures on the ignite cluster. - */ - def broadcast() { - ignite$.bcastRun(() => println("Broadcasting!!!"), null) - } - - /** - * Greats all remote nodes only. - */ - def greetRemotes() { - val me = ignite$.cluster().localNode.id - - // Note that usage Java-based closure. - ignite$.cluster().forRemotes() match { - case p if p.isEmpty => println("No remote nodes!") - case p => p.bcastRun(() => println("Greetings from: " + me), null) - } - } - - /** - * Same as previous greetings for all remote nodes but remote cluster group is filtered manually. - */ - def greetRemotesAgain() { - val me = ignite$.cluster().localNode.id - - // Just show that we can create any groups we like... - // Note that usage of Java-based closure via 'F' typedef. - ignite$.cluster().forPredicate((n: ClusterNode) => n.id != me) match { - case p if p.isEmpty => println("No remote nodes!") - case p => p.bcastRun(() => println("Greetings again from: " + me), null) - } - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarContinuationExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarContinuationExample.scala deleted file mode 100644 index 62b3a13913757..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarContinuationExample.scala +++ /dev/null @@ -1,171 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import org.apache.ignite.compute.ComputeJobContext -import org.apache.ignite.lang.{IgniteClosure, IgniteFuture} -import org.apache.ignite.resources.JobContextResource -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ -import org.jetbrains.annotations.Nullable - -import java.math._ -import java.util - -/** - * This example recursively calculates `Fibonacci` numbers on the ignite cluster. This is - * a powerful design pattern which allows for creation of fully distributively recursive - * (a.k.a. nested) tasks or closures with continuations. This example also shows - * usage of `continuations`, which allows us to wait for results from remote nodes - * without blocking threads. - * - * Note that because this example utilizes local node storage via `NodeLocal`, - * it gets faster if you execute it multiple times, as the more you execute it, - * the more values it will be cached on remote nodes. - * - * Remote nodes should always be started with special configuration file which - * enables P2P class loading: `'ignite.{sh|bat} examples/config/example-ignite.xml'`. - * - * Alternatively you can run `ExampleNodeStartup` in another JVM which will - * start node with `examples/config/example-ignite.xml` configuration. - */ -object ScalarContinuationExample { - def main(args: Array[String]) { - scalar("examples/config/example-ignite.xml") { - // Calculate fibonacci for N. - val N: Long = 100 - - val thisNode = ignite$.cluster().localNode - - val start = System.currentTimeMillis - - // Group that excludes this node if others exists. - val prj = if (ignite$.cluster().nodes().size() > 1) ignite$.cluster().forOthers(thisNode) else ignite$.cluster().forNode(thisNode) - - val fib = ignite$.compute(prj).apply(new FibonacciClosure(thisNode.id()), N) - - val duration = System.currentTimeMillis - start - - println(">>>") - println(">>> Finished executing Fibonacci for '" + N + "' in " + duration + " ms.") - println(">>> Fibonacci sequence for input number '" + N + "' is '" + fib + "'.") - println(">>> You should see prints out every recursive Fibonacci execution on cluster nodes.") - println(">>> Check remote nodes for output.") - println(">>>") - } - } -} - -/** - * Closure to execute. - * - * @param excludeNodeId Node to exclude from execution if there are more then 1 node in cluster. - */ -class FibonacciClosure ( - private[this] val excludeNodeId: util.UUID -) extends IgniteClosure[Long, BigInteger] { - // These fields must be *transient* so they do not get - // serialized and sent to remote nodes. - // However, these fields will be preserved locally while - // this closure is being "held", i.e. while it is suspended - // and is waiting to be continued. - @transient private var fut1, fut2: IgniteFuture[BigInteger] = null - - // Auto-inject job context. - @JobContextResource - private val jobCtx: ComputeJobContext = null - - @Nullable override def apply(num: Long): BigInteger = { - if (fut1 == null || fut2 == null) { - println(">>> Starting fibonacci execution for number: " + num) - - // Make sure n is not negative. - val n = math.abs(num) - - val g = ignite$ - - if (n <= 2) - return if (n == 0) - BigInteger.ZERO - else - BigInteger.ONE - - // Get properly typed node-local storage. - val store = g.cluster().nodeLocalMap[Long, IgniteFuture[BigInteger]]() - - // Check if value is cached in node-local store first. - fut1 = store.get(n - 1) - fut2 = store.get(n - 2) - - val excludeNode = ignite$.cluster().node(excludeNodeId) - - // Group that excludes node with id passed in constructor if others exists. - val prj = if (ignite$.cluster().nodes().size() > 1) ignite$.cluster().forOthers(excludeNode) else ignite$.cluster().forNode(excludeNode) - - val comp = ignite$.compute(prj) - - // If future is not cached in node-local store, cache it. - // Note recursive execution! - if (fut1 == null) { - val futVal = comp.applyAsync(new FibonacciClosure(excludeNodeId), n - 1) - - fut1 = store.putIfAbsent(n - 1, futVal) - - if (fut1 == null) - fut1 = futVal - } - - // If future is not cached in node-local store, cache it. - if (fut2 == null) { - val futVal = comp.applyAsync(new FibonacciClosure(excludeNodeId), n - 2) - - fut2 = store.putIfAbsent(n - 2, futVal) - - if (fut2 == null) - fut2 = futVal - } - - // If futures are not done, then wait asynchronously for the result - if (!fut1.isDone || !fut2.isDone) { - val lsnr = (fut: IgniteFuture[BigInteger]) => { - // This method will be called twice, once for each future. - // On the second call - we have to have both futures to be done - // - therefore we can call the continuation. - if (fut1.isDone && fut2.isDone) - jobCtx.callcc() // Resume job execution. - } - - // Hold (suspend) job execution. - // It will be resumed in listener above via 'callcc()' call - // once both futures are done. - jobCtx.holdcc() - - // Attach the same listener to both futures. - fut1.listen(lsnr) - fut2.listen(lsnr) - - return null - } - } - - assert(fut1.isDone && fut2.isDone) - - // Return cached results. - fut1.get.add(fut2.get) - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCreditRiskExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCreditRiskExample.scala deleted file mode 100644 index e3ba0014ff332..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarCreditRiskExample.scala +++ /dev/null @@ -1,249 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ - -import scala.util.Random -import scala.util.control.Breaks._ - -/** - * Scalar-based Monte-Carlo example. - * - * Remote nodes should always be started with special configuration file which - * enables P2P class loading: `'ignite.{sh|bat} examples/config/example-ignite.xml'`. - * - * Alternatively you can run `ExampleNodeStartup` in another JVM which will - * start node with `examples/config/example-ignite.xml` configuration. - */ -object ScalarCreditRiskExample { - def main(args: Array[String]) { - scalar("examples/config/example-ignite.xml") { - // Create portfolio. - var portfolio = Seq.empty[Credit] - - val rnd = new Random - - // Generate some test portfolio items. - (0 until 5000).foreach(i => - portfolio +:= Credit( - 50000 * rnd.nextDouble, - rnd.nextInt(1000), - rnd.nextDouble / 10, - rnd.nextDouble / 20 + 0.02 - ) - ) - - // Forecast horizon in days. - val horizon = 365 - - // Number of Monte-Carlo iterations. - val iter = 10000 - - // Percentile. - val percentile = 0.95 - - // Mark the stopwatch. - val start = System.currentTimeMillis - - // Calculate credit risk and print it out. - // As you can see the ignite cluster enabling is completely hidden from the caller - // and it is fully transparent to him. In fact, the caller is never directly - // aware if method was executed just locally or on the 100s of cluster nodes. - // Credit risk crdRisk is the minimal amount that creditor has to have - // available to cover possible defaults. - val crdRisk = ignite$ @< (closures(ignite$.cluster().nodes().size(), portfolio.toArray, horizon, iter, percentile), - (s: Seq[Double]) => s.sum / s.size, null) - - println("Credit risk [crdRisk=" + crdRisk + ", duration=" + - (System.currentTimeMillis - start) + "ms]") - } - } - - /** - * Creates closures for calculating credit risks. - * - * @param clusterSize Size of the cluster. - * @param portfolio Portfolio. - * @param horizon Forecast horizon in days. - * @param iter Number of Monte-Carlo iterations. - * @param percentile Percentile. - * @return Collection of closures. - */ - private def closures(clusterSize: Int, portfolio: Array[Credit], horizon: Int, iter: Int, - percentile: Double): Seq[() => Double] = { - val iterPerNode: Int = math.round(iter / clusterSize.asInstanceOf[Float]) - val lastNodeIter: Int = iter - (clusterSize - 1) * iterPerNode - - var cls = Seq.empty[() => Double] - - (0 until clusterSize).foreach(i => { - val nodeIter = if (i == clusterSize - 1) lastNodeIter else iterPerNode - - cls +:= (() => new CreditRiskManager().calculateCreditRiskMonteCarlo( - portfolio, horizon, nodeIter, percentile)) - }) - - cls - } -} - -/** - * This class provides a simple model for a credit contract (or a loan). It is basically - * defines as remaining crediting amount to date, credit remaining term, APR and annual - * probability on default. Although this model is simplified for the purpose - * of this example, it is close enough to emulate the real-life credit - * risk assessment application. - */ -private case class Credit( - remAmnt: Double, // Remaining crediting amount. - remTerm: Int, // Remaining crediting remTerm. - apr: Double, // Annual percentage rate (APR). - edf: Double // Expected annual probability of default (EaDF). -) { - /** - * Gets either credit probability of default for the given period of time - * if remaining term is less than crediting time or probability of default - * for whole remained crediting time. - * - * @param term Default term. - * @return Credit probability of default in relative percents - * (percentage / 100). - */ - def getDefaultProbability(term: Int): Double = { - (1 - math.exp(math.log(1 - edf) * math.min(remTerm, term) / 365.0)) - } -} - -/** - * This class abstracts out the calculation of risk for a credit portfolio. - */ -private class CreditRiskManager { - /** - * Default randomizer with normal distribution. - * Note that since every JVM on the ignite cluster will have its own random - * generator (independently initialized) the Monte-Carlo simulation - * will be slightly skewed when performed on the ignite cluster due to skewed - * normal distribution of the sub-jobs comparing to execution on the - * local node only with single random generator. Real-life applications - * may want to provide its own implementation of distributed random - * generator. - */ - private val rndGen = new Random - - /** - * Calculates credit risk for a given credit portfolio. This calculation uses - * Monte-Carlo Simulation to produce risk value. - * - * @param portfolio Credit portfolio. - * @param horizon Forecast horizon (in days). - * @param num Number of Monte-Carlo iterations. - * @param percentile Cutoff level. - * @return Credit risk value, i.e. the minimal amount that creditor has to - * have available to cover possible defaults. - */ - def calculateCreditRiskMonteCarlo(portfolio: Seq[Credit], horizon: Int, num: - Int, percentile: Double): Double = { - println(">>> Calculating credit risk for portfolio [size=" + portfolio.length + ", horizon=" + - horizon + ", percentile=" + percentile + ", iterations=" + num + "] <<<") - - val start = System.currentTimeMillis - - val losses = calculateLosses(portfolio, horizon, num).sorted - val lossProbs = new Array[Double](losses.size) - - (0 until losses.size).foreach(i => { - if (i == 0) - lossProbs(i) = getLossProbability(losses, 0) - else if (losses(i) != losses(i - 1)) - lossProbs(i) = getLossProbability(losses, i) + lossProbs(i - 1) - else - lossProbs(i) = lossProbs(i - 1) - }) - - var crdRisk = 0.0 - - breakable { - (0 until lossProbs.size).foreach(i => { - if (lossProbs(i) > percentile) { - crdRisk = losses(i - 1) - - break() - } - }) - } - - println(">>> Finished calculating portfolio risk [risk=" + crdRisk + - ", time=" + (System.currentTimeMillis - start) + "ms]") - - crdRisk - } - - /** - * Calculates losses for the given credit portfolio using Monte-Carlo Simulation. - * Simulates probability of default only. - * - * @param portfolio Credit portfolio. - * @param horizon Forecast horizon. - * @param num Number of Monte-Carlo iterations. - * @return Losses array simulated by Monte Carlo method. - */ - private def calculateLosses(portfolio: Seq[Credit], horizon: Int, num: Int): Array[Double] = { - val losses = new Array[Double](num) - - // Count losses using Monte-Carlo method. We generate random probability of default, - // if it exceeds certain credit default value we count losses - otherwise count income. - (0 until num).foreach(i => { - portfolio.foreach(crd => { - val remDays = math.min(crd.remTerm, horizon) - - if (rndGen.nextDouble >= 1 - crd.getDefaultProbability(remDays)) - // (1 + 'r' * min(H, W) / 365) * S. - // Where W is a horizon, H is a remaining crediting term, 'r' is an annual credit rate, - // S is a remaining credit amount. - losses(i) += (1 + crd.apr * math.min(horizon, crd.remTerm) / 365) * crd.remAmnt - else - // - 'r' * min(H,W) / 365 * S - // Where W is a horizon, H is a remaining crediting term, 'r' is a annual credit rate, - // S is a remaining credit amount. - losses(i) -= crd.apr * math.min(horizon, crd.remTerm) / 365 * crd.remAmnt - }) - }) - - losses - } - - /** - * Calculates probability of certain loss in array of losses. - * - * @param losses Array of losses. - * @param i Index of certain loss in array. - * @return Probability of loss with given index. - */ - private def getLossProbability(losses: Array[Double], i: Int): Double = { - var count = 0.0 - - losses.foreach(tmp => { - if (tmp == losses(i)) - count += 1 - }) - - count / losses.size - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarJvmCloudExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarJvmCloudExample.scala deleted file mode 100644 index 814bb2e99611d..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarJvmCloudExample.scala +++ /dev/null @@ -1,95 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import java.util.concurrent.Executors -import java.util.concurrent.TimeUnit._ -import javax.swing.{JComponent, JLabel, JOptionPane} - -import org.apache.ignite.configuration.IgniteConfiguration -import org.apache.ignite.internal.util.scala.impl -import org.apache.ignite.scalar.scalar -import org.apache.ignite.spi.discovery.tcp.TcpDiscoverySpi -import org.apache.ignite.spi.discovery.tcp.ipfinder.vm.TcpDiscoveryVmIpFinder - -/** - * This example demonstrates how you can easily startup multiple nodes - * in the same JVM with Scala. All started nodes use default configuration - * with only difference of the ignite cluster name which has to be different for - * every node so they can be differentiated within JVM. - * - * Starting multiple nodes in the same JVM is especially useful during - * testing and debugging as it allows you to create a full ignite cluster within - * a test case, simulate various scenarios, and watch how jobs and data - * behave within a ignite cluster. - */ -object ScalarJvmCloudExample { - /** Names of nodes to start. */ - val NODES = List("scalar-node-0", "scalar-node-1", "scalar-node-2", "scalar-node-3", "scalar-node-4") - - def main(args: Array[String]) { - try { - // Shared IP finder for in-VM node discovery. - val ipFinder = new TcpDiscoveryVmIpFinder(true) - - val pool = Executors.newFixedThreadPool(NODES.size) - - // Concurrently startup all nodes. - NODES.foreach(name => pool.execute(new Runnable { - @impl def run() { - // All defaults. - val cfg = new IgniteConfiguration - - cfg.setGridName(name) - - // Configure in-VM TCP discovery so we don't - // interfere with other ignites running on the same network. - val discoSpi = new TcpDiscoverySpi - - discoSpi.setIpFinder(ipFinder) - - cfg.setDiscoverySpi(discoSpi) - - // Start node - scalar.start(cfg) - - () - } - })) - - pool.shutdown() - - pool.awaitTermination(Long.MaxValue, MILLISECONDS) - - // Wait until Ok is pressed. - JOptionPane.showMessageDialog( - null, - Array[JComponent]( - new JLabel("Ignite JVM cloud started."), - new JLabel("Number of nodes in the cluster: " + scalar.ignite$(NODES(1)).get.cluster().nodes().size()), - new JLabel("Click OK to stop.") - ), - "Ignite", - JOptionPane.INFORMATION_MESSAGE) - - } - // Stop all nodes - finally - NODES.foreach(node => scalar.stop(node, true)) - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarPingPongExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarPingPongExample.scala deleted file mode 100644 index 75784cfb562b4..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarPingPongExample.scala +++ /dev/null @@ -1,160 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import java.util.UUID -import java.util.concurrent.CountDownLatch - -import org.apache.ignite.messaging.MessagingListenActor -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ - -/** - * Demonstrates simple protocol-based exchange in playing a ping-pong between - * two nodes. It is analogous to `MessagingPingPongExample` on Java side. - * - * Remote nodes should always be started with special configuration file which - * enables P2P class loading: `'ignite.{sh|bat} examples/config/example-ignite.xml'`. - * - * Alternatively you can run `ExampleNodeStartup` in another JVM which will - * start node with `examples/config/example-ignite.xml` configuration. - */ -object ScalarPingPongExample extends App { - scalar("examples/config/example-ignite.xml") { - pingPong() - //pingPong2() - } - - /** - * Implements Ping Pong example between local and remote node. - */ - def pingPong() { - val g = ignite$ - - if (g.cluster().nodes().size < 2) { - println(">>>") - println(">>> I need a partner to play a ping pong!") - println(">>>") - - return - } - else { - // Pick first remote node as a partner. - val nodeB = g.cluster().forNode(g.remoteNodes$().head) - - // Set up remote player: configure remote node 'rmt' to listen - // for messages from local node 'loc'. - g.message(nodeB).remoteListen(null, new MessagingListenActor[String]() { - def receive(nodeId: UUID, msg: String) { - println(msg) - - msg match { - case "PING" => respond("PONG") - case "STOP" => stop() - } - } - }) - - val latch = new CountDownLatch(10) - - // Set up local player: configure local node 'loc' - // to listen for messages from remote node 'rmt'. - ignite$.message().localListen(null, new MessagingListenActor[String]() { - def receive(nodeId: UUID, msg: String) { - println(msg) - - if (latch.getCount == 1) - stop("STOP") - else // We know it's 'PONG'. - respond("PING") - - latch.countDown() - } - }) - - // Serve! - nodeB.send$("PING", null) - - // Wait til the match is over. - latch.await() - } - } - - /** - * Implements Ping Pong example between two remote nodes. - */ - def pingPong2() { - val g = ignite$ - - if (g.cluster().forRemotes().nodes().size() < 2) { - println(">>>") - println(">>> I need at least two remote nodes!") - println(">>>") - } - else { - // Pick two remote nodes. - val n1 = g.cluster().forRemotes().head - val n2 = g.cluster().forRemotes().tail.head - - val n1p = g.cluster().forNode(n1) - val n2p = g.cluster().forNode(n2) - - // Configure remote node 'n1' to receive messages from 'n2'. - g.message(n1p).remoteListen(null, new MessagingListenActor[String] { - def receive(nid: UUID, msg: String) { - println(msg) - - msg match { - case "PING" => respond("PONG") - case "STOP" => stop() - } - } - }) - - // Configure remote node 'n2' to receive messages from 'n1'. - g.message(n2p).remoteListen(null, new MessagingListenActor[String] { - // Get local count down latch. - private lazy val latch: CountDownLatch = g.cluster().nodeLocalMap().get("latch") - - def receive(nid: UUID, msg: String) { - println(msg) - - latch.getCount match { - case 1 => stop("STOP") - case _ => respond("PING") - } - - latch.countDown() - } - }) - - // 1. Sets latch into node local storage so that local actor could use it. - // 2. Sends first 'PING' to 'n1'. - // 3. Waits until all messages are exchanged between two remote nodes. - n2p.run$(() => { - val latch = new CountDownLatch(10) - - g.cluster().nodeLocalMap[String, CountDownLatch].put("latch", latch) - - n1p.send$("PING", null) - - latch.await() - }, null) - } - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarPrimeExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarPrimeExample.scala deleted file mode 100644 index 867783b294298..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarPrimeExample.scala +++ /dev/null @@ -1,134 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import java.util - -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ - -import scala.util.control.Breaks._ - -/** - * Prime Number calculation example based on Scalar. - * - * ==Starting Remote Nodes== - * To try this example you should (but don't have to) start remote ignite instances. - * You can start as many as you like by executing the following script: - * `{IGNITE_HOME}/bin/ignite.{bat|sh} examples/config/example-ignite.xml` - * - * Once remote instances are started, you can execute this example from - * Eclipse, IntelliJ IDEA, or NetBeans (and any other Java IDE) by simply hitting run - * button. You will see that all nodes discover each other and - * all of the nodes will participate in task execution (check node - * output). - * - * Note that when running this example on a multi-core box, simply - * starting additional cluster node on the same box will speed up - * prime number calculation by a factor of 2. - */ -object ScalarPrimeExample { - /** - * Main entry point to application. No arguments required. - * - * @param args Command like argument (not used). - */ - def main(args: Array[String]){ - scalar("examples/config/example-ignite.xml") { - val start = System.currentTimeMillis - - // Values we want to check for prime. - val checkVals = Array(32452841L, 32452843L, 32452847L, 32452849L, 236887699L, 217645199L) - - println(">>>") - println(">>> Starting to check the following numbers for primes: " + util.Arrays.toString(checkVals)) - - val g = ignite$ - - checkVals.foreach(checkVal => { - val divisor = g.reduce$[Option[Long], Option[Option[Long]]]( - closures(g.cluster().nodes().size(), checkVal), _.find(_.isDefined), null) - - if (!divisor.isDefined) - println(">>> Value '" + checkVal + "' is a prime number") - else - println(">>> Value '" + checkVal + "' is divisible by '" + divisor.get.get + '\'') - }) - - val totalTime = System.currentTimeMillis - start - - println(">>> Total time to calculate all primes (milliseconds): " + totalTime) - println(">>>") - } - } - - /** - * Creates closures for checking passed in value for prime. - * - * Every closure gets a range of divisors to check. The lower and - * upper boundaries of this range are passed into closure. - * Closures checks if the value passed in is divisible by any of - * the divisors in the range. - * - * @param clusterSize Size of the cluster. - * @param checkVal Value to check. - * @return Collection of closures. - */ - private def closures(clusterSize: Int, checkVal: Long): Seq[() => Option[Long]] = { - var cls = Seq.empty[() => Option[Long]] - - val taskMinRange = 2L - val numbersPerTask = if (checkVal / clusterSize < 10) 10L else checkVal / clusterSize - - var minRange = 0L - var maxRange = 0L - - var i = 0 - - while (maxRange < checkVal) { - minRange = i * numbersPerTask + taskMinRange - maxRange = (i + 1) * numbersPerTask + taskMinRange - 1 - - if (maxRange > checkVal) - maxRange = checkVal - - val min = minRange - val max = maxRange - - cls +:= (() => { - var divisor: Option[Long] = None - - breakable { - (min to max).foreach(d => { - if (d != 1 && d != checkVal && checkVal % d == 0) { - divisor = Some(d) - - break() - } - }) - } - - divisor - }) - - i += 1 - } - - cls - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarSnowflakeSchemaExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarSnowflakeSchemaExample.scala deleted file mode 100644 index b88cfa5095e45..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarSnowflakeSchemaExample.scala +++ /dev/null @@ -1,319 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import java.lang.{Integer => JavaInt} -import java.util.ConcurrentModificationException -import java.util.concurrent.ThreadLocalRandom -import javax.cache.Cache - -import org.apache.ignite.IgniteCache -import org.apache.ignite.cache.CacheMode -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ - -import scala.collection.JavaConversions._ - -/** - * Snowflake Schema is a logical - * arrangement of data in which data is split into `dimensions` and `facts` - * Dimensions can be referenced or joined by other dimensions or facts, - * however, facts are generally not referenced by other facts. You can view dimensions - * as your master or reference data, while facts are usually large data sets of events or - * other objects that continuously come into the system and may change frequently. In Ignite - * such architecture is supported via cross-cache queries. By storing dimensions in - * `CacheMode#REPLICATED REPLICATED` caches and facts in much larger - * `CacheMode#PARTITIONED PARTITIONED` caches you can freely execute distributed joins across - * your whole in-memory data ignite cluster, thus querying your in memory data without any limitations. - * - * In this example we have two dimensions, `DimProduct` and `DimStore` and - * one fact - `FactPurchase`. Queries are executed by joining dimensions and facts - * in various ways. - * - * Remote nodes should be started using `ExampleNodeStartup` which will - * start node with `examples/config/example-ignite.xml` configuration. - */ -object ScalarSnowflakeSchemaExample { - /** Configuration file name. */ - private val CONFIG = "examples/config/example-ignite.xml" - - /** Name of partitioned cache specified in spring configuration. */ - private val PARTITIONED_CACHE_NAME = "ScalarSnowflakeSchemaExamplePartitioned" - - /** Name of replicated cache specified in spring configuration. */ - private val REPLICATED_CACHE_NAME = "ScalarSnowflakeSchemaExampleReplicated" - - /** ID generator. */ - private[this] val idGen = Stream.from(0).iterator - - /** DimStore data. */ - private[this] val dataStore = scala.collection.mutable.Map[JavaInt, DimStore]() - - /** DimProduct data. */ - private[this] val dataProduct = scala.collection.mutable.Map[JavaInt, DimProduct]() - - /** - * Example entry point. No arguments required. - */ - def main(args: Array[String]) { - scalar(CONFIG) { - println - println(">>> Cache star schema example started.") - - // Destroy caches to clean up the data if any left from previous runs. - destroyCache$(PARTITIONED_CACHE_NAME) - destroyCache$(REPLICATED_CACHE_NAME) - - val dimCache = createCache$[JavaInt, AnyRef](REPLICATED_CACHE_NAME, CacheMode.REPLICATED, Seq(classOf[JavaInt], classOf[DimStore], - classOf[JavaInt], classOf[DimProduct])) - - try { - val factCache = createCache$[JavaInt, FactPurchase](PARTITIONED_CACHE_NAME, indexedTypes = Seq(classOf[JavaInt], classOf[FactPurchase])) - - try { - populateDimensions(dimCache) - populateFacts(factCache) - - queryStorePurchases() - queryProductPurchases() - } - finally { - factCache.destroy() - } - } - finally { - dimCache.destroy() - } - } - } - - /** - * Populate cache with `dimensions` which in our case are - * `DimStore` and `DimProduct` instances. - */ - def populateDimensions(dimCache: IgniteCache[JavaInt, AnyRef]) { - val store1 = new DimStore(idGen.next(), "Store1", "12345", "321 Chilly Dr, NY") - val store2 = new DimStore(idGen.next(), "Store2", "54321", "123 Windy Dr, San Francisco") - - // Populate stores. - dimCache.put(store1.id, store1) - dimCache.put(store2.id, store2) - - dataStore.put(store1.id, store1) - dataStore.put(store2.id, store2) - - for (i <- 1 to 20) { - val product = new DimProduct(idGen.next(), "Product" + i, i + 1, (i + 1) * 10) - - dimCache.put(product.id, product) - - dataProduct.put(product.id, product) - } - } - - /** - * Populate cache with `facts`, which in our case are `FactPurchase` objects. - */ - def populateFacts(factCache: IgniteCache[JavaInt, FactPurchase]) { - for (i <- 1 to 100) { - val store: DimStore = rand(dataStore.values) - val prod: DimProduct = rand(dataProduct.values) - val purchase: FactPurchase = new FactPurchase(idGen.next(), prod.id, store.id, i + 1) - - factCache.put(purchase.id, purchase) - } - } - - /** - * Query all purchases made at a specific store. This query uses cross-cache joins - * between `DimStore` objects stored in `replicated` cache and - * `FactPurchase` objects stored in `partitioned` cache. - */ - def queryStorePurchases() { - val factCache = ignite$.cache[JavaInt, FactPurchase](PARTITIONED_CACHE_NAME) - - val storePurchases = factCache.sql( - "from \"" + REPLICATED_CACHE_NAME + "\".DimStore, \"" + PARTITIONED_CACHE_NAME + "\".FactPurchase " + - "where DimStore.id=FactPurchase.storeId and DimStore.name=?", "Store1") - - printQueryResults("All purchases made at store1:", storePurchases.getAll) - } - - /** - * Query all purchases made at a specific store for 3 specific products. - * This query uses cross-cache joins between `DimStore`, `DimProduct` - * objects stored in `replicated` cache and `FactPurchase` objects - * stored in `partitioned` cache. - */ - private def queryProductPurchases() { - val factCache = ignite$.cache[JavaInt, FactPurchase](PARTITIONED_CACHE_NAME) - - // All purchases for certain product made at store2. - // ================================================= - val p1: DimProduct = rand(dataProduct.values) - val p2: DimProduct = rand(dataProduct.values) - val p3: DimProduct = rand(dataProduct.values) - - println("IDs of products [p1=" + p1.id + ", p2=" + p2.id + ", p3=" + p3.id + ']') - - val prodPurchases = factCache.sql( - "from \"" + REPLICATED_CACHE_NAME + "\".DimStore, \"" + REPLICATED_CACHE_NAME + "\".DimProduct, \"" + - PARTITIONED_CACHE_NAME + "\".FactPurchase " + - "where DimStore.id=FactPurchase.storeId and " + - "DimProduct.id=FactPurchase.productId and " + - "DimStore.name=? and DimProduct.id in(?, ?, ?)", - "Store2", p1.id, p2.id, p3.id) - - printQueryResults("All purchases made at store2 for 3 specific products:", prodPurchases.getAll) - } - - /** - * Print query results. - * - * @param msg Initial message. - * @param res Results to print. - */ - private def printQueryResults[V](msg: String, res: Iterable[Cache.Entry[JavaInt, V]]) { - println(msg) - - for (e <- res) - println(" " + e.getValue.toString) - } - - /** - * Gets random value from given collection. - * - * @param c Input collection (no `null` and not emtpy). - * @return Random value from the input collection. - */ - def rand[T](c: Iterable[_ <: T]): T = { - val n: Int = ThreadLocalRandom.current.nextInt(c.size) - - var i: Int = 0 - - for (t <- c) { - if (i < n) - i += 1 - else - return t - } - - throw new ConcurrentModificationException - } -} - -/** - * Represents a physical store location. In our `snowflake` schema a `store` - * is a `dimension` and will be cached in `CacheMode#REPLICATED` cache. - * - * @param id Primary key. - * @param name Store name. - * @param zip Zip code. - * @param addr Address. - */ -class DimStore( - @ScalarCacheQuerySqlField - val id: Int, - @ScalarCacheQuerySqlField - val name: String, - val zip: String, - val addr: String) { - /** - * `toString` implementation. - */ - override def toString: String = { - val sb: StringBuilder = new StringBuilder - - sb.append("DimStore ") - sb.append("[id=").append(id) - sb.append(", name=").append(name) - sb.append(", zip=").append(zip) - sb.append(", addr=").append(addr) - sb.append(']') - - sb.toString() - } -} - -/** - * Represents a product available for purchase. In our `snowflake` schema a `product` - * is a `dimension` and will be cached in `CacheMode#REPLICATED` cache. - * - * @param id Product ID. - * @param name Product name. - * @param price Product list price. - * @param qty Available product quantity. - */ -class DimProduct( - @ScalarCacheQuerySqlField - val id: Int, - val name: String, - @ScalarCacheQuerySqlField - val price: Float, - val qty: Int) { - /** - * `toString` implementation. - */ - override def toString: String = { - val sb: StringBuilder = new StringBuilder - - sb.append("DimProduct ") - sb.append("[id=").append(id) - sb.append(", name=").append(name) - sb.append(", price=").append(price) - sb.append(", qty=").append(qty) - sb.append(']') - - sb.toString() - } -} - -/** - * Represents a purchase record. In our `snowflake` schema purchase - * is a `fact` and will be cached in larger `CacheMode#PARTITIONED` cache. - * - * @param id Purchase ID. - * @param productId Purchased product ID. - * @param storeId Store ID. - * @param purchasePrice Purchase price. - */ -class FactPurchase( - @ScalarCacheQuerySqlField - val id: Int, - @ScalarCacheQuerySqlField - val productId: Int, - @ScalarCacheQuerySqlField - val storeId: Int, - @ScalarCacheQuerySqlField - val purchasePrice: Float) { - /** - * `toString` implementation. - */ - override def toString: String = { - val sb: StringBuilder = new StringBuilder - - sb.append("FactPurchase ") - sb.append("[id=").append(id) - sb.append(", productId=").append(productId) - sb.append(", storeId=").append(storeId) - sb.append(", purchasePrice=").append(purchasePrice) - sb.append(']') - - sb.toString() - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarTaskExample.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarTaskExample.scala deleted file mode 100644 index 21073e5e7c98a..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarTaskExample.scala +++ /dev/null @@ -1,55 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import java.util - -import org.apache.ignite.compute.{ComputeJob, ComputeJobResult, ComputeTaskSplitAdapter} -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ - -import scala.collection.JavaConversions._ - -/** - * Demonstrates use of full ignite task API using Scalar. Note that using task-based - * ignite enabling gives you all the advanced features of Ignite such as custom topology - * and collision resolution, custom failover, mapping, reduction, load balancing, etc. - * As a trade off in such cases the more code needs to be written vs. simple closure execution. - * - * Remote nodes should always be started with special configuration file which - * enables P2P class loading: `'ignite.{sh|bat} examples/config/example-ignite.xml'`. - * - * Alternatively you can run `ExampleNodeStartup` in another JVM which will - * start node with `examples/config/example-ignite.xml` configuration. - */ -object ScalarTaskExample extends App { - scalar("examples/config/example-ignite.xml") { - ignite$.compute().execute(classOf[IgniteHelloWorld], "Hello Cloud World!") - } - - /** - * This task encapsulates the logic of MapReduce. - */ - class IgniteHelloWorld extends ComputeTaskSplitAdapter[String, Void] { - def split(clusterSize: Int, arg: String): java.util.Collection[_ <: ComputeJob] = { - (for (w <- arg.split(" ")) yield toJob(() => println(w))).toSeq - } - - def reduce(results: util.List[ComputeJobResult]) = null - } -} diff --git a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarWorldShortestMapReduce.scala b/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarWorldShortestMapReduce.scala deleted file mode 100644 index 723cdae67d8bd..0000000000000 --- a/examples/src/main/scala/org/apache/ignite/scalar/examples/ScalarWorldShortestMapReduce.scala +++ /dev/null @@ -1,42 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.examples - -import org.apache.ignite.scalar.scalar -import org.apache.ignite.scalar.scalar._ - -/** - * Shows the world's shortest MapReduce application that calculates non-space - * length of the input string. This example works equally on one computer or - * on thousands requiring no special configuration or deployment. - * - * Remote nodes should always be started with special configuration file which - * enables P2P class loading: `'ignite.{sh|bat} examples/config/example-ignite.xml'`. - * - * Alternatively you can run `ExampleNodeStartup` in another JVM which will - * start node with `examples/config/example-ignite.xml` configuration. - */ -object ScalarWorldShortestMapReduce extends App { - scalar("examples/config/example-ignite.xml") { - val input = "World shortest mapreduce application" - - println("Non-space characters count: " + - ignite$.reduce$[Int, Int](for (w <- input.split(" ")) yield () => w.length, _.sum, null) - ) - } -} diff --git a/examples/src/test/scala/org/apache/ignite/scalar/tests/examples/ScalarExamplesMultiNodeSelfTest.scala b/examples/src/test/scala/org/apache/ignite/scalar/tests/examples/ScalarExamplesMultiNodeSelfTest.scala deleted file mode 100644 index 57efe975d9280..0000000000000 --- a/examples/src/test/scala/org/apache/ignite/scalar/tests/examples/ScalarExamplesMultiNodeSelfTest.scala +++ /dev/null @@ -1,33 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.tests.examples - -/** - * Scalar examples multi-node self test. - */ -class ScalarExamplesMultiNodeSelfTest extends ScalarExamplesSelfTest { - /** */ - protected override def beforeTest() { - startRemoteNodes() - } - - /** */ - protected override def getTestTimeout: Long = { - 10 * 60 * 1000 - } -} diff --git a/examples/src/test/scala/org/apache/ignite/scalar/tests/examples/ScalarExamplesSelfTest.scala b/examples/src/test/scala/org/apache/ignite/scalar/tests/examples/ScalarExamplesSelfTest.scala deleted file mode 100644 index a76da9f42a4a9..0000000000000 --- a/examples/src/test/scala/org/apache/ignite/scalar/tests/examples/ScalarExamplesSelfTest.scala +++ /dev/null @@ -1,119 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.tests.examples - -import org.apache.ignite.scalar.examples._ -import org.apache.ignite.scalar.examples.spark._ -import org.apache.ignite.scalar.scalar -import org.apache.ignite.testframework.junits.common.GridAbstractExamplesTest -import org.junit.Test -import org.scalatest.Suite - -/** - * Scalar examples self test. - */ -class ScalarExamplesSelfTest extends GridAbstractExamplesTest with Suite { - /** */ - private def EMPTY_ARGS = Array.empty[String] - - /** */ - @Test - def testScalarCacheAffinitySimpleExample() { - ScalarCacheAffinityExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarCacheEntryProcessorExample() { - ScalarCacheEntryProcessorExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarCacheExample() { - ScalarCacheExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarCacheQueryExample() { - ScalarCacheQueryExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarClosureExample() { - ScalarClosureExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarContinuationExample() { - ScalarContinuationExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarCreditRiskExample() { - ScalarCreditRiskExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarPingPongExample() { - scalar("modules/scalar/src/test/resources/spring-ping-pong-partner.xml") { - ScalarPingPongExample.main(EMPTY_ARGS) - } - } - - /** */ - @Test - def testScalarPopularNumbersRealTimeExample() { - ScalarCachePopularNumbersExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarPrimeExample() { - ScalarPrimeExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarTaskExample() { - ScalarTaskExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarWorldShortestMapReduceExample() { - ScalarWorldShortestMapReduce.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarSnowflakeSchemaExample() { - ScalarSnowflakeSchemaExample.main(EMPTY_ARGS) - } - - /** */ - @Test - def testScalarSharedRDDExample() { - ScalarSharedRDDExample.main(EMPTY_ARGS) - } -} diff --git a/examples/src/test/scala/org/apache/ignite/scalar/testsuites/ScalarExamplesSelfTestSuite.scala b/examples/src/test/scala/org/apache/ignite/scalar/testsuites/ScalarExamplesSelfTestSuite.scala deleted file mode 100644 index e28b2ba1e8153..0000000000000 --- a/examples/src/test/scala/org/apache/ignite/scalar/testsuites/ScalarExamplesSelfTestSuite.scala +++ /dev/null @@ -1,37 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.testsuites - -import org.apache.ignite.IgniteSystemProperties._ -import org.apache.ignite.scalar.tests.examples.{ScalarExamplesMultiNodeSelfTest, ScalarExamplesSelfTest} -import org.apache.ignite.testframework.GridTestUtils -import org.junit.runner.RunWith -import org.scalatest._ -import org.scalatest.junit.JUnitRunner - -/** - * - */ -@RunWith(classOf[JUnitRunner]) -class ScalarExamplesSelfTestSuite extends Suites( - new ScalarExamplesSelfTest, - new ScalarExamplesMultiNodeSelfTest -) { - System.setProperty(IGNITE_OVERRIDE_MCAST_GRP, - GridTestUtils.getNextMulticastGroup(classOf[ScalarExamplesSelfTest])) -} diff --git a/modules/aop/src/test/config/aop/aspectj/META-INF/aop.xml b/modules/aop/src/test/config/aop/aspectj/META-INF/aop.xml index 8741bd18cd57a..f80c4a5164be7 100644 --- a/modules/aop/src/test/config/aop/aspectj/META-INF/aop.xml +++ b/modules/aop/src/test/config/aop/aspectj/META-INF/aop.xml @@ -93,7 +93,6 @@- * If write-through is enabled, the stored value will be persisted to `GridCacheStore` - * via `GridCacheStore#put(String, GridCacheTx, Object, Object)` method. - * - * ===Transactions=== - * This method is transactional and will enlist the entry into ongoing transaction - * if there is one. - * - * @param kv Key-Value pair to store in cache. - * @return `True` if value was stored in cache, `false` otherwise. - * @see `IgniteCache#putx(...)` - */ - def putx$(kv: (K, V)): Boolean = value.putIfAbsent(kv._1, kv._2) - - /** - * Stores given key-value pair in cache. If filters are provided, then entries will - * be stored in cache only if they pass the filter. Note that filter check is atomic, - * so value stored in cache is guaranteed to be consistent with the filters. - *
- * If write-through is enabled, the stored value will be persisted to `GridCacheStore` - * via `GridCacheStore#put(String, GridCacheTx, Object, Object)` method. - * - * ===Transactions=== - * This method is transactional and will enlist the entry into ongoing transaction - * if there is one. - * - * @param kv Key-Value pair to store in cache. - * @return Previous value associated with specified key, or `null` - * if entry did not pass the filter, or if there was no mapping for the key in swap - * or in persistent storage. - * @see `IgniteCache#put(...)` - */ - def put$(kv: (K, V)): V = value.getAndReplace(kv._1, kv._2) - - /** - * Stores given key-value pair in cache. If filters are provided, then entries will - * be stored in cache only if they pass the filter. Note that filter check is atomic, - * so value stored in cache is guaranteed to be consistent with the filters. - *
- * If write-through is enabled, the stored value will be persisted to `GridCacheStore` - * via `GridCacheStore#put(String, GridCacheTx, Object, Object)` method. - * - * ===Transactions=== - * This method is transactional and will enlist the entry into ongoing transaction - * if there is one. - * - * @param kv Key-Value pair to store in cache. - * @return Previous value associated with specified key as an option. - * @see `IgniteCache#put(...)` - */ - def putOpt$(kv: (K, V)): Option[V] = Option(value.getAndReplace(kv._1, kv._2)) - - /** - * Operator alias for the same function `putx$`. - * - * @param kv Key-Value pair to store in cache. - * @return `True` if value was stored in cache, `false` otherwise. - * @see `IgniteCache#putx(...)` - */ - def +=(kv: (K, V)): Boolean = - putx$(kv) - - /** - * Stores given key-value pairs in cache. - * - * If write-through is enabled, the stored values will be persisted to `GridCacheStore` - * via `GridCacheStore#putAll(String, GridCacheTx, Map)` method. - * - * ===Transactions=== - * This method is transactional and will enlist the entry into ongoing transaction - * if there is one. - * - * @param kv1 Key-value pair to store in cache. - * @param kv2 Key-value pair to store in cache. - * @param kvs Optional key-value pairs to store in cache. - * @see `IgniteCache#putAll(...)` - */ - def putAll$(kv1: (K, V), kv2: (K, V), @Nullable kvs: (K, V)*) { - var m = mutable.Map.empty[K, V] - - m += (kv1, kv2) - - if (kvs != null) - kvs foreach (m += _) - - value.putAll(m) - } - - /** - * Stores given key-value pairs from the sequence in cache. - * - * If write-through is enabled, the stored values will be persisted to `GridCacheStore` - * via `GridCacheStore#putAll(String, GridCacheTx, Map)` method. - * - * ===Transactions=== - * This method is transactional and will enlist the entry into ongoing transaction - * if there is one. - * - * @param kvs Key-value pairs to store in cache. If `null` this function is no-op. - * @see `IgniteCache#putAll(...)` - */ - def putAll$(@Nullable kvs: Seq[(K, V)]) { - if (kvs != null) - value.putAll(mutable.Map(kvs: _*)) - } - - /** - * Removes given key mappings from cache. - * - * If write-through is enabled, the values will be removed from `GridCacheStore` - * via `GridCacheStore#removeAll(String, GridCacheTx, Collection)` method. - * - * ===Transactions=== - * This method is transactional and will enlist the entry into ongoing transaction - * if there is one. - * - * @param ks Sequence of additional keys to remove. If `null` - this function is no-op. - * @see `IgniteCache#removeAll(...)` - */ - def removeAll$(@Nullable ks: Seq[K]) { - if (ks != null) - value.removeAll(toJavaSet(ks)) - } - - /** - * Operator alias for the same function `putAll$`. - * - * @param kv1 Key-value pair to store in cache. - * @param kv2 Key-value pair to store in cache. - * @param kvs Optional key-value pairs to store in cache. - * @see `IgniteCache#putAll(...)` - */ - def +=(kv1: (K, V), kv2: (K, V), @Nullable kvs: (K, V)*) { - putAll$(kv1, kv2, kvs: _*) - } - - /** - * Removes given key mapping from cache. If cache previously contained value for the given key, - * then this value is returned. Otherwise, in case of `CacheMode#REPLICATED` caches, - * the value will be loaded from swap and, if it's not there, and read-through is allowed, - * from the underlying `GridCacheStore` storage. In case of `CacheMode#PARTITIONED` - * caches, the value will be loaded from the primary node, which in its turn may load the value - * from the swap storage, and consecutively, if it's not in swap and read-through is allowed, - * from the underlying persistent storage. If value has to be loaded from persistent - * storage, `GridCacheStore#load(String, GridCacheTx, Object)` method will be used. - * - * If the returned value is not needed, method `removex$(...)` should - * always be used instead of this one to avoid the overhead associated with returning of the - * previous value. - * - * If write-through is enabled, the value will be removed from 'GridCacheStore' - * via `GridCacheStore#remove(String, GridCacheTx, Object)` method. - * - * ===Transactions=== - * This method is transactional and will enlist the entry into ongoing transaction - * if there is one. - * - * @param k Key whose mapping is to be removed from cache. - * @return Previous value associated with specified key, or `null` - * if there was no value for this key. - * @see `IgniteCache#remove(...)` - */ - def remove$(k: K): V = value.getAndRemove(k) - - /** - * Removes given key mapping from cache. If cache previously contained value for the given key, - * then this value is returned. Otherwise, in case of `CacheMode#REPLICATED` caches, - * the value will be loaded from swap and, if it's not there, and read-through is allowed, - * from the underlying `GridCacheStore` storage. In case of `CacheMode#PARTITIONED` - * caches, the value will be loaded from the primary node, which in its turn may load the value - * from the swap storage, and consecutively, if it's not in swap and read-through is allowed, - * from the underlying persistent storage. If value has to be loaded from persistent - * storage, `GridCacheStore#load(String, GridCacheTx, Object)` method will be used. - * - * If the returned value is not needed, method `removex$(...)` should - * always be used instead of this one to avoid the overhead associated with returning of the - * previous value. - * - * If write-through is enabled, the value will be removed from 'GridCacheStore' - * via `GridCacheStore#remove(String, GridCacheTx, Object)` method. - * - * ===Transactions=== - * This method is transactional and will enlist the entry into ongoing transaction - * if there is one. - * - * @param k Key whose mapping is to be removed from cache. - * @return Previous value associated with specified key as an option. - * @see `IgniteCache#remove(...)` - */ - def removeOpt$(k: K): Option[V] = - Option(value.getAndRemove(k)) - - /** - * Operator alias for the same function `remove$`. - * - * @param k Key whose mapping is to be removed from cache. - * @return Previous value associated with specified key, or `null` - * if there was no value for this key. - * @see `IgniteCache#remove(...)` - */ - def -=(k: K): V = remove$(k) - - /** - * Removes given key mappings from cache. - * - * If write-through is enabled, the values will be removed from `GridCacheStore` - * via `GridCacheStore#removeAll(String, GridCacheTx, Collection)` method. - * - * ===Transactions=== - * This method is transactional and will enlist the entry into ongoing transaction - * if there is one. - * - * @param k1 1st key to remove. - * @param k2 2nd key to remove. - * @param ks Optional sequence of additional keys to remove. - * @see `IgniteCache#removeAll(...)` - */ - def removeAll$(k1: K, k2: K, @Nullable ks: K*) { - val s = new mutable.ArrayBuffer[K](2 + (if (ks == null) 0 else ks.length)) - - s += k1 - s += k2 - - if (ks != null) - ks foreach (s += _) - - value.removeAll(toJavaSet(s)) - } - - /** - * Operator alias for the same function `remove$`. - * - * @param k1 1st key to remove. - * @param k2 2nd key to remove. - * @param ks Optional sequence of additional keys to remove. - * @see `IgniteCache#removeAll(...)` - */ - def -=(k1: K, k2: K, @Nullable ks: K*) { - removeAll$(k1, k2, ks: _*) - } - - /** - * Creates and executes ad-hoc `SCAN` query returning its result. - * - * Note that if query is executed more than once (potentially with different - * arguments) it is more performant to create query via standard mechanism - * and execute it multiple times with different arguments. The analogy is - * similar to JDBC `PreparedStatement`. Note also that this function will return - * all results at once without pagination and therefore memory limits should be - * taken into account. - * - * @param cls Query values class. Since cache can, in general, contain values of any subtype of `V` - * query needs to know the exact type it should operate on. - * @param kvp Filter to be used prior to returning key-value pairs to user. See `CacheQuery` for more details. - * @return Collection of cache key-value pairs. - */ - def scan(cls: Class[_ <: V], kvp: KvPred): QueryCursor[Cache.Entry[K, V]] = { - assert(cls != null) - assert(kvp != null) - - value.query(new ScanQuery(kvp)) - } - - /** - * Creates and executes ad-hoc `SCAN` query returning its result. - * - * Note that if query is executed more than once (potentially with different - * arguments) it is more performant to create query via standard mechanism - * and execute it multiple times with different arguments. The analogy is - * similar to JDBC `PreparedStatement`. Note also that this function will return - * all results at once without pagination and therefore memory limits should be - * taken into account. - * - * Note that query value class will be taken implicitly as exact type `V` of this - * cache projection. - * - * @param kvp Filter to be used prior to returning key-value pairs to user. See `CacheQuery` for more details. - * @return Collection of cache key-value pairs. - */ - def scan(kvp: KvPred)(implicit m: Manifest[V]): QueryCursor[Cache.Entry[K, V]] = { - assert(kvp != null) - - scan(m.erasure.asInstanceOf[Class[V]], kvp) - } - - /** - * Creates and executes ad-hoc `SQL` query returning its result. - * - * Note that if query is executed more than once (potentially with different - * arguments) it is more performant to create query via standard mechanism - * and execute it multiple times with different arguments. The analogy is - * similar to JDBC `PreparedStatement`. Note also that this function will return - * all results at once without pagination and therefore memory limits should be - * taken into account. - * - * @param cls Query values class. Since cache can, in general, contain values of any subtype of `V` - * query needs to know the exact type it should operate on. - * @param clause Query SQL clause. See `CacheQuery` for more details. - * @param args Optional list of query arguments. - * @return Collection of cache key-value pairs. - */ - def sql(cls: Class[_ <: V], clause: String, args: Any*): QueryCursor[Cache.Entry[K, V]] = { - assert(cls != null) - assert(clause != null) - assert(args != null) - - val query = new SqlQuery[K, V](cls, clause) - - if (args != null && args.size > 0) - query.setArgs(args.map(_.asInstanceOf[AnyRef]) : _*) - - value.query(query) - } - - /** - * Creates and executes ad-hoc `SQL` query returning its result. - * - * Note that if query is executed more than once (potentially with different - * arguments) it is more performant to create query via standard mechanism - * and execute it multiple times with different arguments. The analogy is - * similar to JDBC `PreparedStatement`. Note also that this function will return - * all results at once without pagination and therefore memory limits should be - * taken into account. - * - * @param cls Query values class. Since cache can, in general, contain values of any subtype of `V` - * query needs to know the exact type it should operate on. - * @param clause Query SQL clause. See `CacheQuery` for more details. - * @return Collection of cache key-value pairs. - */ - def sql(cls: Class[_ <: V], clause: String): QueryCursor[Cache.Entry[K, V]] = { - assert(cls != null) - assert(clause != null) - - sql(cls, clause, Nil:_*) - } - - /** - * Creates and executes ad-hoc `SQL` query returning its result. - * - * Note that if query is executed more than once (potentially with different - * arguments) it is more performant to create query via standard mechanism - * and execute it multiple times with different arguments. The analogy is - * similar to JDBC `PreparedStatement`. Note also that this function will return - * all results at once without pagination and therefore memory limits should be - * taken into account. - * - * Note that query value class will be taken implicitly as exact type `V` of this - * cache projection. - * - * @param clause Query SQL clause. See `CacheQuery` for more details. - * @param args Optional list of query arguments. - * @return Collection of cache key-value pairs. - */ - def sql(clause: String, args: Any*) - (implicit m: Manifest[V]): QueryCursor[Cache.Entry[K, V]] = { - assert(clause != null) - assert(args != null) - - sql(m.erasure.asInstanceOf[Class[V]], clause, args:_*) - } - - /** - * Creates and executes ad-hoc `TEXT` query returning its result. - * - * Note that if query is executed more than once (potentially with different - * arguments) it is more performant to create query via standard mechanism - * and execute it multiple times with different arguments. The analogy is - * similar to JDBC `PreparedStatement`. Note also that this function will return - * all results at once without pagination and therefore memory limits should be - * taken into account. - * - * @param cls Query values class. Since cache can, in general, contain values of any subtype of `V` - * query needs to know the exact type it should operate on. - * @param clause Query text clause. See `CacheQuery` for more details. - * @return Collection of cache key-value pairs. - */ - def text(cls: Class[_ <: V], clause: String): QueryCursor[Cache.Entry[K, V]] = { - assert(cls != null) - assert(clause != null) - - value.query(new TextQuery(cls, clause)) - } - - /** - * Creates and executes ad-hoc `TEXT` query returning its result. - * - * Note that if query is executed more than once (potentially with different - * arguments) it is more performant to create query via standard mechanism - * and execute it multiple times with different arguments. The analogy is - * similar to JDBC `PreparedStatement`. Note also that this function will return - * all results at once without pagination and therefore memory limits should be - * taken into account. - * - * Note that query value class will be taken implicitly as exact type `V` of this - * cache projection. - * - * @param clause Query text clause. See `CacheQuery` for more details. - * @return Collection of cache key-value pairs. - */ - def text(clause: String)(implicit m: Manifest[V]): QueryCursor[Cache.Entry[K, V]] = { - assert(clause != null) - - text(m.erasure.asInstanceOf[Class[V]], clause) - } - - /** - * Creates and executes ad-hoc `SQL` fields query returning its result. - * - * Note that if query is executed more than once (potentially with different - * arguments) it is more performant to create query via standard mechanism - * and execute it multiple times with different arguments. The analogy is - * similar to JDBC `PreparedStatement`. Note also that this function will return - * all results at once without pagination and therefore memory limits should be - * taken into account. - * - * @param clause Query SQL clause. See `CacheQuery` for more details. - * @param args Optional list of query arguments. - * @return Sequence of sequences of field values. - */ - def sqlFields(clause: String, args: Any*): QueryCursor[JavaList[_]] = { - assert(clause != null) - assert(args != null) - - val query = new SqlFieldsQuery(clause) - - if (args != null && args.nonEmpty) - query.setArgs(args.map(_.asInstanceOf[AnyRef]) : _*) - - value.query(query) - } - - /** - * Creates and executes ad-hoc `SQL` no-arg fields query returning its result. - * - * Note that if query is executed more than once (potentially with different - * arguments) it is more performant to create query via standard mechanism - * and execute it multiple times with different arguments. The analogy is - * similar to JDBC `PreparedStatement`. Note also that this function will return - * all results at once without pagination and therefore memory limits should be - * taken into account. - * - * @param clause Query SQL clause. See `CacheQuery` for more details. - * @return Sequence of sequences of field values. - */ - def sqlFields(clause: String): QueryCursor[JavaList[_]] = { - assert(clause != null) - - sqlFields(clause, Nil:_*) - } -} diff --git a/modules/scalar/src/main/scala/org/apache/ignite/scalar/pimps/ScalarGridPimp.scala b/modules/scalar/src/main/scala/org/apache/ignite/scalar/pimps/ScalarGridPimp.scala deleted file mode 100644 index 0f1dfaf27dd51..0000000000000 --- a/modules/scalar/src/main/scala/org/apache/ignite/scalar/pimps/ScalarGridPimp.scala +++ /dev/null @@ -1,92 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.pimps - -import org.apache.ignite.scheduler.SchedulerFuture -import org.apache.ignite.{Ignite, IgniteCluster} -import org.jetbrains.annotations.Nullable - -/** - * Companion object. - */ -object ScalarGridPimp { - /** - * Creates new Scalar grid pimp with given Java-side implementation. - * - * @param impl Java-side implementation. - */ - def apply(impl: Ignite) = { - if (impl == null) - throw new NullPointerException("impl") - - val pimp = new ScalarGridPimp - - pimp.impl = impl.cluster() - - pimp - } -} - -/** - * ==Overview== - * Defines Scalar "pimp" for `Grid` on Java side. - * - * Essentially this class extends Java `GridProjection` interface with Scala specific - * API adapters using primarily implicit conversions defined in `ScalarConversions` object. What - * it means is that you can use functions defined in this class on object - * of Java `GridProjection` type. Scala will automatically (implicitly) convert it into - * Scalar's pimp and replace the original call with a call on that pimp. - * - * Note that Scalar provide extensive library of implicit conversion between Java and - * Scala Ignite counterparts in `ScalarConversions` object - * - * ==Suffix '$' In Names== - * Symbol `$` is used in names when they conflict with the names in the base Java class - * that Scala pimp is shadowing or with Java package name that your Scala code is importing. - * Instead of giving two different names to the same function we've decided to simply mark - * Scala's side method with `$` suffix. - */ -class ScalarGridPimp extends ScalarProjectionPimp[IgniteCluster] with ScalarTaskThreadContext[IgniteCluster] { - /** - * Schedules closure for execution using local cron-based scheduling. - * - * @param s Closure to schedule to run as a background cron-based job. - * @param ptrn Scheduling pattern in UNIX cron format with optional prefix `{n1, n2}` - * where `n1` is delay of scheduling in seconds and `n2` is the number of execution. Both - * parameters are optional. - */ - def scheduleLocalCall[R](@Nullable s: Call[R], ptrn: String): SchedulerFuture[R] = { - assert(ptrn != null) - - value.ignite().scheduler().scheduleLocal(toCallable(s), ptrn) - } - - /** - * Schedules closure for execution using local cron-based scheduling. - * - * @param s Closure to schedule to run as a background cron-based job. - * @param ptrn Scheduling pattern in UNIX cron format with optional prefix `{n1, n2}` - * where `n1` is delay of scheduling in seconds and `n2` is the number of execution. Both - * parameters are optional. - */ - def scheduleLocalRun(@Nullable s: Run, ptrn: String): SchedulerFuture[_] = { - assert(ptrn != null) - - value.ignite().scheduler().scheduleLocal(toRunnable(s), ptrn) - } -} diff --git a/modules/scalar/src/main/scala/org/apache/ignite/scalar/pimps/ScalarProjectionPimp.scala b/modules/scalar/src/main/scala/org/apache/ignite/scalar/pimps/ScalarProjectionPimp.scala deleted file mode 100644 index b1a6b4f739bb0..0000000000000 --- a/modules/scalar/src/main/scala/org/apache/ignite/scalar/pimps/ScalarProjectionPimp.scala +++ /dev/null @@ -1,649 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.pimps - -import org.apache.ignite.cluster.{ClusterGroupEmptyException, ClusterGroup, ClusterNode} -import org.apache.ignite.lang.{IgniteFuture, IgnitePredicate} -import org.jetbrains.annotations._ - -/** - * Companion object. - */ -object ScalarProjectionPimp { - /** - * Creates new Scalar projection pimp with given Java-side implementation. - * - * @param impl Java-side implementation. - */ - def apply(impl: ClusterGroup) = { - if (impl == null) - throw new NullPointerException("impl") - - val pimp = new ScalarProjectionPimp[ClusterGroup] - - pimp.impl = impl - - pimp - } -} - -/** - * ==Overview== - * Defines Scalar "pimp" for `GridProjection` on Java side. - * - * Essentially this class extends Java `GridProjection` interface with Scala specific - * API adapters using primarily implicit conversions defined in `ScalarConversions` object. What - * it means is that you can use functions defined in this class on object - * of Java `GridProjection` type. Scala will automatically (implicitly) convert it into - * Scalar's pimp and replace the original call with a call on that pimp. - * - * Note that Scalar provide extensive library of implicit conversion between Java and - * Scala Ignite counterparts in `ScalarConversions` object - * - * ==Suffix '$' In Names== - * Symbol `$` is used in names when they conflict with the names in the base Java class - * that Scala pimp is shadowing or with Java package name that your Scala code is importing. - * Instead of giving two different names to the same function we've decided to simply mark - * Scala's side method with `$` suffix. - */ -class ScalarProjectionPimp[A <: ClusterGroup] extends PimpedType[A] with Iterable[ClusterNode] - with ScalarTaskThreadContext[A] { - /** */ - lazy val value: A = impl - - /** */ - protected var impl: A = _ - - /** Type alias for '() => Unit'. */ - protected type Run = () => Unit - - /** Type alias for '() => R'. */ - protected type Call[R] = () => R - - /** Type alias for '(E1) => R'. */ - protected type Call1[E1, R] = (E1) => R - - /** Type alias for '(E1, E2) => R'. */ - protected type Call2[E1, E2, R] = (E1, E2) => R - - /** Type alias for '(E1, E2, E3) => R'. */ - protected type Call3[E1, E2, E3, R] = (E1, E2, E3) => R - - /** Type alias for '() => Boolean'. */ - protected type Pred = () => Boolean - - /** Type alias for '(E1) => Boolean'. */ - protected type Pred1[E1] = (E1) => Boolean - - /** Type alias for '(E1, E2) => Boolean'. */ - protected type Pred2[E1, E2] = (E1, E2) => Boolean - - /** Type alias for '(E1, E2, E3) => Boolean'. */ - protected type Pred3[E1, E2, E3] = (E1, E2, E3) => Boolean - - /** Type alias for node filter predicate. */ - protected type NF = IgnitePredicate[ClusterNode] - - /** - * Gets iterator for this projection's nodes. - */ - def iterator = nodes$(null).iterator - - /** - * Utility function to workaround issue that `GridProjection` does not permit `null` predicates. - * - * @param p Optional predicate. - * @return If `p` not `null` return projection for this predicate otherwise return pimped projection. - */ - private def forPredicate(@Nullable p: NF): ClusterGroup = - if (p != null) value.forPredicate(p) else value - - /** - * Gets sequence of all nodes in this projection for given predicate. - * - * @param p Optional node filter predicates. It `null` provided - all nodes will be returned. - * @see `org.apache.ignite.cluster.ClusterGroup.nodes(...)` - */ - def nodes$(@Nullable p: NF): Seq[ClusterNode] = - toScalaSeq(forPredicate(p).nodes()) - - /** - * Gets sequence of all remote nodes in this projection for given predicate. - * - * @param p Optional node filter predicate. It `null` provided - all remote nodes will be returned. - * @see `org.apache.ignite.cluster.ClusterGroup.remoteNodes(...)` - */ - def remoteNodes$(@Nullable p: NF = null): Seq[ClusterNode] = - toScalaSeq(forPredicate(p).forRemotes().nodes()) - - /** - * Alias for method `send$(...)`. - * - * @param obj Optional object to send. If `null` - this method is no-op. - * @param p Optional node filter predicates. If none provided or `null` - - * all nodes in the projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.send(...)` - */ - def !<(@Nullable obj: AnyRef, @Nullable p: NF) { - value.ignite().message(forPredicate(p)).send(null, obj) - } - - /** - * Alias for method `send$(...)`. - * - * @param seq Optional sequence of objects to send. If empty or `null` - this - * method is no-op. - * @param p Optional node filter predicate. If none provided or `null` - - * all nodes in the projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.send(...)` - */ - def !<(@Nullable seq: Seq[AnyRef], @Nullable p: NF) { - value.ignite().message(forPredicate(p)).send(null, seq) - } - - /** - * Sends given object to the nodes in this projection. - * - * @param obj Optional object to send. If `null` - this method is no-op. - * @param p Optional node filter predicate. If none provided or `null` - - * all nodes in the projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.send(...)` - */ - def send$(@Nullable obj: AnyRef, @Nullable p: NF) { - value.ignite().message(forPredicate(p)).send(null, obj) - } - - /** - * Sends given object to the nodes in this projection. - * - * @param seq Optional sequence of objects to send. If empty or `null` - this - * method is no-op. - * @param p Optional node filter predicate. If `null` provided - all nodes in the projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.send(...)` - */ - def send$(@Nullable seq: Seq[AnyRef], @Nullable p: NF) { - value.ignite().message(forPredicate(p)).send(null, seq) - } - - /** - * Synchronous closures call on this projection with return value. - * This call will block until all results are received and ready. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method is no-op and returns `null`. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Sequence of result values from all nodes where given closures were executed or `null` (see above). - */ - def call$[R](@Nullable s: Seq[Call[R]], @Nullable p: NF): Seq[R] = - toScalaSeq(callAsync$(s, p).get) - - /** - * Synchronous closures call on this projection with return value. - * This call will block until all results are received and ready. If this projection - * is empty than `dflt` closure will be executed and its result returned. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method is no-op and returns `null`. - * @param dflt Closure to execute if projection is empty. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Sequence of result values from all nodes where given closures were executed or `null` (see above). - */ - def callSafe[R](@Nullable s: Seq[Call[R]], dflt: () => Seq[R], @Nullable p: NF): Seq[R] = { - assert(dflt != null) - - try - call$(s, p) - catch { - case _: ClusterGroupEmptyException => dflt() - } - } - - /** - * Alias for the same function `call$`. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method is no-op and returns `null`. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Sequence of result values from all nodes where given closures were executed or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def #<[R](@Nullable s: Seq[Call[R]], @Nullable p: NF): Seq[R] = - call$(s, p) - - /** - * Synchronous closure call on this projection with return value. - * This call will block until all results are received and ready. - * - * @param s Optional closure to call. If `null` - this method is no-op and returns `null`. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Sequence of result values from all nodes where given closures were executed or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def call$[R](@Nullable s: Call[R], @Nullable p: NF): Seq[R] = - call$(Seq(s), p) - - /** - * Synchronous closure call on this projection with return value. - * This call will block until all results are received and ready. If this projection - * is empty than `dflt` closure will be executed and its result returned. - * - * @param s Optional closure to call. If `null` - this method is no-op and returns `null`. - * @param dflt Closure to execute if projection is empty. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Sequence of result values from all nodes where given closures were executed or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def callSafe[R](@Nullable s: Call[R], dflt: () => Seq[R], @Nullable p: NF): Seq[R] = { - assert(dflt != null) - - try - call$(Seq(s), p) - catch { - case _: ClusterGroupEmptyException => dflt() - } - } - - /** - * Alias for the same function `call$`. - * - * @param s Optional closure to call. If `null` - this method is no-op and returns `null`. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Sequence of result values from all nodes where given closures were executed - * or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def #<[R](@Nullable s: Call[R], @Nullable p: NF): Seq[R] = - call$(s, p) - - /** - * Synchronous closures call on this projection without return value. - * This call will block until all executions are complete. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method is no-op. - * @param p Optional node filter predicate. If `null` provided- all nodes in projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.run(...)` - */ - def run$(@Nullable s: Seq[Run], @Nullable p: NF) { - runAsync$(s, p).get - } - - /** - * Synchronous broadcast closure call on this projection without return value. - * - * @param r Closure to run all nodes in projection. - * @param p Optional node filter predicate. If `null` provided- all nodes in projection will be used. - */ - def bcastRun(@Nullable r: Run, @Nullable p: NF) { - value.ignite().compute(forPredicate(p)).broadcast(toRunnable(r)) - } - - /** - * Synchronous closures call on this projection without return value. - * This call will block until all executions are complete. If this projection - * is empty than `dflt` closure will be executed. - * - * @param s Optional sequence of closures to call. If empty or `null` - this - * method is no-op. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @param dflt Closure to execute if projection is empty. - * @see `org.apache.ignite.cluster.ClusterGroup.run(...)` - */ - def runSafe(@Nullable s: Seq[Run], @Nullable dflt: Run, @Nullable p: NF) { - try { - run$(s, p) - } - catch { - case _: ClusterGroupEmptyException => if (dflt != null) dflt() else () - } - } - - /** - * Alias alias for the same function `run$`. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method is no-op. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.run(...)` - */ - def *<(@Nullable s: Seq[Run], @Nullable p: NF) { - run$(s, p) - } - - /** - * Synchronous closure call on this projection without return value. - * This call will block until all executions are complete. - * - * @param s Optional closure to call. If empty or `null` - this method is no-op. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.run(...)` - */ - def run$(@Nullable s: Run, @Nullable p: NF) { - run$(Seq(s), p) - } - - /** - * Synchronous closure call on this projection without return value. - * This call will block until all executions are complete. If this projection - * is empty than `dflt` closure will be executed. - * - * @param s Optional closure to call. If empty or `null` - this method is no-op. - * @param dflt Closure to execute if projection is empty. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.run(...)` - */ - def runSafe(@Nullable s: Run, @Nullable dflt: Run, @Nullable p: NF) { - try { - run$(s, p) - } - catch { - case _: ClusterGroupEmptyException => if (dflt != null) dflt() else () - } - } - - /** - * Alias for the same function `run$`. - * - * @param s Optional closure to call. If empty or `null` - this method is no-op. - * @param p Optional node filter predicate. If none provided or `null` - all nodes in projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.run(...)` - */ - def *<(@Nullable s: Run, @Nullable p: NF) { - run$(s, p) - } - - /** - * Asynchronous closures call on this projection with return value. This call will - * return immediately with the future that can be used to wait asynchronously for the results. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method - * is no-op and finished future over `null` is returned. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Future of Java collection containing result values from all nodes where given - * closures were executed or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def callAsync$[R](@Nullable s: Seq[Call[R]], @Nullable p: NF): - IgniteFuture[java.util.Collection[R]] = { - val comp = value.ignite().compute(forPredicate(p)) - - comp.callAsync[R](toJavaCollection(s, (f: Call[R]) => toCallable(f))) - } - - /** - * Alias for the same function `callAsync$`. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method - * is no-op and finished future over `null` is returned. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Future of Java collection containing result values from all nodes where given - * closures were executed or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def #?[R](@Nullable s: Seq[Call[R]], @Nullable p: NF): IgniteFuture[java.util.Collection[R]] = { - callAsync$(s, p) - } - - /** - * Asynchronous closure call on this projection with return value. This call will - * return immediately with the future that can be used to wait asynchronously for the results. - * - * @param s Optional closure to call. If `null` - this method is no-op and finished - * future over `null` is returned. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Future of Java collection containing result values from all nodes where given - * closures were executed or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def callAsync$[R](@Nullable s: Call[R], @Nullable p: NF): IgniteFuture[java.util.Collection[R]] = { - callAsync$(Seq(s), p) - } - - /** - * Alias for the same function `callAsync$`. - * - * @param s Optional closure to call. If `null` - this method is no-op and finished - * future over `null` is returned. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Future of Java collection containing result values from all nodes where given - * closures were executed or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def #?[R](@Nullable s: Call[R], @Nullable p: NF): IgniteFuture[java.util.Collection[R]] = { - callAsync$(s, p) - } - - /** - * Asynchronous closures call on this projection without return value. This call will - * return immediately with the future that can be used to wait asynchronously for the results. - * - * @param s Optional sequence of absolute closures to call. If empty or `null` - this method - * is no-op and finished future over `null` will be returned. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def runAsync$(@Nullable s: Seq[Run], @Nullable p: NF): IgniteFuture[_] = { - val comp = value.ignite().compute(forPredicate(p)) - - comp.runAsync(toJavaCollection(s, (f: Run) => toRunnable(f))) - } - - /** - * Alias for the same function `runAsync$`. - * - * @param s Optional sequence of absolute closures to call. If empty or `null` - this method - * is no-op and finished future over `null` will be returned. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.call(...)` - */ - def *?(@Nullable s: Seq[Run], @Nullable p: NF): IgniteFuture[_] = { - runAsync$(s, p) - } - - /** - * Asynchronous closure call on this projection without return value. This call will - * return immediately with the future that can be used to wait asynchronously for the results. - * - * @param s Optional absolute closure to call. If `null` - this method - * is no-op and finished future over `null` will be returned. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.run(...)` - */ - def runAsync$(@Nullable s: Run, @Nullable p: NF): IgniteFuture[_] = { - runAsync$(Seq(s), p) - } - - /** - * Alias for the same function `runAsync$`. - * - * @param s Optional absolute closure to call. If `null` - this method - * is no-op and finished future over `null` will be returned. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @see `org.apache.ignite.cluster.ClusterGroup.run(...)` - */ - def *?(@Nullable s: Run, @Nullable p: NF): IgniteFuture[_] = { - runAsync$(s, p) - } - - /** - * Asynchronous closures execution on this projection with reduction. This call will - * return immediately with the future that can be used to wait asynchronously for the results. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method - * is no-op and will return finished future over `null`. - * @param r Optional reduction function. If `null` - this method - * is no-op and will return finished future over `null`. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Future over the reduced result or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.reduce(...)` - */ - def reduceAsync$[R1, R2](s: Seq[Call[R1]], r: Seq[R1] => R2, @Nullable p: NF): IgniteFuture[R2] = { - assert(s != null && r != null) - - val comp = value.ignite().compute(forPredicate(p)) - - comp.callAsync(toJavaCollection(s, (f: Call[R1]) => toCallable(f)), r) - } - - /** - * Alias for the same function `reduceAsync$`. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method - * is no-op and will return finished future over `null`. - * @param r Optional reduction function. If `null` - this method - * is no-op and will return finished future over `null`. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Future over the reduced result or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.reduce(...)` - */ - def @?[R1, R2](s: Seq[Call[R1]], r: Seq[R1] => R2, @Nullable p: NF): IgniteFuture[R2] = { - reduceAsync$(s, r, p) - } - - /** - * Synchronous closures execution on this projection with reduction. - * This call will block until all results are reduced. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method - * is no-op and will return `null`. - * @param r Optional reduction function. If `null` - this method - * is no-op and will return `null`. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Reduced result or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.reduce(...)` - */ - def reduce$[R1, R2](@Nullable s: Seq[Call[R1]], @Nullable r: Seq[R1] => R2, @Nullable p: NF): R2 = - reduceAsync$(s, r, p).get - - /** - * Synchronous closures execution on this projection with reduction. - * This call will block until all results are reduced. If this projection - * is empty than `dflt` closure will be executed and its result returned. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method - * is no-op and will return `null`. - * @param r Optional reduction function. If `null` - this method - * is no-op and will return `null`. - * @param dflt Closure to execute if projection is empty. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Reduced result or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.reduce(...)` - */ - def reduceSafe[R1, R2](@Nullable s: Seq[Call[R1]], @Nullable r: Seq[R1] => R2, - dflt: () => R2, @Nullable p: NF): R2 = { - assert(dflt != null) - - try - reduceAsync$(s, r, p).get - catch { - case _: ClusterGroupEmptyException => dflt() - } - } - - /** - * Alias for the same function `reduce$`. - * - * @param s Optional sequence of closures to call. If empty or `null` - this method is no-op and will return `null`. - * @param r Optional reduction function. If `null` - this method is no-op and will return `null`. - * @param p Optional node filter predicate. If `null` provided - all nodes in projection will be used. - * @return Reduced result or `null` (see above). - * @see `org.apache.ignite.cluster.ClusterGroup.reduce(...)` - */ - def @<[R1, R2](@Nullable s: Seq[Call[R1]], @Nullable r: Seq[R1] => R2, @Nullable p: NF): R2 = - reduceAsync$(s, r, p).get - - /** - * Executes given closure on the nodes where data for provided affinity key is located. This - * is known as affinity co-location between compute grid (a closure) and in-memory data grid - * (value with affinity key). Note that implementation of multiple executions of the same closure will - * be wrapped as a single task that splits into multiple `job`s that will be mapped to nodes - * with provided affinity keys. - * - * This method will block until its execution is complete or an exception is thrown. - * All default SPI implementations configured for this grid instance will be - * used (i.e. failover, load balancing, collision resolution, etc.). - * Note that if you need greater control on any aspects of Java code execution on the grid - * you should implement `ComputeTask` which will provide you with full control over the execution. - * - * Notice that `Runnable` and `Callable` implementations must support serialization as required - * by the configured marshaller. For example, JDK marshaller will require that implementations would - * be serializable. Other marshallers, e.g. JBoss marshaller, may not have this limitation. Please consult - * with specific marshaller implementation for the details. Note that all closures and predicates in - * `org.apache.ignite.lang` package are serializable and can be freely used in the distributed - * context with all marshallers currently shipped with Ignite. - * - * @param cacheName Name of the cache to use for affinity co-location. - * @param affKey Affinity key. - * @param r Closure to affinity co-located on the node with given affinity key and execute. - * If `null` - this method is no-op. - * @param p Optional filtering predicate. If `null` provided - all nodes in this projection will be used for topology. - * @throws IgniteCheckedException Thrown in case of any error. - * @throws ClusterGroupEmptyException Thrown in case when this projection is empty. - * Note that in case of dynamic projection this method will take a snapshot of all the - * nodes at the time of this call, apply all filtering predicates, if any, and if the - * resulting collection of nodes is empty - the exception will be thrown. - * @throws IgniteInterruptedException Subclass of `IgniteException` thrown if the wait was interrupted. - * @throws IgniteFutureCancelledException Subclass of `IgniteException` thrown if computation was cancelled. - */ - def affinityRun$(cacheName: String, @Nullable affKey: Any, @Nullable r: Run, @Nullable p: NF) { - affinityRunAsync$(cacheName, affKey, r, p).get - } - - /** - * Executes given closure on the nodes where data for provided affinity key is located. This - * is known as affinity co-location between compute grid (a closure) and in-memory data grid - * (value with affinity key). Note that implementation of multiple executions of the same closure will - * be wrapped as a single task that splits into multiple `job`s that will be mapped to nodes - * with provided affinity keys. - * - * Unlike its sibling method `affinityRun(String, Collection, Runnable, GridPredicate[])` this method does - * not block and returns immediately with future. All default SPI implementations - * configured for this grid instance will be used (i.e. failover, load balancing, collision resolution, etc.). - * Note that if you need greater control on any aspects of Java code execution on the grid - * you should implement `ComputeTask` which will provide you with full control over the execution. - * - * Note that class `GridAbsClosure` implements `Runnable` and class `GridOutClosure` - * implements `Callable` interface. Note also that class `GridFunc` and typedefs provide rich - * APIs and functionality for closures and predicates based processing in Ignite. While Java interfaces - * `Runnable` and `Callable` allow for lowest common denominator for APIs - it is advisable - * to use richer Functional Programming support provided by Ignite available in `org.apache.ignite.lang` - * package. - * - * Notice that `Runnable` and `Callable` implementations must support serialization as required - * by the configured marshaller. For example, JDK marshaller will require that implementations would - * be serializable. Other marshallers, e.g. JBoss marshaller, may not have this limitation. Please consult - * with specific marshaller implementation for the details. Note that all closures and predicates in - * `org.apache.ignite.lang` package are serializable and can be freely used in the distributed - * context with all marshallers currently shipped with Ignite. - * - * @param cacheName Name of the cache to use for affinity co-location. - * @param affKey Affinity key. - * @param r Closure to affinity co-located on the node with given affinity key and execute. - * If `null` - this method is no-op. - * @param p Optional filtering predicate. If `null` provided - all nodes in this projection will be used for topology. - * @throws IgniteCheckedException Thrown in case of any error. - * @throws ClusterGroupEmptyCheckedException Thrown in case when this projection is empty. - * Note that in case of dynamic projection this method will take a snapshot of all the - * nodes at the time of this call, apply all filtering predicates, if any, and if the - * resulting collection of nodes is empty - the exception will be thrown. - * @return Non-cancellable future of this execution. - * @throws IgniteInterruptedException Subclass of `IgniteException` thrown if the wait was interrupted. - * @throws IgniteFutureCancelledException Subclass of `IgniteException` thrown if computation was cancelled. - */ - def affinityRunAsync$(cacheName: String, @Nullable affKey: Any, @Nullable r: Run, - @Nullable p: NF): IgniteFuture[_] = { - val comp = value.ignite().compute(forPredicate(p)) - - comp.affinityRunAsync(cacheName, affKey, toRunnable(r)) - } -} diff --git a/modules/scalar/src/main/scala/org/apache/ignite/scalar/pimps/ScalarTaskThreadContext.scala b/modules/scalar/src/main/scala/org/apache/ignite/scalar/pimps/ScalarTaskThreadContext.scala deleted file mode 100644 index 544ed402925a7..0000000000000 --- a/modules/scalar/src/main/scala/org/apache/ignite/scalar/pimps/ScalarTaskThreadContext.scala +++ /dev/null @@ -1,45 +0,0 @@ -/* - * 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 org.apache.ignite.scalar.pimps - -import org.apache.ignite.cluster.ClusterGroup -import org.apache.ignite.scalar.ScalarConversions -import org.jetbrains.annotations._ - -/** - * This trait provide mixin for properly typed version of `GridProjection#with...()` methods. - * - * Method on `GridProjection` always returns an instance of type `GridProjection` even when - * called on a sub-class. This trait's methods return the instance of the same type - * it was called on. - */ -trait ScalarTaskThreadContext[T <: ClusterGroup] extends ScalarConversions { this: PimpedType[T] => - /** - * Properly typed version of `Compute#withName(...)` method. - * - * @param taskName Name of the task. - */ - def withName$(@Nullable taskName: String): T = - value.ignite().compute(value).withName(taskName).asInstanceOf[T] - - /** - * Properly typed version of `Compute#withNoFailover()` method. - */ - def withNoFailover$(): T = - value.ignite().compute(value).withNoFailover().asInstanceOf[T] -} diff --git a/modules/scalar/src/main/scala/org/apache/ignite/scalar/scalar.scala b/modules/scalar/src/main/scala/org/apache/ignite/scalar/scalar.scala deleted file mode 100644 index 35c95fc23ab15..0000000000000 --- a/modules/scalar/src/main/scala/org/apache/ignite/scalar/scalar.scala +++ /dev/null @@ -1,472 +0,0 @@ -/* - * 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 org.apache.ignite.scalar - -import org.apache.ignite._ -import org.apache.ignite.cache.CacheMode -import org.apache.ignite.cache.query.annotations.{QuerySqlField, QueryTextField} -import org.apache.ignite.cluster.ClusterNode -import org.apache.ignite.configuration.{CacheConfiguration, IgniteConfiguration} -import org.apache.ignite.internal.IgniteVersionUtils._ -import org.jetbrains.annotations.Nullable - -import java.net.URL -import java.util.UUID - -import scala.annotation.meta.field - -/** - * {{{ - * ________ ______ ______ _______ - * __ ___/_____________ ____ /______ _________ __/__ \ __ __ \ - * _____ \ _ ___/_ __ `/__ / _ __ `/__ ___/ ____/ / _ / / / - * ____/ / / /__ / /_/ / _ / / /_/ / _ / _ __/___/ /_/ / - * /____/ \___/ \__,_/ /_/ \__,_/ /_/ /____/_(_)____/ - * - * }}} - * - * ==Overview== - * `scalar` is the main object that encapsulates Scalar DSL. It includes global functions - * on "scalar" keyword, helper converters as well as necessary implicit conversions. `scalar` also - * mimics many methods in `Ignite` class from Java side. - * - * The idea behind Scalar DSL - '''zero additional logic and only conversions''' implemented - * using Scala "Pimp" pattern. Note that most of the Scalar DSL development happened on Java - * side of Ignite 3.0 product line - Java APIs had to be adjusted quite significantly to - * support natural adaptation of functional APIs. That basically means that all functional - * logic must be available on Java side and Scalar only provides conversions from Scala - * language constructs to Java constructs. Note that currently Ignite supports Scala 2.8 - * and up only. - * - * This design approach ensures that Java side does not starve and usage paradigm - * is mostly the same between Java and Scala - yet with full power of Scala behind. - * In other words, Scalar only adds Scala specifics, but not greatly altering semantics - * of how Ignite APIs work. Most of the time the code in Scalar can be written in - * Java in almost the same number of lines. - * - * ==Suffix '$' In Names== - * Symbol `$` is used in names when they conflict with the names in the base Java class - * that Scala pimp is shadowing or with Java package name that your Scala code is importing. - * Instead of giving two different names to the same function we've decided to simply mark - * Scala's side method with `$` suffix. - * - * ==Importing== - * Scalar needs to be imported in a proper way so that necessary objects and implicit - * conversions got available in the scope: - *
- * import org.apache.ignite.scalar._ - * import scalar._ - *- * This way you import object `scalar` as well as all methods declared or inherited in that - * object as well. - * - * ==Examples== - * Here are few short examples of how Scalar can be used to program routine distributed - * task. All examples below use default Ignite configuration and default grid. All these - * examples take an implicit advantage of auto-discovery and failover, load balancing and - * collision resolution, zero deployment and many other underlying technologies in the - * Ignite - while remaining absolutely distilled to the core domain logic. - * - * This code snippet prints out full topology: - *
- * scalar { - * grid$ foreach (n => println("Node: " + n.id8)) - * } - *- * The obligatory example - cloud enabled `Hello World!`. It splits the phrase - * into multiple words and prints each word on a separate grid node: - *
- * scalar { - * grid$ *< (SPREAD, (for (w <- "Hello World!".split(" ")) yield () => println(w))) - * } - *- * This example broadcasts message to all nodes: - *
- * scalar { - * grid$ *< (BROADCAST, () => println("Broadcasting!!!")) - * } - *- * This example "greets" remote nodes only (note usage of Java-side closure): - *
- * scalar { - * val me = grid$.localNode.id - * grid$.remoteProjection() *< (BROADCAST, F.println("Greetings from: " + me)) - * } - *- * - * Next example creates a function that calculates lengths of the string - * using MapReduce type of processing by splitting the input string into - * multiple substrings, calculating each substring length on the remote - * node and aggregating results for the final length of the original string: - *
- * def count(msg: String) = - * grid$ @< (SPREAD, for (w <- msg.split(" ")) yield () => w.length, (s: Seq[Int]) => s.sum) - *- * This example shows a simple example of how Scalar can be used to work with in-memory data grid: - *
- * scalar { - * val t = cache$[Symbol, Double]("partitioned") - * t += ('symbol -> 2.0) - * t -= ('symbol) - * } - *- */ -object scalar extends ScalarConversions { - /** Type alias for `QuerySqlField`. */ - type ScalarCacheQuerySqlField = QuerySqlField @field - - /** Type alias for `QueryTextField`. */ - type ScalarCacheQueryTextField = QueryTextField @field - - /** - * Prints Scalar ASCII-logo. - */ - def logo() { - val NL = System getProperty "line.separator" - - val s = - " ________ ______ " + NL + - " __ ___/_____________ ____ /______ _________ " + NL + - " _____ \\ _ ___/_ __ `/__ / _ __ `/__ ___/ " + NL + - " ____/ / / /__ / /_/ / _ / / /_/ / _ / " + NL + - " /____/ \\___/ \\__,_/ /_/ \\__,_/ /_/ " + NL + NL + - " IGNITE SCALAR" + - " " + COPYRIGHT + NL - - println(s) - } - - /** - * Note that grid instance will be stopped with cancel flat set to `true`. - * - * @param g Grid instance. - * @param body Closure with grid instance as body's parameter. - */ - private def init[T](g: Ignite, body: Ignite => T): T = { - assert(g != null, body != null) - - try { - body(g) - } - finally { - Ignition.stop(g.name, true) - } - } - - /** - * Note that grid instance will be stopped with cancel flat set to `true`. - * - * @param g Grid instance. - * @param body Passed by name body. - */ - private def init0[T](g: Ignite, body: => T): T = { - assert(g != null) - - try { - body - } - finally { - Ignition.stop(g.name, true) - } - } - - /** - * Executes given closure within automatically managed default grid instance. - * If default grid is already started the passed in closure will simply - * execute. - * - * @param body Closure to execute within automatically managed default grid instance. - */ - def apply(body: Ignite => Unit) { - if (!isStarted) init(Ignition.start, body) else body(ignite$) - } - - /** - * Executes given closure within automatically managed default grid instance. - * If default grid is already started the passed in closure will simply - * execute. - * - * @param body Closure to execute within automatically managed default grid instance. - */ - def apply[T](body: Ignite => T): T = - if (!isStarted) init(Ignition.start, body) else body(ignite$) - - /** - * Executes given closure within automatically managed default grid instance. - * If default grid is already started the passed in closure will simply - * execute. - * - * @param body Closure to execute within automatically managed default grid instance. - */ - def apply[T](body: => T): T = - if (!isStarted) init0(Ignition.start, body) else body - - /** - * Executes given closure within automatically managed default grid instance. - * If default grid is already started the passed in closure will simply - * execute. - * - * @param body Closure to execute within automatically managed grid instance. - */ - def apply(body: => Unit) { - if (!isStarted) init0(Ignition.start, body) else body - } - - /** - * Executes given closure within automatically managed grid instance. - * - * @param springCfgPath Spring XML configuration file path or URL. - * @param body Closure to execute within automatically managed grid instance. - */ - def apply(springCfgPath: String)(body: => Unit) { - init0(Ignition.start(springCfgPath), body) - } - - /** - * Executes given closure within automatically managed grid instance. - * - * @param cfg Grid configuration instance. - * @param body Closure to execute within automatically managed grid instance. - */ - def apply(cfg: IgniteConfiguration)(body: => Unit) { - init0(Ignition.start(cfg), body) - } - - /** - * Executes given closure within automatically managed grid instance. - * - * @param springCfgUrl Spring XML configuration file URL. - * @param body Closure to execute within automatically managed grid instance. - */ - def apply(springCfgUrl: URL)(body: => Unit) { - init0(Ignition.start(springCfgUrl), body) - } - - /** - * Gets named cache from default grid. - * - * @param cacheName Name of the cache to get. - */ - @inline def cache$[K, V](cacheName: String): Option[IgniteCache[K, V]] = - Option(Ignition.ignite.cache(cacheName)) - - /** - * Creates cache with specified parameters in default grid. - * - * @param cacheName Name of the cache to get. - */ - @inline def createCache$[K, V](cacheName: String, cacheMode: CacheMode = CacheMode.PARTITIONED, - indexedTypes: Seq[Class[_]] = Seq.empty): IgniteCache[K, V] = { - val cfg = new CacheConfiguration[K, V]() - - cfg.setName(cacheName) - cfg.setCacheMode(cacheMode) - cfg.setIndexedTypes(indexedTypes:_*) - - Ignition.ignite.createCache(cfg) - } - - /** - * Destroy cache with specified name. - * - * @param cacheName Name of the cache to destroy. - */ - @inline def destroyCache$(cacheName: String) = { - Ignition.ignite.destroyCache(cacheName) - } - - /** - * Gets named cache from specified grid. - * - * @param igniteInstanceName Name of the Ignite instance. - * @param cacheName Name of the cache to get. - */ - @inline def cache$[K, V](@Nullable igniteInstanceName: String, - cacheName: String): Option[IgniteCache[K, V]] = - ignite$(igniteInstanceName) match { - case Some(g) => Option(g.cache(cacheName)) - case None => None - } - - /** - * Gets a new instance of data streamer associated with given cache name. - * - * @param cacheName Cache name (`null` for default cache). - * @param bufSize Per node buffer size. - * @return New instance of data streamer. - */ - @inline def dataStreamer$[K, V]( - cacheName: String, - bufSize: Int): IgniteDataStreamer[K, V] = { - val dl = ignite$.dataStreamer[K, V](cacheName) - - dl.perNodeBufferSize(bufSize) - - dl - } - - /** - * Gets default grid instance. - */ - @inline def ignite$: Ignite = Ignition.ignite - - /** - * Gets node ID as ID8 string. - */ - def nid8$(node: ClusterNode) = node.id().toString.take(8).toUpperCase - - /** - * Gets named Ignite instance. - * - * @param name Ignite instance name. - */ - @inline def ignite$(@Nullable name: String): Option[Ignite] = - try { - Option(Ignition.ignite(name)) - } - catch { - case _: IllegalStateException => None - } - - /** - * Gets grid for given node ID. - * - * @param locNodeId Local node ID for which to get grid instance option. - */ - @inline def grid$(locNodeId: UUID): Option[Ignite] = { - assert(locNodeId != null) - - try { - Option(Ignition.ignite(locNodeId)) - } - catch { - case _: IllegalStateException => None - } - } - - /** - * Tests if specified grid is started. - * - * @param name Gird name. - */ - def isStarted(@Nullable name: String) = - Ignition.state(name) == IgniteState.STARTED - - /** - * Tests if specified grid is stopped. - * - * @param name Gird name. - */ - def isStopped(@Nullable name: String) = - Ignition.state(name) == IgniteState.STOPPED - - /** - * Tests if default grid is started. - */ - def isStarted = - Ignition.state == IgniteState.STARTED - - /** - * Tests if default grid is stopped. - */ - def isStopped = - Ignition.state == IgniteState.STOPPED - - /** - * Stops given Ignite instance and specified cancel flag. - * If specified Ignite instance is already stopped - it's no-op. - * - * @param name Ignite instance name to cancel. - * @param cancel Whether or not to cancel all currently running jobs. - */ - def stop(@Nullable name: String, cancel: Boolean) = - if (isStarted(name)) - Ignition.stop(name, cancel) - - /** - * Stops default grid with given cancel flag. - * If default grid is already stopped - it's no-op. - * - * @param cancel Whether or not to cancel all currently running jobs. - */ - def stop(cancel: Boolean) = - if (isStarted) Ignition.stop(cancel) - - /** - * Stops default grid with cancel flag set to `true`. - * If default grid is already stopped - it's no-op. - */ - def stop() = - if (isStarted) Ignition.stop(true) - - /** - * Sets daemon flag to grid factory. Note that this method should be called - * before grid instance starts. - * - * @param f Daemon flag to set. - */ - def daemon(f: Boolean) { - Ignition.setDaemon(f) - } - - /** - * Gets daemon flag set in the grid factory. - */ - def isDaemon = - Ignition.isDaemon - - /** - * Starts default grid. It's no-op if default grid is already started. - * - * @return Started grid. - */ - def start(): Ignite = { - if (!isStarted) Ignition.start else ignite$ - } - - /** - * Starts grid with given parameter(s). - * - * @param springCfgPath Spring XML configuration file path or URL. - * @return Started grid. If Spring configuration contains multiple grid instances, - * then the 1st found instance is returned. - */ - def start(@Nullable springCfgPath: String): Ignite = { - Ignition.start(springCfgPath) - } - - /** - * Starts grid with given parameter(s). - * - * @param cfg Grid configuration. This cannot be `null`. - * @return Started grid. - */ - def start(cfg: IgniteConfiguration): Ignite = { - Ignition.start(cfg) - } - - /** - * Starts grid with given parameter(s). - * - * @param springCfgUrl Spring XML configuration file URL. - * @return Started grid. - */ - def start(springCfgUrl: URL): Ignite = { - Ignition.start(springCfgUrl) - } -} diff --git a/modules/scalar/src/test/resources/spring-cache.xml b/modules/scalar/src/test/resources/spring-cache.xml deleted file mode 100644 index fab6d55f68259..0000000000000 --- a/modules/scalar/src/test/resources/spring-cache.xml +++ /dev/null @@ -1,88 +0,0 @@ - - - - -