简单的C# Socket 通讯,可传文件

三个项目:服务端XJFtpServer,客户端XJFtpServerClient,公共程序集XJFtpServerLib

 

先是公共程序集:

 public class FtpServerDefine
    {
        public const int LISTEN_PORT = 5000;
        public const int MESSAGE_LENGTH=419;
    }
 public enum MsgCommand
    {
        None,
        Login,
        Exit,
        List,
        Upload,
        Download,
        Msg,
        DirInfo,
        File,
        Close
    }
  public enum MsgSendState
    {
        None,
        Single,
        Start,
        Sending,
        End
    }
 public enum MsgType
    {
        None,
        Text,
        Class,
        File
    }
 [Serializable]
    public class Message
    {
        public MsgCommand Command;
        public MsgType Type;
        public MsgSendState SendState;
        public int DataLength;

        public Message()
        {
            Command = MsgCommand.None;
            Type = MsgType.None;
            SendState = MsgSendState.None;
            DataLength = 0;
        }
    }
 [Serializable]
    public class UserInfo
    {
        public string Name;
        public string Password;

        public UserInfo()
        {
            Name = string.Empty;
            Password = string.Empty;
        }
    }
  [Serializable]
    public class PathInfo
    {
        public string Path;

        public PathInfo()
        {
            Path = string.Empty;
        }
    }
 [Serializable]
    public class DirectoryInfo
    {
        public string Name;
        public string FullPath;
        public long Size;
        public DateTime CreateTime;
        public DateTime LastAccessTime;
        public List<string> SubDirectory;
        public List<string> Files;

        public DirectoryInfo()
        {
            SubDirectory = new List<string>();
            Files = new List<string>();
        }

        public override string ToString()
        {
            string str = string.Empty;
            str += string.Format("Name:{0}\tFullPath:{1}\tSize:{2}\tCreateTime:{3}\tLastAccessTime:{4}"
                , Name
                , FullPath
                , Size
                , CreateTime.ToString("yyyy-MM-dd HH:mm:ss")
                , LastAccessTime.ToString("yyyy-MM-dd HH:mm:ss"));
            return str;
        }
    }
 [Serializable]
    public class FileInfo
    {
        public string Name;
        public string FullName;
        public long Size;
        public DateTime CreateTime;
        public DateTime LastAccessTime;

        public FileInfo()
        {

        }

        public override string ToString()
        {
            return string.Format("Name:{0}\tFullName:{1}\tSize:{2}\tCreateTime:{3}\tLastUpdateTime:{4}"
                , Name
                , FullName
                , Size
                , CreateTime.ToString("yyyy-MM-dd HH:mm:ss")
                , LastAccessTime.ToString("yyyy-MM-dd HH:mm:ss"));
        }
    }
 [Serializable]
    public class CloseInfo
    {
        /// <summary>
        /// Close type
        /// 0   Unkown close request
        /// 1   Server close request
        /// 2   Client close request
        /// </summary>
        public int Type;
        public string Message;

        public CloseInfo()
        {
            Type = 0;
            Message = string.Empty;
        }
    }
 public class Utils
    {
        public static byte[] Serialize<T>(T obj)
        {
            try
            {
                IFormatter formatter = new BinaryFormatter();
                MemoryStream stream = new MemoryStream();
                formatter.Serialize(stream, obj);
                stream.Position = 0;
                byte[] buffer = new byte[stream.Length];
                stream.Read(buffer, 0, buffer.Length);
                stream.Flush();
                stream.Close();
                return buffer;
            }
            catch (Exception ex)
            {
                throw new Exception(string.Format("Serialize fail.\r\n{0}", ex.Message));
            }
        }

        public static T Deserialize<T>(T obj, byte[] data)
        {
            try
            {
                obj = default(T);
                IFormatter formatter = new BinaryFormatter();
                byte[] buffer = data;
                MemoryStream stream = new MemoryStream(buffer);
                stream.Seek(0, SeekOrigin.Begin);
                obj = (T)formatter.Deserialize(stream);
                stream.Flush();
                stream.Close();
            }
            catch (Exception ex)
            {
                throw new Exception(string.Format("Deserialize fail.\r\n{0}", ex.Message));
            }
            return obj;
        }
    }


 

 

 public interface IFtpServer
    {
        event Action<string> Debug;
        int Port { get; set; }
        bool IsRunning { get; }
        string RootDir { get; set; }
        bool Start();
        bool Start(int port);
        bool Stop();
        void Dispose();
    }
 public interface IFtpSession
    {
        event Action<string, string> Debug;
        event Action<string> Disconnected;
        string RootDir { get; set; }
        string CurrentDir { get; set; }
        string Client { get; set; }
        bool Start();
        bool Close();
        void Dispose();
    }
 public interface IFtpClient:IDisposable
    {
        event Action<string, string> Debug;
        event Action<string, Message, byte[]> MessageReceived;
        string Host { get; set; }
        int Port { get; set; }
        bool Connect();
        bool Connect(string host, int port);
        bool Close();
        bool Send(Message message, int length, byte[] data);
        void Dispose();
    }


