Salve, è da molto che non programmo in vb.net e infatti sono parecchio arrugginito...
Ho realizzato l'applicazione client server ke legge i dati ed ho creato una seconda istanza del client e server per la ricezione dei file... solo ke provando con un file xls di 9kb, il programma sembra inviare tutto ma il server riceve solo 8kb...
quindi c'è qualkosa che non va...
qui il codice del server:
codice:
Imports System.Net.Sockets
Imports System.Text.Encoding
Public Class frmMain
Private client As New TcpClient
Private fileClient As New TcpClient
Private server As New TcpListener(1989)
Private fileServer As New TcpListener(1001)
Private NetStream, NetFile As NetworkStream
'Percorso su cui salvare il file
Private FileName As String
'Dimensione del file
Private FileSize As Int64
Private Sub frmMain_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
server.Start()
tmrControlConnection.Start()
End Sub
Private Sub Send(ByVal Msg As String, ByVal Stream As NetworkStream)
'Se si può scrivere
If Stream.CanWrite Then
'Converte il messaggio in binario
Dim Bytes() As Byte = ASCII.GetBytes(Msg)
'E lo scrive sul network stream
Stream.Write(Bytes, 0, Bytes.Length)
End If
End Sub
'Ottiene un messaggio dallo stream di rete
Private Function GetMessage(ByVal Stream As NetworkStream) As String
'Se si può leggere
If Stream.CanRead Then
Dim Bytes(client.ReceiveBufferSize) As Byte
Dim Msg As String
'Legge i bytes arrivati
Stream.Read(Bytes, 0, Bytes.Length)
'Li converte in una stringa leggibile
Msg = ASCII.GetString(Bytes)
'E restituisce la stringa
Return Msg.Normalize
Else
Return Nothing
End If
End Function
Function replaceEntity(ByVal str As String)
Return Replace(str, "à", "a")
End Function
Private Sub tmrControlConnection_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles tmrControlConnection.Tick
'Se ci sono connessioni in attesa...
If server.Pending Then
'Ferma il timer per eseguire le operazioni
tmrControlConnection.Stop()
lblStatus.Text = "È stata ricevuta una richiesta ..."
'Accetta la connessione
client = server.AcceptTcpClient
'Apre lo stream di rete condiviso
NetStream = client.GetStream
'Termina l'ascolto
server.Stop()
'Inizia la ricezione di messaggi
tmrGetData.Start()
lblStatus.Text = "STATO: Connesso"
End If
End Sub
Private Sub tmrControlFile_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles tmrControlFile.Tick
'Se c'è una richiesta, l'accetta subito
If fileServer.Pending Then
tmrControlFile.Stop()
fileClient.ReceiveBufferSize = 1024
fileClient = fileServer.AcceptTcpClient
NetFile = fileClient.GetStream
'Ferma il listener
fileClient.ReceiveBufferSize = 1024
fileServer.Stop()
lblStatus.Text = "Flusso di informazioni aperto ..."
'Attiva la ricezione di dati attraverso un background worker
bgReceiveFile.RunWorkerAsync()
End If
End Sub
Private Sub tmrGetData_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles tmrGetData.Tick
If client.Connected And client.Available Then
'Ferma il timer mentre si eseguono le operazioni
tmrGetData.Stop()
'Legge il messaggio
Dim Msg As String = GetMessage(NetStream)
If Msg.StartsWith("ConfirmTransfer") Then
'Divide il messagio in parti in base al carattere pipe
Dim Parts() As String = Msg.Split("|")
'La prima parte è "ConfirmTransfer"
'La seconda è il percorso del file sull'altro computer
Dim File As String = Parts(1)
'La terza è la dimensione
Dim Size As Int64 = CType(Parts(2), Int64)
'Ottiene solo il nome del file, senza percorso
File = IO.Path.GetFileName(File)
'Costruisce il percorso del file su questo computer,
'salvandolo nella cartella del progetto (bin\Debug)
FileName = "C:\" & replaceEntity(File)
'Imposta Size come variabile globale
FileSize = Size
'Manda OK al client
Send("OK", NetStream)
'Intanto si mette in attesa sulla porta 1001 per
'l'invio dei bytes del file
fileServer.Start()
'E attiva il timer di controllo
tmrControlFile.Start()
End If
'Riprende il controllo
tmrGetData.Start()
End If
End Sub
Private Sub bgReceiveFile_DoWork(ByVal sender As System.Object, ByVal e As System.ComponentModel.DoWorkEventArgs) Handles bgReceiveFile.DoWork
'Apre un nuovo stream in base al percorso costruito
'nella procedura precedente
Dim Stream As New IO.FileStream("C:\prova.xlsx", IO.FileMode.Create)
'Crea un indice che indica il progresso
Dim Index As Int64 = 0
lblStatus.Text = "In ricezione ..."
For Block As Int64 = 0 To FileSize Step 8192
If fileClient.Available Then
'Riceve i bytes necessari
Dim Bytes(8192) As Byte
Dim Msg As String = GetMessage(NetFile)
'Se i bytes sono un messaggio stringa e contengono
'"END", oppure la dimensione giusta è già stata
'raggiunta, allora si ferma
If Msg.Contains("END") Then
Exit For
End If
'Preleva i bytes dallo stream di rete
NetFile.Read(Bytes, 0, 8192)
'E li scrive sul file fisico
Stream.Write(Bytes, 0, 8192)
'Incrementa l'indice di 8192
Index += 8192
'E notifica il progresso
bgReceiveFile.ReportProgress(Index * 100 / FileSize)
End If
Next
lblStatus.Text = "File ricevuto ..."
Stream.Close()
End Sub
Private Sub bgReceiveFile_ProgressChanged(ByVal sender As Object, ByVal e As System.ComponentModel.ProgressChangedEventArgs) Handles bgReceiveFile.ProgressChanged
prgProgress.Value = e.ProgressPercentage
End Sub
End Class
Cosa sbaglio?