her.esy.fun/Shakefile.hs

139 lines
5.4 KiB
Haskell
Raw Normal View History

2020-05-25 20:30:22 +00:00
{-# LANGUAGE OverloadedStrings #-}
2020-06-22 07:39:44 +00:00
{-# LANGUAGE NoImplicitPrelude #-}
2020-06-22 09:44:11 +00:00
import Protolude
2020-05-25 20:30:22 +00:00
2020-06-22 09:44:11 +00:00
import Development.Shake
import Development.Shake.Command
import Development.Shake.FilePath
import Development.Shake.Util
2020-06-14 11:19:13 +00:00
2020-06-22 09:44:11 +00:00
import Control.Monad.Fail
import Data.Default ( Default(def) )
import qualified Data.Set as Set
import qualified Data.Text as T
import Text.Pandoc.Class ( PandocPure
, PandocMonad
)
import qualified Text.Pandoc.Class as Pandoc
import Text.Pandoc.Definition ( Pandoc(..)
, Block(..)
, Inline
, nullMeta
, docTitle
, docDate
, docAuthors
)
import Text.Pandoc.Extensions ( getDefaultExtensions )
import Text.Pandoc.Options ( ReaderOptions(..)
, TrackChanges(RejectChanges)
)
import qualified Text.Pandoc.Readers as Readers
import qualified Text.Pandoc.Writers as Writers
2020-05-25 20:28:06 +00:00
main :: IO ()
main = do
2020-06-22 09:44:11 +00:00
let
shOpts = shakeOptions { shakeVerbosity = Chatty
, shakeLintInside = ["\\"]
}
shakeArgs shOpts buildRules
2020-05-25 20:28:06 +00:00
2020-06-22 07:39:44 +00:00
data BlogPost =
BlogPost { postTitle :: T.Text
, postDate :: T.Text
, postAuthors :: [T.Text]
, postUrl :: FilePath
2020-06-22 09:44:11 +00:00
, postBody :: Pandoc
2020-06-22 07:39:44 +00:00
}
inlineToText :: PandocMonad m => [Inline] -> m T.Text
inlineToText inline =
2020-06-22 09:44:11 +00:00
Writers.writeAsciiDoc def (Pandoc nullMeta [Plain inline])
getBlogpostFromMetas
:: (MonadIO m, MonadFail m) => [Char] -> Pandoc -> m BlogPost
getBlogpostFromMetas path pandoc@(Pandoc meta _) = do
eitherBlogpost <- liftIO $ Pandoc.runIO $ do
title <- inlineToText $ docTitle meta
date <- inlineToText $ docDate meta
authors <- mapM inlineToText $ docAuthors meta
-- let url = dropExtension path
return $ BlogPost title date authors path pandoc
case eitherBlogpost of
Left _ -> fail "BAD"
Right bp -> return bp
sortByPostDate :: [BlogPost] -> [BlogPost]
sortByPostDate =
sortBy (\a b -> compare (Down (postDate a)) (Down (postDate b)))
2020-06-22 07:39:44 +00:00
2020-06-14 11:19:13 +00:00
buildRules :: Rules ()
2020-05-25 20:28:06 +00:00
buildRules = do
2020-06-22 09:44:11 +00:00
let siteDir = "_site"
optimDir = "_optim"
build = (</>) siteDir
phony "clean" $ do
putInfo "Cleaning files in _site and _optim"
removeFilesAfter siteDir ["//*"]
removeFilesAfter optimDir ["//*"]
getPost <- newCache $ \path -> do
fileContent <- readFile' path
eitherResult <- liftIO $ Pandoc.runIO $ Readers.readOrg
def
(T.pack fileContent)
case eitherResult of
Left _ -> fail "BAD"
Right pandoc -> getBlogpostFromMetas path pandoc
getPosts <-
newCache
$ \() -> mapM getPost =<< getDirectoryFiles
""
["src/posts//*.org"]
let -- hsDeps = return ["AsciiArt.hs", "Index.hs", "Rot13.hs"]
cssDeps = map (siteDir </>)
<$> getDirectoryFiles "" ["src/css/*.css"]
build "index.html" %> \out -> do
-- hs <- hsDeps
css <- cssDeps
posts <- getPosts ()
need $ css <> map postUrl posts
-- <> [build "atom.xml"]
let titles = map postTitle posts
writeFile' out (mconcat (map T.unpack titles))
build "src/css/*.css" %> \out -> copyFile' (dropDirectory1 out) out
2020-06-22 07:39:44 +00:00
2020-06-14 11:19:13 +00:00
2020-06-22 07:39:44 +00:00
-- "_site//*.html" %> buildPost
2020-06-14 11:19:13 +00:00
-- buildPosts
-- allPosts <- buildPosts
-- buildIndex allPosts
-- buildFeed allPosts
-- copyStaticFiles
2020-06-22 07:39:44 +00:00
-- data Post = Post { postTitle :: T.Text
-- , postAuthor :: T.Text
-- , postDate :: T.Text
-- }
--
-- defaultReaderOpts t =
-- def { readerExtensions = getDefaultExtensions t
-- , readerStandalone = True }
--
-- orgToHTML :: T.Text -> PandocPure T.Text
-- orgToHTML txt = Readers.readOrg (defaultReaderOpts "org") txt
-- >>= Writers.writeHtml5String def
--
-- -- | Load a post, process metadata, write it to output, then return the post object
-- -- Detects changes to either post content or template
-- buildPost :: FilePath -> Action ()
-- buildPost out = do
-- let org = "src/" <> (dropDirectory1 $ out -<.> "org")
-- liftIO . putStrLn $ "Rebuilding post: " <> out
-- postContent <- readFile' org
-- -- load post content and metadata as JSON blob
-- let pandocReturn = Pandoc.runPure $ orgToHTML . T.pack $ postContent
-- case pandocReturn of
-- Left _ -> putError "BAD"
-- Right outData -> writeFile' out (T.unpack outData)