You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ignite.apache.org by sb...@apache.org on 2017/12/05 07:31:17 UTC
[02/11] ignite git commit: IGNITE-6338 .NET: Thin client: LINQ
IGNITE-6338 .NET: Thin client: LINQ
This closes #3125
Project: http://git-wip-us.apache.org/repos/asf/ignite/repo
Commit: http://git-wip-us.apache.org/repos/asf/ignite/commit/1f433752
Tree: http://git-wip-us.apache.org/repos/asf/ignite/tree/1f433752
Diff: http://git-wip-us.apache.org/repos/asf/ignite/diff/1f433752
Branch: refs/heads/ignite-zk
Commit: 1f4337527ee2f75b90b46a297b5056064e78eb40
Parents: f08c9d3
Author: Pavel Tupitsyn <pt...@apache.org>
Authored: Mon Dec 4 11:14:32 2017 +0300
Committer: Pavel Tupitsyn <pt...@apache.org>
Committed: Mon Dec 4 11:14:32 2017 +0300
----------------------------------------------------------------------
.../Apache.Ignite.Core.Tests.DotNetCore.csproj | 2 +
.../Apache.Ignite.Core.Tests.csproj | 2 +
.../Query/Linq/CacheLinqTest.Introspection.cs | 8 +-
.../Client/Cache/CreateCacheTest.cs | 1 -
.../Client/Cache/LinqTest.cs | 117 +++++++++++
.../Client/Cache/SqlQueryTest.cs | 43 +---
.../Client/Cache/SqlQueryTestBase.cs | 68 +++++++
.../Client/RawSocketTest.cs | 1 -
.../TestUtils.Windows.cs | 2 -
.../Impl/Cache/ICacheInternal.cs | 6 +
.../Impl/Client/Cache/CacheClient.cs | 64 +++++-
.../Client/Cache/Query/ClientQueryCursorBase.cs | 4 +-
.../Apache.Ignite.Linq.csproj | 3 +-
.../CacheClientLinqExtensions.cs | 131 ++++++++++++
.../Apache.Ignite.Linq/CacheExtensions.cs | 195 ------------------
.../Apache.Ignite.Linq/CacheLinqExtensions.cs | 197 +++++++++++++++++++
.../Apache.Ignite.Linq/ICacheQueryable.cs | 1 +
.../Impl/CacheFieldsQueryProvider.cs | 2 +-
.../Apache.Ignite.Linq/Impl/CacheQueryable.cs | 8 +-
.../Impl/CacheQueryableBase.cs | 1 +
.../dotnet/Apache.Ignite/IgniteRunner.cs | 1 -
21 files changed, 598 insertions(+), 259 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core.Tests.DotNetCore/Apache.Ignite.Core.Tests.DotNetCore.csproj
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core.Tests.DotNetCore/Apache.Ignite.Core.Tests.DotNetCore.csproj b/modules/platforms/dotnet/Apache.Ignite.Core.Tests.DotNetCore/Apache.Ignite.Core.Tests.DotNetCore.csproj
index 5d735eb..8e4de7f 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core.Tests.DotNetCore/Apache.Ignite.Core.Tests.DotNetCore.csproj
+++ b/modules/platforms/dotnet/Apache.Ignite.Core.Tests.DotNetCore/Apache.Ignite.Core.Tests.DotNetCore.csproj
@@ -64,7 +64,9 @@
<Compile Include="..\Apache.Ignite.Core.Tests\Client\Cache\EmptyObject.cs" Link="ThinClient\Cache\EmptyObject.cs" />
<Compile Include="..\Apache.Ignite.Core.Tests\Client\Cache\Person.cs" Link="ThinClient\Cache\Person.cs" />
<Compile Include="..\Apache.Ignite.Core.Tests\Client\Cache\ScanQueryTest.cs" Link="ThinClient\Cache\ScanQueryTest.cs" />
+ <Compile Include="..\Apache.Ignite.Core.Tests\Client\Cache\SqlQueryTestBase.cs" Link="ThinClient\Cache\SqlQueryTestBase.cs" />
<Compile Include="..\Apache.Ignite.Core.Tests\Client\Cache\SqlQueryTest.cs" Link="ThinClient\Cache\SqlQueryTest.cs" />
+ <Compile Include="..\Apache.Ignite.Core.Tests\Client\Cache\LinqTest.cs" Link="ThinClient\Cache\LinqTest.cs" />
<Compile Include="..\Apache.Ignite.Core.Tests\Client\ClientConnectionTest.cs" Link="ThinClient\ClientConnectionTest.cs" />
<Compile Include="..\Apache.Ignite.Core.Tests\Client\ClientTestBase.cs" Link="ThinClient\ClientTestBase.cs" />
<Compile Include="..\Apache.Ignite.Core.Tests\Client\IgniteClientConfigurationTest.cs" Link="ThinClient\IgniteClientConfigurationTest.cs" />
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Apache.Ignite.Core.Tests.csproj
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Apache.Ignite.Core.Tests.csproj b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Apache.Ignite.Core.Tests.csproj
index 8bd8f28..77b2e6e 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Apache.Ignite.Core.Tests.csproj
+++ b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Apache.Ignite.Core.Tests.csproj
@@ -113,9 +113,11 @@
<Compile Include="Client\Cache\ClientCacheConfigurationTest.cs" />
<Compile Include="Client\Cache\EmptyObject.cs" />
<Compile Include="Client\Cache\CreateCacheTest.cs" />
+ <Compile Include="Client\Cache\LinqTest.cs" />
<Compile Include="Client\Cache\ScanQueryTest.cs" />
<Compile Include="Client\Cache\Person.cs" />
<Compile Include="Client\Cache\SqlQueryTest.cs" />
+ <Compile Include="Client\Cache\SqlQueryTestBase.cs" />
<Compile Include="Client\ClientTestBase.cs" />
<Compile Include="Client\RawSocketTest.cs" />
<Compile Include="Client\ClientConnectionTest.cs" />
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Cache/Query/Linq/CacheLinqTest.Introspection.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Cache/Query/Linq/CacheLinqTest.Introspection.cs b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Cache/Query/Linq/CacheLinqTest.Introspection.cs
index a13131b..6e7483e 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Cache/Query/Linq/CacheLinqTest.Introspection.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Cache/Query/Linq/CacheLinqTest.Introspection.cs
@@ -58,7 +58,9 @@ namespace Apache.Ignite.Core.Tests.Cache.Query.Linq
}).Where(x => x.Key > 10).ToCacheQueryable();
Assert.AreEqual(cache.Name, query.CacheName);
+#pragma warning disable 618 // Type or member is obsolete
Assert.AreEqual(cache.Ignite, query.Ignite);
+#pragma warning restore 618 // Type or member is obsolete
var fq = query.GetFieldsQuery();
@@ -93,10 +95,12 @@ namespace Apache.Ignite.Core.Tests.Cache.Query.Linq
"Timeout=00:00:02.5000000, ReplicatedOnly=True, Colocated=True, Schema=, Lazy=True]]", str);
// Check fields query
- var fieldsQuery = (ICacheQueryable)cache.AsCacheQueryable().Select(x => x.Value.Name);
+ var fieldsQuery = cache.AsCacheQueryable().Select(x => x.Value.Name).ToCacheQueryable();
Assert.AreEqual(cache.Name, fieldsQuery.CacheName);
- Assert.AreEqual(cache.Ignite, fieldsQuery.Ignite);
+#pragma warning disable 618 // Type or member is obsolete
+ Assert.AreEqual(cache.Ignite, query.Ignite);
+#pragma warning restore 618 // Type or member is obsolete
fq = fieldsQuery.GetFieldsQuery();
Assert.AreEqual(GetSqlEscapeAll()
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/CreateCacheTest.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/CreateCacheTest.cs b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/CreateCacheTest.cs
index 4489462..94ae6cd 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/CreateCacheTest.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/CreateCacheTest.cs
@@ -22,7 +22,6 @@ namespace Apache.Ignite.Core.Tests.Client.Cache
using Apache.Ignite.Core.Client;
using Apache.Ignite.Core.Client.Cache;
using Apache.Ignite.Core.Configuration;
- using Apache.Ignite.Core.Impl.Client;
using Apache.Ignite.Core.Tests.Cache;
using NUnit.Framework;
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/LinqTest.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/LinqTest.cs b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/LinqTest.cs
new file mode 100644
index 0000000..e61f712
--- /dev/null
+++ b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/LinqTest.cs
@@ -0,0 +1,117 @@
+/*
+ * 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.Tests.Client.Cache
+{
+ using System;
+ using System.Linq;
+ using Apache.Ignite.Linq;
+ using NUnit.Framework;
+
+ /// <summary>
+ /// Tests LINQ in thin client.
+ /// </summary>
+ public class LinqTest : SqlQueryTestBase
+ {
+ /// <summary>
+ /// Tests basic queries.
+ /// </summary>
+ [Test]
+ public void TestBasicQueries()
+ {
+ var cache = GetClientCache<Person>();
+
+ // All items.
+ var qry = cache.AsCacheQueryable();
+ Assert.AreEqual(Count, qry.Count());
+
+ // Filter.
+ qry = cache.AsCacheQueryable().Where(x => x.Value.Name.EndsWith("7"));
+ Assert.AreEqual(7, qry.Single().Key);
+ Assert.AreEqual("select _T0._KEY, _T0._VAL from \"cache\".PERSON as _T0 where (_T0.NAME like '%' || ?) ",
+ qry.ToCacheQueryable().GetFieldsQuery().Sql);
+
+ // DateTime.
+ var arg = DateTime.UtcNow.AddDays(Count - 1);
+ var qry2 = cache.AsCacheQueryable(false, "Person")
+ .Where(x => x.Value.DateTime > arg).Select(x => x.Key);
+ Assert.AreEqual(Count, qry2.Single());
+ }
+
+ /// <summary>
+ /// Tests joins.
+ /// </summary>
+ [Test]
+ public void TestJoins()
+ {
+ var cache1 = Client.GetCache<int, Person>(CacheName);
+ var cache2 = Client.GetCache<int, Person>(CacheName2);
+
+ // Non-distributed join returns incomplete results.
+ var persons1 = cache1.AsCacheQueryable(false);
+ var persons2 = cache2.AsCacheQueryable();
+
+ var qry = persons1
+ .Join(persons2, p1 => p1.Value.Id, p2 => Count + 1 - p2.Value.Id, (p1, p2) => p2.Value.Name);
+
+ Assert.Greater(Count, qry.ToArray().Length);
+
+
+ // Distributed join fixes the problem.
+ persons1 = cache1.AsCacheQueryable(new QueryOptions {EnableDistributedJoins = true});
+ persons2 = cache2.AsCacheQueryable(new QueryOptions {EnableDistributedJoins = true});
+
+ var qry2 =
+ from p1 in persons1
+ join p2 in persons2 on p1.Value.Id equals Count + 1 - p2.Value.Id
+ select p2.Value.DateTime;
+
+ Assert.AreEqual(Count, qry2.ToArray().Length);
+ }
+
+ /// <summary>
+ /// Tests DML via LINQ.
+ /// </summary>
+ [Test]
+ public void TestDml()
+ {
+ var cache = GetClientCache<Person>();
+
+ Assert.AreEqual(Count, cache.GetSize());
+
+ var res = cache.AsCacheQueryable().Where(x => x.Key % 3 == 0).RemoveAll();
+ Assert.AreEqual(Count / 3, res);
+
+ Assert.AreEqual(Count - res, cache.GetSize());
+ }
+
+ /// <summary>
+ /// Tests the compiled query.
+ /// </summary>
+ [Test]
+ public void TestCompiledQuery()
+ {
+ var cache = GetClientCache<Person>();
+ var persons = cache.AsCacheQueryable();
+
+ var qry = CompiledQuery.Compile((int id) => persons.Where(x => x.Value.Id == id));
+
+ Assert.AreEqual(1, qry(1).Single().Key);
+ Assert.AreEqual(3, qry(3).Single().Key);
+ }
+ }
+}
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/SqlQueryTest.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/SqlQueryTest.cs b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/SqlQueryTest.cs
index 720a71b..6f6df11 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/SqlQueryTest.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/SqlQueryTest.cs
@@ -19,7 +19,6 @@ namespace Apache.Ignite.Core.Tests.Client.Cache
{
using System;
using System.Linq;
- using Apache.Ignite.Core.Cache.Configuration;
using Apache.Ignite.Core.Cache.Query;
using Apache.Ignite.Core.Client;
using NUnit.Framework;
@@ -27,36 +26,9 @@ namespace Apache.Ignite.Core.Tests.Client.Cache
/// <summary>
/// Tests SQL queries via thin client.
/// </summary>
- public class SqlQueryTest : ClientTestBase
+ public class SqlQueryTest : SqlQueryTestBase
{
/// <summary>
- /// Cache item count.
- /// </summary>
- private const int Count = 10;
-
- /// <summary>
- /// Second cache name.
- /// </summary>
- private const string CacheName2 = CacheName + "2";
-
- /// <summary>
- /// Initializes a new instance of the <see cref="ScanQueryTest"/> class.
- /// </summary>
- public SqlQueryTest() : base(2)
- {
- // No-op.
- }
-
- /// <summary>
- /// Sets up the test.
- /// </summary>
- public override void TestSetUp()
- {
- InitCache(CacheName);
- InitCache(CacheName2);
- }
-
- /// <summary>
/// Tests the SQL query.
/// </summary>
[Test]
@@ -251,18 +223,5 @@ namespace Apache.Ignite.Core.Tests.Client.Cache
Assert.AreEqual(1, res[0][0]);
Assert.AreEqual("baz", cache[-10].Name);
}
-
- /// <summary>
- /// Initializes the cache.
- /// </summary>
- private static void InitCache(string cacheName)
- {
- var cache = Ignition.GetIgnite().GetOrCreateCache<int, Person>(
- new CacheConfiguration(cacheName, new QueryEntity(typeof(int), typeof(Person))));
-
- cache.RemoveAll();
-
- cache.PutAll(Enumerable.Range(1, Count).ToDictionary(x => x, x => new Person(x)));
- }
}
}
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/SqlQueryTestBase.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/SqlQueryTestBase.cs b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/SqlQueryTestBase.cs
new file mode 100644
index 0000000..7efcb9c
--- /dev/null
+++ b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/Cache/SqlQueryTestBase.cs
@@ -0,0 +1,68 @@
+/*
+ * 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.Tests.Client.Cache
+{
+ using System.Linq;
+ using Apache.Ignite.Core.Cache.Configuration;
+
+ /// <summary>
+ /// Base class for SQL tests.
+ /// </summary>
+ public class SqlQueryTestBase : ClientTestBase
+ {
+ /// <summary>
+ /// Cache item count.
+ /// </summary>
+ protected const int Count = 10;
+
+ /// <summary>
+ /// Second cache name.
+ /// </summary>
+ protected const string CacheName2 = CacheName + "2";
+
+ /// <summary>
+ /// Initializes a new instance of the <see cref="ScanQueryTest"/> class.
+ /// </summary>
+ public SqlQueryTestBase() : base(2)
+ {
+ // No-op.
+ }
+
+ /// <summary>
+ /// Sets up the test.
+ /// </summary>
+ public override void TestSetUp()
+ {
+ InitCache(CacheName);
+ InitCache(CacheName2);
+ }
+
+ /// <summary>
+ /// Initializes the cache.
+ /// </summary>
+ private static void InitCache(string cacheName)
+ {
+ var cache = Ignition.GetIgnite().GetOrCreateCache<int, Person>(
+ new CacheConfiguration(cacheName, new QueryEntity(typeof(int), typeof(Person))));
+
+ cache.RemoveAll();
+
+ cache.PutAll(Enumerable.Range(1, Count).ToDictionary(x => x, x => new Person(x)));
+ }
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/RawSocketTest.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/RawSocketTest.cs b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/RawSocketTest.cs
index b088bb6..8ab110f 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/RawSocketTest.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/Client/RawSocketTest.cs
@@ -25,7 +25,6 @@ namespace Apache.Ignite.Core.Tests.Client
using Apache.Ignite.Core.Impl;
using Apache.Ignite.Core.Impl.Binary;
using Apache.Ignite.Core.Impl.Binary.IO;
- using Apache.Ignite.Core.Impl.Client;
using NUnit.Framework;
/// <summary>
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core.Tests/TestUtils.Windows.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/TestUtils.Windows.cs b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/TestUtils.Windows.cs
index 14b58f2..2169630 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core.Tests/TestUtils.Windows.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Core.Tests/TestUtils.Windows.cs
@@ -20,10 +20,8 @@ namespace Apache.Ignite.Core.Tests
using System;
using System.Diagnostics;
using System.Diagnostics.CodeAnalysis;
- using System.Linq;
using Apache.Ignite.Core.Configuration;
using Apache.Ignite.Core.Impl;
- using Apache.Ignite.Core.Impl.Binary;
using Apache.Ignite.Core.Impl.Common;
using Apache.Ignite.Core.Tests.Process;
using NUnit.Framework;
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Cache/ICacheInternal.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Cache/ICacheInternal.cs b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Cache/ICacheInternal.cs
index 0349db8..1ec5341 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Cache/ICacheInternal.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Cache/ICacheInternal.cs
@@ -19,6 +19,7 @@ namespace Apache.Ignite.Core.Impl.Cache
{
using System;
using Apache.Ignite.Core.Binary;
+ using Apache.Ignite.Core.Cache.Configuration;
using Apache.Ignite.Core.Cache.Query;
/// <summary>
@@ -50,5 +51,10 @@ namespace Apache.Ignite.Core.Impl.Cache
/// </returns>
T DoOutInOpExtension<T>(int extensionId, int opCode, Action<IBinaryRawWriter> writeAction,
Func<IBinaryRawReader, T> readFunc);
+
+ /// <summary>
+ /// Gets the cache configuration.
+ /// </summary>
+ CacheConfiguration GetConfiguration();
}
}
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/CacheClient.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/CacheClient.cs b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/CacheClient.cs
index 45c0b0f..93829c2 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/CacheClient.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/CacheClient.cs
@@ -20,9 +20,11 @@ namespace Apache.Ignite.Core.Impl.Client.Cache
using System;
using System.Collections.Generic;
using System.Diagnostics;
+ using System.Diagnostics.CodeAnalysis;
using System.IO;
using Apache.Ignite.Core.Binary;
using Apache.Ignite.Core.Cache;
+ using Apache.Ignite.Core.Cache.Configuration;
using Apache.Ignite.Core.Cache.Query;
using Apache.Ignite.Core.Client;
using Apache.Ignite.Core.Client.Cache;
@@ -37,7 +39,7 @@ namespace Apache.Ignite.Core.Impl.Client.Cache
/// <summary>
/// Client cache implementation.
/// </summary>
- internal sealed class CacheClient<TK, TV> : ICacheClient<TK, TV>
+ internal sealed class CacheClient<TK, TV> : ICacheClient<TK, TV>, ICacheInternal
{
/** Scan query filter platform code: .NET filter. */
private const byte FilterPlatformDotnet = 2;
@@ -188,10 +190,17 @@ namespace Apache.Ignite.Core.Impl.Client.Cache
IgniteArgumentCheck.NotNull(sqlFieldsQuery, "sqlFieldsQuery");
IgniteArgumentCheck.NotNull(sqlFieldsQuery.Sql, "sqlFieldsQuery.Sql");
- return DoOutInOp(ClientOp.QuerySqlFields, w => WriteSqlFieldsQuery(w, sqlFieldsQuery),
- s => new ClientFieldsQueryCursor(
- _ignite, s.ReadLong(), _keepBinary, s, ClientOp.QuerySqlFieldsCursorGetPage,
- ClientFieldsQueryCursor.ReadColumns(_marsh.StartUnmarshal(s))));
+ return DoOutInOp(ClientOp.QuerySqlFields,
+ w => WriteSqlFieldsQuery(w, sqlFieldsQuery),
+ s => GetFieldsCursor(s));
+ }
+
+ /** <inheritDoc /> */
+ public IQueryCursor<T> QueryFields<T>(SqlFieldsQuery sqlFieldsQuery, Func<IBinaryRawReader, int, T> readerFunc)
+ {
+ return DoOutInOp(ClientOp.QuerySqlFields,
+ w => WriteSqlFieldsQuery(w, sqlFieldsQuery, false),
+ s => GetFieldsCursorNoColumnNames(s, readerFunc));
}
/** <inheritDoc /> */
@@ -361,6 +370,12 @@ namespace Apache.Ignite.Core.Impl.Client.Cache
}
/** <inheritDoc /> */
+ CacheConfiguration ICacheInternal.GetConfiguration()
+ {
+ return GetConfiguration().ToCacheConfiguration();
+ }
+
+ /** <inheritDoc /> */
public ICacheClient<TK1, TV1> WithKeepBinary<TK1, TV1>()
{
if (_keepBinary)
@@ -380,6 +395,15 @@ namespace Apache.Ignite.Core.Impl.Client.Cache
return new CacheClient<TK1, TV1>(_ignite, _name, true);
}
+ /** <inheritDoc /> */
+ [ExcludeFromCodeCoverage]
+ public T DoOutInOpExtension<T>(int extensionId, int opCode, Action<IBinaryRawWriter> writeAction,
+ Func<IBinaryRawReader, T> readFunc)
+ {
+ // Should not be called, there are no usages for thin client.
+ throw IgniteClient.GetClientNotSupportedException();
+ }
+
/// <summary>
/// Does the out in op.
/// </summary>
@@ -492,7 +516,8 @@ namespace Apache.Ignite.Core.Impl.Client.Cache
/// <summary>
/// Writes the SQL fields query.
/// </summary>
- private static void WriteSqlFieldsQuery(IBinaryRawWriter writer, SqlFieldsQuery qry)
+ private static void WriteSqlFieldsQuery(IBinaryRawWriter writer, SqlFieldsQuery qry,
+ bool includeColumns = true)
{
Debug.Assert(qry != null);
@@ -513,10 +538,33 @@ namespace Apache.Ignite.Core.Impl.Client.Cache
writer.WriteBoolean(qry.Colocated);
writer.WriteBoolean(qry.Lazy);
writer.WriteTimeSpanAsLong(qry.Timeout);
+ writer.WriteBoolean(includeColumns);
- // Always include field names.
- writer.WriteBoolean(true);
+ }
+
+ /// <summary>
+ /// Gets the fields cursor.
+ /// </summary>
+ private ClientFieldsQueryCursor GetFieldsCursor(IBinaryStream s)
+ {
+ var cursorId = s.ReadLong();
+ var columnNames = ClientFieldsQueryCursor.ReadColumns(_marsh.StartUnmarshal(s));
+
+ return new ClientFieldsQueryCursor(_ignite, cursorId, _keepBinary, s,
+ ClientOp.QuerySqlFieldsCursorGetPage, columnNames);
+ }
+
+ /// <summary>
+ /// Gets the fields cursor.
+ /// </summary>
+ private ClientQueryCursorBase<T> GetFieldsCursorNoColumnNames<T>(IBinaryStream s,
+ Func<IBinaryRawReader, int, T> readerFunc)
+ {
+ var cursorId = s.ReadLong();
+ var columnCount = s.ReadInt();
+ return new ClientQueryCursorBase<T>(_ignite, cursorId, _keepBinary, s,
+ ClientOp.QuerySqlFieldsCursorGetPage, r => readerFunc(r, columnCount));
}
/// <summary>
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/Query/ClientQueryCursorBase.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/Query/ClientQueryCursorBase.cs b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/Query/ClientQueryCursorBase.cs
index 5123537..5a0a1f6 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/Query/ClientQueryCursorBase.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Core/Impl/Client/Cache/Query/ClientQueryCursorBase.cs
@@ -26,7 +26,7 @@ namespace Apache.Ignite.Core.Impl.Client.Cache.Query
/// <summary>
/// Client query cursor base.
/// </summary>
- internal abstract class ClientQueryCursorBase<T> : QueryCursorBase<T>
+ internal class ClientQueryCursorBase<T> : QueryCursorBase<T>
{
/** Ignite. */
private readonly IgniteClient _ignite;
@@ -46,7 +46,7 @@ namespace Apache.Ignite.Core.Impl.Client.Cache.Query
/// <param name="initialBatchStream">Optional stream with initial batch.</param>
/// <param name="getPageOp">The get page op.</param>
/// <param name="readFunc">Read func.</param>
- protected ClientQueryCursorBase(IgniteClient ignite, long cursorId, bool keepBinary,
+ public ClientQueryCursorBase(IgniteClient ignite, long cursorId, bool keepBinary,
IBinaryStream initialBatchStream, ClientOp getPageOp, Func<BinaryReader, T> readFunc)
: base(ignite.Marshaller, keepBinary, readFunc, initialBatchStream)
{
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Linq/Apache.Ignite.Linq.csproj
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Linq/Apache.Ignite.Linq.csproj b/modules/platforms/dotnet/Apache.Ignite.Linq/Apache.Ignite.Linq.csproj
index 735e4f2..fc13914 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Linq/Apache.Ignite.Linq.csproj
+++ b/modules/platforms/dotnet/Apache.Ignite.Linq/Apache.Ignite.Linq.csproj
@@ -51,7 +51,8 @@
<Reference Include="System.Core" />
</ItemGroup>
<ItemGroup>
- <Compile Include="CacheExtensions.cs" />
+ <Compile Include="CacheClientLinqExtensions.cs" />
+ <Compile Include="CacheLinqExtensions.cs" />
<Compile Include="CompiledQuery.cs" />
<Compile Include="ICacheQueryable.cs" />
<Compile Include="Impl\AliasDictionary.cs" />
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Linq/CacheClientLinqExtensions.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Linq/CacheClientLinqExtensions.cs b/modules/platforms/dotnet/Apache.Ignite.Linq/CacheClientLinqExtensions.cs
new file mode 100644
index 0000000..0c3544b
--- /dev/null
+++ b/modules/platforms/dotnet/Apache.Ignite.Linq/CacheClientLinqExtensions.cs
@@ -0,0 +1,131 @@
+/*
+ * 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.Linq
+{
+ using System.Linq;
+ using Apache.Ignite.Core.Cache;
+ using Apache.Ignite.Core.Cache.Configuration;
+ using Apache.Ignite.Core.Cache.Query;
+ using Apache.Ignite.Core.Client.Cache;
+ using Apache.Ignite.Core.Impl.Cache;
+ using Apache.Ignite.Core.Impl.Common;
+ using Apache.Ignite.Linq.Impl;
+
+ /// <summary>
+ /// Extensions methods for <see cref="ICacheClient{TK,TV}"/>.
+ /// </summary>
+ public static class CacheClientLinqExtensions
+ {
+ /// <summary>
+ /// Gets an <see cref="IQueryable{T}"/> instance over this cache.
+ /// <para />
+ /// Resulting query will be translated to cache SQL query and executed over the cache instance
+ /// via either <see cref="ICacheClient{TK,TV}.Query(SqlFieldsQuery)"/>.
+ /// <para />
+ /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable"/>
+ /// for introspection, or converted with <see cref="CacheLinqExtensions.ToCacheQueryable{T}"/>
+ /// extension method.
+ /// </summary>
+ /// <typeparam name="TKey">The type of the key.</typeparam>
+ /// <typeparam name="TValue">The type of the value.</typeparam>
+ /// <param name="cache">The cache.</param>
+ /// <returns><see cref="IQueryable{T}"/> instance over this cache.</returns>
+ public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
+ this ICacheClient<TKey, TValue> cache)
+ {
+ IgniteArgumentCheck.NotNull(cache, "cache");
+
+ return AsCacheQueryable(cache, false, null);
+ }
+
+ /// <summary>
+ /// Gets an <see cref="IQueryable{T}"/> instance over this cache.
+ /// <para />
+ /// Resulting query will be translated to cache SQL query and executed over the cache instance
+ /// via either <see cref="ICacheClient{TK,TV}.Query(SqlFieldsQuery)"/>.
+ /// <para />
+ /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable"/> for introspection.
+ /// </summary>
+ /// <typeparam name="TKey">The type of the key.</typeparam>
+ /// <typeparam name="TValue">The type of the value.</typeparam>
+ /// <param name="cache">The cache.</param>
+ /// <param name="local">Local flag. When set query will be executed only on local node, so only local
+ /// entries will be returned as query result.</param>
+ /// <returns><see cref="IQueryable{T}"/> instance over this cache.</returns>
+ public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
+ this ICacheClient<TKey, TValue> cache, bool local)
+ {
+ IgniteArgumentCheck.NotNull(cache, "cache");
+
+ return AsCacheQueryable(cache, local, null);
+ }
+
+ /// <summary>
+ /// Gets an <see cref="IQueryable{T}" /> instance over this cache.
+ /// <para />
+ /// Resulting query will be translated to cache SQL query and executed over the cache instance
+ /// via either <see cref="ICacheClient{TK,TV}.Query(SqlFieldsQuery)"/>.
+ /// <para />
+ /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable" /> for introspection.
+ /// </summary>
+ /// <typeparam name="TKey">The type of the key.</typeparam>
+ /// <typeparam name="TValue">The type of the value.</typeparam>
+ /// <param name="cache">The cache.</param>
+ /// <param name="local">Local flag. When set query will be executed only on local node, so only local
+ /// entries will be returned as query result.</param>
+ /// <param name="tableName">
+ /// Name of the table.
+ /// <para />
+ /// Table name is equal to short class name of a cache value.
+ /// When a cache has only one type of values, or only one <see cref="QueryEntity"/> defined,
+ /// table name will be inferred and can be omitted.
+ /// </param>
+ /// <returns><see cref="IQueryable{T}" /> instance over this cache.</returns>
+ public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
+ this ICacheClient<TKey, TValue> cache, bool local, string tableName)
+ {
+ IgniteArgumentCheck.NotNull(cache, "cache");
+
+ return AsCacheQueryable(cache, new QueryOptions {Local = local, TableName = tableName});
+ }
+
+ /// <summary>
+ /// Gets an <see cref="IQueryable{T}" /> instance over this cache.
+ /// <para />
+ /// Resulting query will be translated to cache SQL query and executed over the cache instance
+ /// via either <see cref="ICacheClient{TK,TV}.Query(SqlFieldsQuery)"/>.
+ /// <para />
+ /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable" /> for introspection.
+ /// </summary>
+ /// <typeparam name="TKey">The type of the key.</typeparam>
+ /// <typeparam name="TValue">The type of the value.</typeparam>
+ /// <param name="cache">The cache.</param>
+ /// <param name="queryOptions">The query options.</param>
+ /// <returns>
+ /// <see cref="IQueryable{T}" /> instance over this cache.
+ /// </returns>
+ public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
+ this ICacheClient<TKey, TValue> cache, QueryOptions queryOptions)
+ {
+ IgniteArgumentCheck.NotNull(cache, "cache");
+ IgniteArgumentCheck.NotNull(queryOptions, "queryOptions");
+
+ return new CacheQueryable<TKey, TValue>((ICacheInternal) cache, queryOptions);
+ }
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Linq/CacheExtensions.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Linq/CacheExtensions.cs b/modules/platforms/dotnet/Apache.Ignite.Linq/CacheExtensions.cs
deleted file mode 100644
index f759dbb..0000000
--- a/modules/platforms/dotnet/Apache.Ignite.Linq/CacheExtensions.cs
+++ /dev/null
@@ -1,195 +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.
- */
-
-namespace Apache.Ignite.Linq
-{
- using System;
- using System.Diagnostics.CodeAnalysis;
- using System.Linq;
- using System.Linq.Expressions;
- using Apache.Ignite.Core.Cache;
- using Apache.Ignite.Core.Cache.Configuration;
- using Apache.Ignite.Core.Impl.Common;
- using Apache.Ignite.Linq.Impl;
- using Apache.Ignite.Linq.Impl.Dml;
-
- /// <summary>
- /// Extensions methods for <see cref="ICache{TK,TV}"/>.
- /// </summary>
- public static class CacheLinqExtensions
- {
- /// <summary>
- /// Gets an <see cref="IQueryable{T}"/> instance over this cache.
- /// <para />
- /// Resulting query will be translated to cache SQL query and executed over the cache instance
- /// via either <see cref="ICache{TK,TV}.Query"/> or <see cref="ICache{TK,TV}.QueryFields"/>,
- /// depending on requested result.
- /// <para />
- /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable"/> for introspection.
- /// </summary>
- /// <typeparam name="TKey">The type of the key.</typeparam>
- /// <typeparam name="TValue">The type of the value.</typeparam>
- /// <param name="cache">The cache.</param>
- /// <returns><see cref="IQueryable{T}"/> instance over this cache.</returns>
- public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
- this ICache<TKey, TValue> cache)
- {
- IgniteArgumentCheck.NotNull(cache, "cache");
-
- return cache.AsCacheQueryable(false, null);
- }
-
- /// <summary>
- /// Gets an <see cref="IQueryable{T}"/> instance over this cache.
- /// <para />
- /// Resulting query will be translated to cache SQL query and executed over the cache instance
- /// via either <see cref="ICache{TK,TV}.Query"/> or <see cref="ICache{TK,TV}.QueryFields"/>,
- /// depending on requested result.
- /// <para />
- /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable"/> for introspection.
- /// </summary>
- /// <typeparam name="TKey">The type of the key.</typeparam>
- /// <typeparam name="TValue">The type of the value.</typeparam>
- /// <param name="cache">The cache.</param>
- /// <param name="local">Local flag. When set query will be executed only on local node, so only local
- /// entries will be returned as query result.</param>
- /// <returns><see cref="IQueryable{T}"/> instance over this cache.</returns>
- public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
- this ICache<TKey, TValue> cache, bool local)
- {
- IgniteArgumentCheck.NotNull(cache, "cache");
-
- return cache.AsCacheQueryable(local, null);
- }
-
- /// <summary>
- /// Gets an <see cref="IQueryable{T}" /> instance over this cache.
- /// <para />
- /// Resulting query will be translated to cache SQL query and executed over the cache instance
- /// via either <see cref="ICache{TK,TV}.Query" /> or <see cref="ICache{TK,TV}.QueryFields" />,
- /// depending on requested result.
- /// <para />
- /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable" /> for introspection.
- /// </summary>
- /// <typeparam name="TKey">The type of the key.</typeparam>
- /// <typeparam name="TValue">The type of the value.</typeparam>
- /// <param name="cache">The cache.</param>
- /// <param name="local">Local flag. When set query will be executed only on local node, so only local
- /// entries will be returned as query result.</param>
- /// <param name="tableName">
- /// Name of the table.
- /// <para />
- /// Table name is equal to short class name of a cache value.
- /// When a cache has only one type of values, or only one <see cref="QueryEntity"/> defined,
- /// table name will be inferred and can be omitted.
- /// </param>
- /// <returns><see cref="IQueryable{T}" /> instance over this cache.</returns>
- public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
- this ICache<TKey, TValue> cache, bool local, string tableName)
- {
- IgniteArgumentCheck.NotNull(cache, "cache");
-
- return cache.AsCacheQueryable(new QueryOptions {Local = local, TableName = tableName});
- }
-
- /// <summary>
- /// Gets an <see cref="IQueryable{T}" /> instance over this cache.
- /// <para />
- /// Resulting query will be translated to cache SQL query and executed over the cache instance
- /// via either <see cref="ICache{TK,TV}.Query" /> or <see cref="ICache{TK,TV}.QueryFields" />,
- /// depending on requested result.
- /// <para />
- /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable" /> for introspection.
- /// </summary>
- /// <typeparam name="TKey">The type of the key.</typeparam>
- /// <typeparam name="TValue">The type of the value.</typeparam>
- /// <param name="cache">The cache.</param>
- /// <param name="queryOptions">The query options.</param>
- /// <returns>
- /// <see cref="IQueryable{T}" /> instance over this cache.
- /// </returns>
- public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
- this ICache<TKey, TValue> cache, QueryOptions queryOptions)
- {
- IgniteArgumentCheck.NotNull(cache, "cache");
- IgniteArgumentCheck.NotNull(queryOptions, "queryOptions");
-
- return new CacheQueryable<TKey, TValue>(cache, queryOptions);
- }
-
- /// <summary>
- /// Casts this query to <see cref="ICacheQueryable"/>.
- /// </summary>
- public static ICacheQueryable ToCacheQueryable<T>(this IQueryable<T> query)
- {
- IgniteArgumentCheck.NotNull(query, "query");
-
- return (ICacheQueryable) query;
- }
-
- /// <summary>
- /// Removes all rows that are matched by the specified query.
- /// <para />
- /// This method results in "DELETE FROM" distributed SQL query, performing bulk delete
- /// (as opposed to fetching all rows locally).
- /// </summary>
- /// <typeparam name="TKey">Key type.</typeparam>
- /// <typeparam name="TValue">Value type.</typeparam>
- /// <param name="query">The query.</param>
- /// <returns>Affected row count.</returns>
- [SuppressMessage("Microsoft.Design", "CA1062:Validate arguments of public methods",
- Justification = "Validation is present.")]
- public static int RemoveAll<TKey, TValue>(this IQueryable<ICacheEntry<TKey, TValue>> query)
- {
- IgniteArgumentCheck.NotNull(query, "query");
-
- var method = RemoveAllExpressionNode.RemoveAllMethodInfo.MakeGenericMethod(typeof(TKey), typeof(TValue));
-
- return query.Provider.Execute<int>(Expression.Call(null, method, query.Expression));
- }
-
- /// <summary>
- /// Deletes all rows that are matched by the specified query.
- /// <para />
- /// This method results in "DELETE FROM" distributed SQL query, performing bulk delete
- /// (as opposed to fetching all rows locally).
- /// </summary>
- /// <typeparam name="TKey">Key type.</typeparam>
- /// <typeparam name="TValue">Value type.</typeparam>
- /// <param name="query">The query.</param>
- /// <param name="predicate">The predicate.</param>
- /// <returns>
- /// Affected row count.
- /// </returns>
- [SuppressMessage("Microsoft.Design", "CA1011:ConsiderPassingBaseTypesAsParameters",
- Justification = "Only specified type of predicate is valid.")]
- [SuppressMessage("Microsoft.Design", "CA1062:Validate arguments of public methods",
- Justification = "Validation is present.")]
- public static int RemoveAll<TKey, TValue>(this IQueryable<ICacheEntry<TKey, TValue>> query,
- Expression<Func<ICacheEntry<TKey, TValue>, bool>> predicate)
- {
- IgniteArgumentCheck.NotNull(query, "query");
- IgniteArgumentCheck.NotNull(predicate, "predicate");
-
- var method = RemoveAllExpressionNode.RemoveAllPredicateMethodInfo
- .MakeGenericMethod(typeof(TKey), typeof(TValue));
-
- return query.Provider.Execute<int>(Expression.Call(null, method, query.Expression,
- Expression.Quote(predicate)));
- }
- }
-}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Linq/CacheLinqExtensions.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Linq/CacheLinqExtensions.cs b/modules/platforms/dotnet/Apache.Ignite.Linq/CacheLinqExtensions.cs
new file mode 100644
index 0000000..940b23b
--- /dev/null
+++ b/modules/platforms/dotnet/Apache.Ignite.Linq/CacheLinqExtensions.cs
@@ -0,0 +1,197 @@
+/*
+ * 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.Linq
+{
+ using System;
+ using System.Diagnostics.CodeAnalysis;
+ using System.Linq;
+ using System.Linq.Expressions;
+ using Apache.Ignite.Core.Cache;
+ using Apache.Ignite.Core.Cache.Configuration;
+ using Apache.Ignite.Core.Impl.Cache;
+ using Apache.Ignite.Core.Impl.Common;
+ using Apache.Ignite.Linq.Impl;
+ using Apache.Ignite.Linq.Impl.Dml;
+
+ /// <summary>
+ /// Extensions methods for <see cref="ICache{TK,TV}"/>.
+ /// </summary>
+ public static class CacheLinqExtensions
+ {
+ /// <summary>
+ /// Gets an <see cref="IQueryable{T}"/> instance over this cache.
+ /// <para />
+ /// Resulting query will be translated to cache SQL query and executed over the cache instance
+ /// via either <see cref="ICache{TK,TV}.Query"/> or <see cref="ICache{TK,TV}.QueryFields"/>,
+ /// depending on requested result.
+ /// <para />
+ /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable"/>
+ /// for introspection, or converted with <see cref="ToCacheQueryable{T}"/> extension method.
+ /// </summary>
+ /// <typeparam name="TKey">The type of the key.</typeparam>
+ /// <typeparam name="TValue">The type of the value.</typeparam>
+ /// <param name="cache">The cache.</param>
+ /// <returns><see cref="IQueryable{T}"/> instance over this cache.</returns>
+ public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
+ this ICache<TKey, TValue> cache)
+ {
+ IgniteArgumentCheck.NotNull(cache, "cache");
+
+ return cache.AsCacheQueryable(false, null);
+ }
+
+ /// <summary>
+ /// Gets an <see cref="IQueryable{T}"/> instance over this cache.
+ /// <para />
+ /// Resulting query will be translated to cache SQL query and executed over the cache instance
+ /// via either <see cref="ICache{TK,TV}.Query"/> or <see cref="ICache{TK,TV}.QueryFields"/>,
+ /// depending on requested result.
+ /// <para />
+ /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable"/> for introspection.
+ /// </summary>
+ /// <typeparam name="TKey">The type of the key.</typeparam>
+ /// <typeparam name="TValue">The type of the value.</typeparam>
+ /// <param name="cache">The cache.</param>
+ /// <param name="local">Local flag. When set query will be executed only on local node, so only local
+ /// entries will be returned as query result.</param>
+ /// <returns><see cref="IQueryable{T}"/> instance over this cache.</returns>
+ public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
+ this ICache<TKey, TValue> cache, bool local)
+ {
+ IgniteArgumentCheck.NotNull(cache, "cache");
+
+ return cache.AsCacheQueryable(local, null);
+ }
+
+ /// <summary>
+ /// Gets an <see cref="IQueryable{T}" /> instance over this cache.
+ /// <para />
+ /// Resulting query will be translated to cache SQL query and executed over the cache instance
+ /// via either <see cref="ICache{TK,TV}.Query" /> or <see cref="ICache{TK,TV}.QueryFields" />,
+ /// depending on requested result.
+ /// <para />
+ /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable" /> for introspection.
+ /// </summary>
+ /// <typeparam name="TKey">The type of the key.</typeparam>
+ /// <typeparam name="TValue">The type of the value.</typeparam>
+ /// <param name="cache">The cache.</param>
+ /// <param name="local">Local flag. When set query will be executed only on local node, so only local
+ /// entries will be returned as query result.</param>
+ /// <param name="tableName">
+ /// Name of the table.
+ /// <para />
+ /// Table name is equal to short class name of a cache value.
+ /// When a cache has only one type of values, or only one <see cref="QueryEntity"/> defined,
+ /// table name will be inferred and can be omitted.
+ /// </param>
+ /// <returns><see cref="IQueryable{T}" /> instance over this cache.</returns>
+ public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
+ this ICache<TKey, TValue> cache, bool local, string tableName)
+ {
+ IgniteArgumentCheck.NotNull(cache, "cache");
+
+ return cache.AsCacheQueryable(new QueryOptions {Local = local, TableName = tableName});
+ }
+
+ /// <summary>
+ /// Gets an <see cref="IQueryable{T}" /> instance over this cache.
+ /// <para />
+ /// Resulting query will be translated to cache SQL query and executed over the cache instance
+ /// via either <see cref="ICache{TK,TV}.Query" /> or <see cref="ICache{TK,TV}.QueryFields" />,
+ /// depending on requested result.
+ /// <para />
+ /// Result of this method (and subsequent query) can be cast to <see cref="ICacheQueryable" /> for introspection.
+ /// </summary>
+ /// <typeparam name="TKey">The type of the key.</typeparam>
+ /// <typeparam name="TValue">The type of the value.</typeparam>
+ /// <param name="cache">The cache.</param>
+ /// <param name="queryOptions">The query options.</param>
+ /// <returns>
+ /// <see cref="IQueryable{T}" /> instance over this cache.
+ /// </returns>
+ public static IQueryable<ICacheEntry<TKey, TValue>> AsCacheQueryable<TKey, TValue>(
+ this ICache<TKey, TValue> cache, QueryOptions queryOptions)
+ {
+ IgniteArgumentCheck.NotNull(cache, "cache");
+ IgniteArgumentCheck.NotNull(queryOptions, "queryOptions");
+
+ return new CacheQueryable<TKey, TValue>((ICacheInternal) cache, queryOptions, cache.Ignite);
+ }
+
+ /// <summary>
+ /// Casts this query to <see cref="ICacheQueryable"/>.
+ /// </summary>
+ public static ICacheQueryable ToCacheQueryable<T>(this IQueryable<T> query)
+ {
+ IgniteArgumentCheck.NotNull(query, "query");
+
+ return (ICacheQueryable) query;
+ }
+
+ /// <summary>
+ /// Removes all rows that are matched by the specified query.
+ /// <para />
+ /// This method results in "DELETE FROM" distributed SQL query, performing bulk delete
+ /// (as opposed to fetching all rows locally).
+ /// </summary>
+ /// <typeparam name="TKey">Key type.</typeparam>
+ /// <typeparam name="TValue">Value type.</typeparam>
+ /// <param name="query">The query.</param>
+ /// <returns>Affected row count.</returns>
+ [SuppressMessage("Microsoft.Design", "CA1062:Validate arguments of public methods",
+ Justification = "Validation is present.")]
+ public static int RemoveAll<TKey, TValue>(this IQueryable<ICacheEntry<TKey, TValue>> query)
+ {
+ IgniteArgumentCheck.NotNull(query, "query");
+
+ var method = RemoveAllExpressionNode.RemoveAllMethodInfo.MakeGenericMethod(typeof(TKey), typeof(TValue));
+
+ return query.Provider.Execute<int>(Expression.Call(null, method, query.Expression));
+ }
+
+ /// <summary>
+ /// Deletes all rows that are matched by the specified query.
+ /// <para />
+ /// This method results in "DELETE FROM" distributed SQL query, performing bulk delete
+ /// (as opposed to fetching all rows locally).
+ /// </summary>
+ /// <typeparam name="TKey">Key type.</typeparam>
+ /// <typeparam name="TValue">Value type.</typeparam>
+ /// <param name="query">The query.</param>
+ /// <param name="predicate">The predicate.</param>
+ /// <returns>
+ /// Affected row count.
+ /// </returns>
+ [SuppressMessage("Microsoft.Design", "CA1011:ConsiderPassingBaseTypesAsParameters",
+ Justification = "Only specified type of predicate is valid.")]
+ [SuppressMessage("Microsoft.Design", "CA1062:Validate arguments of public methods",
+ Justification = "Validation is present.")]
+ public static int RemoveAll<TKey, TValue>(this IQueryable<ICacheEntry<TKey, TValue>> query,
+ Expression<Func<ICacheEntry<TKey, TValue>, bool>> predicate)
+ {
+ IgniteArgumentCheck.NotNull(query, "query");
+ IgniteArgumentCheck.NotNull(predicate, "predicate");
+
+ var method = RemoveAllExpressionNode.RemoveAllPredicateMethodInfo
+ .MakeGenericMethod(typeof(TKey), typeof(TValue));
+
+ return query.Provider.Execute<int>(Expression.Call(null, method, query.Expression,
+ Expression.Quote(predicate)));
+ }
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Linq/ICacheQueryable.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Linq/ICacheQueryable.cs b/modules/platforms/dotnet/Apache.Ignite.Linq/ICacheQueryable.cs
index ef641e2..426d52c 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Linq/ICacheQueryable.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Linq/ICacheQueryable.cs
@@ -37,6 +37,7 @@ namespace Apache.Ignite.Linq
/// <summary>
/// Gets the Ignite instance associated with this query.
/// </summary>
+ [Obsolete("Deprecated, null for thin client.")]
IIgnite Ignite { get; }
/// <summary>
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheFieldsQueryProvider.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheFieldsQueryProvider.cs b/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheFieldsQueryProvider.cs
index cce89fd..4f35a42 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheFieldsQueryProvider.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheFieldsQueryProvider.cs
@@ -63,7 +63,6 @@ namespace Apache.Ignite.Linq.Impl
{
Debug.Assert(queryParser != null);
Debug.Assert(executor != null);
- Debug.Assert(ignite != null);
Debug.Assert(cacheConfiguration != null);
Debug.Assert(cacheValueType != null);
@@ -85,6 +84,7 @@ namespace Apache.Ignite.Linq.Impl
/// <summary>
/// Gets the ignite.
/// </summary>
+ [Obsolete("Deprecated, null for thin client, only used for ICacheQueryable.")]
public IIgnite Ignite
{
get { return _ignite; }
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryable.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryable.cs b/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryable.cs
index e271363..5148020 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryable.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryable.cs
@@ -18,6 +18,7 @@
namespace Apache.Ignite.Linq.Impl
{
using System.Linq;
+ using Apache.Ignite.Core;
using Apache.Ignite.Core.Cache;
using Apache.Ignite.Core.Impl.Cache;
@@ -31,10 +32,11 @@ namespace Apache.Ignite.Linq.Impl
/// </summary>
/// <param name="cache">The cache.</param>
/// <param name="queryOptions">The query options.</param>
- public CacheQueryable(ICache<TKey, TValue> cache, QueryOptions queryOptions)
+ /// <param name="ignite">The ignite.</param>
+ public CacheQueryable(ICacheInternal cache, QueryOptions queryOptions, IIgnite ignite = null)
: base(new CacheFieldsQueryProvider(CacheQueryParser.Instance,
- new CacheFieldsQueryExecutor((ICacheInternal) cache, queryOptions),
- cache.Ignite, cache.GetConfiguration(), queryOptions.TableName, typeof(TValue)))
+ new CacheFieldsQueryExecutor(cache, queryOptions),
+ ignite, cache.GetConfiguration(), queryOptions.TableName, typeof(TValue)))
{
// No-op.
}
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryableBase.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryableBase.cs b/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryableBase.cs
index 5702f4f..c585119 100644
--- a/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryableBase.cs
+++ b/modules/platforms/dotnet/Apache.Ignite.Linq/Impl/CacheQueryableBase.cs
@@ -55,6 +55,7 @@ namespace Apache.Ignite.Linq.Impl
}
/** <inheritdoc /> */
+ [Obsolete("Deprecated, null for thin client.")]
public IIgnite Ignite
{
get { return CacheQueryProvider.Ignite; }
http://git-wip-us.apache.org/repos/asf/ignite/blob/1f433752/modules/platforms/dotnet/Apache.Ignite/IgniteRunner.cs
----------------------------------------------------------------------
diff --git a/modules/platforms/dotnet/Apache.Ignite/IgniteRunner.cs b/modules/platforms/dotnet/Apache.Ignite/IgniteRunner.cs
index 6d8aa6b..c6660c3 100644
--- a/modules/platforms/dotnet/Apache.Ignite/IgniteRunner.cs
+++ b/modules/platforms/dotnet/Apache.Ignite/IgniteRunner.cs
@@ -25,7 +25,6 @@ namespace Apache.Ignite
using System.Threading;
using Apache.Ignite.Config;
using Apache.Ignite.Core;
- using Apache.Ignite.Core.Impl;
using Apache.Ignite.Service;
/// <summary>