From 288ceae4fdb9e55169aa930075d17022a1f9a3a2 Mon Sep 17 00:00:00 2001 From: nek0 Date: Wed, 30 Sep 2015 03:09:21 +0200 Subject: [PATCH 1/3] added support for feed logos and item enclosures --- yesod-newsfeed/Yesod/AtomFeed.hs | 11 ++++++++++- yesod-newsfeed/Yesod/FeedTypes.hs | 2 ++ yesod-newsfeed/Yesod/RssFeed.hs | 16 +++++++++++++++- 3 files changed, 27 insertions(+), 2 deletions(-) diff --git a/yesod-newsfeed/Yesod/AtomFeed.hs b/yesod-newsfeed/Yesod/AtomFeed.hs index 26b500cf..fa6b48ff 100644 --- a/yesod-newsfeed/Yesod/AtomFeed.hs +++ b/yesod-newsfeed/Yesod/AtomFeed.hs @@ -28,6 +28,7 @@ module Yesod.AtomFeed import Yesod.Core import Yesod.FeedTypes +import Yesod.Common import Text.Hamlet (hamlet) import qualified Data.ByteString.Char8 as S8 import Data.Text (Text) @@ -70,15 +71,23 @@ template Feed {..} render = : Element "id" Map.empty [NodeContent $ render feedLinkHome] : Element "author" Map.empty [NodeElement $ Element "name" Map.empty [NodeContent feedAuthor]] : map (flip entryTemplate render) feedEntries + ++ + case feedLogo of + Nothing -> [] + Just (route, _) -> [Element "logo" Map.empty [NodeContent $ render route]] entryTemplate :: FeedEntry url -> (url -> Text) -> Element -entryTemplate FeedEntry {..} render = Element "entry" Map.empty $ map NodeElement +entryTemplate FeedEntry {..} render = Element "entry" Map.empty $ map NodeElement $ [ Element "id" Map.empty [NodeContent $ render feedEntryLink] , Element "link" (Map.singleton "href" $ render feedEntryLink) [] , Element "updated" Map.empty [NodeContent $ formatW3 feedEntryUpdated] , Element "title" Map.empty [NodeContent feedEntryTitle] , Element "content" (Map.singleton "type" "html") [NodeContent $ toStrict $ renderHtml feedEntryContent] ] + ++ + case feedEntryEnclosure of + Nothing -> [] + Just (route, _, _) -> [Element "link" (Map.fromList [("rel", "enclosure"), ("href", render route)]) []] -- | Generates a link tag in the head of a widget. atomLink :: MonadWidget m diff --git a/yesod-newsfeed/Yesod/FeedTypes.hs b/yesod-newsfeed/Yesod/FeedTypes.hs index 33760360..fdc5d84b 100644 --- a/yesod-newsfeed/Yesod/FeedTypes.hs +++ b/yesod-newsfeed/Yesod/FeedTypes.hs @@ -23,6 +23,7 @@ data Feed url = Feed , feedLanguage :: Text , feedUpdated :: UTCTime + , feedLogo :: Maybe (url, Text) , feedEntries :: [FeedEntry url] } @@ -32,4 +33,5 @@ data FeedEntry url = FeedEntry , feedEntryUpdated :: UTCTime , feedEntryTitle :: Text , feedEntryContent :: Html + , feedEntryEnclosure :: Maybe (url, Int, Text) } diff --git a/yesod-newsfeed/Yesod/RssFeed.hs b/yesod-newsfeed/Yesod/RssFeed.hs index 05155fca..430f23db 100644 --- a/yesod-newsfeed/Yesod/RssFeed.hs +++ b/yesod-newsfeed/Yesod/RssFeed.hs @@ -24,6 +24,7 @@ module Yesod.RssFeed import Yesod.Core import Yesod.FeedTypes +import Yesod.Common import Text.Hamlet (hamlet) import qualified Data.ByteString.Char8 as S8 import Data.Text (Text, pack) @@ -66,15 +67,28 @@ template Feed {..} render = : Element "lastBuildDate" Map.empty [NodeContent $ formatRFC822 feedUpdated] : Element "language" Map.empty [NodeContent feedLanguage] : map (flip entryTemplate render) feedEntries + ++ + case feedLogo of + Nothing -> [] + Just (route, desc) -> [Element "image" Map.empty + [ NodeElement $ Element "url" Map.empty [NodeContent $ render route] + , NodeElement $ Element "title" Map.empty [NodeContent desc] + , NodeElement $ Element "link" Map.empty [NodeContent $ render feedLinkHome] + ] + ] entryTemplate :: FeedEntry url -> (url -> Text) -> Element -entryTemplate FeedEntry {..} render = Element "item" Map.empty $ map NodeElement +entryTemplate FeedEntry {..} render = Element "item" Map.empty $ map NodeElement $ [ Element "title" Map.empty [NodeContent feedEntryTitle] , Element "link" Map.empty [NodeContent $ render feedEntryLink] , Element "guid" Map.empty [NodeContent $ render feedEntryLink] , Element "pubDate" Map.empty [NodeContent $ formatRFC822 feedEntryUpdated] , Element "description" Map.empty [NodeContent $ toStrict $ renderHtml feedEntryContent] ] + ++ + case feedEntryEnclosure of + Nothing -> [] + Just (route, length, mime) -> [Element "enclosure" (Map.fromList [("type", mime), ("length", pack $ show length), ("url", render route)]) []] -- | Generates a link tag in the head of a widget. rssLink :: MonadWidget m From f7dfeee9b137795975dfeae251e8669acd64be29 Mon Sep 17 00:00:00 2001 From: nek0 Date: Wed, 30 Sep 2015 03:09:21 +0200 Subject: [PATCH 2/3] added support for feed logos and item enclosures forgot a file --- yesod-newsfeed/Yesod/AtomFeed.hs | 11 ++++++++++- yesod-newsfeed/Yesod/Common.hs | 9 +++++++++ yesod-newsfeed/Yesod/FeedTypes.hs | 2 ++ yesod-newsfeed/Yesod/RssFeed.hs | 16 +++++++++++++++- 4 files changed, 36 insertions(+), 2 deletions(-) create mode 100644 yesod-newsfeed/Yesod/Common.hs diff --git a/yesod-newsfeed/Yesod/AtomFeed.hs b/yesod-newsfeed/Yesod/AtomFeed.hs index 26b500cf..fa6b48ff 100644 --- a/yesod-newsfeed/Yesod/AtomFeed.hs +++ b/yesod-newsfeed/Yesod/AtomFeed.hs @@ -28,6 +28,7 @@ module Yesod.AtomFeed import Yesod.Core import Yesod.FeedTypes +import Yesod.Common import Text.Hamlet (hamlet) import qualified Data.ByteString.Char8 as S8 import Data.Text (Text) @@ -70,15 +71,23 @@ template Feed {..} render = : Element "id" Map.empty [NodeContent $ render feedLinkHome] : Element "author" Map.empty [NodeElement $ Element "name" Map.empty [NodeContent feedAuthor]] : map (flip entryTemplate render) feedEntries + ++ + case feedLogo of + Nothing -> [] + Just (route, _) -> [Element "logo" Map.empty [NodeContent $ render route]] entryTemplate :: FeedEntry url -> (url -> Text) -> Element -entryTemplate FeedEntry {..} render = Element "entry" Map.empty $ map NodeElement +entryTemplate FeedEntry {..} render = Element "entry" Map.empty $ map NodeElement $ [ Element "id" Map.empty [NodeContent $ render feedEntryLink] , Element "link" (Map.singleton "href" $ render feedEntryLink) [] , Element "updated" Map.empty [NodeContent $ formatW3 feedEntryUpdated] , Element "title" Map.empty [NodeContent feedEntryTitle] , Element "content" (Map.singleton "type" "html") [NodeContent $ toStrict $ renderHtml feedEntryContent] ] + ++ + case feedEntryEnclosure of + Nothing -> [] + Just (route, _, _) -> [Element "link" (Map.fromList [("rel", "enclosure"), ("href", render route)]) []] -- | Generates a link tag in the head of a widget. atomLink :: MonadWidget m diff --git a/yesod-newsfeed/Yesod/Common.hs b/yesod-newsfeed/Yesod/Common.hs new file mode 100644 index 00000000..148fc7f3 --- /dev/null +++ b/yesod-newsfeed/Yesod/Common.hs @@ -0,0 +1,9 @@ +module Yesod.Common + ( removeItem + ) where + +removeItem :: Eq a => a -> [a] -> [a] +removeItem _ [] = [] +removeItem r (x:xs) + | r == x = removeItem r xs + | otherwise = x : removeItem r xs diff --git a/yesod-newsfeed/Yesod/FeedTypes.hs b/yesod-newsfeed/Yesod/FeedTypes.hs index 33760360..fdc5d84b 100644 --- a/yesod-newsfeed/Yesod/FeedTypes.hs +++ b/yesod-newsfeed/Yesod/FeedTypes.hs @@ -23,6 +23,7 @@ data Feed url = Feed , feedLanguage :: Text , feedUpdated :: UTCTime + , feedLogo :: Maybe (url, Text) , feedEntries :: [FeedEntry url] } @@ -32,4 +33,5 @@ data FeedEntry url = FeedEntry , feedEntryUpdated :: UTCTime , feedEntryTitle :: Text , feedEntryContent :: Html + , feedEntryEnclosure :: Maybe (url, Int, Text) } diff --git a/yesod-newsfeed/Yesod/RssFeed.hs b/yesod-newsfeed/Yesod/RssFeed.hs index 05155fca..430f23db 100644 --- a/yesod-newsfeed/Yesod/RssFeed.hs +++ b/yesod-newsfeed/Yesod/RssFeed.hs @@ -24,6 +24,7 @@ module Yesod.RssFeed import Yesod.Core import Yesod.FeedTypes +import Yesod.Common import Text.Hamlet (hamlet) import qualified Data.ByteString.Char8 as S8 import Data.Text (Text, pack) @@ -66,15 +67,28 @@ template Feed {..} render = : Element "lastBuildDate" Map.empty [NodeContent $ formatRFC822 feedUpdated] : Element "language" Map.empty [NodeContent feedLanguage] : map (flip entryTemplate render) feedEntries + ++ + case feedLogo of + Nothing -> [] + Just (route, desc) -> [Element "image" Map.empty + [ NodeElement $ Element "url" Map.empty [NodeContent $ render route] + , NodeElement $ Element "title" Map.empty [NodeContent desc] + , NodeElement $ Element "link" Map.empty [NodeContent $ render feedLinkHome] + ] + ] entryTemplate :: FeedEntry url -> (url -> Text) -> Element -entryTemplate FeedEntry {..} render = Element "item" Map.empty $ map NodeElement +entryTemplate FeedEntry {..} render = Element "item" Map.empty $ map NodeElement $ [ Element "title" Map.empty [NodeContent feedEntryTitle] , Element "link" Map.empty [NodeContent $ render feedEntryLink] , Element "guid" Map.empty [NodeContent $ render feedEntryLink] , Element "pubDate" Map.empty [NodeContent $ formatRFC822 feedEntryUpdated] , Element "description" Map.empty [NodeContent $ toStrict $ renderHtml feedEntryContent] ] + ++ + case feedEntryEnclosure of + Nothing -> [] + Just (route, length, mime) -> [Element "enclosure" (Map.fromList [("type", mime), ("length", pack $ show length), ("url", render route)]) []] -- | Generates a link tag in the head of a widget. rssLink :: MonadWidget m From fea89a933fcd74ade1526834d86790a2a43653ce Mon Sep 17 00:00:00 2001 From: nek0 Date: Wed, 30 Sep 2015 15:24:56 +0200 Subject: [PATCH 3/3] added Changelog and cleaned Yesod/Commen remnants --- yesod-newsfeed/ChangeLog.md | 23 +++++++++++++++++++++++ yesod-newsfeed/Yesod/AtomFeed.hs | 1 - yesod-newsfeed/Yesod/Common.hs | 9 --------- yesod-newsfeed/Yesod/RssFeed.hs | 1 - 4 files changed, 23 insertions(+), 11 deletions(-) delete mode 100644 yesod-newsfeed/Yesod/Common.hs diff --git a/yesod-newsfeed/ChangeLog.md b/yesod-newsfeed/ChangeLog.md index e69de29b..e2d022ec 100644 --- a/yesod-newsfeed/ChangeLog.md +++ b/yesod-newsfeed/ChangeLog.md @@ -0,0 +1,23 @@ +#Changelog + +##2015-09-30: + +###Yesod/FeedTypes.hs + +* added `feedLogo` field to `Feed` type as `Maybe (url, Text)`. Should this field result in `Nothing`, nothing will be added to the feed. + * `url`: Defines the URL to the logi image + * `Text`: Is the description of the logo image. Will only be used for RSS feeds +* added `feedEntryEnclosure` field to `FeedEntry` type as `Maybe (url, Int, Text)`. Should this field result in `Nothing`, no data will be added to the feed entry. + * `url`: Defines the URL to the enclosed data + * `Int`: Is the content size in bytes. RSS requires this. + * `Text`: Is the MIME-type of the enclosed file. RSS requires this + +###Yesod/AtomFeed.hs + +* modified `template` function to append an `url` tag at the end of the feed, when the provided `feedLogo` is not `Nothing`. This might look awkward, since it will be appended *after* the entries. +* modified `entryTemplate` to append an `` to the feed entry. + +###Yesod/RssFeed.hs + +* modified `template` function to append an `` tag with its three required components ``, `` and `<link>`. `<url>` and `<title>` will be filled from `feedLogo`, `<link>` will be `feedLinkHome`. +* modified `entryTemplate` function to append an `<enclosure type=mime length=length url=url>` to the feed entry diff --git a/yesod-newsfeed/Yesod/AtomFeed.hs b/yesod-newsfeed/Yesod/AtomFeed.hs index fa6b48ff..af6a9ae7 100644 --- a/yesod-newsfeed/Yesod/AtomFeed.hs +++ b/yesod-newsfeed/Yesod/AtomFeed.hs @@ -28,7 +28,6 @@ module Yesod.AtomFeed import Yesod.Core import Yesod.FeedTypes -import Yesod.Common import Text.Hamlet (hamlet) import qualified Data.ByteString.Char8 as S8 import Data.Text (Text) diff --git a/yesod-newsfeed/Yesod/Common.hs b/yesod-newsfeed/Yesod/Common.hs deleted file mode 100644 index 148fc7f3..00000000 --- a/yesod-newsfeed/Yesod/Common.hs +++ /dev/null @@ -1,9 +0,0 @@ -module Yesod.Common - ( removeItem - ) where - -removeItem :: Eq a => a -> [a] -> [a] -removeItem _ [] = [] -removeItem r (x:xs) - | r == x = removeItem r xs - | otherwise = x : removeItem r xs diff --git a/yesod-newsfeed/Yesod/RssFeed.hs b/yesod-newsfeed/Yesod/RssFeed.hs index 430f23db..7963276b 100644 --- a/yesod-newsfeed/Yesod/RssFeed.hs +++ b/yesod-newsfeed/Yesod/RssFeed.hs @@ -24,7 +24,6 @@ module Yesod.RssFeed import Yesod.Core import Yesod.FeedTypes -import Yesod.Common import Text.Hamlet (hamlet) import qualified Data.ByteString.Char8 as S8 import Data.Text (Text, pack)