introduce outbox page

This commit is contained in:
me 2024-12-17 10:46:59 +02:00
parent a36f3a2bed
commit a0bdd57e83
3 changed files with 60 additions and 8 deletions

View file

@ -41,8 +41,8 @@ mkFediApp :: IO Twain.Application
mkFediApp = do
detailsFile <- lookupEnv "FEDI_DETAILS"
<&> maybe (error "missing FEDI_DETAILS") id
details <- A.decodeFileStrict detailsFile
<&> maybe (error $ "could not read file '" <> detailsFile <> "'.") id
details <- A.eitherDecodeFileStrict detailsFile
<&> either (\err -> error $ "could not read file '" <> detailsFile <> "'.\n" <> err) id
pure $ foldr ($)
(Twain.notFound $ Twain.send $ Twain.text "Error: not found.")

View file

@ -1,5 +1,6 @@
module Fedi.Activity where
import Data.Maybe (listToMaybe)
import Data.Aeson qualified as A
import Data.Text qualified as T
import Fedi.Types
@ -35,11 +36,18 @@ type Following = [Actor]
type Inbox = Collection Ordered Activity
type Outbox = Collection Unordered Activity
type OutboxPage = Collection Unordered Activity
type OutboxPage = OrderedCollectionPage Activity
data Ordered
data Unordered
data OrderedCollectionPage a
= OrderedCollectionPage
{ id :: Url
, partOf :: Url
, orderedItems :: [a]
}
data Collection order a
= Collection
{ summary :: String
@ -87,6 +95,8 @@ instance A.ToJSON a => A.ToJSON (Collection Ordered a) where
, "summary" A..= collection.summary
, "totalItems" A..= length collection.items
, "orderedItems" A..= collection.items
, "first" A..= listToMaybe (take 1 collection.items)
, "last" A..= listToMaybe (take 1 $ reverse collection.items)
]
instance A.ToJSON a => A.ToJSON (Collection Unordered a) where
@ -99,4 +109,17 @@ instance A.ToJSON a => A.ToJSON (Collection Unordered a) where
, "summary" A..= collection.summary
, "totalItems" A..= length collection.items
, "items" A..= collection.items
, "first" A..= listToMaybe (take 1 collection.items)
, "last" A..= listToMaybe (take 1 $ reverse collection.items)
]
instance A.ToJSON a => A.ToJSON (OrderedCollectionPage a) where
toJSON collection =
A.object
[ "@context" A..=
[ "https://www.w3.org/ns/activitystreams" :: String
]
, "type" A..= ("OrderedCollectionPage" :: String)
, "partOf" A..= collection.partOf
, "orderedItems" A..= collection.orderedItems
]

View file

@ -18,7 +18,7 @@ routes details =
handleUser details
, Twain.get (matchOutbox details) do
handleOutbox details
handleOutbox details []
, Twain.get matchWebfinger do
handleWebfinger details
@ -61,7 +61,36 @@ matchOutbox :: UserDetails -> Twain.PathPattern
matchOutbox details =
fromString ("/" <> details.username <> "/outbox")
handleOutbox :: UserDetails -> Twain.ResponderM b
handleOutbox details = do
let content = Collection { summary = details.username <> "'s notes", items = [] } :: Outbox
Twain.send $ jsonLD (A.encode content)
handleOutbox :: UserDetails -> [Activity] -> Twain.ResponderM b
handleOutbox details items = do
isPage <- Twain.queryParamMaybe "page"
let
outboxUrl =
"https://"
<> details.domain
<> "/"
<> details.username
<> "/outbox"
let
response =
case isPage of
Just True ->
let
content :: OutboxPage
content =
OrderedCollectionPage
{ id = outboxUrl <> "?page=true"
, partOf = outboxUrl
, orderedItems = items
}
in A.encode content
_ ->
let
content :: Outbox
content =
Collection
{ summary = details.username <> "'s notes"
, items = items
}
in A.encode content
Twain.send $ jsonLD response