Golang input/output

From wikinotes
Revision as of 20:45, 18 June 2022 by Will (talk | contribs) (→‎Reading)

Documentation

fmt https://pkg.go.dev/fmt@go1.18.2
io/ioutil (read/write) https://pkg.go.dev/io/ioutil@go1.18.3
textproto (sockets) https://pkg.go.dev/net/textproto@go1.18.3

Stdin, Stdout, Stderr

fmt.Fprintln(os.Stdout, "writes stdout")
fmt.Fprintln(os.Stderr, "writes stderr")

Reader, Writer

// read a file into `[]bytes` until EOF
conts, err := os.ReadAll(reader)
buf := make([]byte, 64)
_, err := os.ReadFull(reader, buf) // fill buffer to capacity, reading from reader
switch {
    case errors.Is(err, os.EOF):
        // nothing to read (0 bytes)
    case errors.Is(err, os.ErrUnexpectedEOF):
        // end of file, before filling buffer
}
filepath := "/var/tmp/foo.txt"

_, err := os.WriteString(writer, "abcd")

Files

If the files are small, you can work with them using os

Reading

Small Files

import "os"

// read entire file into []byte
conts, err := os.ReadFile("/var/tmp/foo.txt")

Buffered Reading

// create or open file for reading
fd, err := os.Open("/var/tmp/foo.txt")        // open for reading
fd, err := os.OpenFile("/var/tmp/foo.txt",    // open, setting open-mode flags
                       os.O_RDWR|os.O_APPEND,
                       0644)
defer fd.Close()

// read up to 5 bytes
buf := make([]byte, 5)
bytes_r, err := fd.Read(buf)

Auto-Buffered Reader

fd, err := os.OpenFile("/var/tmp/foo.txt",    // open, setting open-mode flags
                       os.O_RDWR|os.O_APPEND,
                       0644)
defer fd.Close()
reader := bufio.NewReader(fd)

bytes, err := reader.ReadBytes("\n")   // read all characters until first occurrence of '\n'
string, err := reader.ReadString("\n") // read all characters until first occurrence of '\n'

// fill buffer to capacity, reading from reader
buf := make([]byte, 64)
_, err := os.ReadFull(reader, buf)
switch {
    case errors.Is(err, os.EOF):
        // nothing to read (0 bytes)
    case errors.Is(err, os.ErrUnexpectedEOF):
        // end of file, before filling buffer
}

Writing

Small Files

import "os"

// replace file (creating if necessary)
err := os.WriteFile("/var/tmp/foo.txt", []byte("abc"), 0644)

Manually Buffered Writing

fd, err := os.Create(filepath)                 // create, or truncate file (0666 perms)
fd, err := os.OpenFile("/var/tmp/foo.txt",    // open, setting open-mode flags
                       os.O_RDWR|os.O_APPEND,
                       0644)
defer fd.Close()

bytes_w, err := fd.Write([]byte("abc"))
bytes_w, err := fd.WriteString("abc")

fd.Sync()  // sync writes to disk

Auto Buffered Writer

import "os"
import "bufio"

fd, err := os.OpenFile("foo.txt", os.O_WRONLY|os.O_APPEND, 0644)
defer fd.Close()

writer := bufio.NewWriter(fd)
bytes_w, err := writer.Write([]byte("abc"))
bytes_w, err := writer.WriteString("abc")

writer.Flush()  // ensure all writes written to disk before closing

Networking

Sockets

net.Dial() creates sockets of various types.

import "net"

// unix socketfile
conn, err = net.Dial("unix", "/var/tmp/foo.sock")

// inet socket
conn, err = net.Dial("tcp", "10.10.10.10:6600")
defer conn.Close()

// sending message to socket
_, err = conn.Write([]byte("search title 'it ceases to be'"))
reply := make([]byte, 1024)
_, err = conn.Read(reply)
fmt.Println(string(reply))

HTTP