服务端:

 

class FtpServer : IFtpServer
    {
        private TcpListener mFtpListener;
        private List<FtpSession> mFtpSessions;
        private int mCheckSessionInterval;
        private Timer mCheckActiveTimer;
        private int mListenPort;
        private bool mIsRunning;
        private string mRootDir;

        public FtpServer()
        {
            mFtpSessions = new List<FtpSession>();
            mCheckSessionInterval = Common.CHECK_CLIENT_INTEVAL;
            mListenPort = FtpServerDefine.LISTEN_PORT;
            mIsRunning = false;
            mRootDir = AppDomain.CurrentDomain.BaseDirectory;
        }

        private void SubAcceptClient(IAsyncResult result)
        {
            try
            {
                TcpListener listener = result.AsyncState as TcpListener;
                Socket socketClient = listener.EndAcceptSocket(result);
                SubDebug(string.Format("New client connected.\tClient:{0}", socketClient.RemoteEndPoint));
                FtpSession session = new FtpSession(socketClient);
                session.Debug += new Action<string, string>(session_Debug);
                session.Disconnected += new Action<string>(session_Disconnected);
                session.RootDir = mRootDir;
                mFtpSessions.Add(session);
                session.Start();
                listener.BeginAcceptSocket(SubAcceptClient, listener);
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Accept client fail.\tAccept client breaked."));
                mIsRunning = false;
            }
        }

        void session_Disconnected(string client)
        {
            try
            {
                SubDebug(string.Format("Session:{0} disconnected.", client));
                FtpSession session = mFtpSessions.Where(s => s.Client == client).First();
                mFtpSessions.Remove(session);
                SubDebug(string.Format("Session:{0} has removed.", client));
                session.Dispose();
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Remove session fail.\r\n{0}", ex.ToString()));
            }
        }

        void session_Debug(string client, string msg)
        {
            SubDebug(string.Format("Session:{0}\t{1}", client, msg));
        }

        void mCheckActiveTimer_Elapsed(object sender, ElapsedEventArgs e)
        {
            SubDebug(string.Format("Check online client.\tCount:{0}", mFtpSessions.Count));
            try
            {
                for (int i = mFtpSessions.Count - 1; i >= 0; i--)
                {
                    FtpSession session = mFtpSessions[i];
                    SubDebug(string.Format("Online client:{0}", session.Client));
                    if (session.LastActiveTime.AddSeconds(20) < DateTime.Now)
                    {
                        mFtpSessions.Remove(session);
                        SubDebug(string.Format("Session:{0} has removed.", session.Client));
                        session.Close();
                    }
                }
            }
            catch { }
        }

        private void SubDebug(string msg)
        {
            if (Debug != null)
            {
                Debug(msg);
            }
        }

        #region IFtpServer 成员

        public event Action<string> Debug;

        public int Port
        {
            get { return mListenPort; }
            set { mListenPort = value; }
        }

        public bool IsRunning
        {
            get { return mIsRunning; }
        }

        public string RootDir
        {
            get
            {
                return mRootDir;
            }
            set
            {
                mRootDir = value;
            }
        }

        public bool Start()
        {
            try
            {
                SubDebug(string.Format("Ftp server starting..."));
                if (mFtpListener != null)
                {
                    try
                    {
                        mFtpListener.Stop();
                        mFtpListener = null;
                    }
                    catch { }
                }
                mFtpListener = new TcpListener(IPAddress.Any, mListenPort);
                mFtpListener.Start();
                mIsRunning = true;
                SubDebug(string.Format("Listener started.\tLocal endpoint:{0}", mFtpListener.LocalEndpoint));
                mFtpListener.BeginAcceptSocket(new AsyncCallback(SubAcceptClient), mFtpListener);
                mCheckActiveTimer = new Timer(mCheckSessionInterval * 1000);
                mCheckActiveTimer.Elapsed += new ElapsedEventHandler(mCheckActiveTimer_Elapsed);
                mCheckActiveTimer.Start();
                SubDebug(string.Format("Check active timer started."));
                SubDebug(string.Format("Ftp Server started.\tRootDir:{0}", mRootDir));
                return true;
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Ftp server start fail.\r\n{0}", ex.ToString()));
                return false;
            }
        }

        public bool Start(int port)
        {
            mListenPort = port;
            return Start();
        }

        public bool Stop()
        {
            Dispose();
            SubDebug(string.Format("Ftp server stopped."));
            return true;
        }

        public void Dispose()
        {
            if (mFtpSessions != null)
            {
                foreach (FtpSession session in mFtpSessions)
                {
                    session.Dispose();
                }
                mFtpSessions.Clear();
                SubDebug(string.Format("All session removed."));
            }
            if (mFtpListener != null)
            {
                try
                {
                    mFtpListener.Stop();
                    mFtpListener = null;
                    SubDebug(string.Format("Ftp Listener stopped."));
                }
                catch { }
            }
            if (mCheckActiveTimer != null)
            {
                try
                {
                    mCheckActiveTimer.Stop();
                    SubDebug(string.Format("Check active timer stopped."));
                }
                catch { }
            }
        }

        #endregion
    }
 class FtpSession : IFtpSession
    {
        private string mClient;
        private Socket mSocket;
        private bool mIsLogined;
        private string mRootDir;
        private string mCurrentDir;
        private byte[] mMsgBuffer;
        private byte[] mDataBuffer;
        private int mMsgLength;
        private DateTime mLastActiveTime;

        public DateTime LastActiveTime
        {
            get { return mLastActiveTime; }
        }

        public FtpSession(Socket socket)
        {
            mSocket = socket;
            mClient = mSocket.RemoteEndPoint.ToString();
            mIsLogined = false;
            mRootDir = AppDomain.CurrentDomain.BaseDirectory;
            mCurrentDir = string.Empty;
            mMsgLength = FtpServerDefine.MESSAGE_LENGTH;
            mMsgBuffer = new byte[mMsgLength];
            mLastActiveTime = DateTime.Now;
        }

        private void SubReceiveMessage(IAsyncResult result)
        {
            mLastActiveTime = DateTime.Now;
            int iReceiveLength = 0;
            Socket socket = result.AsyncState as Socket;
            try
            {
                iReceiveLength = socket.EndReceive(result);
            }
            catch (Exception ex)
            {
                SocketException sex = ex as SocketException;
                if (sex != null)
                {
                    SubDebug(string.Format("End receive message fail.\tClient disconected.\tReceive message break"));
                    SubDisconnected();
                }
                else
                {
                    SubDebug(string.Format("End receive message fail.\tReceive message break."));
                }
                return;
            }
            Message message = new Message();
            int dataLength = 0;
            if (iReceiveLength == mMsgLength)
            {
                try
                {
                    message = Utils.Deserialize<Message>(message, mMsgBuffer);
                    dataLength = message.DataLength;
                    mDataBuffer = new byte[dataLength];
                }
                catch (Exception ex)
                {
                    SubDebug(string.Format("Receive message fail.\r\n{0}", ex.ToString()));
                }
            }
            else
            {
                SubDebug(string.Format("Receive message length invalid.\tLength:{0}\tReceive message break.", iReceiveLength));
            }
            try
            {
                if (dataLength > 0)
                {
                    socket.BeginReceive(mDataBuffer, 0, dataLength, SocketFlags.None, new AsyncCallback(SubReceiveData), message);
                }
                else
                {
                    socket.BeginReceive(mMsgBuffer, 0, mMsgLength, SocketFlags.None, new AsyncCallback(SubReceiveMessage), socket);
                }
            }
            catch (Exception ex)
            {
                SocketException sex = ex as SocketException;
                if (sex != null)
                {
                    SubDebug(string.Format("Begin receive fail.\tClient disconnected."));
                    SubDisconnected();
                }
                else
                {
                    SubDebug(string.Format("Begin receive fail.\tReceive message break."));
                }
            }
        }

        private void SubReceiveData(IAsyncResult result)
        {
            int iReceiveLength = 0;
            Socket socket;
            Message message;
            try
            {
                socket = mSocket;
                message = result.AsyncState as Message;
                iReceiveLength = socket.EndReceive(result);
            }
            catch (Exception ex)
            {
                SocketException sex = ex as SocketException;
                if (sex != null)
                {
                    SubDebug(string.Format("End receive data fail.\tClient disconected.\tReceive data break"));
                    SubDisconnected();
                }
                else
                {
                    SubDebug(string.Format("End receive data fail.\tReceive data break."));
                }
                return;
            }
            if (iReceiveLength == message.DataLength)
            {
                switch (message.Command)
                {
                    case MsgCommand.Login:
                        DealLogin(message, mDataBuffer);
                        break;
                    case MsgCommand.List:
                        DealList(message, mDataBuffer);
                        break;
                    case MsgCommand.Download:
                        DealDowloadCommand(mDataBuffer);
                        break;
                    case MsgCommand.Close:
                        DealCloseCommand(message, mDataBuffer);
                        break;
                    default:
                        SubDebug(string.Format("Invalid command.\tCommand:{0}", message.Command));
                        break;
                }
            }
            else
            {
                SubDebug(string.Format("Receive data length invalid.\tLength:{0}\tNeed:{1}\tReceive data breaked.", iReceiveLength, message.DataLength));
            }
            try
            {
                socket.BeginReceive(mMsgBuffer, 0, mMsgLength, SocketFlags.None, new AsyncCallback(SubReceiveMessage), socket);
            }
            catch (Exception ex)
            {
                SocketException sex = ex as SocketException;
                if (sex != null)
                {
                    SubDebug(string.Format("Begin receive fail.\tClient disconnected."));
                    SubDisconnected();
                }
                else
                {
                    SubDebug(string.Format("Begin receive fail.\tReceive message break."));
                }
            }
        }

        private bool SendMessage(Message message, int length, byte[] data)
        {
            if (mSocket == null && !mSocket.Connected)
            {
                SubDebug(string.Format("Send message fail.\tMsg:{0}\tSocket is null or not connected.", message.Command));
                return false;
            }
            try
            {
                message.DataLength = length;
                byte[] bMsg = Utils.Serialize<Message>(message);
                mSocket.Send(bMsg);
                mSocket.Send(data, length, SocketFlags.None);
                mLastActiveTime = DateTime.Now;
            }
            catch (Exception ex)
            {
                //SubDebug(string.Format("Send message fail.\tMsg:{0}\r\n{1}", message.Command, ex.ToString()));
                return false;
            }
            return true;
        }

        private bool DealLogin(Message message, byte[] data)
        {
            SubDebug(string.Format("Deal login command."));
            try
            {
                UserInfo userInfo = new UserInfo();
                userInfo = Utils.Deserialize<UserInfo>(userInfo, data);
                Message retMessage = new Message();
                retMessage.Command = MsgCommand.Msg;
                retMessage.Type = MsgType.Text;
                byte[] msg;
                if (userInfo.Name != "administrator")
                {
                    msg = Encoding.UTF8.GetBytes("User not exist.");
                    SendMessage(retMessage, msg.Length, msg);
                    return false;
                }
                if (userInfo.Password != "voicecyber")
                {
                    msg = Encoding.UTF8.GetBytes("Password error.");
                    SendMessage(retMessage, msg.Length, msg);
                    return false;
                }
                mIsLogined = true;
                msg = Encoding.UTF8.GetBytes(string.Format("{0}\t Logined", userInfo.Name));
                SendMessage(retMessage, msg.Length, msg);
                SubDebug(string.Format("{0} Logined.", userInfo.Name));
                return true;
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Deal Login command fail.\r\n{0}", ex.ToString()));
                return false;
            }
        }

        private bool DealList(Message message, byte[] data)
        {
            SubDebug(string.Format("Deal list command."));
            try
            {
                Message retMessage = new Message();
                retMessage.Command = MsgCommand.Msg;
                retMessage.Type = MsgType.Text;
                byte[] retData;
                if (!mIsLogined)
                {
                    retData = Encoding.UTF8.GetBytes("Not login.");
                    SendMessage(retMessage, retData.Length, retData);
                    return false;
                }
                PathInfo pathInfo = new PathInfo();
                pathInfo = Utils.Deserialize<PathInfo>(pathInfo, data);
                string path = pathInfo.Path;
                path = System.IO.Path.Combine(mRootDir, mCurrentDir, path);

                if (!System.IO.Directory.Exists(path))
                {
                    retData = Encoding.UTF8.GetBytes(string.Format("Directory not exist.\t{0}", path));
                    SendMessage(retMessage, retData.Length, retData);
                    return false;
                }
                DirectoryInfo dirInfo = GetDirInfo(path);
                retMessage.Command = MsgCommand.DirInfo;
                retMessage.Type = MsgType.Class;
                retData = Utils.Serialize<DirectoryInfo>(dirInfo);
                SendMessage(retMessage, retData.Length, retData);
                return true;
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Deal List command fail.\r\n{0}", ex.ToString()));
                return false;
            }
        }

        private bool DealDowloadCommand(byte[] data)
        {
            SubDebug(string.Format("Deal Download command."));
            try
            {
                PathInfo pathInfo = new PathInfo();
                pathInfo = Utils.Deserialize<PathInfo>(pathInfo, data);
                Message retMessage = new Message();
                retMessage.Command = MsgCommand.Msg;
                retMessage.Type = MsgType.Text;
                byte[] msg;
                string filePath = System.IO.Path.Combine(mRootDir, pathInfo.Path);
                if (!System.IO.File.Exists(filePath))
                {
                    msg = Encoding.UTF8.GetBytes(string.Format("File not exist.\t{0}", filePath));
                    SendMessage(retMessage, msg.Length, msg);
                    return false;
                }
                using (System.IO.FileStream fs = new System.IO.FileStream(filePath, System.IO.FileMode.Open, System.IO.FileAccess.Read))
                {
                    long iLength = fs.Length;
                    byte[] buffer = new byte[1024];
                    int iRead = 0;
                    while (true)
                    {
                        iRead = fs.Read(buffer, 0, 1024);
                        if (iRead <= 0)
                        {
                            break;
                        }
                        if (iRead < 1024)
                        {
                            retMessage.Command = MsgCommand.File;
                            retMessage.Type = MsgType.File;
                            retMessage.SendState = MsgSendState.End;
                            SendMessage(retMessage, iRead, buffer);
                            break;
                        }
                        retMessage.Command = MsgCommand.File;
                        retMessage.Type = MsgType.File;
                        retMessage.SendState = MsgSendState.Sending;
                        SendMessage(retMessage, 1024, buffer);
                    }
                }
                return true;
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Deal Download command fail.\r\n{0}", ex.ToString()));
                return false;
            }
        }

        private bool DealCloseCommand(Message message, byte[] data)
        {
            SubDebug(string.Format("Deal Close command."));
            try
            {
                CloseInfo closeInfo = new CloseInfo();
                closeInfo = Utils.Deserialize<CloseInfo>(closeInfo, data);
                SubDebug(string.Format("Receive close command.\tType:{0}\tMessage:{1}", closeInfo.Type, closeInfo.Message));
                Close();
                SubDisconnected();
                return true;
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Deal Close command fail.\r\n{0}", ex.ToString()));
                return false;
            }
        }

        private DirectoryInfo GetDirInfo(string path)
        {
            System.IO.DirectoryInfo dirInfo = new System.IO.DirectoryInfo(path);
            DirectoryInfo diretoryInfo = new DirectoryInfo();
            diretoryInfo.Name = dirInfo.Name;
            diretoryInfo.FullPath = dirInfo.FullName;
            //diretoryInfo.CreateTime = dirInfo.CreationTime;
            //diretoryInfo.LastAccessTime = dirInfo.LastAccessTime;
            diretoryInfo.Size = 0;
            foreach (System.IO.DirectoryInfo subDir in dirInfo.GetDirectories())
            {
                DirectoryInfo subDirectory = GetDirInfo(subDir.FullName);
                diretoryInfo.Size += subDirectory.Size;
                //diretoryInfo.SubDirectory.Add(subDirectory);
                diretoryInfo.SubDirectory.Add(subDirectory.Name);
            }
            foreach (System.IO.FileInfo subFile in dirInfo.GetFiles())
            {
                FileInfo fileInfo = new FileInfo();
                fileInfo.Name = subFile.Name;
                fileInfo.FullName = subFile.FullName;
                fileInfo.Size = subFile.Length;
                //fileInfo.CreateTime = subFile.CreationTime;
                //fileInfo.LastAccessTime = subFile.LastAccessTime;
                diretoryInfo.Size += fileInfo.Size;
                //diretoryInfo.Files.Add(fileInfo);
                diretoryInfo.Files.Add(fileInfo.Name);
            }
            return diretoryInfo;
        }

        private void SubDebug(string msg)
        {
            if (Debug != null)
            {
                Debug(mClient, msg);
            }
        }
        private void SubDisconnected()
        {
            if (Disconnected != null)
            {
                Disconnected(mClient);
            }
        }

        #region IFtpSession 成员

        public event Action<string, string> Debug;

        public event Action<string> Disconnected;

        public string RootDir
        {
            get
            {
                return mRootDir;
            }
            set
            {
                mRootDir = value;
            }
        }

        public string CurrentDir
        {
            get
            {
                return mCurrentDir;
            }
            set
            {
                mCurrentDir = value;
            }
        }

        public string Client
        {
            get { return mClient; }
            set { mClient = value; }
        }

        public bool Start()
        {
            if (mSocket == null || !mSocket.Connected)
            {
                SubDebug(string.Format("Session start fail.\tSocket is null or not connected."));
                return false;
            }
            try
            {
                mSocket.BeginReceive(mMsgBuffer, 0, mMsgLength, SocketFlags.None, new AsyncCallback(SubReceiveMessage), mSocket);
            }
            catch (Exception ex)
            {
                SocketException sex = ex as SocketException;
                if (sex != null)
                {
                    SubDebug(string.Format("Begin receive fail.\tClient disconnected."));
                    SubDisconnected();
                }
                else
                {
                    SubDebug(string.Format("Begin receive fail.\tReceive message break."));
                }
                return false;
            }
            Message message = new Message();
            message.Command = MsgCommand.Msg;
            message.Type = MsgType.Text;
            byte[] data = Encoding.UTF8.GetBytes(string.Format("Welcome MDMSFtpServer!\tCurrent directory:{0}", mCurrentDir));
            SendMessage(message, data.Length, data);
            return true;
        }

        public bool Close()
        {
            if (mSocket != null && mSocket.Connected)
            {
                try
                {
                    mSocket.Close();
                    SubDebug(string.Format("Socket closed."));
                }
                catch (Exception ex)
                {
                    SubDebug(string.Format("Socket close fail.\r\n{0}", ex.ToString()));
                    return false;
                }
            }
            return true;
        }

        public void Dispose()
        {
            if (mSocket != null)
            {
                try
                {
                    mSocket.Close();
                }
                catch { }
            }
        }

        #endregion
    }


 

