MagicOnion基本使用
官方的github的链接??https://github.com/Cysharp/MagicOnion
MagicOnion是一个实时网络引擎,如SignalR,Socket.io和RPC-Web API框架(如任何网络框架)。MagicOnion基于gRPC构建,因此传输速度非常快(HTTP / 2)和紧凑的(二进制)网络传输。它不需要.proto并生成与普通gRPC不同的内容。协议架构可以共享C#接口和类。
1.1快速开始
Nuget控制台:
Install-Package MagicOnion
1.2 来个官方的demo
IService<IMyFirstService>这种类型是最简单的传输
服务端的定义:
using Grpc.Core; using MagicOnion; using MagicOnion.Server; using System; // implement RPC service to Server Project. // inehrit ServiceBase<interface>, interface public class MyFirstService : ServiceBase<IMyFirstService>, IMyFirstService { // You can use async syntax directly. public async UnaryResult<int> SumAsync(int x, int y) { Logger.Debug($"Received:{x}, {y}"); return x + y; } } // define interface as Server/Client IDL. // implements T : IService<T> and share this type between server and client. public interface IMyFirstService : IService<IMyFirstService> { // Return type must be `UnaryResult<T>` or `Task<UnaryResult<T>>`. // If you can use C# 7.0 or newer, recommend to use `UnaryResult<T>`. UnaryResult<int> SumAsync(int x, int y); }
服务端的启动
class Program { static void Main(string[] args) { GrpcEnvironment.SetLogger(new Grpc.Core.Logging.ConsoleLogger());//这里会打印输出客户端退出的错误,注释掉就行 // setup MagicOnion and option. var service = MagicOnionEngine.BuildServerServiceDefinition(isReturnExceptionStackTraceInErrorDetail: true); var server = new global::Grpc.Core.Server { Services = { service }, Ports = { new ServerPort("localhost", 12345, ServerCredentials.Insecure) }//默认端口是12345 }; // launch gRPC Server. server.Start(); // and wait. Console.ReadLine(); } }
客户端这边
class Program { static async void Main(string[] args) { // standard gRPC channel var channel = new Channel("localhost", 12345, ChannelCredentials.Insecure); // get MagicOnion dynamic client proxy var client = MagicOnionClient.Create<IMyFirstService>(channel); // call method. var result = await client.SumAsync(100, 200); Console.WriteLine("Client Received:" + result); } }
一种简单的通道类似WebService的服务就建立了,客户端能够请求服务端,(服务端不能主动请求连上的客户端中的方法)。
看一下
UnaryResult<TResponse>
// 摘要: // Wrapped AsyncUnaryCall. [AsyncMethodBuilder(typeof(CompilerServices.AsyncUnaryResultMethodBuilder<>))] public struct UnaryResult<TResponse> { public UnaryResult(TResponse rawValue); public UnaryResult(Task<TResponse> rawTaskValue); public UnaryResult(Task<ResponseContext<TResponse>> response); // // 摘要: // Asynchronous call result. public Task<TResponse> ResponseAsync { get; } // // 摘要: // Asynchronous access to response headers. public Task<Metadata> ResponseHeadersAsync { get; } // // 摘要: // Provides means to cleanup after the call. If the call has already finished normally // (request stream has been completed and call result has been received), doesn‘t // do anything. Otherwise, requests cancellation of the call which should terminate // all pending async operations associated with the call. As a result, all resources // being used by the call should be released eventually. // // 言论: // Normally, there is no need for you to dispose the call unless you want to utilize // the "Cancel" semantics of invoking Dispose. public void Dispose(); // // 摘要: // Allows awaiting this object directly. public TaskAwaiter<TResponse> GetAwaiter(); // // 摘要: // Gets the call status if the call has already finished. Throws InvalidOperationException // otherwise. public Status GetStatus(); // // 摘要: // Gets the call trailing metadata if the call has already finished. Throws InvalidOperationException // otherwise. public Metadata GetTrailers(); }