命令 (Command)
SuperSocket 中的命令设计出来是为了处理来自客户端的请求的, 它在业务逻辑处理之中起到了很重要的作用。
命令类必须实现下面的基本命令接口, 根据你的需要选择实现同步命令或异步命令:
// 同步命令
public interface ICommand<TAppSession, TPackageInfo>
where TAppSession : IAppSession
{
void Execute(TAppSession session, TPackageInfo package);
}
// 异步命令
public interface IAsyncCommand<TAppSession, TPackageInfo> : ICommand
where TAppSession : IAppSession
{
ValueTask ExecuteAsync(TAppSession session, TPackageInfo package);
}
请求包的处理代码应被放置于方法 “Execute” 或 "ExecuteAsync"之内。 每个命令都有自己的包含Name和Key的元数据。
Name: 人们可以直接理解的名字; Key: 用于匹配接收到的包的Key的对象;
我们可以通过给Command增加Attribute来定义它的元数据 (Name=‘ShowVoltage’, Key=0x03):
指的应该就是这里的代码段了
我们多多使用异步
就是这个咯
我们可以通过给Command增加Attribute来定义它的元数据 (Name=‘ShowVoltage’, Key=0x03):
[Command(Key = 0x03)]
public class ShowVoltage : IAsyncCommand<StringPackageInfo>
{
public async ValueTask ExecuteAsync(IAppSession session, StringPackageInfo package)
{
...
}
}
请求处理代码必须被放置于方法 “Execute” or “ExecuteAsync” 之中,并且属性 “Keys” 的值用于匹配接收到请求实例(packageInfo)的Key。当一个请求实例(packageInfo) 被收到时,SuperSocket 将会通过匹配请求实例(package)的Key和命令的Keys的方法来查找用于处理该请求的命令。
如果命令没有定义元数据的Attribute,它的Name 和 Key 将会默认为这个命令类的类名。
元数据中的Key的值是用于匹配接收到的包请求的。当一个包被接收到,SuperSocket会去通过包的Key去寻找拥有相同Key的命令,找到的命令将会用于处理这个包。
但是,有个前提条件是包的类型必须实现接口 IKeyedPackageInfo (TKey 可以是任意元数据类型如 int,string,short 或 byte), 例如 StringPackageInfo:
配置命令能干甚么 当然是交给SuperSocket管理咯
自己找到key 自己帮你处理 多棒阿对吧
只要这么做一下 下面的就可以注释掉了
直接删掉把 碍眼 哈哈哈
然后呢 SuperSocket还提供了类似AOP(面向切面编程)的功能
即在命令执行前做点事情 执行后在做点事情
这就是他说的命令过滤器
怎么用呢
创建
同样的注册就可以用了
当然我这里是全局注册的 单个的使用可以用属性
现在当我们触发LOGIN命令的时候就会发生什么事情呢
触发了AOP 就很棒嘎嘎嘎
上代码
using Microsoft.Extensions.Hosting;
using SuperSocket;
using SuperSocket.ProtoBase;
using System.Text;
using System.Threading.Tasks;
using SuperSocket.Command;
using System.Buffers;
namespace SuperSocketVersionTwo
{
class Program
{
static async Task Main(string[] args)
{
var host = SuperSocketHostBuilder.Create<StringPackageInfo, CommandLinePipelineFilter>().//创建宿主
UseCommand((o)=> {
// 一个一个的注册命令
o.AddCommand<LOGIN>();
//o.AddCommand<MULT>();
//o.AddCommand<SUB>();
// 注册程序集重的所有命令
//o.AddCommandAssembly(typeof(SUB).GetTypeInfo().Assembly);
// register global command filter
o.AddGlobalCommandFilter<AsyncHelloCommandFilterAttribute>();
}).Build();
await host.RunAsync();
}
public class LOGIN : IAsyncCommand<StringPackageInfo>
{
public async ValueTask ExecuteAsync(IAppSession session, StringPackageInfo package)
{
System.Console.WriteLine(package.Body);
await session.SendAsync(Encoding.UTF8.GetBytes("LoginSucess" + "\r\n"));
}
}
public class AsyncHelloCommandFilterAttribute : AsyncCommandFilterAttribute
{
public override async ValueTask OnCommandExecutedAsync(CommandExecutingContext commandContext)
{
System.Console.WriteLine("Hello");
await Task.Delay(0);
}
public override async ValueTask<bool> OnCommandExecutingAsync(CommandExecutingContext commandContext)
{
System.Console.WriteLine("Bye bye");
await Task.Delay(0);
return true;
}
}
}
}
————————————————
版权声明:本文为CSDN博主「亮大大大」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/weixin_38083655/article/details/111478381
https://blog.csdn.net/weixin_38083655/article/details/111478381