Skip to content

Add socket/tcp_io_readfull example #909

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Apr 11, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions examples/socket/tcp_io_readfull/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
app
25 changes: 25 additions & 0 deletions examples/socket/tcp_io_readfull/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
# io.ReadFull()のサンプル

```sh
$ task
task: [build] go build -o app .
task: [run] ./app -timeout 100ms
03:01:14.980749 [C] recv start
03:01:15.081186 netErr.Timeout()
task: [run] ./app -timeout 3s
03:01:15.091656 [C] recv start
03:01:15.592085 io.ErrUnexpectedEOF
task: [run] ./app -length 10 -timeout 3s
03:01:15.602765 [C] recv start
03:01:15.602902 [C] data=(hhhh)
03:01:15.602912 [C] data=(hhhh)
03:01:16.103520 io.ErrUnexpectedEOF
task: [run] ./app -bufsize 6 -length 12 -timeout 3s
03:01:16.113780 [C] recv start
03:01:16.113887 [C] data=(hhhhhh)
03:01:16.113901 [C] data=(hhhhhh)
03:01:16.614526 io.EOF
```


- [io.ReadFull](https://pkg.go.dev/io@latest#ReadFull)
18 changes: 18 additions & 0 deletions examples/socket/tcp_io_readfull/Taskfile.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
# https://taskfile.dev

version: '3'

tasks:
default:
cmds:
- task: build
- task: run
build:
cmds:
- go build -o app .
run:
cmds:
- ./app -timeout 100ms
- ./app -timeout 3s
- ./app -length 10 -timeout 3s
- ./app -bufsize 6 -length 12 -timeout 3s
106 changes: 106 additions & 0 deletions examples/socket/tcp_io_readfull/main.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
package main

import (
"errors"
"flag"
"io"
"log"
"net"
"strings"
"time"
)

type (
Args struct {
bufsize int
length int
timeout time.Duration
}
)

var (
args Args
)

func init() {
flag.IntVar(&args.bufsize, "bufsize", 4, "bufsize")
flag.IntVar(&args.length, "length", 2, "length")
flag.DurationVar(&args.timeout, "timeout", 1*time.Second, "timeout")
}

func main() {
log.SetFlags(log.Lmicroseconds)
flag.Parse()

ln, err := net.Listen("tcp", ":8888")
if err != nil {
panic(err)
}
defer ln.Close()

go func() {
conn, err := ln.Accept()
if err != nil {
if errors.Is(err, net.ErrClosed) {
return
}
panic(err)
}
defer conn.Close()

buf := []byte(strings.Repeat("h", args.length))
_, err = conn.Write(buf)
if err != nil {
panic(err)
}

time.Sleep(500 * time.Millisecond)
}()

if err := run(); err != nil {
panic(err)
}
}

func run() error {
conn, err := net.Dial("tcp", ":8888")
if err != nil {
return err
}
defer conn.Close()

log.Println("[C] recv start")
{
buf := make([]byte, args.bufsize)
for {
clear(buf)

err = conn.SetReadDeadline(time.Now().Add(args.timeout))
if err != nil {
return err
}

n, err := io.ReadFull(conn, buf)
if err != nil {
switch {
case errors.Is(err, io.EOF):
log.Println("io.EOF")
return nil
case errors.Is(err, io.ErrUnexpectedEOF):
log.Println("io.ErrUnexpectedEOF")
return nil
default:
var netErr net.Error
if errors.As(err, &netErr) && netErr.Timeout() {
log.Println("netErr.Timeout()")
return nil
}
}

return err
}

log.Printf("[C] data=(%s)", buf[:n])
}
}
}
Loading