Fetch a URL
Alan A. A. Donovan and Brian W. Kernighan, The Go Programming Language. Addison-Wesley, 2016, Chapter 1, Tutorial
Exercises 1.7, 1.8 and 1.9
Exercise 1.7: The function call
io.Copy(dst, src)reads fromsrcand writes todst. Use it instead ofioutil.ReadAllto copy the response body toos.Stdoutwithout requiring a buffer large enough to hold the entire stream. Be sure to chec the error result ofio.Copy.Exercise 1.8: Modify
fetchto add the prefixhttp://to each argument URL if it is missing. You might want to usestrings.HasPrefix.Exercise 1.9: Modify
fetchto also print the HTTP status code, found inresp.Status.
My solution
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
package main
import (
	"fmt"
	"io"
	"net/http"
	"os"
	"strings"
)
func main() {
	for _, url := range os.Args[1:] {
		// Modification for Exercise 1.8.
		if !strings.HasPrefix(url, "http://") {
			url = "http://" + url
		}
		// Get `url` and store data in `resp`, whic is a struct with a
		// `Body` field that contains the server response as a readable
		// stream.
		resp, err_http := http.Get(url)
		if err_http != nil {
			fmt.Fprintf(os.Stderr, "fetch: %v\n", err_http)
			os.Exit(1)
		}
		// Original code provided in Section 1.5:
		// b, err := ioutil.ReadAll(resp.Body)
		// Modifications for Exercise 1.7 and 1.9.
		fmt.Println("Status:", resp.Status)
		_, err_copy := io.Copy(os.Stdout, resp.Body)
		resp.Body.Close()
		if err_copy != nil {
			fmt.Fprintf(os.Stderr, "fetch: reading %s: %v\n", url, err_copy)
			os.Exit(1)
		}
	}
}