透过 Socket API 让 PDA 和远程 PC 联机

版工目前有一个 ASP.NET 项目,server 上的数据库是用 Sybase ASE 12.5.1,将来会需要用 PDA (操作系统为 Windows Mobile 6),透过网络联机至远程的 server,再将数据传送至 server 上的 Sybase。但 PDA 用的数据库是 SQL Server Compact,因此无法与 Sybase 直接联机,也就无法直接交换数据库中的数据。

要交换两边不同厂商数据库的数据,版工目前想到两种解决方案:

1. 使用者在 PDA 输入的数据,直接存到 .txt 纯文字文件中,等 PDA 和 server 联机后,再将该个 .txt 档上载至 server 中。但这样一来 PDA 中的 SQL Server Compact 数据库,即无用武之地。虽然它是 Windows Mobile 6 免费内建在 ROM 中的,但不好好利用有点可惜。

2. 用 .NET 的网络和 Socket 函式库,自己写网络程序,先从 PDA 建立联机至远程 server,再将 PDA 中的文字数据上传至 server 上。


以下两段代码,为上述第 2 点的源代码。透过 System.Net.Sockets namespace 的 NetworkStream class,达成我们想要的,跨越网络的数据交换作业。第一段的 server 端代码,是在书上找到的 VB.NET Windows Form 范例;第二段的 client 端 (PDA) 代码,为版工我随手写的 C# 范例。

server 端代码
Imports System.Text
Imports
 System.Net.Sockets
Imports
 System.Threading
Imports
 System.Net

Public Class FormNetServer
Class FormNetServer

    
Dim intPort As Integer

    
Dim myTcpListener As TcpListener
    
Dim myNetworkStream As
 NetworkStream

    
Private Sub btnListener_Click()
Sub btnListener_Click(ByVal sender As System.Object, _
                
ByVal e As System.EventArgs) Handles
 btnListener.Click
        
Dim myThread As New Thread(New ThreadStart(AddressOf
 StartListen))
        myThread.Start()
    
End Sub


    
Private Sub StartListen()Sub StartListen()
        Label.CheckForIllegalCrossThreadCalls 
= False

        TextBox.CheckForIllegalCrossThreadCalls 
= False

        intPort 
= Integer.Parse(txtPort.Text)
        myTcpListener 
= New TcpListener(IPAddress.Parse("192.168.0.1"
), intPort)

        
Dim blnConection As Boolean = False


        
Try
            myTcpListener.Start()
            lblMessage.Text 
= "等待連線中 ……"
            
Dim mySocket As Socket = myTcpListener.AcceptSocket()
            
Do

                
If mySocket.Connected = True Then
                    lblMessage.Text 
= "通訊埠 " + txtPort.Text + " 連線成功"
                    myNetworkStream 
= New NetworkStream(mySocket)
                    
Do

                        
Dim strContent As String
                        
Dim myByte(1024As Byte
                        
Dim lngRead As Integer = myNetworkStream.Read(myByte, 01024)
                        
If lngRead < 0 Then Exit Do

                        strContent 
= Encoding.UTF8.GetString(myByte)
                        txtContent.Text 
+=
 strContent
                    
Loop

                
End If
            
Loop

        
Catch ex As SocketException
            MessageBox.Show _
            (ex.Message, 
"開啟連接錯誤"
, MessageBoxButtons.OK, _
            MessageBoxIcon.Warning)
        
End Try


    
End Sub


    
Private Sub btnClose_Click()Sub btnClose_Click(ByVal sender As System.Object, _
            
ByVal e As System.EventArgs) Handles
 btnClose.Click
        myTcpListener.Stop()
    
End Sub


End Class

client 端 (PDA) 代码
using System.Data.SqlServerCe;
using
 System.IO;
//
using System.Data.SqlClient;
//using Sybase.Data.AseClient;

using System.Net;
using
 System.Net.Sockets;

namespace
 DeviceApplication01
{
    
public partial class
 Form1 : Form
    
{
        TcpClient myTcpClient 
= new
 TcpClient();
        NetworkStream myNetworkStream;

        
public
 Form1()
        
{
            InitializeComponent();
        }


        
// 透過 .NET 的 Socket API,從 PDA 連線至遠端 PC (可正確執行)
        private void button6_Click(object sender, EventArgs e)
        
{
            
string strHostName =
 txtHostName.Text;
            
int intPort =
 Int32.Parse(txtPort.Text);
            
try

            
{
                myTcpClient.Connect(strHostName, intPort);
                myNetworkStream 
=
 myTcpClient.GetStream();
                lblMessage.Text 
= "ip:" + strHostName + ", port: " + intPort.ToString() + ", 連接成功"
;
            }

            
catch (ArgumentOutOfRangeException ex)
            
{
                MessageBox.Show(
"ArgumentOutOfRangeException 例外: " + ex.Message + ", 通訊埠號碼不正確"
);
            }

            
catch (SocketException ex)
            
{
                MessageBox.Show(
"SocketException 例外: " + ex.Message + ",連接錯誤"
);
            }

            
catch (Exception ex)
            
{
                MessageBox.Show(
"Exception 例外: " +
 ex.Message);
            }

        }



        
// 將 TextBox 中使用者輸入的內容,從 PDA 傳送到已連線的遠端 PC 上 (可正確執行)
        private void btnTransString_Click(object sender, EventArgs e)
        
{
            
string strTransString =
 tbTransString.Text;
            
byte[] byteArray1 =
 Encoding.UTF8.GetBytes(strTransString);
            lblMessage.Text 
= ("已經建立網路串流,將字串寫入串流!"
);
            myNetworkStream 
=
 myTcpClient.GetStream();
            
            
// Check to see if this NetworkStream is writable.

            if (myNetworkStream.CanWrite)
            
{
                myNetworkStream.Write(byteArray1, 
0
, byteArray1.Length);

                
//
byte[] myWriteBuffer = Encoding.ASCII.GetBytes("Are you receiving this message?");
                
//myNetworkStream.Write(myWriteBuffer, 0, myWriteBuffer.Length);

            }

            
else
            
{
                lblMessage.Text 
= ("Sorry.  You cannot write to this NetworkStream."
);
            }

        }


    }
 // end of class
}
 // end of namespace


上述源代码,可由此处下载:
http://files.cnblogs.com/WizardWu/080706.zip
(此代码是在繁体中文版的 Windows、VS 2005 上开发,尚未在简体中文的环境里编译、执行、测试过)


执行画面如下方四张图。

图 1 中,我们先在 server 中 (IP 为 192.168.0.1),开启 8020 port 并等待 client-side 联机。
图 2 中,我们在 PDA 中的两个 TextBox 先输入要联机的 server IP 和 port,并按下「socket 连接远程 PC」Button,先和 server 建立网络联机。
图 3 中,继续在 PDA 中,按下「传下列 TextBox 字符串到远程 PC」Button,就会将该 Button 下方 TextBox 里,使用者输入的文字内容,传送至 server 上。
图 4 中,server 接收到 PDA 所传来的文字内容。


图 1

figure2
图 2

figure3
图 3

figure4
图 4


测试环境,为一台个人 PC 当作 server,另一台 Notebook 上的 PDA 仿真器当作 client,双方透过一条网络线直接对连,模拟 LAN 环境。


上述 server 端的代码,会一直跑 loop,逐渐吃掉 server 上的系统资源,且代码中建立的网络通讯,似乎开启后也忘了 close。看来即使是书上的代码范例,也还有很大的改善空间。台湾的计算机书,好坏差别是相当大的,不能太指望书附光盘里的代码,其执行结果的正确性,有 bug 是很正常的。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值