Sending Data to a TCP Client Using GO

Priyansh SaoPriyansh Sao
3 min read
    package main

    import (
        "crypto/rand"
        "errors"
        "fmt"
        "net"
        "io"
    )

    func main() {
        // creating a payload
        payload := make([]byte, 1<<24) //size is 16MiB
        _, err := rand.Read(payload)// adding random data
        if err != nil {
            fmt.Println("[main] unable to create payload: ", err)
            return
        }

        listener, err := net.Listen("tcp", "127.0.0.1:8080")
        if err != nil {
            fmt.Println("[main] unble to create listener: ", err)
            return
        }

        go func() {
            // just accepting one connection then closing listener
            conn, err := listener.Accept()
            if err != nil {
                fmt.Println("[server] unable to accept connections: ", err)
                return
            }
            listener.Close()
            defer conn.Close()

            fmt.Printf("[server] client connected (port:%s)\n", conn.RemoteAddr())

            // writing to client 
            total:=0

            for total < len(payload) {
                n, err := conn.Write(payload[total:])
                if err != nil {
                    fmt.Println("[server] unable to write payload :", err)
                    return
                }

                total += n
            }

            fmt.Printf("[server] written %d bytes\n", total)
        }()

        // client part
        conn, err := net.Dial("tcp", listener.Addr().String())
        if err != nil {
            fmt.Println("[main] unable to create client: ", err)
            return
        }

        defer conn.Close()

        buf := make([]byte, 512<<10) //making a buffer to read in size is 512KiB
        total := 0
        for {
            n, err := conn.Read(buf)

            if n>0 {
                total += n
                fmt.Printf("[client] read %d (total: %d)\n", n, total)
            }

            if err != nil {
                if errors.Is(err, io.EOF) {
                    fmt.Println("[client] reached end of data: ", err)
                    break
                }
                fmt.Println("[client] read error: ", err)
                return
            }
        }

        // just checking if the overall operation is a success or not
        if total != len(payload) {
            fmt.Printf("WARNING: expected %d bytes but read %d\n", len(payload), total)
        } else {
            fmt.Printf("[client] all %d bytes read successfully\n", total)
        }

    }

Here’s a short, point-by-point explanation of what your code does:

  1. Generate test data

    • Creates a 16 MiB byte slice.

    • Fills it with random data using crypto/rand.

  2. Start TCP server

    • Listens on 127.0.0.1:8080.

    • Waits for one incoming client connection.

  3. Handle client connection

    • Prints the connected client’s IP:port.

    • Sends the 16 MiB payload to the client in chunks until all bytes are sent.

    • Prints total bytes written.

  4. Start client

    • Connects to the server using its address.

    • Uses a 512 KiB buffer to repeatedly read data from the server.

    • Keeps a running total of bytes read and prints each chunk size.

  5. End of transmission

    • When server finishes sending, client detects io.EOF.

    • Compares total bytes read to expected payload size.

    • Prints success or warning message.

  6. Key networking detail

    • The client’s port is randomly assigned (ephemeral port) by the OS, so it differs from the server’s fixed port 8080.

output:

[server] client connected (port:127.0.0.1:57178)
[client] read 524288 (total: 524288)
[server] written 16777216 bytes
[client] read 524288 (total: 1048576)
[client] read 261109 (total: 1309685)
[client] read 524288 (total: 1833973)
[client] read 524288 (total: 2358261)
[client] read 524288 (total: 2882549)
[client] read 524288 (total: 3406837)
[client] read 524288 (total: 3931125)
[client] read 524288 (total: 4455413)
[client] read 524288 (total: 4979701)
[client] read 524288 (total: 5503989)
[client] read 524288 (total: 6028277)
[client] read 524288 (total: 6552565)
[client] read 524288 (total: 7076853)
[client] read 524288 (total: 7601141)
[client] read 524288 (total: 8125429)
[client] read 524288 (total: 8649717)
[client] read 524288 (total: 9174005)
[client] read 524288 (total: 9698293)
[client] read 524288 (total: 10222581)
[client] read 524288 (total: 10746869)
[client] read 524288 (total: 11271157)
[client] read 524288 (total: 11795445)
[client] read 524288 (total: 12319733)
[client] read 524288 (total: 12844021)
[client] read 524288 (total: 13368309)
[client] read 524288 (total: 13892597)
[client] read 524288 (total: 14416885)
[client] read 524288 (total: 14941173)
[client] read 524288 (total: 15465461)
[client] read 524288 (total: 15989749)
[client] read 524288 (total: 16514037)
[client] read 252468 (total: 16766505)
[client] read 10711 (total: 16777216)
[client] reached end of data
[client] all 16777216 bytes read successfully
0
Subscribe to my newsletter

Read articles from Priyansh Sao directly inside your inbox. Subscribe to the newsletter, and don't miss out.

Written by

Priyansh Sao
Priyansh Sao