客户端:

 

 public class FtpClient : IFtpClient
    {
        private string mClient;
        private Socket mSocket;
        private string mHost;
        private int mPort;
        private int mMsgLength;
        private byte[] mBuffer;
        private int mReceiveLength;
        private bool mIsReceiveMessage;
        private Message mMessage;

        public FtpClient()
        {
            mClient = string.Empty;
            mHost = string.Empty;
            mPort = FtpServerDefine.LISTEN_PORT;
            mMsgLength = FtpServerDefine.MESSAGE_LENGTH;
            mIsReceiveMessage = true;
            mMessage = new Message();
        }

        public FtpClient(string client)
            : this()
        {
            mClient = client;
        }

        public bool Send(Message message, byte[] data)
        {
            return Send(message, data.Length, data);
        }

        private bool ConnectToServer()
        {
            try
            {
                Dispose();
                mSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                mSocket.Connect(mHost, mPort);
                if (mSocket.Connected)
                {
                    mReceiveLength = mMsgLength;
                    mBuffer = new byte[mReceiveLength];
                    mIsReceiveMessage = true;
                    mSocket.BeginReceive(mBuffer, 0, mReceiveLength, SocketFlags.None, new AsyncCallback(SubReceiveMessage), mSocket);
                    return true;
                }
                else
                {
                    return false;
                }
            }
            catch (Exception ex)
            {
                SocketException sex = ex as SocketException;
                if (sex != null)
                {
                    SubDebug(string.Format("Begin receive fail.\tClient disconnected."));
                }
                SubDebug(string.Format("Connect to server fail.\r\n{0}", ex.ToString()));
                return false;
            }
        }

        private void SubReceiveMessage(IAsyncResult result)
        {
            int iReceiveLength = 0;
            Socket socket = result.AsyncState as Socket;
            try
            {
                iReceiveLength = socket.EndReceive(result);
            }
            catch (Exception ex)
            {
                SocketException sex = ex as SocketException;
                if (sex != null)
                {
                    SubDebug(string.Format("End receive message fail.\tServer disconected.\tReceive data break"));
                }
                else
                {
                    SubDebug(string.Format("End receive message fail.\tReceive data break."));
                }
                return;
            }
            if (iReceiveLength == 0)
            {
                SubDebug(string.Format("Receive 0 bytes.\tReceive message break."));
                return;
            }
            int index = 0;
            if (iReceiveLength < mReceiveLength)
            {
                mReceiveLength = mReceiveLength - iReceiveLength;
                index = iReceiveLength;
            }
            else
            {
                if (mIsReceiveMessage)
                {
                    mIsReceiveMessage = false;
                    Message message = new Message();
                    message = Utils.Deserialize<Message>(message, mBuffer);
                    mMessage = message;
                    mReceiveLength = message.DataLength;
                    mBuffer = new byte[mReceiveLength];
                }
                else
                {
                    mIsReceiveMessage = true;
                    SubMessageReceived(mMessage, mBuffer);
                    mReceiveLength = mMsgLength;
                    mBuffer = new byte[mReceiveLength];
                }
            }
            try
            {
                socket.BeginReceive(mBuffer, index, mReceiveLength, SocketFlags.None, new AsyncCallback(SubReceiveMessage), socket);
            }
            catch (Exception ex)
            {
                SocketException sex = ex as SocketException;
                if (sex != null)
                {
                    SubDebug(string.Format("Begin receive fail.\tClient disconnected."));
                }
                else
                {
                    SubDebug(string.Format("Begin receive fail.\tReceive message break."));
                }
            }
        }

        private bool SendMessage(Message message, int length, byte[] data)
        {
            try
            {
                message.DataLength = length;
                byte[] bMsg = Utils.Serialize<Message>(message);
                mSocket.Send(bMsg);
                mSocket.Send(data, length, SocketFlags.None);
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Send message fail.\tMsg:{0}\r\n{1}", message.Command, ex.ToString()));
                return false;
            }
            return true;
        }

        private void SubMessageReceived(Message message, byte[] data)
        {
            if (MessageReceived != null)
            {
                MessageReceived(mClient, message, data);
            }
        }
        public void SubDebug(string msg)
        {
            if (Debug != null)
            {
                Debug(mClient, msg);
            }
        }

        #region IFtpClient 成员

        public event Action<string, string> Debug;

        public event Action<string, Message, byte[]> MessageReceived;

        public string Host
        {
            get { return mHost; }
            set { mHost = value; }
        }

        public int Port
        {
            get { return mPort; }
            set { mPort = value; }
        }

        public bool Connect()
        {
            if (!ConnectToServer())
            {
                return false;
            }
            return true;
        }

        public bool Connect(string host, int port)
        {
            mHost = host;
            mPort = port;
            return Connect();
        }

        public bool Close()
        {
            if (mSocket != null && mSocket.Connected)
            {
                try
                {
                    mSocket.Close();
                    SubDebug(string.Format("Socket closed."));
                }
                catch (Exception ex)
                {
                    SubDebug(string.Format("Socket close fail.\r\n{0}", ex.ToString()));
                    return false;
                }
            }
            return true;
        }

        public bool Send(Message message, int length, byte[] data)
        {
            return SendMessage(message, length, data);
        }

        public void Dispose()
        {
            if (mSocket != null && mSocket.Connected)
            {
                try
                {
                    mSocket.Close();
                    mSocket = null;
                }
                catch { }
            }
        }

        #endregion

    }


 

 文件操作:

 

public class FileOperator : IDisposable
    {
        public event Action<string> Debug;

        private string mPath;
        private FileStream mFileStream;

        public FileOperator()
        {

        }

        public bool Create(string path)
        {
            if (!Path.IsPathRooted(path))
            {
                mPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, path);
            }
            else
            {
                mPath = path;
            }
            try
            {
                if (File.Exists(mPath))
                {
                    File.Delete(mPath);
                }
                mFileStream = new FileStream(mPath, FileMode.OpenOrCreate, FileAccess.Write);
                return true;
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Create file fail.\r\n{0}", ex.ToString()));
                return false;
            }
        }

        public bool WriteData(int length, byte[] data)
        {
            try
            {
                if (mFileStream == null)
                {
                    mFileStream = new FileStream(mPath, FileMode.OpenOrCreate, FileAccess.Write);
                }
                mFileStream.Write(data, 0, length);
                return true;
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Write data fail.\r\n{0}", ex.ToString()));
                return false;
            }

        }
        public bool Close()
        {
            try
            {
                if (mFileStream != null)
                {
                    mFileStream.Close();
                    mFileStream = null;
                }
                return true;
            }
            catch (Exception ex)
            {
                SubDebug(string.Format("Write data fail.\r\n{0}", ex.ToString()));
                return false;
            }
        }

        private void SubDebug(string msg)
        {
            if (Debug != null)
            {
                Debug(msg);
            }
        }

        #region IDisposable 成员

        public void Dispose()
        {
            if (mFileStream != null)
            {
                try
                {
                    mFileStream.Close();
                    mFileStream = null;
                }
                catch { }
            }
        }
        #endregion
    }


 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值