SuperSocket 2.0學習04:命令和命令過濾器


官方學習資料:命令和命令過濾器

本文開發環境:Win10 + VS2019 + .NetCore 3.1 + SuperSocket 2.0.0-beta.8。

Gitee:SuperSocketV2Sample

1、創建項目

使用VS2019創建.NET Core控制台程序,選擇.Net Core 3.1,通過NuGet引入SuperSocket(2.0.0-beta.8)。

2、添加配置文件

在項目根目錄添加appsettings.json配置文件,並設置其文件屬性為“如果較新則復制”。配置文件內容不再贅述。

3、命令和命令過濾器

命令相關類

using System.Text;
using System.Threading.Tasks;
using SuperSocket;
using SuperSocket.Command;
using SuperSocket.ProtoBase;

namespace SuperSocketV2Sample.Command.Commands
{
    public abstract class BaseCommand : IAsyncCommand<StringPackageInfo>
    {
        public async ValueTask ExecuteAsync(IAppSession session, StringPackageInfo package)
        {
            await Task.Delay(0);

            var result = GetResult(package);

            //發送消息給客戶端
            await session.SendAsync(Encoding.UTF8.GetBytes(result + "\r\n"));
        }

        protected abstract string GetResult(StringPackageInfo package);
    }
}

using System;
using System.Linq;
using SuperSocket.Command;
using SuperSocket.ProtoBase;
using SuperSocketV2Sample.Command.Server;

namespace SuperSocketV2Sample.Command.Commands
{
    /// <summary>
    /// 加法命令
    /// </summary>
    [Command(Key = "ADD")]
    [AsyncKeyUpperCommandFilter]
    public class AddCommand : BaseCommand
    {
        protected override string GetResult(StringPackageInfo package)
        {
            string result;
            try
            {
                result = package.Parameters
                    // ReSharper disable once ConvertClosureToMethodGroup
                    .Select(t => int.Parse(t))
                    .Sum()
                    .ToString();
            }
            catch (Exception e)
            {
                result = e.Message;
            }

            return result;
        }
    }
}

using System;
using System.Linq;
using SuperSocket.Command;
using SuperSocket.ProtoBase;
using SuperSocketV2Sample.Command.Server;

namespace SuperSocketV2Sample.Command.Commands
{
    /// <summary>
    /// 減法命令
    /// </summary>
    [Command(Key = "SUB")]
    [AsyncKeyUpperCommandFilter]
    public class SubCommand : BaseCommand
    {
        protected override string GetResult(StringPackageInfo package)
        {
            string result;
            try
            {
                result = package.Parameters
                    // ReSharper disable once ConvertClosureToMethodGroup
                    .Select(t => int.Parse(t))
                    .Aggregate((x, y) => x - y)
                    .ToString();
            }
            catch (Exception e)
            {
                result = e.Message;
            }

            return result;
        }
    }
}

using System;
using System.Linq;
using SuperSocket.Command;
using SuperSocket.ProtoBase;
using SuperSocketV2Sample.Command.Server;

namespace SuperSocketV2Sample.Command.Commands
{
    /// <summary>
    /// 乘法命令
    /// </summary>
    [Command(Key = "MUL")]
    [AsyncKeyUpperCommandFilter]
    public class MulCommand : BaseCommand
    {
        protected override string GetResult(StringPackageInfo package)
        {
            string result;
            try
            {
                result = package.Parameters
                    // ReSharper disable once ConvertClosureToMethodGroup
                    .Select(t => int.Parse(t))
                    .Aggregate((x, y) => x * y)
                    .ToString();
            }
            catch (Exception e)
            {
                result = e.Message;
            }

            return result;
        }
    }
}

using System;
using System.Globalization;
using System.Linq;
using SuperSocket.Command;
using SuperSocket.ProtoBase;
using SuperSocketV2Sample.Command.Server;

namespace SuperSocketV2Sample.Command.Commands
{
    /// <summary>
    /// 除法命令
    /// </summary>
    [Command(Key = "DIV")]
    [AsyncKeyUpperCommandFilter]
    public class DivCommand : BaseCommand
    {
        protected override string GetResult(StringPackageInfo package)
        {
            string result;
            try
            {
                result = package.Parameters
                    // ReSharper disable once ConvertClosureToMethodGroup
                    .Select(t => float.Parse(t))
                    .Aggregate((x, y) => x * 1f / y)
                    .ToString(CultureInfo.InvariantCulture);
            }
            catch (Exception e)
            {
                result = e.Message;
            }

            return result;
        }
    }
}

using SuperSocket.Command;
using SuperSocket.ProtoBase;
using SuperSocketV2Sample.Command.Server;

namespace SuperSocketV2Sample.Command.Commands
{
    /// <summary>
    /// ECHO命令
    /// </summary>
    [Command(Key = "ECHO")]
    [AsyncKeyUpperCommandFilter]
    public class EchoCommand : BaseCommand
    {
        protected override string GetResult(StringPackageInfo package)
        {
            return package.Body;
        }
    }
}

命令過濾器

using System;
using SuperSocket.Command;
using System.Threading.Tasks;
using SuperSocket.ProtoBase;

namespace SuperSocketV2Sample.Command.Server
{
    public class AsyncKeyUpperCommandFilterAttribute : AsyncCommandFilterAttribute
    {
        public override async ValueTask<bool> OnCommandExecutingAsync(CommandExecutingContext commandContext)
        {
            if (commandContext.Package is StringPackageInfo package)
            {
                Console.WriteLine($"session ip: {commandContext.Session.RemoteEndPoint}, " +
                                  $" command: {package.Key}");
            }

            await Task.Delay(0);
            return true;
        }

        public override async ValueTask OnCommandExecutedAsync(CommandExecutingContext commandContext)
        {
            await Task.Delay(0);
        }
    }
}

4、測試代碼 

using System;
using System.Text;
using System.Threading.Tasks;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using SuperSocket;
using SuperSocket.Command;
using SuperSocket.ProtoBase;
using SuperSocketV2Sample.Command.Commands;

namespace SuperSocketV2Sample.Command
{
    class Program
    {
        static async Task Main()
        {
            //創建宿主:用Package的類型和PipelineFilter的類型創建SuperSocket宿主。
            var host = SuperSocketHostBuilder.Create<StringPackageInfo, CommandLinePipelineFilter>()
                //注冊用於處理連接、關閉的Session處理器
                .UseSessionHandler(async (session) =>
                {
                    Console.WriteLine($"session connected: {session.RemoteEndPoint}");

                    //發送消息給客戶端
                    var msg = $@"Welcome to TelnetServer: {session.RemoteEndPoint}";
                    await session.SendAsync(Encoding.UTF8.GetBytes(msg + "\r\n"));
                }, async (session, reason) =>
                {
                    await Task.Delay(0);
                    Console.WriteLine($"session {session.RemoteEndPoint} closed: {reason}");
                })
                .UseCommand((commandOptions) =>
                {
                    //注冊命令
                    commandOptions.AddCommand<AddCommand>();
                    commandOptions.AddCommand<DivCommand>();
                    commandOptions.AddCommand<MulCommand>();
                    commandOptions.AddCommand<SubCommand>();
                    commandOptions.AddCommand<EchoCommand>();
                })
                //配置日志
                .ConfigureLogging((hostCtx, loggingBuilder) =>
                {
                    loggingBuilder.AddConsole();
                })
                .Build();
            await host.RunAsync();
        }
    }
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM