Description
In case .Net -> .Net service call Ignite loses array type information.
using Apache.Ignite.Core; using Apache.Ignite.Core.Discovery.Tcp; using Apache.Ignite.Core.Discovery.Tcp.Static; using Apache.Ignite.Core.Services; using Castle.DynamicProxy; using System; using System.Linq; using Xunit; namespace Ignite.ServiceReturnsArray { public class Test : IDisposable { private readonly IIgnite igniteSrv; private readonly IIgnite ignite; public Test() { IgniteConfiguration IgniteConfig(bool clientMode) => new IgniteConfiguration() { ClientMode = clientMode, IgniteInstanceName = Guid.NewGuid().ToString(), DiscoverySpi = new TcpDiscoverySpi { IpFinder = new TcpDiscoveryStaticIpFinder { Endpoints = new[] { "127.0.0.1:47500" } } } }; igniteSrv = Ignition.Start(IgniteConfig(false)); ignite = Ignition.Start(IgniteConfig(true)); ignite.GetServices().DeployClusterSingleton(nameof(ArrayFactoryService), new ArrayFactoryService()); } public void Dispose() { ignite.Dispose(); igniteSrv.Dispose(); } [Fact] public void ServiceReturnsArray() { var arr = ignite.GetServices().GetServiceProxy<IArrayFactory>(nameof(ArrayFactoryService), false) .CreateArray(2, 1); Assert.IsType<Result[]>(arr); Assert.Equal(1, arr?[1]?.Value); } [Fact] public void ServiceReturnsArrayWithReflection() { var arr = typeof(IArrayFactory).GetMethod(nameof(IArrayFactory.CreateArray)).Invoke( ignite.GetServices().GetServiceProxy<IArrayFactory>(nameof(ArrayFactoryService)), new object[] { 2, 1 }); Assert.IsType<Result[]>(arr); Assert.Equal(1, ((Result[])arr)?[1]?.Value); } [Fact] public void ServiceReturnsArrayWithCastleProxy() { var interceptor = new ServiceInterceptor<IArrayFactory>(ignite, nameof(ArrayFactoryService)); var arr = new ProxyGenerator().CreateInterfaceProxyWithoutTarget<IArrayFactory>(interceptor) .CreateArray(2, 1); Assert.IsType<Result[]>(arr); Assert.Equal(1, arr?[1]?.Value); } public sealed class Result { public int Value { get; set; } } public interface IArrayFactory { Result[] CreateArray(int size, int dlftVal); } public sealed class ArrayFactoryService : IArrayFactory, IService { public Result[] CreateArray(int size, int dfltVal) { return Enumerable.Repeat(new Result { Value = dfltVal }, size).ToArray(); } public void Cancel(IServiceContext context) { } public void Execute(IServiceContext context) { } public void Init(IServiceContext context) { } } private sealed class ServiceInterceptor<T> : IInterceptor where T: class { private readonly IIgnite ignite; private readonly string name; public ServiceInterceptor(IIgnite ignite, string name) { this.ignite = ignite; this.name = name; } public void Intercept(IInvocation invocation) { var svc = ignite.GetServices().GetServiceProxy<T>(name, false); invocation.ReturnValue = invocation.Method.Invoke(svc, invocation.Arguments); } } } }
Above test fail on type check.
Attachments
Issue Links
- is related to
-
IGNITE-14313 .NET: Add test to call .Net service from .Net
- Resolved
-
IGNITE-14320 .NET: Collections can't be used as service method parameters
- Resolved
-
IGNITE-14742 Store array component type in binary object
- Resolved
-
IGNITE-16083 .NET: Thin client services don't work properly
- Resolved
-
IGNITE-16076 .NET: Remove duplicate test class
- Resolved
- relates to
-
IGNITE-12823 .NET: Service method with user type array parameter can't be found
- Resolved
-
IGNITE-13734 .NET Service loses returned array type information
- Resolved
-
IGNITE-13897 .NET: Service can't assign correct type to passed array parameters
- Resolved
-
IGNITE-14328 .NET: Array of Collections can't be used as service method parameters
- Open
- links to