Add parsing and associated modules
This commit is contained in:
parent
0ac0ae8d61
commit
0f9a03822e
2 changed files with 36 additions and 3 deletions
|
|
@ -3,6 +3,14 @@ module EpubParser where
|
||||||
import Codec.Archive.Zip (toArchive, findEntryByPath, fromEntry, Archive)
|
import Codec.Archive.Zip (toArchive, findEntryByPath, fromEntry, Archive)
|
||||||
import qualified Data.ByteString.Lazy as BL
|
import qualified Data.ByteString.Lazy as BL
|
||||||
import qualified Data.ByteString.Lazy.Char8 as C8
|
import qualified Data.ByteString.Lazy.Char8 as C8
|
||||||
|
import Text.HTML.TagSoup (parseTags, fromAttrib, (~==), Tag, innerText, sections)
|
||||||
|
import System.FilePath (takeDirectory)
|
||||||
|
|
||||||
|
data BookInfo = BookInfo
|
||||||
|
{ title :: String
|
||||||
|
, author :: String
|
||||||
|
} deriving (Show)
|
||||||
|
|
||||||
|
|
||||||
openEpub :: FilePath -> IO (Either String Archive)
|
openEpub :: FilePath -> IO (Either String Archive)
|
||||||
openEpub path = toArchive <$> BL.readFile path >>= \archive -> maybe (pure $ Left "Error reading file") (\entry -> if fromEntry entry == C8.pack "application/epub+zip" then pure (Right archive) else pure (Left "Wrong mimetype")) (findEntryByPath "mimetype" archive)
|
openEpub path = toArchive <$> BL.readFile path >>= \archive -> maybe (pure $ Left "Error reading file") (\entry -> if fromEntry entry == C8.pack "application/epub+zip" then pure (Right archive) else pure (Left "Wrong mimetype")) (findEntryByPath "mimetype" archive)
|
||||||
|
|
@ -10,5 +18,29 @@ openEpub path = toArchive <$> BL.readFile path >>= \archive -> maybe (pure $ Lef
|
||||||
getOpfPath :: Archive -> Maybe FilePath
|
getOpfPath :: Archive -> Maybe FilePath
|
||||||
getOpfPath archive = do
|
getOpfPath archive = do
|
||||||
entry <- findEntryByPath "META-INF/container.xml" archive
|
entry <- findEntryByPath "META-INF/container.xml" archive
|
||||||
|
let content = C8.unpack (fromEntry entry)
|
||||||
|
|
||||||
return "OEBPS/content.opf"
|
let tags = parseTags content
|
||||||
|
|
||||||
|
let rootfileTags = filter (~== "<rootfile>") tags
|
||||||
|
|
||||||
|
-- If we found at least one, get the "full-path" attribute
|
||||||
|
case rootfileTags of
|
||||||
|
(t:_) -> Just (fromAttrib "full-path" t)
|
||||||
|
[] -> Nothing
|
||||||
|
|
||||||
|
getRootPrefix :: FilePath -> FilePath
|
||||||
|
getRootPrefix path =
|
||||||
|
let dir = takeDirectory path
|
||||||
|
in if dir == "."
|
||||||
|
then ""
|
||||||
|
else dir ++ "/"
|
||||||
|
|
||||||
|
tagify :: String -> String
|
||||||
|
tagify item = "<" ++ item ++ ">"
|
||||||
|
|
||||||
|
getTagText :: String -> [Tag String] -> String
|
||||||
|
getTagText tagName tags =
|
||||||
|
case sections (~== tagify tagName) tags of
|
||||||
|
(x:_) -> innerText x
|
||||||
|
[] -> ""
|
||||||
|
|
|
||||||
|
|
@ -62,8 +62,9 @@ executable svitak
|
||||||
build-depends: base ^>=4.21.0.0,
|
build-depends: base ^>=4.21.0.0,
|
||||||
bytestring >= 0.12.2.0,
|
bytestring >= 0.12.2.0,
|
||||||
epub-metadata >=5.4,
|
epub-metadata >=5.4,
|
||||||
zip-archive >= 0.4.3.2,
|
filepath >= 1.5.4.0,
|
||||||
tagsoup
|
tagsoup,
|
||||||
|
zip-archive >= 0.4.3.2
|
||||||
|
|
||||||
hs-source-dirs: app
|
hs-source-dirs: app
|
||||||
default-language: Haskell2010
|
default-language: Haskell2010
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue