izapple2/storage/resources.go

102 lines
2.0 KiB
Go
Raw Normal View History

package storage
import (
"archive/zip"
"bytes"
"compress/gzip"
"io"
"io/ioutil"
"net/http"
"os"
"strings"
2020-10-03 21:38:26 +00:00
"github.com/ivanizag/izapple2/romdumps"
)
const (
internalPrefix = "<internal>/"
httpPrefix = "http://"
httpsPrefix = "https://"
)
func isInternalResource(filename string) bool {
return strings.HasPrefix(filename, internalPrefix)
}
func isHTTPResource(filename string) bool {
return strings.HasPrefix(filename, httpPrefix) ||
strings.HasPrefix(filename, httpsPrefix)
}
// LoadResource loads in memory a file from the filesystem, http or embedded
func LoadResource(filename string) ([]uint8, error) {
var file io.Reader
if isInternalResource(filename) {
// load from embedded resource
resource := strings.TrimPrefix(filename, internalPrefix)
resourceFile, err := romdumps.Assets.Open(resource)
if err != nil {
2019-10-05 23:26:00 +00:00
return nil, err
}
defer resourceFile.Close()
file = resourceFile
} else if isHTTPResource(filename) {
response, err := http.Get(filename)
if err != nil {
2019-10-05 23:26:00 +00:00
return nil, err
}
defer response.Body.Close()
file = response.Body
} else {
diskFile, err := os.Open(filename)
if err != nil {
2019-10-05 23:26:00 +00:00
return nil, err
}
defer diskFile.Close()
file = diskFile
}
data, err := ioutil.ReadAll(file)
if err != nil {
2019-10-05 23:26:00 +00:00
return nil, err
}
contentType := http.DetectContentType(data)
if contentType == "application/x-gzip" {
gz, err := gzip.NewReader(bytes.NewReader(data))
if err != nil {
return nil, err
}
defer gz.Close()
data, err = ioutil.ReadAll(gz)
if err != nil {
return nil, err
}
} else if contentType == "application/zip" {
z, err := zip.NewReader(bytes.NewReader(data), int64(len(data)))
if err != nil {
return nil, err
}
for _, zf := range z.File {
f, err := zf.Open()
if err != nil {
return nil, err
}
defer f.Close()
bytes, err := ioutil.ReadAll(f)
if err != nil {
return nil, err
}
if isFileDsk(bytes) || isFileNib(bytes) || isFileWoz(bytes) {
data = bytes
break
}
}
}
2019-10-05 23:26:00 +00:00
return data, nil
}