diff --git a/js/domRenderer.js b/js/domRenderer.js index eff7aea..ec4cba5 100644 --- a/js/domRenderer.js +++ b/js/domRenderer.js @@ -37,15 +37,15 @@ function DomRenderer(modules) { }); } - function article(url, markdown, limit) { - var headerEnd = markdown.search(/\n\n/); - var header = getDiv(markdown.slice(0, headerEnd)); - var lines = markdown.slice(headerEnd+2).split(/\n/); + function article(key, markdown, limit) { + var url = ["", blog.path.articlesPath, key + (limit != undefined ? '.html' : '.md')].join('/'); + var lines = markdown.split(/\n/).slice(blog.articles[key].bodyOffset); var div = getDiv(lines.slice(0, limit).join('\n')); - var title = header.getElementsByTagName('h1')[0]; - return title == undefined ? null : modules.dom.make('article', {}, [ + return modules.dom.make('article', {}, [ modules.dom.make('header', {}, [ - modules.dom.make('a', {class: (limit != undefined ? 'navigation' : []), href: url}, [title]) + modules.dom.make('a', {class: (limit != undefined ? 'navigation' : []), href: url}, [ + modules.dom.make('h1', {innerText: blog.articles[key].title}) + ]) ]), div ]); diff --git a/js/navigation.js b/js/navigation.js index 3c18dcc..9d71b52 100644 --- a/js/navigation.js +++ b/js/navigation.js @@ -1,5 +1,6 @@ function Navigation(modules) { - var articles = modules.cache.make(function(url) { + var articles = modules.cache.make(function(key) { + var url = ["", blog.path.articlesPath, key + '.md'].join('/'); return modules.async.bind( modules.async.http({method: 'GET', url: url}), function(queryResult) { @@ -42,30 +43,29 @@ function Navigation(modules) { var path = url.split("/").slice(1); if(blog.tags[path[0]] != undefined) { show(getArticlesList(path[0], path[1] == "all.html")); - } else if(path[0].length > 0 && !path[0].match(/\.html$/)) { - show(getArticle(url.replace(/html$/, 'md'))); + } else if(path[0] == blog.path.articlesPath) { + show(getArticle(path[1].replace(/\.html$/, ''))); } else { show(getArticlesList(null, path[0] == "all.html")); } } - function getArticle(url) { + function getArticle(key) { return modules.async.bind( - articles.get(url), + articles.get(key), modules.async.map( - function(contents) {return [modules.domRenderer.article(url, contents)];} + function(contents) {return [modules.domRenderer.article(key, contents)];} ) ); } - function preview(articleId) { - var source = blog.articles[articleId].source; + function preview(key) { return modules.async.bind( - articles.get(source), + articles.get(key), function(contents) { return modules.async.wrap( modules.domRenderer.article( - source.replace(/md$/, 'html'), + key, contents, blog.skin.previewLinesCount ) diff --git a/src/Article.hs b/src/Article.hs index d8d9fe7..0507102 100644 --- a/src/Article.hs +++ b/src/Article.hs @@ -3,7 +3,7 @@ module Article ( Article(..) , at - , key + , getKey , preview , titleP ) where @@ -27,7 +27,7 @@ import Text.ParserCombinators.Parsec ( type Metadata = Map String String data Article = Article { - urlPath :: FilePath + key :: String , title :: String , metadata :: Metadata , bodyOffset :: Int @@ -87,9 +87,9 @@ at filePath = do fmap build . parse articleP filePath <$> readFile filePath where makeArticle metaFilter (title, metadata, bodyOffset, body) = ( - key filePath + getKey filePath , Article { - urlPath = dropExtension filePath + key = getKey filePath , title , metadata = metaFilter metadata , bodyOffset @@ -97,8 +97,8 @@ at filePath = do } ) -key :: FilePath -> String -key = dropExtension . takeFileName +getKey :: FilePath -> String +getKey = dropExtension . takeFileName preview :: Int -> Article -> Article preview linesCount article = article {body = take linesCount $ body article} diff --git a/src/Blog.hs b/src/Blog.hs index 9a0d986..b17ebd0 100644 --- a/src/Blog.hs +++ b/src/Blog.hs @@ -11,7 +11,7 @@ module Blog ( import Arguments (Arguments) import qualified Arguments (name) import Article (Article) -import qualified Article (at, key) +import qualified Article (at, getKey) import Blog.Path (Path(..)) import qualified Blog.Path as Path (build) import Blog.Skin (Skin(..)) @@ -57,7 +57,7 @@ tagged collection path = do keys <- forM links $ \link -> do fileExists <- doesFileExist link return $ if fileExists - then let articleKey = Article.key link in + then let articleKey = Article.getKey link in if Map.member articleKey collection then Set.singleton articleKey else Set.empty else Set.empty return (takeFileName path, foldl Set.union Set.empty keys) diff --git a/src/Blog/Skin.hs b/src/Blog/Skin.hs index ecece72..3f7fcf4 100644 --- a/src/Blog/Skin.hs +++ b/src/Blog/Skin.hs @@ -24,7 +24,7 @@ data Skin = Skin { findFavicon :: Arguments -> IO (Maybe FilePath) findFavicon arguments = case Arguments.favicon arguments of - Just path -> return $ Just path + Just path -> return . Just $ absolute path _ -> fmap absolute . listToMaybe <$> filterM doesFileExist pathsToCheck where directories = [".", "image", "images", "pictures", "skin", "static"] diff --git a/src/Dom.hs b/src/Dom.hs index d12f373..10009f4 100644 --- a/src/Dom.hs +++ b/src/Dom.hs @@ -7,7 +7,7 @@ module Dom ( import Article (Article(..)) import qualified Article (preview) import ArticlesList (ArticlesList(..), otherLink, otherUrl, pageTitle) -import Blog (Blog(..), Skin(..)) +import Blog (Blog(..), Path(..), Skin(..)) import qualified Blog (get) import Control.Monad.Reader (ReaderT) import qualified Data.Map as Map (keys) @@ -46,10 +46,11 @@ instance Page ArticlesList where ) article :: Bool -> Article -> HtmlGenerator () -article raw (Article {body, title, urlPath}) = +article raw (Article {key, body, title}) = do + url <- ("/" ) . ( key <.> extension) <$> (Blog.get $path.$articlesPath) article_ (do header_ (do - aElem [href_ . pack $ "/" urlPath <.> extension] . h1_ $ toHtml title + aElem [href_ . pack $ url] . h1_ $ toHtml title ) pre_ . toHtml $ unlines body ) diff --git a/src/HTML.hs b/src/HTML.hs index 4fa789d..8a35c9e 100644 --- a/src/HTML.hs +++ b/src/HTML.hs @@ -58,9 +58,9 @@ articlesLists (Collection {articlesFeatured, basePath, tag}) = do generateArticles :: [Article] -> ReaderT Blog IO () generateArticles = mapM_ $ \article -> do - filePath <- ( urlPath article <.> "html") <$> (Blog.get $path.$root) + baseDir <- () <$> (Blog.get $path.$root) <*> (Blog.get $path.$articlesPath) (renderTextT $ page article) - >>= liftIO . TextIO.writeFile filePath + >>= liftIO . TextIO.writeFile (baseDir key article <.> "html") generateCollection :: Collection -> ReaderT Blog IO () generateCollection (Collection {articlesFeatured = []}) = return () diff --git a/src/JSON.hs b/src/JSON.hs index 9b188d8..9ac9fb5 100644 --- a/src/JSON.hs +++ b/src/JSON.hs @@ -14,12 +14,10 @@ import Data.ByteString.Lazy (ByteString) import Data.Map (Map, mapWithKey) import qualified Data.Map as Map (filter, keys) import qualified Data.Set as Set (elems, member) -import System.FilePath.Posix ((), (<.>)) import GHC.Generics data ArticleExport = ArticleExport { - source :: String - , title :: String + title :: String , bodyOffset :: Int , metadata :: Map String String , tagged :: [String] @@ -56,8 +54,7 @@ instance ToJSON BlogDB where export :: Blog -> String -> Article -> ArticleExport export blog key article = ArticleExport { - source = "/" Article.urlPath article <.> "md" - , title = Article.title article + title = Article.title article , bodyOffset = Article.bodyOffset article , metadata = Article.metadata article , tagged = Map.keys . Map.filter (Set.member key) $ Blog.tags blog diff --git a/src/TODO b/src/TODO new file mode 100644 index 0000000..6bbcdea --- /dev/null +++ b/src/TODO @@ -0,0 +1,3 @@ +pre { + white-space: pre-wrap; +}