http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/QueryBase.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/QueryBase.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/QueryBase.cs new file mode 100644 index 0000000..3cb9e58 --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/QueryBase.cs @@ -0,0 +1,82 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cache.Query +{ + using Apache.Ignite.Core.Impl.Cache; + using Apache.Ignite.Core.Impl.Portable; + + /// <summary> + /// Base class for all Ignite cache entry queries. + /// </summary> + public abstract class QueryBase + { + /** Default page size. */ + public const int DfltPageSize = 1024; + + /// <summary> + /// Initializes a new instance of the <see cref="QueryBase"/> class. + /// </summary> + protected internal QueryBase() + { + PageSize = DfltPageSize; + } + + /// <summary> + /// Local flag. When set query will be executed only on local node, so only local + /// entries will be returned as query result. + /// <para /> + /// Defaults to <c>false</c>. + /// </summary> + public bool Local { get; set; } + + /// <summary> + /// Optional page size. If set to <code>0</code>, then <code>CacheQueryConfiguration.pageSize</code> is used. + /// </summary> + public int PageSize { get; set; } + + /// <summary> + /// Writes this instance to a stream created with a specified delegate. + /// </summary> + /// <param name="writer">Writer.</param> + /// <param name="keepPortable">Keep portable flag.</param> + internal abstract void Write(PortableWriterImpl writer, bool keepPortable); + + /// <summary> + /// Gets the interop opcode. + /// </summary> + internal abstract CacheOp OpId { get; } + + /// <summary> + /// Write query arguments. + /// </summary> + /// <param name="writer">Writer.</param> + /// <param name="args">Arguments.</param> + internal static void WriteQueryArgs(PortableWriterImpl writer, object[] args) + { + if (args == null) + writer.WriteInt(0); + else + { + writer.WriteInt(args.Length); + + foreach (var arg in args) + writer.WriteObject(arg); + } + } + } +}
http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/ScanQuery.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/ScanQuery.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/ScanQuery.cs new file mode 100644 index 0000000..44f8486 --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/ScanQuery.cs @@ -0,0 +1,77 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +namespace Apache.Ignite.Core.Cache.Query +{ + using Apache.Ignite.Core.Impl.Cache; + using Apache.Ignite.Core.Impl.Portable; + + /// <summary> + /// Scan query over cache entries. Will accept all the entries if no predicate was set. + /// </summary> + public class ScanQuery<TK, TV> : QueryBase + { + /// <summary> + /// Initializes a new instance of the <see cref="ScanQuery{K, V}"/> class. + /// </summary> + /// <param name="filter">The filter.</param> + public ScanQuery(ICacheEntryFilter<TK, TV> filter = null) + { + Filter = filter; + } + + /// <summary> + /// Gets or sets the predicate. + /// </summary> + public ICacheEntryFilter<TK, TV> Filter { get; set; } + + /// <summary> + /// Gets or sets partition number over which this query should iterate. If null, query will iterate + /// over all partitions in the cache. Must be in the range [0, N) where N is partition number in the cache. + /// </summary> + public int? Partition { get; set; } + + /** <inheritDoc /> */ + internal override void Write(PortableWriterImpl writer, bool keepPortable) + { + writer.WriteBoolean(Local); + writer.WriteInt(PageSize); + + writer.WriteBoolean(Partition.HasValue); + + if (Partition.HasValue) + writer.WriteInt(Partition.Value); + + if (Filter == null) + writer.WriteObject<CacheEntryFilterHolder>(null); + else + { + var holder = new CacheEntryFilterHolder(Filter, (key, val) => Filter.Invoke( + new CacheEntry<TK, TV>((TK) key, (TV) val)), writer.Marshaller, keepPortable); + + writer.WriteObject(holder); + writer.WriteLong(holder.Handle); + } + } + + /** <inheritDoc /> */ + internal override CacheOp OpId + { + get { return CacheOp.QryScan; } + } + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/SqlFieldsQuery.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/SqlFieldsQuery.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/SqlFieldsQuery.cs new file mode 100644 index 0000000..c0d58ca --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/SqlFieldsQuery.cs @@ -0,0 +1,81 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cache.Query +{ + using System.Diagnostics.CodeAnalysis; + + /// <summary> + /// SQL fields query. + /// </summary> + public class SqlFieldsQuery + { + /** Default page size. */ + public const int DfltPageSize = 1024; + + /// <summary> + /// Constructor. + /// </summary> + /// <param name="sql">SQL.</param> + /// <param name="args">Arguments.</param> + public SqlFieldsQuery(string sql, params object[] args) : this(sql, false, args) + { + // No-op. + } + + /// <summary> + /// Constructor, + /// </summary> + /// <param name="sql">SQL.</param> + /// <param name="loc">Whether query should be executed locally.</param> + /// <param name="args">Arguments.</param> + public SqlFieldsQuery(string sql, bool loc, params object[] args) + { + Sql = sql; + Local = loc; + Arguments = args; + + PageSize = DfltPageSize; + } + + /// <summary> + /// SQL. + /// </summary> + public string Sql { get; set; } + + /// <summary> + /// Arguments. + /// </summary> + [SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")] + public object[] Arguments { get; set; } + + /// <summary> + /// Local flag. When set query will be executed only on local node, so only local + /// entries will be returned as query result. + /// <para /> + /// Defaults to <c>false</c>. + /// </summary> + public bool Local { get; set; } + + /// <summary> + /// Optional page size. + /// <para /> + /// Defautls to <see cref="DfltPageSize"/>. + /// </summary> + public int PageSize { get; set; } + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/SqlQuery.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/SqlQuery.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/SqlQuery.cs new file mode 100644 index 0000000..303048b --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/SqlQuery.cs @@ -0,0 +1,119 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cache.Query +{ + using System; + using System.Diagnostics.CodeAnalysis; + using Apache.Ignite.Core.Impl.Cache; + using Apache.Ignite.Core.Impl.Portable; + + /// <summary> + /// SQL Query. + /// </summary> + public class SqlQuery : QueryBase + { + /// <summary> + /// Constructor. + /// </summary> + /// <param name="typ">Type.</param> + /// <param name="sql">SQL.</param> + /// <param name="args">Arguments.</param> + public SqlQuery(Type typ, string sql, params object[] args) : this(typ, sql, false, args) + { + // No-op. + } + + /// <summary> + /// Constructor. + /// </summary> + /// <param name="typ">Type.</param> + /// <param name="sql">SQL.</param> + /// <param name="loc">Whether query should be executed locally.</param> + /// <param name="args">Arguments.</param> + public SqlQuery(Type typ, string sql, bool loc, params object[] args) : this(typ.Name, sql, loc, args) + { + // No-op. + } + + /// <summary> + /// Constructor. + /// </summary> + /// <param name="typ">Type.</param> + /// <param name="sql">SQL.</param> + /// <param name="args">Arguments.</param> + public SqlQuery(string typ, string sql, params object[] args) : this(typ, sql, false, args) + { + // No-op. + } + + /// <summary> + /// Constructor. + /// </summary> + /// <param name="typ">Type.</param> + /// <param name="sql">SQL.</param> + /// <param name="loc">Whether query should be executed locally.</param> + /// <param name="args">Arguments.</param> + public SqlQuery(string typ, string sql, bool loc, params object[] args) + { + Type = typ; + Sql = sql; + Local = loc; + Arguments = args; + } + + /// <summary> + /// Type. + /// </summary> + public string Type { get; set; } + + /// <summary> + /// SQL. + /// </summary> + public string Sql { get; set; } + + /// <summary> + /// Arguments. + /// </summary> + [SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")] + public object[] Arguments { get; set; } + + /** <inheritDoc /> */ + internal override void Write(PortableWriterImpl writer, bool keepPortable) + { + if (string.IsNullOrEmpty(Sql)) + throw new ArgumentException("Sql cannot be null or empty"); + + if (string.IsNullOrEmpty(Type)) + throw new ArgumentException("Type cannot be null or empty"); + + // 2. Prepare. + writer.WriteBoolean(Local); + writer.WriteString(Sql); + writer.WriteString(Type); + writer.WriteInt(PageSize); + + WriteQueryArgs(writer, Arguments); + } + + /** <inheritDoc /> */ + internal override CacheOp OpId + { + get { return CacheOp.QrySql; } + } + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/TextQuery.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/TextQuery.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/TextQuery.cs new file mode 100644 index 0000000..835271b --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Query/TextQuery.cs @@ -0,0 +1,104 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +namespace Apache.Ignite.Core.Cache.Query +{ + using System; + using Apache.Ignite.Core.Impl.Cache; + using Apache.Ignite.Core.Impl.Portable; + + /// <summary> + /// Text query. + /// </summary> + public class TextQuery : QueryBase + { + /// <summary> + /// Constructor. + /// </summary> + /// <param name="typ">Type.</param> + /// <param name="txt">Text.</param> + public TextQuery(Type typ, string txt) : this(typ, txt, false) + { + // No-op. + } + + /// <summary> + /// Constructor. + /// </summary> + /// <param name="typ">Type.</param> + /// <param name="txt">Text.</param> + /// <param name="loc">Whether query should be executed locally.</param> + public TextQuery(Type typ, string txt, bool loc) : this(typ.Name, txt, loc) + { + // No-op. + } + + /// <summary> + /// Constructor. + /// </summary> + /// <param name="typ">Type.</param> + /// <param name="txt">Text.</param> + public TextQuery(string typ, string txt) : this(typ, txt, false) + { + // No-op. + } + + /// <summary> + /// Constructor. + /// </summary> + /// <param name="typ">Type.</param> + /// <param name="txt">Text.</param> + /// <param name="loc">Whether query should be executed locally.</param> + public TextQuery(string typ, string txt, bool loc) + { + Type = typ; + Text = txt; + Local = loc; + } + + /// <summary> + /// Type. + /// </summary> + public string Type { get; set; } + + /// <summary> + /// Text. + /// </summary> + public string Text { get; set; } + + /** <inheritDoc /> */ + internal override void Write(PortableWriterImpl writer, bool keepPortable) + { + if (string.IsNullOrEmpty(Text)) + throw new ArgumentException("Text cannot be null or empty"); + + if (string.IsNullOrEmpty(Type)) + throw new ArgumentException("Type cannot be null or empty"); + + writer.WriteBoolean(Local); + writer.WriteString(Text); + writer.WriteString(Type); + writer.WriteInt(PageSize); + } + + /** <inheritDoc /> */ + internal override CacheOp OpId + { + get { return CacheOp.QryTxt; } + } + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheParallelLoadStoreAdapter.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheParallelLoadStoreAdapter.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheParallelLoadStoreAdapter.cs new file mode 100644 index 0000000..cf4a77d --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheParallelLoadStoreAdapter.cs @@ -0,0 +1,205 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cache.Store +{ + using System; + using System.Collections; + using System.Collections.Generic; + using System.Linq; + using System.Threading.Tasks; + + /// <summary> + /// Cache storage adapter with parallel loading in LoadAll method. + /// </summary> + /// <remarks> + /// LoadCache calls GetInputData() and iterates over it in parallel. + /// GetInputData().GetEnumerator() result will be disposed if it implements IDisposable. + /// Any additional post-LoadCache steps can be performed by overriding LoadCache method. + /// </remarks> + public abstract class CacheParallelLoadStoreAdapter : ICacheStore + { + /// <summary> + /// Default number of working threads (equal to the number of available processors). + /// </summary> + public static readonly int DefaultThreadsCount = Environment.ProcessorCount; + + /// <summary> + /// Constructor. + /// </summary> + protected CacheParallelLoadStoreAdapter() + { + MaxDegreeOfParallelism = DefaultThreadsCount; + } + + /// <summary> + /// Loads all values from underlying persistent storage. Note that keys are + /// not passed, so it is up to implementation to figure out what to load. + /// This method is called whenever <see cref="ICache{K,V}.LocalLoadCache" /> + /// method is invoked which is usually to preload the cache from persistent storage. + /// <para /> + /// This method is optional, and cache implementation + /// does not depend on this method to do anything. + /// <para /> + /// For every loaded value method provided action should be called. + /// The action will then make sure that the loaded value is stored in cache. + /// </summary> + /// <param name="act">Action for loaded values.</param> + /// <param name="args">Optional arguemnts passed to <see cref="ICache{K,V}.LocalLoadCache" /> method.</param> + /// <exception cref="CacheStoreException" /> + public virtual void LoadCache(Action<object, object> act, params object[] args) + { + if (MaxDegreeOfParallelism == 0 || MaxDegreeOfParallelism < -1) + throw new ArgumentOutOfRangeException("MaxDegreeOfParallelism must be either positive or -1: " + + MaxDegreeOfParallelism); + + var options = new ParallelOptions {MaxDegreeOfParallelism = MaxDegreeOfParallelism}; + + Parallel.ForEach(GetInputData().OfType<object>(), options, item => + { + var cacheEntry = Parse(item, args); + + if (cacheEntry != null) + act(cacheEntry.Value.Key, cacheEntry.Value.Value); + }); + } + + /// <summary> + /// Gets the input data sequence to be used in LoadCache. + /// </summary> + protected abstract IEnumerable GetInputData(); + + /// <summary> + /// This method should transform raw data records from GetInputData + /// into valid key-value pairs to be stored into cache. + /// </summary> + protected abstract KeyValuePair<object, object>? Parse(object inputRecord, params object[] args); + + /// <summary> + /// Gets or sets the maximum degree of parallelism to use in LoadCache. + /// Must be either positive or -1 for unlimited amount of threads. + /// <para /> + /// Defaults to <see cref="DefaultThreadsCount"/>. + /// </summary> + public int MaxDegreeOfParallelism { get; set; } + + /// <summary> + /// Loads an object. Application developers should implement this method to customize the loading + /// of a value for a cache entry. + /// This method is called by a cache when a requested entry is not in the cache. + /// If the object can't be loaded <code>null</code> should be returned. + /// </summary> + /// <param name="key">The key identifying the object being loaded.</param> + /// <returns> + /// The value for the entry that is to be stored in the cache + /// or <code>null</code> if the object can't be loaded + /// </returns> + public virtual object Load(object key) + { + return null; + } + + /// <summary> + /// Loads multiple objects. Application developers should implement this method to customize + /// the loading of cache entries. This method is called when the requested object is not in the cache. + /// If an object can't be loaded, it is not returned in the resulting map. + /// </summary> + /// <param name="keys">Keys identifying the values to be loaded.</param> + /// <returns> + /// A map of key, values to be stored in the cache. + /// </returns> + public virtual IDictionary LoadAll(ICollection keys) + { + return null; + } + + /// <summary> + /// Write the specified value under the specified key to the external resource. + /// <para /> + /// This method is intended to support both key/value creation and value update. + /// </summary> + /// <param name="key">Key to write.</param> + /// <param name="val">Value to write.</param> + public virtual void Write(object key, object val) + { + // No-op. + } + + /// <summary> + /// Write the specified entries to the external resource. + /// This method is intended to support both insert and update. + /// <para /> + /// The order that individual writes occur is undefined. + /// <para /> + /// If this operation fails (by throwing an exception) after a partial success, + /// the writer must remove any successfully written entries from the entries collection + /// so that the caching implementation knows what succeeded and can mutate the cache. + /// </summary> + /// <param name="entries">a mutable collection to write. Upon invocation, it contains the entries + /// to write for write-through. Upon return the collection must only contain entries + /// that were not successfully written. (see partial success above).</param> + public virtual void WriteAll(IDictionary entries) + { + // No-op. + } + + /// <summary> + /// Delete the cache entry from the external resource. + /// <para /> + /// Expiry of a cache entry is not a delete hence will not cause this method to be invoked. + /// <para /> + /// This method is invoked even if no mapping for the key exists. + /// </summary> + /// <param name="key">The key that is used for the delete operation.</param> + public virtual void Delete(object key) + { + // No-op. + } + + /// <summary> + /// Remove data and keys from the external resource for the given collection of keys, if present. + /// <para /> + /// The order that individual deletes occur is undefined. + /// <para /> + /// If this operation fails (by throwing an exception) after a partial success, + /// the writer must remove any successfully written entries from the entries collection + /// so that the caching implementation knows what succeeded and can mutate the cache. + /// <para /> + /// Expiry of a cache entry is not a delete hence will not cause this method to be invoked. + /// <para /> + /// This method may include keys even if there is no mapping for that key, + /// in which case the data represented by that key should be removed from the underlying resource. + /// </summary> + /// <param name="keys">a mutable collection of keys for entries to delete. Upon invocation, + /// it contains the keys to delete for write-through. Upon return the collection must only contain + /// the keys that were not successfully deleted.</param> + public virtual void DeleteAll(ICollection keys) + { + // No-op. + } + + /// <summary> + /// Tells store to commit or rollback a transaction depending on the value of the + /// <c>commit</c> parameter. + /// </summary> + /// <param name="commit"><c>True</c> if transaction should commit, <c>false</c> for rollback.</param> + public virtual void SessionEnd(bool commit) + { + // No-op. + } + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheStoreAdapter.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheStoreAdapter.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheStoreAdapter.cs new file mode 100644 index 0000000..1930d0c --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheStoreAdapter.cs @@ -0,0 +1,146 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cache.Store +{ + using System; + using System.Collections; + using System.Linq; + + /// <summary> + /// Cache storage convenience adapter. It provides default implementation for + /// bulk operations, such as <code>LoadAll</code>, <code>PutAll</code> and + /// <code>RemoveAll</code> by sequentially calling corresponding <code>Load</code>, + /// <code>Put</code> and <code>Remove</code> operations. Use this adapter whenever + /// such behaviour is acceptable. However in many cases it maybe more preferable + /// to take advantage of database batch update functionality, and therefore default + /// adapter implementation may not be the best option. + /// <para/> + /// Note that <code>LoadCache</code> method has empty implementation because it is + /// essentially up to the user to invoke it with specific arguments. + /// </summary> + public abstract class CacheStoreAdapter : ICacheStore + { + /// <summary> + /// Loads all values from underlying persistent storage. Note that keys are + /// not passed, so it is up to implementation to figure out what to load. + /// This method is called whenever <see cref="ICache{K,V}.LocalLoadCache" /> + /// method is invoked which is usually to preload the cache from persistent storage. + /// <para /> + /// This method is optional, and cache implementation + /// does not depend on this method to do anything. + /// <para /> + /// For every loaded value method provided action should be called. + /// The action will then make sure that the loaded value is stored in cache. + /// </summary> + /// <param name="act">Action for loaded values.</param> + /// <param name="args">Optional arguemnts passed to <see cref="ICache{K,V}.LocalLoadCache" /> method.</param> + public virtual void LoadCache(Action<object, object> act, params object[] args) + { + // No-op. + } + + /// <summary> + /// Loads multiple objects. Application developers should implement this method to customize + /// the loading of cache entries. This method is called when the requested object is not in the cache. + /// If an object can't be loaded, it is not returned in the resulting map. + /// </summary> + /// <param name="keys">Keys identifying the values to be loaded.</param> + /// <returns> + /// A map of key, values to be stored in the cache. + /// </returns> + public virtual IDictionary LoadAll(ICollection keys) + { + return keys.OfType<object>().ToDictionary(key => key, Load); + } + + /// <summary> + /// Writes all. + /// </summary> + /// <param name="entries">The map.</param> + public virtual void WriteAll(IDictionary entries) + { + foreach (DictionaryEntry entry in entries) + Write(entry.Key, entry.Value); + } + + /// <summary> + /// Remove data and keys from the external resource for the given collection of keys, if present. + /// <para /> + /// The order that individual deletes occur is undefined. + /// <para /> + /// If this operation fails (by throwing an exception) after a partial success, + /// the writer must remove any successfully written entries from the entries collection + /// so that the caching implementation knows what succeeded and can mutate the cache. + /// <para /> + /// Expiry of a cache entry is not a delete hence will not cause this method to be invoked. + /// <para /> + /// This method may include keys even if there is no mapping for that key, + /// in which case the data represented by that key should be removed from the underlying resource. + /// </summary> + /// <param name="keys">a mutable collection of keys for entries to delete. Upon invocation, + /// it contains the keys to delete for write-through. Upon return the collection must only contain + /// the keys that were not successfully deleted.</param> + public virtual void DeleteAll(ICollection keys) + { + foreach (object key in keys) + Delete(key); + } + + /// <summary> + /// Tells store to commit or rollback a transaction depending on the value of the + /// <c>commit</c> parameter. + /// </summary> + /// <param name="commit"><c>True</c> if transaction should commit, <c>false</c> for rollback.</param> + public virtual void SessionEnd(bool commit) + { + // No-op. + } + + /// <summary> + /// Loads an object. Application developers should implement this method to customize the loading + /// of a value for a cache entry. + /// This method is called by a cache when a requested entry is not in the cache. + /// If the object can't be loaded <code>null</code> should be returned. + /// </summary> + /// <param name="key">The key identifying the object being loaded.</param> + /// <returns> + /// The value for the entry that is to be stored in the cache + /// or <code>null</code> if the object can't be loaded + /// </returns> + public abstract object Load(object key); + + /// <summary> + /// Write the specified value under the specified key to the external resource. + /// <para /> + /// This method is intended to support both key/value creation and value update. + /// </summary> + /// <param name="key">Key to write.</param> + /// <param name="val">Value to write.</param> + public abstract void Write(object key, object val); + + /// <summary> + /// Delete the cache entry from the external resource. + /// <para /> + /// Expiry of a cache entry is not a delete hence will not cause this method to be invoked. + /// <para /> + /// This method is invoked even if no mapping for the key exists. + /// </summary> + /// <param name="key">The key that is used for the delete operation.</param> + public abstract void Delete(object key); + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheStoreException.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheStoreException.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheStoreException.cs new file mode 100644 index 0000000..f5f398b --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/CacheStoreException.cs @@ -0,0 +1,66 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cache.Store +{ + using System; + using System.Runtime.Serialization; + + /// <summary> + /// Indicates an error during CacheStore operation. + /// </summary> + [Serializable] + public class CacheStoreException : CacheException + { + /// <summary> + /// Initializes a new instance of the <see cref="CacheStoreException"/> class. + /// </summary> + public CacheStoreException() + { + // No-op. + } + + /// <summary> + /// Initializes a new instance of the <see cref="CacheStoreException"/> class. + /// </summary> + /// <param name="message">The message that describes the error.</param> + public CacheStoreException(string message) : base(message) + { + // No-op. + } + + /// <summary> + /// Initializes a new instance of the <see cref="CacheStoreException"/> class. + /// </summary> + /// <param name="message">The message.</param> + /// <param name="cause">The cause.</param> + public CacheStoreException(string message, Exception cause) : base(message, cause) + { + // No-op. + } + + /// <summary> + /// Initializes a new instance of the <see cref="CacheStoreException"/> class. + /// </summary> + /// <param name="info">Serialization information.</param> + /// <param name="ctx">Streaming context.</param> + protected CacheStoreException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) + { + // No-op. + } + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/ICacheStore.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/ICacheStore.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/ICacheStore.cs new file mode 100644 index 0000000..4660dab --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/ICacheStore.cs @@ -0,0 +1,184 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cache.Store +{ + using System; + using System.Collections; + using Apache.Ignite.Core.Transactions; + + /// <summary> + /// API for cache persistent storage for read-through and write-through behavior. + /// + /// Persistent store is configured in Ignite's Spring XML configuration file via + /// <c>CacheConfiguration.setStore()</c> property. If you have an implementation + /// of cache store in .NET, you should use special Java wrapper which accepts assembly name and + /// class name of .NET store implementation (both properties are mandatory). + /// + /// Optionally, you may specify "properies" property to set any property values on an instance of your store. + /// <example> + /// Here is an example: + /// <code> + /// <bean class="org.apache.ignite.configuration.CacheConfiguration"> + /// ... + /// <property name="cacheStoreFactory"> + /// <bean class="org.apache.ignite.platform.dotnet.PlatformDotNetCacheStoreFactory"> + /// <property name="assemblyName" value="MyAssembly"/> + /// <property name="className" value="MyApp.MyCacheStore"/> + /// <property name="properties"> + /// <map> + /// <entry key="IntProperty"> + /// <value type="java.lang.Integer">42</value> + /// </entry> + /// <entry key="StringProperty" value="String value"/> + /// </map> + /// </property> + /// </bean> + /// </property> + /// ... + /// </bean> + /// </code> + /// </example> + /// Assemply name and class name are passed to <a target="_blank" href="http://msdn.microsoft.com/en-us/library/d133hta4.aspx"><b>System.Activator.CreateInstance(String, String)</b></a> + /// method during node startup to create an instance of cache store. Refer to its documentation for details. + /// <para/> + /// All transactional operations of this API are provided with ongoing <see cref="ITransaction"/>, + /// if any. You can attach any metadata to transaction, e.g. to recognize if several operations + /// belong to the same transaction or not. + /// <example> + /// Here is an example of how attach a ODBC connection as transaction metadata: + /// <code> + /// OdbcConnection conn = tx.Meta("some.name"); + /// + /// if (conn == null) + /// { + /// conn = ...; // Create or get connection. + /// + /// // Store connection in transaction metadata, so it can be accessed + /// // for other operations on the same transaction. + /// tx.AddMeta("some.name", conn); + /// } + /// </code> + /// </example> + /// </summary> + public interface ICacheStore + { + /// <summary> + /// Loads all values from underlying persistent storage. Note that keys are + /// not passed, so it is up to implementation to figure out what to load. + /// This method is called whenever <see cref="ICache{K,V}.LocalLoadCache"/> + /// method is invoked which is usually to preload the cache from persistent storage. + /// <para/> + /// This method is optional, and cache implementation + /// does not depend on this method to do anything. + /// <para/> + /// For every loaded value method provided action should be called. + /// The action will then make sure that the loaded value is stored in cache. + /// </summary> + /// <param name="act">Action for loaded values.</param> + /// <param name="args">Optional arguemnts passed to <see cref="ICache{K,V}.LocalLoadCache"/> method.</param> + /// <exception cref="CacheStoreException" /> + void LoadCache(Action<object, object> act, params object[] args); + + /// <summary> + /// Loads an object. Application developers should implement this method to customize the loading + /// of a value for a cache entry. + /// This method is called by a cache when a requested entry is not in the cache. + /// If the object can't be loaded <code>null</code> should be returned. + /// </summary> + /// <param name="key">The key identifying the object being loaded.</param> + /// <returns>The value for the entry that is to be stored in the cache + /// or <code>null</code> if the object can't be loaded</returns> + /// <exception cref="CacheStoreException" /> + object Load(object key); + + /// <summary> + /// Loads multiple objects. Application developers should implement this method to customize + /// the loading of cache entries. This method is called when the requested object is not in the cache. + /// If an object can't be loaded, it is not returned in the resulting map. + /// </summary> + /// <param name="keys">Keys identifying the values to be loaded.</param> + /// <returns>A map of key, values to be stored in the cache.</returns> + /// <exception cref="CacheStoreException" /> + IDictionary LoadAll(ICollection keys); + + /// <summary> + /// Write the specified value under the specified key to the external resource. + /// <para /> + /// This method is intended to support both key/value creation and value update. + /// </summary> + /// <param name="key">Key to write.</param> + /// <param name="val">Value to write.</param> + /// <exception cref="CacheStoreException" /> + void Write(object key, object val); + + /// <summary> + /// Write the specified entries to the external resource. + /// This method is intended to support both insert and update. + /// <para /> + /// The order that individual writes occur is undefined. + /// <para /> + /// If this operation fails (by throwing an exception) after a partial success, + /// the writer must remove any successfully written entries from the entries collection + /// so that the caching implementation knows what succeeded and can mutate the cache. + /// </summary> + /// <param name="entries">a mutable collection to write. Upon invocation, it contains the entries + /// to write for write-through. Upon return the collection must only contain entries + /// that were not successfully written. (see partial success above).</param> + /// <exception cref="CacheStoreException" /> + void WriteAll(IDictionary entries); + + /// <summary> + /// Delete the cache entry from the external resource. + /// <para /> + /// Expiry of a cache entry is not a delete hence will not cause this method to be invoked. + /// <para /> + /// This method is invoked even if no mapping for the key exists. + /// </summary> + /// <param name="key">The key that is used for the delete operation.</param> + /// <exception cref="CacheStoreException" /> + void Delete(object key); + + /// <summary> + /// Remove data and keys from the external resource for the given collection of keys, if present. + /// <para /> + /// The order that individual deletes occur is undefined. + /// <para /> + /// If this operation fails (by throwing an exception) after a partial success, + /// the writer must remove any successfully written entries from the entries collection + /// so that the caching implementation knows what succeeded and can mutate the cache. + /// <para /> + /// Expiry of a cache entry is not a delete hence will not cause this method to be invoked. + /// <para /> + /// This method may include keys even if there is no mapping for that key, + /// in which case the data represented by that key should be removed from the underlying resource. + /// </summary> + /// <param name="keys">a mutable collection of keys for entries to delete. Upon invocation, + /// it contains the keys to delete for write-through. Upon return the collection must only contain + /// the keys that were not successfully deleted.</param> + /// <exception cref="CacheStoreException" /> + void DeleteAll(ICollection keys); + + /// <summary> + /// Tells store to commit or rollback a transaction depending on the value of the + /// <c>commit</c> parameter. + /// </summary> + /// <param name="commit"><c>True</c> if transaction should commit, <c>false</c> for rollback.</param> + /// <exception cref="CacheStoreException" /> + void SessionEnd(bool commit); + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/ICacheStoreSession.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/ICacheStoreSession.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/ICacheStoreSession.cs new file mode 100644 index 0000000..e20a660 --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cache/Store/ICacheStoreSession.cs @@ -0,0 +1,42 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cache.Store +{ + using System.Collections.Generic; + + /// <summary> + /// Session for the cache store operations. The main purpose of cache store session + /// is to hold context between multiple store invocations whenever in transaction. For example, + /// you can save current database connection in the session <see cref="Properties"/> map. You can then + /// commit this connection in the <see cref="ICacheStore.SessionEnd(bool)"/> method. + /// </summary> + public interface ICacheStoreSession + { + /// <summary> + /// Cache name for the current store operation. Note that if the same store + /// is reused between different caches, then the cache name will change between + /// different store operations. + /// </summary> + string CacheName { get; } + + /// <summary> + /// Current session properties. You can add properties directly to the returned map. + /// </summary> + IDictionary<object, object> Properties { get; } + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ClusterGroupEmptyException.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ClusterGroupEmptyException.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ClusterGroupEmptyException.cs new file mode 100644 index 0000000..81e4a56 --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ClusterGroupEmptyException.cs @@ -0,0 +1,70 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cluster +{ + using System; + using System.Runtime.Serialization; + using Apache.Ignite.Core.Common; + + /// <summary> + /// Indicates an illegal call on empty projection. Thrown by projection when operation + /// that requires at least one node is called on empty projection. + /// </summary> + [Serializable] + public class ClusterGroupEmptyException : IgniteException + { + /// <summary> + /// Initializes a new instance of the <see cref="ClusterGroupEmptyException"/> class. + /// </summary> + public ClusterGroupEmptyException() + { + // No-op. + } + + /// <summary> + /// Initializes a new instance of the <see cref="ClusterGroupEmptyException"/> class. + /// </summary> + /// <param name="msg">Exception message.</param> + public ClusterGroupEmptyException(string msg) : base(msg) + { + // No-op. + } + + /// <summary> + /// Initializes a new instance of the <see cref="ClusterGroupEmptyException"/> class. + /// </summary> + /// <param name="message">The message.</param> + /// <param name="cause">The cause.</param> + public ClusterGroupEmptyException(string message, Exception cause) + : base(message, cause) + { + // No-op. + } + + /// <summary> + /// Initializes a new instance of the <see cref="ClusterGroupEmptyException"/> class. + /// </summary> + /// <param name="info">Serialization info.</param> + /// <param name="ctx">Streaming context.</param> + protected ClusterGroupEmptyException(SerializationInfo info, StreamingContext ctx) + : base(info, ctx) + { + // No-op. + } + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ClusterTopologyException.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ClusterTopologyException.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ClusterTopologyException.cs new file mode 100644 index 0000000..ba30f51 --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ClusterTopologyException.cs @@ -0,0 +1,69 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cluster +{ + using System; + using System.Runtime.Serialization; + using Apache.Ignite.Core.Common; + + /// <summary> + /// Indicates an error with grid topology (e.g., crashed node, etc.) + /// </summary> + [Serializable] + public class ClusterTopologyException : IgniteException + { + /// <summary> + /// Initializes a new instance of the <see cref="ClusterTopologyException"/> class. + /// </summary> + public ClusterTopologyException() + { + // No-op. + } + + /// <summary> + /// Initializes a new instance of the <see cref="ClusterTopologyException"/> class. + /// </summary> + /// <param name="msg">Exception message.</param> + public ClusterTopologyException(string msg) : base(msg) + { + // No-op. + } + + /// <summary> + /// Initializes a new instance of the <see cref="ClusterTopologyException"/> class. + /// </summary> + /// <param name="message">The message.</param> + /// <param name="cause">The cause.</param> + public ClusterTopologyException(string message, Exception cause) + : base(message, cause) + { + // No-op. + } + + /// <summary> + /// Initializes a new instance of the <see cref="ClusterTopologyException"/> class. + /// </summary> + /// <param name="info">Serialization info.</param> + /// <param name="ctx">Streaming context.</param> + protected ClusterTopologyException(SerializationInfo info, StreamingContext ctx) + : base(info, ctx) + { + // No-op. + } + } +} \ No newline at end of file http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ICluster.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ICluster.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ICluster.cs new file mode 100644 index 0000000..405375e --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/ICluster.cs @@ -0,0 +1,80 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +namespace Apache.Ignite.Core.Cluster +{ + using System; + using System.Collections.Generic; + using Apache.Ignite.Core.Common; + + /// <summary> + /// Represents whole cluster (group of all nodes in a cluster). + /// <para/> + /// All members are thread-safe and may be used concurrently from multiple threads. + /// </summary> + public interface ICluster : IClusterGroup + { + /// <summary> + /// Gets monadic projection consisting from the local node. + /// </summary> + /// <returns>Monadic projection consisting from the local node.</returns> + IClusterGroup ForLocal(); + + /// <summary> + /// Gets local Ignite node. + /// </summary> + /// <returns>Local Ignite node.</returns> + IClusterNode LocalNode + { + get; + } + + /// <summary> + /// Pings a remote node. + /// </summary> + /// <param name="nodeId">ID of a node to ping.</param> + /// <returns>True if node for a given ID is alive, false otherwise.</returns> + bool PingNode(Guid nodeId); + + /// <summary> + /// Gets current topology version. In case of TCP discovery topology versions are sequential + /// - they start from 1 and get incremented every time whenever a node joins or leaves. + /// For other discovery SPIs topology versions may not be (and likely are not) sequential. + /// </summary> + /// <value> + /// Current topology version. + /// </value> + long TopologyVersion { get; } + + /// <summary> + /// Gets a topology by version. Returns null if topology history storage doesn't contain + /// specified topology version (history currently keeps the last 1000 snapshots). + /// </summary> + /// <param name="ver">Topology version.</param> + /// <returns>Collection of Ignite nodes which represented by specified topology version, + /// if it is present in history storage, null otherwise.</returns> + /// <exception cref="IgniteException">If underlying SPI implementation does not support + /// topology history. Currently only <code>org.apache.ignite.spi.discovery.tcp.TcpDiscoverySpi</code> + /// supports topology history.</exception> + ICollection<IClusterNode> Topology(long ver); + + /// <summary> + /// Resets local I/O, job, and task execution metrics. + /// </summary> + void ResetMetrics(); + } +} \ No newline at end of file http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/IClusterGroup.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/IClusterGroup.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/IClusterGroup.cs new file mode 100644 index 0000000..1fa11b5 --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/IClusterGroup.cs @@ -0,0 +1,229 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cluster +{ + using System; + using System.Collections.Generic; + using Apache.Ignite.Core.Compute; + using Apache.Ignite.Core.Events; + using Apache.Ignite.Core.Messaging; + using Apache.Ignite.Core.Services; + + /// <summary> + /// Defines grid projection which represents a common functionality over a group of nodes. + /// Grid projection allows to group Ignite nodes into various subgroups to perform distributed + /// operations on them. All ForXXX(...)' methods will create a child grid projection + /// from existing projection. If you create a new projection from current one, then the resulting + /// projection will include a subset of nodes from current projection. The following code snippet + /// shows how to create grid projections: + /// <code> + /// var g = Ignition.GetIgnite(); + /// + /// // Projection over remote nodes. + /// var remoteNodes = g.ForRemotes(); + /// + /// // Projection over random remote node. + /// var randomNode = g.ForRandom(); + /// + /// // Projection over all nodes with cache named "myCache" enabled. + /// var cacheNodes = g.ForCacheNodes("myCache"); + /// + /// // Projection over all nodes that have user attribute "group" set to value "worker". + /// var workerNodes = g.ForAttribute("group", "worker"); + /// </code> + /// Grid projection provides functionality for executing tasks and closures over + /// nodes in this projection using <see cref="IClusterGroup.Compute()"/>. + /// <para/> + /// All members are thread-safe and may be used concurrently from multiple threads. + /// </summary> + public interface IClusterGroup { + /// <summary> + /// Instance of grid. + /// </summary> + IIgnite Ignite + { + get; + } + + /// <summary> + /// Gets compute functionality over this grid projection. All operations + /// on the returned ICompute instance will only include nodes from + /// this projection. + /// </summary> + /// <returns>Compute instance over this grid projection.</returns> + ICompute Compute(); + + /// <summary> + /// Creates a grid projection over a given set of nodes. + /// </summary> + /// <param name="nodes">Collection of nodes to create a projection from.</param> + /// <returns>Projection over provided Ignite nodes.</returns> + IClusterGroup ForNodes(IEnumerable<IClusterNode> nodes); + + /// <summary> + /// Creates a grid projection over a given set of nodes. + /// </summary> + /// <param name="nodes">Collection of nodes to create a projection from.</param> + /// <returns>Projection over provided Ignite nodes.</returns> + IClusterGroup ForNodes(params IClusterNode[] nodes); + + /// <summary> + /// Creates a grid projection over a given set of node IDs. + /// </summary> + /// <param name="ids">Collection of node IDs to create a projection from.</param> + /// <returns>Projection over provided Ignite node IDs.</returns> + IClusterGroup ForNodeIds(IEnumerable<Guid> ids); + + /// <summary> + /// Creates a grid projection over a given set of node IDs. + /// </summary> + /// <param name="ids">Collection of node IDs to create a projection from.</param> + /// <returns>Projection over provided Ignite node IDs.</returns> + IClusterGroup ForNodeIds(params Guid[] ids); + + /// <summary> + /// Creates a grid projection which includes all nodes that pass the given predicate filter. + /// </summary> + /// <param name="p">Predicate filter for nodes to include into this projection.</param> + /// <returns>Grid projection for nodes that passed the predicate filter.</returns> + IClusterGroup ForPredicate(Func<IClusterNode, bool> p); + + /// <summary> + /// Creates projection for nodes containing given name and value + /// specified in user attributes. + /// </summary> + /// <param name="name">Name of the attribute.</param> + /// <param name="val">Optional attribute value to match.</param> + /// <returns>Grid projection for nodes containing specified attribute.</returns> + IClusterGroup ForAttribute(string name, string val); + + /// <summary> + /// Creates projection for all nodes that have cache with specified name running. + /// </summary> + /// <param name="name">Cache name to include into projection.</param> + /// <returns>Projection over nodes that have specified cache running.</returns> + IClusterGroup ForCacheNodes(string name); + + /// <summary> + /// Creates projection for all nodes that have cache with specified name running + /// and cache distribution mode is PARTITIONED_ONLY or NEAR_PARTITIONED. + /// </summary> + /// <param name="name">Cache name to include into projection.</param> + /// <returns>Projection over nodes that have specified cache running.</returns> + IClusterGroup ForDataNodes(string name); + + /// <summary> + /// Creates projection for all nodes that have cache with specified name running + /// and cache distribution mode is CLIENT_ONLY or NEAR_ONLY. + /// </summary> + /// <param name="name">Cache name to include into projection.</param> + /// <returns>Projection over nodes that have specified cache running.</returns> + IClusterGroup ForClientNodes(string name); + + /// <summary> + /// Gets grid projection consisting from the nodes in this projection excluding the local node. + /// </summary> + /// <returns>Grid projection consisting from the nodes in this projection excluding the local node.</returns> + IClusterGroup ForRemotes(); + + /// <summary> + /// Gets grid projection consisting from the nodes in this projection residing on the + /// same host as given node. + /// </summary> + /// <param name="node">Node residing on the host for which projection is created.</param> + /// <returns>Projection for nodes residing on the same host as passed in node.</returns> + IClusterGroup ForHost(IClusterNode node); + + /// <summary> + /// Creates grid projection with one random node from current projection. + /// </summary> + /// <returns>Grid projection with one random node from current projection.</returns> + IClusterGroup ForRandom(); + + /// <summary> + /// Creates grid projection with one oldest node in the current projection. + /// The resulting projection is dynamic and will always pick the next oldest + /// node if the previous one leaves topology even after the projection has + /// been created. + /// </summary> + /// <returns>Grid projection with one oldest node from the current projection.</returns> + IClusterGroup ForOldest(); + + /// <summary> + /// Creates grid projection with one youngest node in the current projection. + /// The resulting projection is dynamic and will always pick the newest + /// node in the topology, even if more nodes entered after the projection + /// has been created. + /// </summary> + /// <returns>Grid projection with one youngest node from the current projection.</returns> + IClusterGroup ForYoungest(); + + /// <summary> + /// Creates grid projection for nodes supporting .Net, i.e. for nodes started with Ignite.exe. + /// </summary> + /// <returns>Grid projection for nodes supporting .Net.</returns> + IClusterGroup ForDotNet(); + + /// <summary> + /// Gets read-only collections of nodes in this projection. + /// </summary> + /// <returns>All nodes in this projection.</returns> + ICollection<IClusterNode> Nodes(); + + /// <summary> + /// Gets a node for given ID from this grid projection. + /// </summary> + /// <param name="id">Node ID.</param> + /// <returns>Node with given ID from this projection or null if such node does not + /// exist in this projection.</returns> + IClusterNode Node(Guid id); + + /// <summary> + /// Gets first node from the list of nodes in this projection. + /// </summary> + /// <returns>Node.</returns> + IClusterNode Node(); + + /// <summary> + /// Gets a metrics snapshot for this projection + /// </summary> + /// <returns>Grid projection metrics snapshot.</returns> + IClusterMetrics Metrics(); + + /// <summary> + /// Gets messaging facade over nodes within this cluster group. All operations on the returned + /// <see cref="IMessaging"/>> instance will only include nodes from current cluster group. + /// </summary> + /// <returns>Messaging instance over this cluster group.</returns> + IMessaging Message(); + + /// <summary> + /// Gets events facade over nodes within this cluster group. All operations on the returned + /// <see cref="IEvents"/>> instance will only include nodes from current cluster group. + /// </summary> + /// <returns>Events instance over this cluster group.</returns> + IEvents Events(); + + /// <summary> + /// Gets services facade over nodes within this cluster group. All operations on the returned + /// <see cref="IServices"/>> instance will only include nodes from current cluster group. + /// </summary> + /// <returns>Services instance over this cluster group.</returns> + IServices Services(); + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/5cec202c/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/IClusterMetrics.cs ---------------------------------------------------------------------- diff --git a/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/IClusterMetrics.cs b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/IClusterMetrics.cs new file mode 100644 index 0000000..24f0249 --- /dev/null +++ b/modules/platform/src/main/dotnet/Apache.Ignite.Core/Cluster/IClusterMetrics.cs @@ -0,0 +1,515 @@ +/* + * 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. + */ + +namespace Apache.Ignite.Core.Cluster +{ + using System; + + /// <summary> + /// Represents runtime information of a cluster. Apart from obvious + /// statistical value, this information is used for implementation of + /// load balancing, failover, and collision SPIs. For example, collision SPI + /// in combination with fail-over SPI could check if other nodes don't have + /// any active or waiting jobs and fail-over some jobs to those nodes. + /// <para /> + /// Node metrics for any node can be accessed via <see cref="IClusterNode.Metrics()"/> + /// method. Keep in mind that there will be a certain network delay (usually + /// equal to heartbeat delay) for the accuracy of node metrics. However, when accessing + /// metrics on local node the metrics are always accurate and up to date. + /// </summary> + public interface IClusterMetrics + { + /// <summary> + /// Last update time of this node metrics. + /// </summary> + DateTime LastUpdateTime + { + get; + } + + /// <summary> + /// Maximum number of jobs that ever ran concurrently on this node. + /// </summary> + int MaximumActiveJobs + { + get; + } + + /// <summary> + /// Number of currently active jobs concurrently executing on the node. + /// </summary> + int CurrentActiveJobs + { + get; + } + + /// <summary> + /// Average number of active jobs. + /// </summary> + float AverageActiveJobs + { + get; + } + + /// <summary> + /// Maximum number of waiting jobs. + /// </summary> + int MaximumWaitingJobs + { + get; + } + + /// <summary> + /// Number of queued jobs currently waiting to be executed. + /// </summary> + int CurrentWaitingJobs + { + get; + } + + /// <summary> + /// Average number of waiting jobs. + /// </summary> + float AverageWaitingJobs + { + get; + } + + /// <summary> + /// Maximum number of jobs rejected at once. + /// </summary> + int MaximumRejectedJobs + { + get; + } + + /// <summary> + /// Number of jobs rejected after more recent collision resolution operation. + /// </summary> + int CurrentRejectedJobs + { + get; + } + + /// <summary> + /// Average number of jobs this node rejects during collision resolution operations. + /// </summary> + float AverageRejectedJobs + { + get; + } + + /// <summary> + /// Total number of jobs this node rejects during collision resolution operations since node startup. + /// </summary> + int TotalRejectedJobs + { + get; + } + + /// <summary> + /// Maximum number of cancelled jobs ever had running concurrently. + /// </summary> + int MaximumCancelledJobs + { + get; + } + + /// <summary> + /// Number of cancelled jobs that are still running. + /// </summary> + int CurrentCancelledJobs + { + get; + } + + /// <summary> + /// Average number of cancelled jobs. + /// </summary> + float AverageCancelledJobs + { + get; + } + + /// <summary> + /// Total number of cancelled jobs since node startup. + /// </summary> + int TotalCancelledJobs + { + get; + } + + /// <summary> + /// Total number of jobs handled by the node since node startup. + /// </summary> + int TotalExecutedJobs + { + get; + } + + /// <summary> + /// Maximum time a job ever spent waiting in a queue to be executed. + /// </summary> + long MaximumJobWaitTime + { + get; + } + + /// <summary> + /// Current time an oldest jobs has spent waiting to be executed. + /// </summary> + long CurrentJobWaitTime + { + get; + } + + /// <summary> + /// Average time jobs spend waiting in the queue to be executed. + /// </summary> + double AverageJobWaitTime + { + get; + } + + /// <summary> + /// Time it took to execute the longest job on the node. + /// </summary> + long MaximumJobExecuteTime + { + get; + } + + /// <summary> + /// Longest time a current job has been executing for. + /// </summary> + long CurrentJobExecuteTime + { + get; + } + + /// <summary> + /// Average job execution time. + /// </summary> + double AverageJobExecuteTime + { + get; + } + + /// <summary> + /// Total number of jobs handled by the node. + /// </summary> + int TotalExecutedTasks + { + get; + } + + /// <summary> + /// Total time this node spent executing jobs. + /// </summary> + long TotalBusyTime + { + get; + } + + /// <summary> + /// Total time this node spent idling. + /// </summary> + long TotalIdleTime + { + get; + } + + /// <summary> + /// Time this node spend idling since executing last job. + /// </summary> + long CurrentIdleTime + { + get; + } + + /// <summary> + /// Percentage of time this node is busy. + /// </summary> + float BusyTimePercentage + { + get; + } + + /// <summary> + /// Percentage of time this node is idle + /// </summary> + float IdleTimePercentage + { + get; + } + + /// <summary> + /// Returns the number of CPUs available to the Java Virtual Machine. + /// </summary> + int TotalCpus + { + get; + } + + /// <summary> + /// Returns the CPU usage usage in [0, 1] range. + /// </summary> + double CurrentCpuLoad + { + get; + } + + /// <summary> + /// Average of CPU load values in [0, 1] range over all metrics kept in the history. + /// </summary> + double AverageCpuLoad + { + get; + } + + /// <summary> + /// Average time spent in CG since the last update. + /// </summary> + double CurrentGcCpuLoad + { + get; + } + + /// <summary> + /// Amount of heap memory in bytes that the JVM + /// initially requests from the operating system for memory management. + /// This method returns <code>-1</code> if the initial memory size is undefined. + /// <para /> + /// This value represents a setting of the heap memory for Java VM and is + /// not a sum of all initial heap values for all memory pools. + /// </summary> + long HeapMemoryInitialized + { + get; + } + + /// <summary> + /// Current heap size that is used for object allocation. + /// The heap consists of one or more memory pools. This value is + /// the sum of used heap memory values of all heap memory pools. + /// <para /> + /// The amount of used memory in the returned is the amount of memory + /// occupied by both live objects and garbage objects that have not + /// been collected, if any. + /// </summary> + long HeapMemoryUsed + { + get; + } + + /// <summary> + /// Amount of heap memory in bytes that is committed for the JVM to use. This amount of memory is + /// guaranteed for the JVM to use. The heap consists of one or more memory pools. This value is + /// the sum of committed heap memory values of all heap memory pools. + /// </summary> + long HeapMemoryCommitted + { + get; + } + + /// <summary> + /// Mmaximum amount of heap memory in bytes that can be used for memory management. + /// This method returns <code>-1</code> if the maximum memory size is undefined. + /// <para /> + /// This amount of memory is not guaranteed to be available for memory management if + /// it is greater than the amount of committed memory. The JVM may fail to allocate + /// memory even if the amount of used memory does not exceed this maximum size. + /// <para /> + /// This value represents a setting of the heap memory for Java VM and is + /// not a sum of all initial heap values for all memory pools. + /// </summary> + long HeapMemoryMaximum + { + get; + } + + /// <summary> + /// Total amount of heap memory in bytes. This method returns <code>-1</code> + /// if the total memory size is undefined. + /// <para /> + /// This amount of memory is not guaranteed to be available for memory management if it is + /// greater than the amount of committed memory. The JVM may fail to allocate memory even + /// if the amount of used memory does not exceed this maximum size. + /// <para /> + /// This value represents a setting of the heap memory for Java VM and is + /// not a sum of all initial heap values for all memory pools. + /// </summary> + long HeapMemoryTotal + { + get; + } + + /// <summary> + /// Amount of non-heap memory in bytes that the JVM initially requests from the operating + /// system for memory management. + /// </summary> + long NonHeapMemoryInitialized + { + get; + } + + /// <summary> + /// Current non-heap memory size that is used by Java VM. + /// </summary> + long NonHeapMemoryUsed + { + get; + } + + /// <summary> + /// Amount of non-heap memory in bytes that is committed for the JVM to use. + /// </summary> + long NonHeapMemoryCommitted + { + get; + } + + /// <summary> + /// Maximum amount of non-heap memory in bytes that can be used for memory management. + /// </summary> + long NonHeapMemoryMaximum + { + get; + } + + /// <summary> + /// Total amount of non-heap memory in bytes that can be used for memory management. + /// </summary> + long NonHeapMemoryTotal + { + get; + } + + /// <summary> + /// Uptime of the JVM in milliseconds. + /// </summary> + long UpTime + { + get; + } + + /// <summary> + /// Start time of the JVM in milliseconds. + /// </summary> + DateTime StartTime + { + get; + } + + /// <summary> + /// Start time of the Ignite node in milliseconds. + /// </summary> + DateTime NodeStartTime + { + get; + } + + /// <summary> + /// Current number of live threads. + /// </summary> + int CurrentThreadCount + { + get; + } + + /// <summary> + /// The peak live thread count. + /// </summary> + int MaximumThreadCount + { + get; + } + + /// <summary> + /// The total number of threads started. + /// </summary> + long TotalStartedThreadCount + { + get; + } + + /// <summary> + /// Current number of live daemon threads. + /// </summary> + int CurrentDaemonThreadCount + { + get; + } + + /// <summary> + /// Ignite assigns incremental versions to all cache operations. This property provides + /// the latest data version on the node. + /// </summary> + long LastDataVersion + { + get; + } + + /// <summary> + /// Sent messages count + /// </summary> + int SentMessagesCount + { + get; + } + + /// <summary> + /// Sent bytes count. + /// </summary> + long SentBytesCount + { + get; + } + + /// <summary> + /// Received messages count. + /// </summary> + int ReceivedMessagesCount + { + get; + } + + /// <summary> + /// Received bytes count. + /// </summary> + long ReceivedBytesCount + { + get; + } + + /// <summary> + /// Outbound messages queue size. + /// </summary> + int OutboundMessagesQueueSize + { + get; + } + + /// <summary> + /// Gets total number of nodes. + /// </summary> + int TotalNodes + { + get; + } + } +}
