Files
epuppy/pkg/epub/book.go

100 lines
1.8 KiB
Go
Raw Permalink Normal View History

2025-10-15 00:54:19 +02:00
package epub
import (
"archive/zip"
"encoding/xml"
"fmt"
"io"
"log"
2025-10-15 00:54:19 +02:00
"path"
)
// a section in the book
type Section struct {
File, Title, MediaType string
}
2025-10-15 00:54:19 +02:00
// Book epub book
type Book struct {
2025-10-19 20:39:04 +02:00
Ncx Ncx `json:"ncx"`
Opf Opf `json:"opf"`
Container Container `json:"-"`
Mimetype string `json:"-"`
Content []Content
fd *zip.ReadCloser
CoverImage []byte
CoverFile string
CoverMediaType string
Sections []Section
dumpxml bool
2025-10-15 00:54:19 +02:00
}
// Open open resource file
func (p *Book) Open(n string) (io.ReadCloser, error) {
return p.open(p.filename(n))
}
// Files list resource files
func (p *Book) Files() []string {
var fns []string
for _, f := range p.fd.File {
fns = append(fns, f.Name)
}
return fns
}
// -----------------------------------------------------------------------------
func (p *Book) filename(n string) string {
return path.Join(path.Dir(p.Container.Rootfile.Path), n)
}
func (p *Book) readXML(n string, v interface{}) error {
fd, err := p.open(n)
if err != nil {
return nil
}
defer func() {
if err := fd.Close(); err != nil {
log.Fatal(err)
}
}()
2025-10-15 00:54:19 +02:00
dec := xml.NewDecoder(fd)
if err := dec.Decode(v); err != nil {
return fmt.Errorf("XML decoder error %w", err)
}
return nil
2025-10-15 00:54:19 +02:00
}
func (p *Book) readBytes(n string) ([]byte, error) {
fd, err := p.open(n)
if err != nil {
return nil, nil
}
defer func() {
if err := fd.Close(); err != nil {
log.Fatal(err)
}
}()
2025-10-15 00:54:19 +02:00
data, err := io.ReadAll(fd)
if err != nil {
return nil, fmt.Errorf("failed to read contents from %s %w", n, err)
}
2025-10-15 00:54:19 +02:00
return data, nil
2025-10-15 00:54:19 +02:00
}
func (p *Book) open(n string) (io.ReadCloser, error) {
for _, f := range p.fd.File {
if f.Name == n {
return f.Open()
}
}
2025-10-15 00:54:19 +02:00
return nil, fmt.Errorf("file %s not exist", n)
}