1 #region Copyright notice and license 2 3 // Copyright 2015 gRPC authors. 4 // 5 // Licensed under the Apache License, Version 2.0 (the "License"); 6 // you may not use this file except in compliance with the License. 7 // You may obtain a copy of the License at 8 // 9 // http://www.apache.org/licenses/LICENSE-2.0 10 // 11 // Unless required by applicable law or agreed to in writing, software 12 // distributed under the License is distributed on an "AS IS" BASIS, 13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 // See the License for the specific language governing permissions and 15 // limitations under the License. 16 17 #endregion 18 19 using System; 20 using System.Diagnostics; 21 using System.Linq; 22 using System.Text; 23 using System.Threading; 24 using System.Threading.Tasks; 25 using Grpc.Core; 26 using Grpc.Core.Internal; 27 using Grpc.Core.Utils; 28 using NUnit.Framework; 29 30 namespace Grpc.Core.Tests 31 { 32 public class CompressionTest 33 { 34 MockServiceHelper helper; 35 Server server; 36 Channel channel; 37 38 [SetUp] Init()39 public void Init() 40 { 41 helper = new MockServiceHelper(); 42 43 server = helper.GetServer(); 44 server.Start(); 45 channel = helper.GetChannel(); 46 } 47 48 [TearDown] Cleanup()49 public void Cleanup() 50 { 51 channel.ShutdownAsync().Wait(); 52 server.ShutdownAsync().Wait(); 53 } 54 55 [Test] WriteOptions_Unary()56 public void WriteOptions_Unary() 57 { 58 helper.UnaryHandler = new UnaryServerMethod<string, string>((request, context) => 59 { 60 context.WriteOptions = new WriteOptions(WriteFlags.NoCompress); 61 return Task.FromResult(request); 62 }); 63 64 var callOptions = new CallOptions(writeOptions: new WriteOptions(WriteFlags.NoCompress)); 65 Calls.BlockingUnaryCall(helper.CreateUnaryCall(callOptions), "abc"); 66 } 67 68 [Test] WriteOptions_DuplexStreaming()69 public async Task WriteOptions_DuplexStreaming() 70 { 71 helper.DuplexStreamingHandler = new DuplexStreamingServerMethod<string, string>(async (requestStream, responseStream, context) => 72 { 73 await requestStream.ToListAsync(); 74 75 context.WriteOptions = new WriteOptions(WriteFlags.NoCompress); 76 77 await context.WriteResponseHeadersAsync(new Metadata { { "ascii-header", "abcdefg" } }); 78 79 await responseStream.WriteAsync("X"); 80 81 responseStream.WriteOptions = null; 82 await responseStream.WriteAsync("Y"); 83 84 responseStream.WriteOptions = new WriteOptions(WriteFlags.NoCompress); 85 await responseStream.WriteAsync("Z"); 86 }); 87 88 var callOptions = new CallOptions(writeOptions: new WriteOptions(WriteFlags.NoCompress)); 89 var call = Calls.AsyncDuplexStreamingCall(helper.CreateDuplexStreamingCall(callOptions)); 90 91 // check that write options from call options are propagated to request stream. 92 Assert.IsTrue((call.RequestStream.WriteOptions.Flags & WriteFlags.NoCompress) != 0); 93 94 call.RequestStream.WriteOptions = new WriteOptions(); 95 await call.RequestStream.WriteAsync("A"); 96 97 call.RequestStream.WriteOptions = null; 98 await call.RequestStream.WriteAsync("B"); 99 100 call.RequestStream.WriteOptions = new WriteOptions(WriteFlags.NoCompress); 101 await call.RequestStream.WriteAsync("C"); 102 103 await call.RequestStream.CompleteAsync(); 104 105 await call.ResponseStream.ToListAsync(); 106 } 107 108 [Test] CanReadCompressedMessages()109 public void CanReadCompressedMessages() 110 { 111 var compressionMetadata = new Metadata 112 { 113 { new Metadata.Entry(Metadata.CompressionRequestAlgorithmMetadataKey, "gzip") } 114 }; 115 116 helper.UnaryHandler = new UnaryServerMethod<string, string>(async (req, context) => 117 { 118 await context.WriteResponseHeadersAsync(compressionMetadata); 119 return req; 120 }); 121 122 var stringBuilder = new StringBuilder(); 123 for (int i = 0; i < 200000; i++) 124 { 125 stringBuilder.Append('a'); 126 } 127 var request = stringBuilder.ToString(); 128 var response = Calls.BlockingUnaryCall(helper.CreateUnaryCall(new CallOptions(compressionMetadata)), request); 129 130 Assert.AreEqual(request, response); 131 } 132 } 133 } 134