First version of File interface.

This will allow you to easily find and extract files.
Extraction of whole folders coming next. (Maybe)
This commit is contained in:
Caleb Gardner
2020-11-27 00:36:21 -06:00
parent 8358cb2805
commit 23ec7ea6dd
4 changed files with 45 additions and 22 deletions
+6 -2
View File
@@ -32,6 +32,7 @@ type File struct {
//get a File from a directory.entry //get a File from a directory.entry
func (r *Reader) newFileFromDirEntry(entry *directory.Entry) (fil *File, err error) { func (r *Reader) newFileFromDirEntry(entry *directory.Entry) (fil *File, err error) {
fil = new(File)
fil.in, err = r.getInodeFromEntry(entry) fil.in, err = r.getInodeFromEntry(entry)
if err != nil { if err != nil {
return nil, err return nil, err
@@ -39,12 +40,12 @@ func (r *Reader) newFileFromDirEntry(entry *directory.Entry) (fil *File, err err
fil.Name = entry.Name fil.Name = entry.Name
fil.r = r fil.r = r
fil.filType = fil.in.Type fil.filType = fil.in.Type
return return
} }
//GetChildren returns a *squashfs.File slice of every direct child of the directory. If the File is not a directory, will return ErrNotDirectory //GetChildren returns a *squashfs.File slice of every direct child of the directory. If the File is not a directory, will return ErrNotDirectory
func (f *File) GetChildren() (children []*File, err error) { func (f *File) GetChildren() (children []*File, err error) {
children = make([]*File, 0)
if f.r == nil { if f.r == nil {
return nil, ErrNotReading return nil, ErrNotReading
} }
@@ -62,7 +63,9 @@ func (f *File) GetChildren() (children []*File, err error) {
return return
} }
fil.Parent = f fil.Parent = f
if f.Name != "" {
fil.Path = f.Path + "/" + f.Name fil.Path = f.Path + "/" + f.Name
}
children = append(children, fil) children = append(children, fil)
} }
return return
@@ -70,6 +73,7 @@ func (f *File) GetChildren() (children []*File, err error) {
//GetChildrenRecursively returns ALL children. Goes down ALL folder paths. //GetChildrenRecursively returns ALL children. Goes down ALL folder paths.
func (f *File) GetChildrenRecursively() (children []*File, err error) { func (f *File) GetChildrenRecursively() (children []*File, err error) {
children = make([]*File, 0)
if f.r == nil { if f.r == nil {
return nil, ErrNotReading return nil, ErrNotReading
} }
@@ -104,7 +108,7 @@ func (f *File) IsDir() bool {
} }
//Close frees up the memory held up by the underlying reader. Should NOT be called when writing. //Close frees up the memory held up by the underlying reader. Should NOT be called when writing.
//When reading, Close is safe to use, as any subsequent Read calls reinitialize the reader. //When reading, Close is safe to use, but any subsequent Read calls resets to the beginning of the file.
func (f *File) Close() error { func (f *File) Close() error {
if f.IsDir() { if f.IsDir() {
return ErrNotFile return ErrNotFile
+2
View File
@@ -59,7 +59,9 @@ func (r *Reader) newFileReader(in *inode.Inode) (*fileReader, error) {
//Close runs Close on the data reader and frees the fragmentdata //Close runs Close on the data reader and frees the fragmentdata
func (f *fileReader) Close() error { func (f *fileReader) Close() error {
if f.data != nil {
f.data.Close() f.data.Close()
}
f.fragmentData = nil f.fragmentData = nil
return nil return nil
} }
+8 -2
View File
@@ -76,6 +76,7 @@ func NewSquashfsReader(r io.ReaderAt) (*Reader, error) {
//GetRootFolder returns a squashfs.File that references the root directory of the squashfs archive. //GetRootFolder returns a squashfs.File that references the root directory of the squashfs archive.
func (r *Reader) GetRootFolder() (root *File, err error) { func (r *Reader) GetRootFolder() (root *File, err error) {
root = new(File)
mr, err := r.newMetadataReaderFromInodeRef(r.super.RootInodeRef) mr, err := r.newMetadataReaderFromInodeRef(r.super.RootInodeRef)
if err != nil { if err != nil {
return nil, err return nil, err
@@ -86,6 +87,7 @@ func (r *Reader) GetRootFolder() (root *File, err error) {
} }
root.Path = "/" root.Path = "/"
root.filType = root.in.Type root.filType = root.in.Type
root.r = r
return root, nil return root, nil
} }
@@ -158,7 +160,7 @@ func (r *Reader) FindAll(query func(*File) bool) (all []*File) {
//GetFileAtPath will return the file at the given path. If the file cannot be found, will return nil. //GetFileAtPath will return the file at the given path. If the file cannot be found, will return nil.
func (r *Reader) GetFileAtPath(path string) *File { func (r *Reader) GetFileAtPath(path string) *File {
path = "/" + strings.TrimSuffix(strings.TrimPrefix(path, "/"), "/") path = strings.TrimSuffix(strings.TrimPrefix(path, "/"), "/")
pathDirs := strings.Split(path, "/") pathDirs := strings.Split(path, "/")
dir, err := r.GetRootFolder() dir, err := r.GetRootFolder()
if err != nil { if err != nil {
@@ -172,15 +174,19 @@ func (r *Reader) GetFileAtPath(path string) *File {
for _, child := range children { for _, child := range children {
if child.Name == folder { if child.Name == folder {
dir = child dir = child
if dir.IsDir() {
children, err = dir.GetChildren() children, err = dir.GetChildren()
if err != nil { if err != nil {
return nil return nil
} }
} else {
children = make([]*File, 0)
}
break break
} }
} }
} }
if dir.Path+"/"+dir.Name == path { if dir.Path+"/"+dir.Name == "/"+path {
return dir return dir
} }
return nil return nil
+24 -13
View File
@@ -1,9 +1,11 @@
package squashfs package squashfs
import ( import (
"fmt"
"io" "io"
"net/http" "net/http"
"os" "os"
"strings"
"testing" "testing"
goappimage "github.com/CalebQ42/GoAppImage" goappimage "github.com/CalebQ42/GoAppImage"
@@ -27,7 +29,7 @@ func TestMain(t *testing.T) {
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
} else { } else if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer aiFil.Close() defer aiFil.Close()
@@ -37,22 +39,31 @@ func TestMain(t *testing.T) {
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
extractionFil := "code-oss.desktop" rdr.FindAll(func(fil *File) bool {
os.Remove(wd + "/testing/" + extractionFil) return strings.HasSuffix(fil.Name, ".desktop")
desk, err := os.Create(wd + "/testing/" + extractionFil)
if err != nil {
t.Fatal(err)
}
ext := rdr.FindFile(func(fil *File) bool {
return fil.Name == extractionFil
}) })
if ext == nil { fils, err := rdr.GetAllFiles()
t.Fatal("Cannot find file")
}
_, err = io.Copy(desk, ext)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
for _, fil := range fils {
fmt.Println(fil.Path + "/" + fil.Name)
}
// extractionFil := "code-oss.desktop"
// os.Remove(wd + "/testing/" + extractionFil)
// desk, err := os.Create(wd + "/testing/" + extractionFil)
// if err != nil {
// t.Fatal(err)
// }
// ext := rdr.GetFileAtPath(extractionFil)
// if ext == nil {
// t.Fatal("Cannot find file")
// }
// defer ext.Close()
// _, err = io.Copy(desk, ext)
// if err != nil {
// t.Fatal(err)
// }
t.Fatal("No problems here!") t.Fatal("No problems here!")
} }