1// Copyright 2009 The Go Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style
3// license that can be found in the LICENSE file.
4
5package os_test
6
7import (
8	"bytes"
9	. "os"
10	"path/filepath"
11	"runtime"
12	"testing"
13)
14
15func checkNamedSize(t *testing.T, path string, size int64) {
16	dir, err := Stat(path)
17	if err != nil {
18		t.Fatalf("Stat %q (looking for size %d): %s", path, size, err)
19	}
20	if dir.Size() != size {
21		t.Errorf("Stat %q: size %d want %d", path, dir.Size(), size)
22	}
23}
24
25func TestReadFile(t *testing.T) {
26	t.Parallel()
27
28	filename := "rumpelstilzchen"
29	contents, err := ReadFile(filename)
30	if err == nil {
31		t.Fatalf("ReadFile %s: error expected, none found", filename)
32	}
33
34	filename = "read_test.go"
35	contents, err = ReadFile(filename)
36	if err != nil {
37		t.Fatalf("ReadFile %s: %v", filename, err)
38	}
39
40	checkNamedSize(t, filename, int64(len(contents)))
41}
42
43func TestWriteFile(t *testing.T) {
44	t.Parallel()
45
46	f, err := CreateTemp("", "os-test")
47	if err != nil {
48		t.Fatal(err)
49	}
50	defer f.Close()
51	defer Remove(f.Name())
52
53	msg := "Programming today is a race between software engineers striving to " +
54		"build bigger and better idiot-proof programs, and the Universe trying " +
55		"to produce bigger and better idiots. So far, the Universe is winning."
56
57	if err := WriteFile(f.Name(), []byte(msg), 0644); err != nil {
58		t.Fatalf("WriteFile %s: %v", f.Name(), err)
59	}
60
61	data, err := ReadFile(f.Name())
62	if err != nil {
63		t.Fatalf("ReadFile %s: %v", f.Name(), err)
64	}
65
66	if string(data) != msg {
67		t.Fatalf("ReadFile: wrong data:\nhave %q\nwant %q", string(data), msg)
68	}
69}
70
71func TestReadOnlyWriteFile(t *testing.T) {
72	if Getuid() == 0 {
73		t.Skipf("Root can write to read-only files anyway, so skip the read-only test.")
74	}
75	if runtime.GOOS == "wasip1" {
76		t.Skip("no support for file permissions on " + runtime.GOOS)
77	}
78	t.Parallel()
79
80	// We don't want to use CreateTemp directly, since that opens a file for us as 0600.
81	tempDir, err := MkdirTemp("", t.Name())
82	if err != nil {
83		t.Fatal(err)
84	}
85	defer RemoveAll(tempDir)
86	filename := filepath.Join(tempDir, "blurp.txt")
87
88	shmorp := []byte("shmorp")
89	florp := []byte("florp")
90	err = WriteFile(filename, shmorp, 0444)
91	if err != nil {
92		t.Fatalf("WriteFile %s: %v", filename, err)
93	}
94	err = WriteFile(filename, florp, 0444)
95	if err == nil {
96		t.Fatalf("Expected an error when writing to read-only file %s", filename)
97	}
98	got, err := ReadFile(filename)
99	if err != nil {
100		t.Fatalf("ReadFile %s: %v", filename, err)
101	}
102	if !bytes.Equal(got, shmorp) {
103		t.Fatalf("want %s, got %s", shmorp, got)
104	}
105}
106
107func TestReadDir(t *testing.T) {
108	t.Parallel()
109
110	dirname := "rumpelstilzchen"
111	_, err := ReadDir(dirname)
112	if err == nil {
113		t.Fatalf("ReadDir %s: error expected, none found", dirname)
114	}
115
116	dirname = "."
117	list, err := ReadDir(dirname)
118	if err != nil {
119		t.Fatalf("ReadDir %s: %v", dirname, err)
120	}
121
122	foundFile := false
123	foundSubDir := false
124	for _, dir := range list {
125		switch {
126		case !dir.IsDir() && dir.Name() == "read_test.go":
127			foundFile = true
128		case dir.IsDir() && dir.Name() == "exec":
129			foundSubDir = true
130		}
131	}
132	if !foundFile {
133		t.Fatalf("ReadDir %s: read_test.go file not found", dirname)
134	}
135	if !foundSubDir {
136		t.Fatalf("ReadDir %s: exec directory not found", dirname)
137	}
138}
139