Simplify dirArchive by using os.dirFS and have Archive.Open return fs.File

This commit is contained in:
Philipp Wolfer 2025-05-24 02:20:07 +02:00
parent 0231331209
commit 975e208254
No known key found for this signature in database
GPG key ID: 8FDF744D4919943B
2 changed files with 20 additions and 22 deletions

View file

@ -30,6 +30,7 @@ import (
"archive/zip"
"fmt"
"io"
"io/fs"
"os"
"path/filepath"
)
@ -37,7 +38,7 @@ import (
// Generic archive interface.
type Archive interface {
Close() error
OpenFile(path string) (io.ReadCloser, error)
Open(path string) (fs.File, error)
Glob(pattern string) ([]FileInfo, error)
}
@ -53,14 +54,14 @@ func OpenArchive(path string) (Archive, error) {
switch mode := fi.Mode(); {
case mode.IsRegular():
archive := &zipArchive{}
err := archive.Open(path)
err := archive.OpenArchive(path)
if err != nil {
return nil, err
}
return archive, nil
case mode.IsDir():
archive := &dirArchive{}
err := archive.Open(path)
err := archive.OpenArchive(path)
if err != nil {
return nil, err
}
@ -95,7 +96,7 @@ type zipArchive struct {
zip *zip.ReadCloser
}
func (a *zipArchive) Open(path string) error {
func (a *zipArchive) OpenArchive(path string) error {
zip, err := zip.OpenReader(path)
if err != nil {
return err
@ -129,7 +130,7 @@ func (a *zipArchive) Glob(pattern string) ([]FileInfo, error) {
return result, nil
}
func (a *zipArchive) OpenFile(path string) (io.ReadCloser, error) {
func (a *zipArchive) Open(path string) (fs.File, error) {
file, err := a.zip.Open(path)
if err != nil {
return nil, err
@ -139,11 +140,13 @@ func (a *zipArchive) OpenFile(path string) (io.ReadCloser, error) {
// An implementation of the archiveBackend interface for directories.
type dirArchive struct {
dir string
path string
dirFS fs.FS
}
func (a *dirArchive) Open(path string) error {
a.dir = filepath.Clean(path)
func (a *dirArchive) OpenArchive(path string) error {
a.path = filepath.Clean(path)
a.dirFS = os.DirFS(path)
return nil
}
@ -151,28 +154,23 @@ func (a *dirArchive) Close() error {
return nil
}
func (a *dirArchive) OpenFile(path string) (io.ReadCloser, error) {
file, err := os.Open(filepath.Join(a.dir, path))
if err != nil {
return nil, err
}
return file, nil
// Open opens the named file in the archive.
// [fs.File.Close] must be called to release any associated resources.
func (a *dirArchive) Open(path string) (fs.File, error) {
return a.dirFS.Open(path)
}
func (a *dirArchive) Glob(pattern string) ([]FileInfo, error) {
files, err := filepath.Glob(filepath.Join(a.dir, pattern))
files, err := fs.Glob(a.dirFS, pattern)
if err != nil {
return nil, err
}
result := make([]FileInfo, 0)
for _, filename := range files {
name, err := filepath.Rel(a.dir, filename)
if err != nil {
return nil, err
}
for _, name := range files {
fullPath := filepath.Join(a.path, name)
info := FileInfo{
Name: name,
File: &filesystemFile{path: filename},
File: &filesystemFile{path: fullPath},
}
result = append(result, info)
}

View file

@ -63,7 +63,7 @@ func (a *ExportArchive) Close() error {
// Read the user information from the archive.
func (a *ExportArchive) UserInfo() (UserInfo, error) {
f, err := a.backend.OpenFile("user.json")
f, err := a.backend.Open("user.json")
if err != nil {
return UserInfo{}, err
}