Exemplo n.º 1
0
        static async Task Main(string[] args)
        {
            // DI
            var services = new ServiceCollection();

            var loggerFactory = LoggerFactory.Create(logging =>
            {
                logging.AddConsole();
                logging.SetMinimumLevel(LogLevel.Debug);
            });

            var serverErrors = new HttpStatusCode[] {
                HttpStatusCode.BadGateway,
                HttpStatusCode.GatewayTimeout,
                HttpStatusCode.ServiceUnavailable,
                HttpStatusCode.InternalServerError,
                HttpStatusCode.TooManyRequests,
                HttpStatusCode.RequestTimeout
            };

            var gRpcErrors = new StatusCode[] {
                StatusCode.DeadlineExceeded,
                StatusCode.Internal,
                StatusCode.NotFound,
                StatusCode.ResourceExhausted,
                StatusCode.Unavailable,
                StatusCode.Unknown
            };

            Func <HttpRequestMessage, IAsyncPolicy <HttpResponseMessage> > retryFunc = (request) =>
            {
                return(Policy.HandleResult <HttpResponseMessage>(r => {
                    var grpcStatus = StatusManager.GetStatusCode(r);
                    var httpStatusCode = r.StatusCode;

                    return (grpcStatus == null && serverErrors.Contains(httpStatusCode)) ||         // if the server send an error before gRPC pipeline
                    (httpStatusCode == HttpStatusCode.OK && gRpcErrors.Contains(grpcStatus.Value)); // if gRPC pipeline handled the request (gRPC always answers OK)
                })
                       .WaitAndRetryAsync(3, (input) => TimeSpan.FromSeconds(3 + input), (result, timeSpan, retryCount, context) =>
                {
                    var grpcStatus = StatusManager.GetStatusCode(result.Result);
                    Console.WriteLine($"Request failed with {grpcStatus}. Retry");
                }));
            };

            // https://grpcwebdemo.azurewebsites.net
            // gRPC
            services.AddGrpcClient <CountryServiceClient>(o =>
            {
                o.Address = new Uri("https://localhost:5001");
            }).AddPolicyHandler(retryFunc);
            var provider = services.BuildServiceProvider();
            var client   = provider.GetRequiredService <CountryServiceClient>();


            // gRPC-Web
            //var handler = new GrpcWebHandler(GrpcWebMode.GrpcWebText, new HttpClientHandler());
            //var channel = GrpcChannel.ForAddress("https://grpcwebdemo.azurewebsites.net", new GrpcChannelOptions
            //{
            //    HttpClient = new HttpClient(handler),
            //    LoggerFactory = loggerFactory
            //});
            //var clientWeb = new CountryServiceClient(channel);


            try
            {
                // Get all gRPC
                var countries = (await client.GetAllAsync(new EmptyRequest())).Countries.Select(x => new Country
                {
                    CountryId   = x.Id,
                    Description = x.Description,
                    CountryName = x.Name
                }).ToList();

                Console.WriteLine("Found countries");
                countries.ForEach(x => Console.WriteLine($"Found country {x.CountryName} ({x.CountryId}) {x.Description}"));


                // Get all gRPC - web
                //var countriesweb = (await clientWeb.GetAllAsync(new EmptyRequest())).Countries.Select(x => new Country
                //{
                //    CountryId = x.Id,
                //    Description = x.Description,
                //    CountryName = x.Name
                //}).ToList();

                //Console.WriteLine("Found countries with gRPC-Web");
                //countriesweb.ForEach(x => Console.WriteLine($"Found country with gRPC-Web:  {x.CountryName} ({x.CountryId}) {x.Description}"));
            }
            catch (RpcException e)
            {
                var errors = e.GetValidationErrors(); // Gets validation errors list
                Console.WriteLine(e.Message);
            }
        }
Exemplo n.º 2
0
        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {
            #region Discount gRPC client
            // Enable support for unencrypted HTTP2
            //AppContext.SetSwitch("System.Net.Http.SocketsHttpHandler.Http2UnencryptedSupport", true);
            //AppContext.SetSwitch("System.Net.Http.SocketsHttpHandler.Http2Support", true);

            Random jitterer = new Random();

            var loggerFactory = LoggerFactory.Create(logging =>
            {
                logging.AddConsole();
                logging.SetMinimumLevel(LogLevel.Debug);
            });

            var serverErrors = new HttpStatusCode[] {
                HttpStatusCode.BadGateway,
                HttpStatusCode.GatewayTimeout,
                HttpStatusCode.ServiceUnavailable,
                HttpStatusCode.InternalServerError,
                HttpStatusCode.TooManyRequests,
                HttpStatusCode.RequestTimeout
            };

            var gRpcErrors = new StatusCode[] {
                StatusCode.DeadlineExceeded,
                StatusCode.Internal,
                StatusCode.NotFound,
                StatusCode.ResourceExhausted,
                StatusCode.Unavailable,
                StatusCode.Unknown
            };


            Func <HttpRequestMessage, IAsyncPolicy <HttpResponseMessage> > retryFunc = (request) =>
            {
                return(Policy.HandleResult <HttpResponseMessage>(r => {
                    var grpcStatus = StatusManager.GetStatusCode(r);
                    var httpStatusCode = r.StatusCode;

                    return (grpcStatus == null && serverErrors.Contains(httpStatusCode)) ||         // if the server send an error before gRPC pipeline
                    (httpStatusCode == HttpStatusCode.OK && gRpcErrors.Contains(grpcStatus.Value)); // if gRPC pipeline handled the request (gRPC always answers OK)
                })
                       .WaitAndRetryAsync(3, (input) => TimeSpan.FromSeconds(3 + input), (result, timeSpan, retryCount, context) =>
                {
                    var grpcStatus = StatusManager.GetStatusCode(result.Result);
                    Console.WriteLine($"Request failed with {grpcStatus}. Retry");
                }));
            };

            services.AddGrpcClient <DiscountProtoService.DiscountProtoServiceClient>(options =>
            {
                options.Address = new Uri(Configuration["GrpcSettings:DiscountUrl"]);
                options.ChannelOptionsActions.Add(channelOptions =>
                {
                    channelOptions.Credentials = ChannelCredentials.Insecure;
                });
            }).AddPolicyHandler(retryFunc);

            services.AddScoped <DiscountGrpcService>();

            #endregion

            #region Redis connection configuration
            services.AddStackExchangeRedisCache(options =>
            {
                options.Configuration = Configuration.GetValue <string>("CacheSettings:ConnectionString");
            });
            #endregion

            services.AddControllers();
            services.AddSwaggerGen(c =>
            {
                c.SwaggerDoc("v1", new OpenApiInfo {
                    Title = "Basket.API", Version = "v1"
                });
            });

            #region Data repositories registration
            services.AddScoped <IBasketRepository, BasketRepository>();
            #endregion
        }