private void TestInterceptorExceptions(IMyObjectPrx prx) { var exceptions = new List <(string operation, string kind)> { ("raiseBeforeDispatch", "invalidInput"), ("raiseBeforeDispatch", "notExist"), ("raiseAfterDispatch", "invalidInput"), ("raiseAfterDispatch", "notExist") }; foreach ((string operation, string kind) in exceptions) { var ctx = new Dictionary <string, string> { { operation, kind } }; try { prx.IcePing(ctx); Assert(false); } catch (InvalidInputException) when(kind.Equals("invalidInput")) { } catch (ObjectNotExistException) when(kind.Equals("notExist")) { } } }
public override void run(string[] args) { using (var communicator = initialize(ref args)) { // // Create OA and servants // communicator.SetProperty("MyOA.AdapterId", "myOA"); Ice.ObjectAdapter oa = communicator.createObjectAdapterWithEndpoints("MyOA2", "tcp -h localhost"); var interceptor = new InterceptorI <MyObject, MyObjectTraits>(new MyObjectI()); var prx = IMyObjectPrx.UncheckedCast(oa.Add((incoming, current) => interceptor.Dispatch(incoming, current))); var output = getWriter(); output.WriteLine("Collocation optimization on"); runTest(prx, interceptor); output.WriteLine("Now with AMD"); interceptor.clear(); runAmdTest(prx, interceptor); oa.Activate(); // Only necessary for non-collocation optimized tests output.WriteLine("Collocation optimization off"); interceptor.clear(); prx = prx.Clone(collocationOptimized: false); runTest(prx, interceptor); output.WriteLine("Now with AMD"); interceptor.clear(); runAmdTest(prx, interceptor); } }
public override void Run(string[] args) { Communicator communicator = Initialize(ref args); // // Create OA and servants // communicator.SetProperty("MyOA.AdapterId", "myOA"); ObjectAdapter oa = communicator.CreateObjectAdapterWithEndpoints("MyOA2", "tcp -h localhost"); var myObject = new MyObject(); var interceptor = new Interceptor(myObject); IMyObjectPrx prx = oa.AddWithUUID(interceptor, IMyObjectPrx.Factory); System.IO.TextWriter output = GetWriter(); output.WriteLine("Collocation optimization on"); runTest(prx, interceptor); output.WriteLine("Now with AMD"); interceptor.clear(); runAmdAssert(prx, interceptor); oa.Activate(); // Only necessary for non-collocation optimized tests output.WriteLine("Collocation optimization off"); interceptor.clear(); prx = prx.Clone(collocationOptimized: false); runTest(prx, interceptor); output.WriteLine("Now with AMD"); interceptor.clear(); runAmdAssert(prx, interceptor); }
public override async Task RunAsync(string[] args) { string pluginPath = string.Format("msbuild/plugin/{0}/Plugin.dll", Path.GetFileName(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location))); await using Communicator communicator = Initialize( ref args, new Dictionary <string, string>() { { "Ice.Plugin.InvocationPlugin", $"{pluginPath }:ZeroC.Ice.Test.Interceptor.InvocationPluginFactory" } }); IMyObjectPrx prx = AllTests.Run(this); await prx.ShutdownAsync(); }
public override async Task RunAsync(string[] args) { await using Communicator communicator = Initialize(ref args); // // Create OA and servants // communicator.SetProperty("MyOA.AdapterId", "myOA"); ObjectAdapter oa = communicator.CreateObjectAdapterWithEndpoints("MyOA2", "tcp -h localhost"); var myObject = new MyObject(); var interceptor = new Interceptor(myObject); IMyObjectPrx prx = oa.AddWithUUID(interceptor, IMyObjectPrx.Factory); System.IO.TextWriter output = GetWriter(); output.WriteLine("With sync dispatch"); Run(prx, interceptor); output.WriteLine("Now with AMD"); interceptor.Clear(); RunAmd(prx, interceptor); }
private void runAmdAssert(IMyObjectPrx prx, Interceptor interceptor) { System.IO.TextWriter output = GetWriter(); output.Write("testing simple interceptor... "); output.Flush(); Assert(interceptor.getLastOperation() == null); Assert(!interceptor.AsyncCompletion); Assert(prx.amdAdd(33, 12) == 45); Assert(interceptor.getLastOperation() !.Equals("amdAdd")); Assert(interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing retry... "); output.Flush(); Assert(prx.amdAddWithRetry(33, 12) == 45); Assert(interceptor.getLastOperation() !.Equals("amdAddWithRetry")); Assert(interceptor.AsyncCompletion); { var ctx = new Dictionary <string, string> { { "retry", "yes" } }; for (int i = 0; i < 10; ++i) { Assert(prx.amdAdd(33, 12, ctx) == 45); Assert(interceptor.getLastOperation() !.Equals("amdAdd")); Assert(interceptor.AsyncCompletion); } } output.WriteLine("ok"); output.Write("testing user exception... "); try { prx.amdBadAdd(33, 12); Assert(false); } catch (InvalidInputException) { // expected } Assert(interceptor.getLastOperation() !.Equals("amdBadAdd")); Assert(interceptor.AsyncCompletion); Console.WriteLine("ok"); output.Write("testing ONE... "); output.Flush(); interceptor.clear(); try { prx.amdNotExistAdd(33, 12); Assert(false); } catch (ObjectNotExistException) { // expected } Assert(interceptor.getLastOperation() !.Equals("amdNotExistAdd")); Assert(interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing exceptions raised by the interceptor... "); output.Flush(); TestInterceptorExceptions(prx); output.WriteLine("ok"); }
private void runTest(IMyObjectPrx prx, Interceptor interceptor) { System.IO.TextWriter output = GetWriter(); output.Write("testing simple interceptor... "); output.Flush(); Assert(interceptor.getLastOperation() == null); Assert(!interceptor.AsyncCompletion); prx.IcePing(); Assert(interceptor.getLastOperation() !.Equals("ice_ping")); Assert(!interceptor.AsyncCompletion); string typeId = prx.IceId(); Assert(interceptor.getLastOperation() !.Equals("ice_id")); Assert(!interceptor.AsyncCompletion); Assert(prx.IceIsA(typeId)); Assert(interceptor.getLastOperation() !.Equals("ice_isA")); Assert(!interceptor.AsyncCompletion); Assert(prx.add(33, 12) == 45); Assert(interceptor.getLastOperation() !.Equals("add")); Assert(!interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing retry... "); output.Flush(); Assert(prx.addWithRetry(33, 12) == 45); Assert(interceptor.getLastOperation() !.Equals("addWithRetry")); Assert(!interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing remote exception... "); output.Flush(); try { prx.badAdd(33, 12); Assert(false); } catch (InvalidInputException) { // expected } Assert(interceptor.getLastOperation() !.Equals("badAdd")); Assert(!interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing ONE... "); output.Flush(); interceptor.clear(); try { prx.notExistAdd(33, 12); Assert(false); } catch (ObjectNotExistException) { // expected } Assert(interceptor.getLastOperation() !.Equals("notExistAdd")); Assert(!interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing exceptions raised by the interceptor... "); output.Flush(); TestInterceptorExceptions(prx); output.WriteLine("ok"); }
allTests(global::Test.TestHelper helper) { var output = helper.getWriter(); Communicator communicator = helper.communicator(); ObjectAdapter oa = communicator.createObjectAdapterWithEndpoints("MyOA", "tcp -h localhost"); oa.Activate(); var servantI = new MyObjectI(); var servantT = default(MyObjectTraits); Disp servantD = (incoming, current) => servantT.Dispatch(servantI, incoming, current); // // Register default servant with category "foo" // oa.AddDefaultServant(servantD, "foo"); // // Start test // output.Write("testing single category... "); output.Flush(); Disp r = oa.FindDefaultServant("foo"); test(r == servantD); r = oa.FindDefaultServant("bar"); test(r == null); Ice.Identity identity = new Ice.Identity(); identity.category = "foo"; string[] names = new string[] { "foo", "bar", "x", "y", "abcdefg" }; IMyObjectPrx prx = null; for (int idx = 0; idx < 5; ++idx) { identity.name = names[idx]; prx = IMyObjectPrx.UncheckedCast(oa.CreateProxy(identity)); prx.IcePing(); test(prx.getName() == names[idx]); } identity.name = "ObjectNotExist"; prx = IMyObjectPrx.UncheckedCast(oa.CreateProxy(identity)); try { prx.IcePing(); test(false); } catch (ObjectNotExistException) { // Expected } try { prx.getName(); test(false); } catch (ObjectNotExistException) { // Expected } identity.name = "FacetNotExist"; prx = IMyObjectPrx.UncheckedCast(oa.CreateProxy(identity)); try { prx.IcePing(); test(false); } catch (FacetNotExistException) { // Expected } try { prx.getName(); test(false); } catch (FacetNotExistException) { // Expected } identity.category = "bar"; for (int idx = 0; idx < 5; idx++) { identity.name = names[idx]; prx = Test.IMyObjectPrx.UncheckedCast(oa.CreateProxy(identity)); try { prx.IcePing(); test(false); } catch (Ice.ObjectNotExistException) { // Expected } try { prx.getName(); test(false); } catch (Ice.ObjectNotExistException) { // Expected } } oa.RemoveDefaultServant("foo"); identity.category = "foo"; prx = Test.IMyObjectPrx.UncheckedCast(oa.CreateProxy(identity)); try { prx.IcePing(); } catch (Ice.ObjectNotExistException) { // Expected } output.WriteLine("ok"); output.Write("testing default category... "); output.Flush(); oa.AddDefaultServant(servantD, ""); r = oa.FindDefaultServant("bar"); test(r == null); r = oa.FindDefaultServant(""); test(r == servantD); for (int idx = 0; idx < 5; ++idx) { identity.name = names[idx]; prx = Test.IMyObjectPrx.UncheckedCast(oa.CreateProxy(identity)); prx.IcePing(); test(prx.getName() == names[idx]); } output.WriteLine("ok"); }
public static IMyObjectPrx Run(TestHelper helper) { bool ice2 = helper.Protocol == Protocol.Ice2; var prx = IMyObjectPrx.Parse(helper.GetTestProxy("test"), helper.Communicator !); System.IO.TextWriter output = helper.Output; output.Write("testing retry... "); output.Flush(); TestHelper.Assert(prx.AddWithRetry(33, 12) == 45); output.WriteLine("ok"); output.Write("testing remote exception... "); output.Flush(); try { prx.BadAdd(33, 12); TestHelper.Assert(false); } catch (InvalidInputException) { // expected } output.WriteLine("ok"); output.Write("testing ONE... "); output.Flush(); try { prx.NotExistAdd(33, 12); TestHelper.Assert(false); } catch (ObjectNotExistException) { // expected } output.WriteLine("ok"); output.Write("testing exceptions raised by the interceptor... "); output.Flush(); var exceptions = new List <(string operation, string kind)> { ("raiseBeforeDispatch", "invalidInput"), ("raiseBeforeDispatch", "notExist"), ("raiseAfterDispatch", "invalidInput"), ("raiseAfterDispatch", "notExist") }; foreach ((string operation, string kind) in exceptions) { var ctx = new Dictionary <string, string> { { operation, kind } }; try { prx.IcePing(ctx); TestHelper.Assert(false); } catch (InvalidInputException) when(kind == "invalidInput") { } catch (ObjectNotExistException) when(kind == "notExist") { } } output.WriteLine("ok"); output.Write("testing invocation interceptors... "); output.Flush(); { var tasks = new List <Task>(); var invocationContext = new AsyncLocal <int>(); using var communicator = new Communicator( prx.Communicator.GetProperties(), invocationInterceptors: new InvocationInterceptor[] { (target, request, next, cancel) => { if (ice2) { request.ContextOverride["interceptor-1"] = "interceptor-1"; request.AddBinaryContextEntry(110, 110, (ostr, v) => ostr.WriteInt(v)); } return(next(target, request, cancel)); }, async(target, request, next, cancel) => { if (ice2) { TestHelper.Assert(request.Context["interceptor-1"] == "interceptor-1"); request.ContextOverride["interceptor-2"] = "interceptor-2"; request.AddBinaryContextEntry(120, 120, (ostr, v) => ostr.WriteInt(v)); } IncomingResponseFrame response = await next(target, request, cancel); TestHelper.Assert(invocationContext.Value == int.Parse(request.Context["local-user"])); if (ice2) { TestHelper.Assert(response.BinaryContext.ContainsKey(110)); TestHelper.Assert(response.BinaryContext[110].Read(istr => istr.ReadInt()) == 110); TestHelper.Assert(response.BinaryContext.ContainsKey(120)); TestHelper.Assert(response.BinaryContext[120].Read(istr => istr.ReadInt()) == 120); } return(response); } }); for (int i = 0; i < 10; ++i) { invocationContext.Value = i; var prx1 = IMyObjectPrx.Parse(prx.ToString() !, communicator); Task t = prx1.Op1Async(new Dictionary <string, string> { { "local-user", $"{i}" } }); tasks.Add(t); } Task.WaitAll(tasks.ToArray()); } { IncomingResponseFrame?response = null; int invocations = 0; // An interceptor can stop the chain and directly return a response without calling next, // the first invocation calls next and subsequent invocations reuse the first response. using var communicator = new Communicator( prx.Communicator.GetProperties(), invocationInterceptors: new InvocationInterceptor[] { (target, request, next, cancel) => { if (ice2) { request.ContextOverride["interceptor-1"] = "interceptor-1"; } return(next(target, request, cancel)); }, async(target, request, next, cancel) => { if (response == null) { response = await next(target, request, cancel); } return(response); }, (target, request, next, cancel) => { invocations++; TestHelper.Assert(response == null); return(next(target, request, cancel)); } }); var prx1 = IMyObjectPrx.Parse(prx.ToString() !, communicator); prx1.Op1(new Dictionary <string, string> { { "local-user", "10" } }); prx1.Op1(new Dictionary <string, string> { { "local-user", "11" } }); prx1.Op1(new Dictionary <string, string> { { "local-user", "12" } }); TestHelper.Assert(invocations == 1); } { // throwing from an interceptor stops the interceptor chain using var communicator = new Communicator( prx.Communicator.GetProperties(), invocationInterceptors: new InvocationInterceptor[] { (target, request, next, cancel) => { request.ContextOverride["interceptor-1"] = "interceptor-1"; return(next(target, request, cancel)); }, (target, request, next, cancel) => { TestHelper.Assert(request.Context["interceptor-1"] == "interceptor-1"); throw new InvalidOperationException("stop interceptor chain"); }, (target, request, next, cancel) => { TestHelper.Assert(false); return(next(target, request, cancel)); } }); var prx1 = IMyObjectPrx.Parse(prx.ToString() !, communicator); try { prx1.Op1(); TestHelper.Assert(false); } catch (InvalidOperationException) { } } output.WriteLine("ok"); output.Write("testing binary context... "); output.Flush(); if (ice2) { for (int size = 128; size < 4096; size *= 2) { var token = new Token(1, "mytoken", Enumerable.Range(0, size).Select(i => (byte)2).ToArray()); var request = OutgoingRequestFrame.WithArgs(prx, "opWithBinaryContext", idempotent: false, compress: false, format: default,
private void runAmdTest(IMyObjectPrx prx, Interceptor interceptor) { var output = getWriter(); output.Write("testing simple interceptor... "); output.Flush(); test(interceptor.getLastOperation() == null); test(!interceptor.getLastStatus()); test(prx.amdAdd(33, 12) == 45); test(interceptor.getLastOperation().Equals("amdAdd")); test(interceptor.getLastStatus()); output.WriteLine("ok"); output.Write("testing retry... "); output.Flush(); test(prx.amdAddWithRetry(33, 12) == 45); test(interceptor.getLastOperation().Equals("amdAddWithRetry")); test(interceptor.getLastStatus()); { var ctx = new Dictionary <string, string>(); ctx.Add("retry", "yes"); for (int i = 0; i < 10; ++i) { test(prx.amdAdd(33, 12, ctx) == 45); test(interceptor.getLastOperation().Equals("amdAdd")); test(interceptor.getLastStatus()); } } output.WriteLine("ok"); output.Write("testing user exception... "); try { prx.amdBadAdd(33, 12); test(false); } catch (InvalidInputException) { // expected } test(interceptor.getLastOperation().Equals("amdBadAdd")); test(interceptor.getLastStatus()); Console.WriteLine("ok"); output.Write("testing ONE... "); output.Flush(); interceptor.clear(); try { prx.amdNotExistAdd(33, 12); test(false); } catch (ObjectNotExistException) { // expected } test(interceptor.getLastOperation().Equals("amdNotExistAdd")); test(interceptor.getLastStatus()); output.WriteLine("ok"); output.Write("testing system exception... "); output.Flush(); interceptor.clear(); try { prx.amdBadSystemAdd(33, 12); test(false); } catch (UnknownException) { test(!prx.IsCollocationOptimized); } catch (MySystemException) { test(prx.IsCollocationOptimized); } catch (Exception) { test(false); } test(interceptor.getLastOperation().Equals("amdBadSystemAdd")); test(interceptor.getLastStatus()); output.WriteLine("ok"); output.Write("testing exceptions raised by the interceptor... "); output.Flush(); testInterceptorExceptions(prx); output.WriteLine("ok"); }
allTests(global::Test.TestHelper helper) { var output = helper.getWriter(); Communicator communicator = helper.communicator(); ObjectAdapter oa = communicator.CreateObjectAdapterWithEndpoints("MyOA", "tcp -h localhost"); oa.Activate(); var servantI = new MyObject(); Disp servantD = (servantI as IObject).Dispatch; // // Register default servant with category "foo" // oa.AddDefaultServant(servantD, "foo"); // // Start test // output.Write("testing single category... "); output.Flush(); Disp r = oa.FindDefaultServant("foo"); test(r == servantD); r = oa.FindDefaultServant("bar"); test(r == null); Identity identity = new Identity("", "foo"); string[] names = new string[] { "foo", "bar", "x", "y", "abcdefg" }; IMyObjectPrx prx = null; for (int idx = 0; idx < 5; ++idx) { identity = new Identity(names[idx], identity.Category); prx = oa.CreateProxy(identity, IMyObjectPrx.Factory); prx.IcePing(); test(prx.getName() == names[idx]); } identity = new Identity("ObjectNotExist", identity.Category); prx = oa.CreateProxy(identity, IMyObjectPrx.Factory); try { prx.IcePing(); test(false); } catch (ObjectNotExistException) { // Expected } try { prx.getName(); test(false); } catch (ObjectNotExistException) { // Expected } identity = new Identity("FacetNotExist", identity.Category); prx = oa.CreateProxy(identity, IMyObjectPrx.Factory); try { prx.IcePing(); test(false); } catch (FacetNotExistException) { // Expected } try { prx.getName(); test(false); } catch (FacetNotExistException) { // Expected } identity = new Identity(identity.Name, "bar"); for (int idx = 0; idx < 5; idx++) { identity = new Identity(names[idx], identity.Category); prx = oa.CreateProxy(identity, Test.IMyObjectPrx.Factory); try { prx.IcePing(); test(false); } catch (Ice.ObjectNotExistException) { // Expected } try { prx.getName(); test(false); } catch (Ice.ObjectNotExistException) { // Expected } } oa.RemoveDefaultServant("foo"); identity = new Identity(identity.Name, "foo"); prx = oa.CreateProxy(identity, IMyObjectPrx.Factory); try { prx.IcePing(); } catch (ObjectNotExistException) { // Expected } output.WriteLine("ok"); output.Write("testing default category... "); output.Flush(); oa.AddDefaultServant(servantD, ""); r = oa.FindDefaultServant("bar"); test(r == null); r = oa.FindDefaultServant(""); test(r == servantD); for (int idx = 0; idx < 5; ++idx) { identity = new Identity(names[idx], identity.Category); prx = oa.CreateProxy(identity, IMyObjectPrx.Factory); prx.IcePing(); test(prx.getName() == names[idx]); } output.WriteLine("ok"); }
private void Run(IMyObjectPrx prx, Interceptor interceptor) { System.IO.TextWriter output = GetWriter(); output.Write("testing simple interceptor... "); output.Flush(); Assert(interceptor.GetLastOperation() == null); Assert(!interceptor.AsyncCompletion); prx.IcePing(); Assert(interceptor.GetLastOperation() !.Equals("ice_ping")); Assert(!interceptor.AsyncCompletion); string typeId = prx.IceId(); Assert(interceptor.GetLastOperation() !.Equals("ice_id")); Assert(!interceptor.AsyncCompletion); Assert(prx.IceIsA(typeId)); Assert(interceptor.GetLastOperation() !.Equals("ice_isA")); Assert(!interceptor.AsyncCompletion); Assert(prx.Add(33, 12) == 45); Assert(interceptor.GetLastOperation() !.Equals("add")); Assert(!interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing retry... "); output.Flush(); Assert(prx.AddWithRetry(33, 12) == 45); Assert(interceptor.GetLastOperation() !.Equals("addWithRetry")); Assert(!interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing remote exception... "); output.Flush(); try { prx.BadAdd(33, 12); Assert(false); } catch (InvalidInputException) { // expected } Assert(interceptor.GetLastOperation() !.Equals("badAdd")); Assert(!interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing ONE... "); output.Flush(); interceptor.Clear(); try { prx.NotExistAdd(33, 12); Assert(false); } catch (ObjectNotExistException) { // expected } Assert(interceptor.GetLastOperation() !.Equals("notExistAdd")); Assert(!interceptor.AsyncCompletion); output.WriteLine("ok"); output.Write("testing exceptions raised by the interceptor... "); output.Flush(); TestInterceptorExceptions(prx); output.WriteLine("ok"); output.Write("testing binary context... "); output.Flush(); bool ice2 = Communicator() !.DefaultProtocol != Protocol.Ice1; if (ice2) { for (int size = 128; size < 4096; size *= 2) { var token = new Token(1, "mytoken", Enumerable.Range(0, size).Select(i => (byte)2).ToArray()); var request = OutgoingRequestFrame.WithParamList(prx, "opWithBinaryContext", idempotent: false, compress: false, format: default,
public static IMyObjectPrx Run(TestHelper helper) { bool ice2 = helper.Protocol == Protocol.Ice2; var prx = IMyObjectPrx.Parse(helper.GetTestProxy("test"), helper.Communicator !); System.IO.TextWriter output = helper.Output; output.Write("testing retry... "); output.Flush(); TestHelper.Assert(prx.AddWithRetry(33, 12) == 45); output.WriteLine("ok"); output.Write("testing remote exception... "); output.Flush(); try { prx.BadAdd(33, 12); TestHelper.Assert(false); } catch (InvalidInputException) { // expected } output.WriteLine("ok"); output.Write("testing ONE... "); output.Flush(); try { prx.NotExistAdd(33, 12); TestHelper.Assert(false); } catch (ObjectNotExistException) { // expected } output.WriteLine("ok"); output.Write("testing exceptions raised by the interceptor... "); output.Flush(); var exceptions = new List <(string operation, string kind)> { ("raiseBeforeDispatch", "invalidInput"), ("raiseBeforeDispatch", "notExist"), ("raiseAfterDispatch", "invalidInput"), ("raiseAfterDispatch", "notExist") }; foreach ((string operation, string kind) in exceptions) { var ctx = new Dictionary <string, string> { { operation, kind } }; try { prx.IcePing(ctx); TestHelper.Assert(false); } catch (InvalidInputException) when(kind == "invalidInput") { } catch (ObjectNotExistException) when(kind == "notExist") { } } output.WriteLine("ok"); output.Write("testing invocation interceptors... "); output.Flush(); { var tasks = new List <Task>(); var invocationContext = new AsyncLocal <int>(); using var communicator = new Communicator(prx.Communicator.GetProperties()); communicator.DefaultInvocationInterceptors = ImmutableList.Create <InvocationInterceptor>( (target, request, next, cancel) => { request.WritableContext["interceptor-1"] = "interceptor-1"; if (ice2) { request.BinaryContextOverride.Add(110, ostr => ostr.WriteInt(110)); } return(next(target, request, cancel)); }, async(target, request, next, cancel) => { TestHelper.Assert(request.Context["interceptor-1"] == "interceptor-1"); request.WritableContext["interceptor-2"] = "interceptor-2"; if (ice2) { request.BinaryContextOverride.Add(120, ostr => ostr.WriteInt(120)); } IncomingResponseFrame response = await next(target, request, cancel); TestHelper.Assert(invocationContext.Value == int.Parse(request.Context["local-user"])); if (ice2) { TestHelper.Assert(response.BinaryContext.ContainsKey(110)); TestHelper.Assert(response.BinaryContext[110].Read(istr => istr.ReadInt()) == 110); TestHelper.Assert(response.BinaryContext.ContainsKey(120)); TestHelper.Assert(response.BinaryContext[120].Read(istr => istr.ReadInt()) == 120); } return(response); }); communicator.ActivateAsync().GetAwaiter().GetResult(); for (int i = 0; i < 10; ++i) { invocationContext.Value = i; var prx1 = IMyObjectPrx.Parse(prx.ToString() !, communicator); Task t = prx1.Op1Async(new Dictionary <string, string> { { "local-user", $"{i}" } }); tasks.Add(t); } Task.WaitAll(tasks.ToArray()); } { IncomingResponseFrame?response = null; int invocations = 0; // An interceptor can stop the chain and directly return a response without calling next, // the first invocation calls next and subsequent invocations reuse the first response. using var communicator = new Communicator(prx.Communicator.GetProperties()); communicator.DefaultInvocationInterceptors = ImmutableList.Create <InvocationInterceptor>( (target, request, next, cancel) => { request.WritableContext["interceptor-1"] = "interceptor-1"; return(next(target, request, cancel)); }, async(target, request, next, cancel) => { if (response == null) { response = await next(target, request, cancel); } return(response); }, (target, request, next, cancel) => { invocations++; TestHelper.Assert(response == null); return(next(target, request, cancel)); }); TestHelper.Assert(communicator.DefaultInvocationInterceptors.Count == 3); communicator.ActivateAsync().GetAwaiter().GetResult(); TestHelper.Assert(communicator.DefaultInvocationInterceptors.Count == 4); var prx1 = IMyObjectPrx.Parse(prx.ToString() !, communicator); // Truly reference equal TestHelper.Assert(prx1.InvocationInterceptors == communicator.DefaultInvocationInterceptors); prx1.Op1(new Dictionary <string, string> { { "local-user", "10" } }); prx1.Op1(new Dictionary <string, string> { { "local-user", "11" } }); prx1.Op1(new Dictionary <string, string> { { "local-user", "12" } }); TestHelper.Assert(invocations == 1); } { // throwing from an interceptor stops the interceptor chain using var communicator = new Communicator(prx.Communicator.GetProperties()); communicator.DefaultInvocationInterceptors = ImmutableList.Create <InvocationInterceptor>( (target, request, next, cancel) => { request.WritableContext["interceptor-1"] = "interceptor-1"; return(next(target, request, cancel)); }, (target, request, next, cancel) => { TestHelper.Assert(request.Context["interceptor-1"] == "interceptor-1"); throw new InvalidOperationException("stop interceptor chain"); }, (target, request, next, cancel) => { TestHelper.Assert(false); return(next(target, request, cancel)); }); communicator.ActivateAsync().GetAwaiter().GetResult(); var prx1 = IMyObjectPrx.Parse(prx.ToString() !, communicator); try { prx1.Op1(); TestHelper.Assert(false); } catch (InvalidOperationException) { } } output.WriteLine("ok"); output.Write("testing binary context... "); output.Flush(); if (ice2) { for (int size = 128; size < 4096; size *= 2) { var token = new Token(1, "mytoken", Enumerable.Range(0, size).Select(i => (byte)2).ToArray()); { using var request = OutgoingRequestFrame.WithArgs(prx, "opWithBinaryContext", idempotent: false, compress: false, format: default, context: null, token, Token.IceWriter); request.BinaryContextOverride.Add(1, ostr => ostr.WriteStruct(token)); request.BinaryContextOverride.Add(3, ostr => ostr.WriteShort((short)size)); request.BinaryContextOverride.Add( 2, ostr => ostr.WriteSequence( Enumerable.Range(0, 10).Select(i => $"string-{i}").ToArray(), (ostr, s) => ostr.WriteString(s))); using IncomingResponseFrame response = prx.InvokeAsync(request).Result; } { // repeat with compressed frame using OutgoingRequestFrame request = OutgoingRequestFrame.WithArgs(prx, "opWithBinaryContext", idempotent: false, compress: false, format: default, context: null, token, Token.IceWriter); request.BinaryContextOverride.Add(1, ostr => ostr.WriteStruct(token)); request.BinaryContextOverride.Add(3, ostr => ostr.WriteShort((short)size)); request.BinaryContextOverride.Add( 2, ostr => ostr.WriteSequence( Enumerable.Range(0, 10).Select(i => $"string-{i}").ToArray(), (ostr, s) => ostr.WriteString(s))); TestHelper.Assert(request.CompressPayload() == CompressionResult.Success); using IncomingResponseFrame response = prx.InvokeAsync(request).Result; } { // repeat compressed the frame before writing the context using OutgoingRequestFrame request = OutgoingRequestFrame.WithArgs(prx, "opWithBinaryContext", idempotent: false, compress: false, format: default, context: null, token, Token.IceWriter); TestHelper.Assert(request.CompressPayload() == CompressionResult.Success); request.BinaryContextOverride.Add(1, ostr => ostr.WriteStruct(token)); request.BinaryContextOverride.Add(3, ostr => ostr.WriteShort((short)size)); request.BinaryContextOverride.Add( 2, ostr => ostr.WriteSequence( Enumerable.Range(0, 10).Select(i => $"string-{i}").ToArray(), (ostr, s) => ostr.WriteString(s))); using IncomingResponseFrame response = prx.InvokeAsync(request).Result; } } } else { var token = new Token(1, "mytoken", Enumerable.Range(0, 256).Select(i => (byte)2).ToArray()); using var request = OutgoingRequestFrame.WithArgs(prx, "opWithBinaryContext", idempotent: false, compress: false, format: default, context: null, token, Token.IceWriter); try { request.BinaryContextOverride.Add(1, ostr => ostr.WriteStruct(token)); TestHelper.Assert(false); } catch (NotSupportedException) { } using IncomingResponseFrame response = prx.InvokeAsync(request).Result; } output.WriteLine("ok"); output.Write("testing per proxy invocation interceptors... "); output.Flush(); { var communicator = helper.Communicator !; SortedDictionary <string, string>?context = prx.Op2(); TestHelper.Assert(context["context1"] == "plug-in"); TestHelper.Assert(context["context2"] == "plug-in"); TestHelper.Assert(!context.ContainsKey("context3")); prx = prx.Clone(invocationInterceptors: ImmutableList.Create <InvocationInterceptor>( (target, request, next, cancel) => { request.WritableContext["context2"] = "proxy"; request.WritableContext["context3"] = "proxy"; return(next(target, request, cancel)); }).AddRange(communicator.DefaultInvocationInterceptors)); context = prx.Op2(); TestHelper.Assert(context["context1"] == "plug-in"); TestHelper.Assert(context["context2"] == "plug-in"); TestHelper.Assert(context["context3"] == "proxy"); // Calling next twice doesn't change the result prx = prx.Clone(invocationInterceptors: ImmutableList.Create <InvocationInterceptor>( (target, request, next, cancel) => { request.WritableContext["context2"] = "proxy"; request.WritableContext["context3"] = "proxy"; _ = next(target, request, cancel); return(next(target, request, cancel)); }).AddRange(communicator.DefaultInvocationInterceptors)); context = prx.Op2(); TestHelper.Assert(context["context1"] == "plug-in"); TestHelper.Assert(context["context2"] == "plug-in"); TestHelper.Assert(context["context3"] == "proxy"); // Cloning the proxy preserve its interceptors prx = prx.Clone(invocationTimeout: TimeSpan.FromSeconds(10)); context = prx.Op2(); TestHelper.Assert(context["context1"] == "plug-in"); TestHelper.Assert(context["context2"] == "plug-in"); TestHelper.Assert(context["context3"] == "proxy"); // The server increments the result with each call when using the invocation interceptor we // return a cached response, and we will see the same result with each call. IncomingResponseFrame?response = null; prx = prx.Clone(invocationInterceptors: ImmutableList.Create <InvocationInterceptor>( async(target, request, next, cancel) => { response ??= await next(target, request, cancel); return(response); }).AddRange(communicator.DefaultInvocationInterceptors)); TestHelper.Assert(prx.Op3() == 0); TestHelper.Assert(prx.Op3() == 0); // After clearing the invocation interceptors we should see the result increase with each call prx = prx.Clone(invocationInterceptors: communicator.DefaultInvocationInterceptors); TestHelper.Assert(prx.Op3() == 1); TestHelper.Assert(prx.Op3() == 2); } output.WriteLine("ok"); return(prx); }