您的位置:首页 > 其它

可扩展的SockBase设计和实现(3)

2006-08-05 11:19 295 查看
目录

摘要

嵌入式消息带来的问题

自定义消息命令类的设计实现

自定义消息命令类的使用

摘要

在前面的文章中,我们对于所有通过SockBase发送的消息都是直接通过嵌入式的字符串来完成的.比如”login”,”logout”,这样带来的一个问题就是如果不小心,写错一个字,在编译期是不能检查出来的.而且由于是直接内嵌在代码中的,和逻辑代码混在一起,不便于增加/修改消息.所以我们提出了使用自定义的消息命令类.

嵌入式消息带来的问题

由于这是一个基于Sockets的网络编程,所以我们通过Sockets输任何消息命令以及数据信息.在SockBase的实现中,我们通过Send(string)函数直接发送消息.在具体的使用SockBase的Send函数的时候,我们写的代码类似这样的:

private void GetFileHandler(string cmdText)

{

//检查文件是否存在

if((new FileManager()).CheckFileExist(cmdTxt))

{

Send(“OK”);

}

else

{

Send(“Failure”);

}

}

在这个里面,我们可以看到我们发送的消息就是直接写在代码中的”OK”,”Failure”等字符串.当然了,我们这个Send函数只能发送字符串..在这个程序中,这样是没问题的.

如果,后面的版本中,我们修改了消息命令体,把”OK”换成了”OKEY”,”Failure”换成了”Fail”,这时我们就得通过VS.NET IDE的搜索功能或是自己去手动的把原来的字符串替换成现在的.如果这个程序代码不多,就100多行,那很简单.一会儿就搞定了.但是如果这个程序比较大呢?有上千行代码?有很多地方使用到了这些个字符串呢?

这时,修改程序就成了一个恶梦,在修改的过程中就得异常小心,稍有不慎,程序就出现Bugs.这种情况出现的原因是因为消息是具有不确定性的,而我们在代码中是直接内嵌消息体(以字符串的形式),和逻辑代码直接混合在一起,影响程序的修改,扩展性.

自定义消息命令类的设计实现

基于上面分析的原因,我们不使用以字符串的形式的直接内嵌的消息命令.取而代之,我们使用我们自定义的消息命令类.

我们的消息命令有两部分,一部分就是消息体,另一部分就是此消息对应的参数.所以,我们定义消息命令类CommandBuilder如下:

public class CommandBuilder

{

private string m_Command;

private string m_CommandText;

private string m_AllCmdText;

//命令前缀,即命令

public string Command

{

get{return m_Command;}

set{m_Command=value;}

}

//命令内容

public string CommandText

{

get{return m_CommandText;}

set{m_CommandText=value;}

}

}

通过构造函数对其进行初始化:

//外部消息发送

public CommandBuilder(string commandPrefix,string commandText)

{

m_Command=commandPrefix;

m_CommandText=commandText;

}

//构造函数为已经完整的命令

public CommandBuilder(string AllcommandText)

{

m_AllCmdText=AllcommandText;

}

由于我们通过SockBase发送的是整个消息,包括消息体和参数,即我们得把消息体和参数连接起来.为了方便进行消息体和参数的解析,我们还得在消息体和参数中加入一个分隔符.基于上面所说的同样的原因.我们也不使用直接内嵌的字符串,使用CommandBuilder内部的一个成员变量来存放分隔符.

private string m_SpliteChars = “;”;

这样,如果我们要修改,只要直接修改这一个成员的值就行了.而且我们还可以把分隔符存储在配置文件中,使用的时候直接从配置文件进行读取.这样更加灵活.但是在这里,我们就使用上述方式.

好了,消息命令类基本的数据成员完成了.

现在提供一个函数,直接把最终的可以直接通过SockBase的Send函数发的送的字符串输出:

public string SenderMsg

{

get

{

if( m_AllCmdText!=null && m_AllCmdText!=String.Empty )

return m_AllCmdText;

else

{

return m_Command+ m_SpliteChars +m_CommandText;

}

}

}

现在消息命令类已基本完成了,现在就差对命令进行包装了.我们可以直接写成一个类的静态成员,所有对消息的引用都直接使用这个类中的静态成员.同样的,我们也可以直接写到一个配置文件中.这里,为了简单,我们就直接使用类的静态成员.定义CommandList定义如下:

public class CommandList

{

//命令字符串

public static string GETFILE = "GetFile";

public static string OK = “OK”;

public static string FAILURE = “FAILURE”;

}

好,现在就可以开始使用CommandBuilder和CommandList代替内嵌字符串了.

自定义消息命令类的使用

这里,我们就没必要去修改SockBase了,只要修改前面文章中的Client_ListenThread类即可.修改后的代码如下:

private void GetFileHandler(string cmdText)

{

CommandBuilder cmdBuilder ;

//检查文件是否存在

if((new FileManager()).CheckFileExist(cmdTxt))

{

cmdBuilder = new CommandBuilder(CommandList.GETFILE,CommandList.OK);

}

else

{

cmdBuilder = new CommandBuilder(CommandList.GETFILE,CommandList. FAILURE);

}

Send(cmdBuilder.SenderMsg);

}

总结

将程序中的字符串等封装成类的(静态)变量是一个很好的习惯,特别是在变化比较大的程序开发中.这样有利于代码的复用,以及代码的修改的维护.
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