zoukankan      html  css  js  c++  java
  • SuperSocket 1.4系列文档(13) 连接过滤器(Connection Filter)

    SuperSocket中连接过滤器(Connection Filter)是用与对客户端连接进行过滤的接口。通过连接过滤器, 你可以允许或者禁止指定来源的客户端对服务器进行连接。

    连接过滤器(Connection Filter)接口:

    /// <summary>
    /// The basic interface of connection filter
    /// </summary>
    public interface IConnectionFilter
    {
        /// <summary>
        /// Initializes the connection filter
        /// </summary>
        /// <param name="name">The name.</param>
        /// <param name="options">The options.</param>
        /// <returns></returns>
        bool Initialize(string name, NameValueCollection options);
     
        /// <summary>
        /// Gets the name of the filter.
        /// </summary>
        string Name { get; }
     
        /// <summary>
        /// Whether allows the connect according the remote endpoint
        /// </summary>
        /// <param name="remoteAddress">The remote address.</param>
        /// <returns></returns>
        bool AllowConnect(IPEndPoint remoteAddress);
    }

    bool Initialize(string name, NameValueCollection options);

    此方法用于初始化连接过滤器, name是Filter的名称, options是配置文件中此connection filter元素的属性。

    string Name { get; }

    返回Filter的名称

    bool AllowConnect(IPEndPoint remoteAddress);

    此方法需要实现通过客户端的endpoint来判断是否允许连接服务器。

    下面是一个实现了只允许来自某些IP地址段的客户端的连接的连接过滤器:

    using System;
    using System.Collections.Generic;
    using System.Collections.Specialized;
    using System.Linq;
    using System.Net;
    using System.Text;
    using SuperSocket.Common;
    using SuperSocket.SocketBase;
     
    namespace SuperSocket.QuickStart.ConnectionFilter
    {
        public class IPConnectionFilter : IConnectionFilter
        {
            private Tuple<long, long>[] m_IpRanges;
     
            public bool Initialize(string name, NameValueCollection options)
            {
                Name = name;
     
                var ipRange = options.GetValue("ipRange");
     
                string[] ipRangeArray;
     
                if (string.IsNullOrEmpty(ipRange)
                    || (ipRangeArray = ipRange.Split(new char[] { ',', ';' }, StringSplitOptions.RemoveEmptyEntries)).Length <= 0)
                {
                    throw new ArgumentException("The ipRange doesn't exist in configuration!");
                }
     
                m_IpRanges = new Tuple<long, long>[ipRangeArray.Length];
     
                for (int i = 0; i < ipRangeArray.Length; i++)
                {
                    var range = ipRangeArray[i];
                    m_IpRanges[i] = GenerateIpRange(range);
                }
     
                return true;
            }
     
            private Tuple<long, long> GenerateIpRange(string range)
            {
                var ipArray = range.Split(new char[] { '-' }, StringSplitOptions.RemoveEmptyEntries);
     
                if(ipArray.Length != 2)
                    throw new ArgumentException("Invalid ipRange exist in configuration!");
     
                return new Tuple<long, long>(ConvertIpToLong(ipArray[0]), ConvertIpToLong(ipArray[1]));
            }
     
            private long ConvertIpToLong(string ip)
            {
                var points = ip.Split(new char[] { '.' }, StringSplitOptions.RemoveEmptyEntries);
     
                if(points.Length != 4)
                    throw new ArgumentException("Invalid ipRange exist in configuration!");
     
                long value = 0;
                long unit = 1;
     
                for (int i = points.Length - 1; i >= 0; i--)
                {
                    value += unit * points[i].ToInt32();
                    unit *= 256;
                }
     
                return value;
            }
     
            public string Name { get; private set; }
     
            public bool AllowConnect(IPEndPoint remoteAddress)
            {
                var ip = remoteAddress.Address.ToString();
                var ipValue = ConvertIpToLong(ip);
     
                for (var i = 0; i < m_IpRanges.Length; i++)
                {
                    var range = m_IpRanges[i];
     
                    if (ipValue > range.Item2)
                        return false;
     
                    if (ipValue < range.Item1)
                        return false;
                }
     
                return true;
            }
        }
    }

    然后你需要更新配置文件来使用这个连接过滤器:

    <?xml version="1.0" encoding="utf-8" ?>
    <configuration>
      <configSections>
        <section name="socketServer" type="SuperSocket.SocketEngine.Configuration.SocketServiceConfig, SuperSocket.SocketEngine"/>
      </configSections>
      <appSettings>
        <add key="ServiceName" value="EchoService"/>
      </appSettings>
      <socketServer loggingMode="IndependantFile">
        <servers>
          <server name="EchoServer"
                  serviceName="EchoService" ip="Any" port="911" mode="Async"
                  connectionFilters="IpRangeFilter">
          </server>
        </servers>
        <services>
          <service name="EchoService"
                   type="SuperSocket.QuickStart.EchoService.EchoServer, SuperSocket.QuickStart.EchoService" />
        </services>
        <connectionFilters>
          <connectionFilter name="IpRangeFilter"
                        type="SuperSocket.QuickStart.ConnectionFilter.IPConnectionFilter, SuperSocket.QuickStart.ConnectionFilter"
                        ipRange="127.0.1.0-127.0.1.255"/>
        </connectionFilters>
      </socketServer>
      <startup>
        <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.0" />
      </startup>
    </configuration>

    在配置文件中启用连接过滤器需要注意两点:

    1) 在SuperSocket配置节点中增加connectionFilters子节点,然后添加你新增的connection filter的相应的配置到connectionFilters到节点之中。

    2) 在服务器实例节点中增加connectionFilters属性,属性值为你想为该服务器实例启用的connection filter的名称,多个connection filter用逗号隔开。

    完成上面的配置,然后启动SuperSocket,你的连接过滤器就生效了。

    作者:江振宇
    出处:http://jzywh.cnblogs.com
    本文版权归作者所有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文链接,否则保留追究法律责任的权利。
  • 相关阅读:
    使用正则匹配数字
    钻石和玻璃球游戏(钻石位置不固定)
    简单绘图
    未解决问题02
    Sqlite3 实现学生信息增删改查
    【Python】科赫雪花绘制
    【Python爬虫】抖音去水印
    【MATLAB】数学计算软件 MathWorks MATLAB R2020a 中文破解版
    【C语言】用指针作为形参完成数据的升序排列
    【C语言】数组名作函数参数完成数据的升序排列
  • 原文地址:https://www.cnblogs.com/jzywh/p/2046174.html
Copyright © 2011-2022 走看看