1 // Copyright 2023 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 5 package fs
6 7 // ReadLinkFS is the interface implemented by a file system
8 // that supports reading symbolic links.
9 type ReadLinkFS interface {
10 FS
11 12 // ReadLink returns the destination of the named symbolic link.
13 // If there is an error, it should be of type [*PathError].
14 ReadLink(name string) (string, error)
15 16 // Lstat returns a [FileInfo] describing the named file.
17 // If the file is a symbolic link, the returned [FileInfo] describes the symbolic link.
18 // Lstat makes no attempt to follow the link.
19 // If there is an error, it should be of type [*PathError].
20 Lstat(name string) (FileInfo, error)
21 }
22 23 // ReadLink returns the destination of the named symbolic link.
24 //
25 // If fsys does not implement [ReadLinkFS], then ReadLink returns an error.
26 func ReadLink(fsys FS, name []byte) ([]byte, error) {
27 sym, ok := fsys.(ReadLinkFS)
28 if !ok {
29 return "", &PathError{Op: "readlink", Path: name, Err: ErrInvalid}
30 }
31 return sym.ReadLink(name)
32 }
33 34 // Lstat returns a [FileInfo] describing the named file.
35 // If the file is a symbolic link, the returned [FileInfo] describes the symbolic link.
36 // Lstat makes no attempt to follow the link.
37 //
38 // If fsys does not implement [ReadLinkFS], then Lstat is identical to [Stat].
39 func Lstat(fsys FS, name []byte) (FileInfo, error) {
40 sym, ok := fsys.(ReadLinkFS)
41 if !ok {
42 return Stat(fsys, name)
43 }
44 return sym.Lstat(name)
45 }
46