diff --git a/hbs2-git/hbs2-git-oracle/lib/HBS2/Git/Oracle/Html.hs b/hbs2-git/hbs2-git-oracle/lib/HBS2/Git/Oracle/Html.hs index 6b981b74..d257b552 100644 --- a/hbs2-git/hbs2-git-oracle/lib/HBS2/Git/Oracle/Html.hs +++ b/hbs2-git/hbs2-git-oracle/lib/HBS2/Git/Oracle/Html.hs @@ -23,8 +23,7 @@ import Data.Word import Data.List qualified as List import Data.HashMap.Strict qualified as HM import Data.ByteString.Lazy -import Text.Pandoc -import Text.Pandoc.Error (handleError) +import Text.Pandoc hiding (getPOSIXTime) import Text.InterpolatedString.Perl6 (qc) @@ -61,42 +60,54 @@ onClickCopy :: Text -> Attribute onClickCopy s = hyper_ [qc|on click writeText('{s}') into the navigator's clipboard add .clicked to me wait 2s remove .clicked from me|] -renderEntries :: Monad m => PluginMethod -> [(HashVal, Text, Text, Word64)] -> m ByteString -renderEntries (Method _ kw) items = pure $ renderBS do +renderEntries :: MonadIO m => PluginMethod -> [(HashVal, Text, Text, Word64)] -> m ByteString +renderEntries (Method _ kw) items = do - -- TODO: ugly - let hrefBase = HM.lookup "URL_PREFIX" kw & List.singleton . maybe "/" Text.unpack + now <- liftIO getPOSIXTime <&> fromIntegral . round - wrapped do - main_ do + pure $ renderBS do - section_ do - h1_ "Git repositories" - form_ [class_ "search"] do - input_ [type_ "search", id_ "search"] - button_ [class_ "search"] mempty + -- TODO: ugly + let hrefBase = HM.lookup "URL_PREFIX" kw & List.singleton . maybe "/" Text.unpack + + wrapped do + main_ do + + section_ do + h1_ "Git repositories" + form_ [class_ "search"] do + input_ [type_ "search", id_ "search"] + button_ [class_ "search"] mempty - section_ [id_ "repo-search-results"] do + section_ [id_ "repo-search-results"] do - for_ items $ \(h,n,b,t) -> do + for_ items $ \(h,n,b,t) -> do - let s = if Text.length n > 2 then n else "unnamed" - let refpart = Text.take 8 $ Text.pack $ show $ pretty h - let sref = show $ pretty h - let ref = Text.pack sref + let days = "updated" <+> if d == 0 then "today" else viaShow d <+> "days ago" + where d = ( now - t ) `div` 86400 - let suff = ["repo", sref] + let s = if Text.length n > 2 then n else "unnamed" + let refpart = Text.take 8 $ Text.pack $ show $ pretty h + let sref = show $ pretty h + let ref = Text.pack sref - let url = path (hrefBase <> suff) + let suff = ["repo", sref] - div_ [class_ "repo-list-item"] do - div_ [class_ "repo-info"] do - h2_ [class_ "xclip", onClickCopy ref] $ toHtml (s <> "-" <> refpart) + let url = path (hrefBase <> suff) - p_ $ a_ [href_ url] (toHtml ref) + div_ [class_ "repo-list-item"] do + div_ [class_ "repo-info", style_ "flex: 1; flex-basis: 70%;"] do + + h2_ [class_ "xclip", onClickCopy ref] $ toHtml (s <> "-" <> refpart) + + p_ $ a_ [href_ url] (toHtml ref) + + renderMarkdown b + + div_ [ class_ "attr" ] do + div_ [ class_ "attrname"] (toHtml $ show days) - renderMarkdown b wrapped :: Monad m => HtmlT m a -> HtmlT m a wrapped f = do @@ -142,6 +153,18 @@ renderRepoHtml (Method _ kw) page@(GitRepoPage{..}) = pure $ renderBS $ wrapped repoMenuItem mempty $ a_ [href_ hrefBase] "root" repoMenuItem0 mempty "manifest" + section_ [] do + + div_ [class_ "attr"] do + + let ref = headDef "" [ r | GitLwwRef r <- universeBi page ] + & Text.pack . show . pretty + + div_ [class_ "attrname"] "reference" + + div_ [class_ "attrval", style_ "align: left; width: 20rem;"] do + span_ [class_ "xclip", onClickCopy ref] (toHtml ref) + section_ [id_ "repo-data"] do for_ name' $ \name -> do h1_ (toHtml name) diff --git a/hbs2-git/hbs2-git.cabal b/hbs2-git/hbs2-git.cabal index fd496055..feb3036c 100644 --- a/hbs2-git/hbs2-git.cabal +++ b/hbs2-git/hbs2-git.cabal @@ -92,6 +92,7 @@ common shared-properties , random , vector , unix + , friendly-time library diff --git a/hbs2-peer/app/Browser/Root.hs b/hbs2-peer/app/Browser/Root.hs index a7006cc7..37562b78 100644 --- a/hbs2-peer/app/Browser/Root.hs +++ b/hbs2-peer/app/Browser/Root.hs @@ -229,18 +229,20 @@ div .repo-list-item { .attr { display: flex; + flex-direction: row; + gap: 2rem; margin-bottom: 0.5em; + padding-right: 1rem; } -.attrname, .attribute-value { +.attrname, { flex: 1; margin-right: 0.5em; } .attrval { - text-align: right; - font-weight: bold; - flex-basis: 30%; + text-align: left; + flex-basis: 70%; text-align: right; } @@ -263,19 +265,30 @@ form.search button { } .xclip::after { - content: ""; display: inline-block; - height: 16px; - width: 16px; - vertical-align: top; + content: url('/icon/xclip.svg'); + vertical-align: middle; + width: 24px; + height: 24px; + opacity: 0; + transition: opacity 0.2s; + left: 16px; + position: relative; } .xclip:hover::after { + left: 16px; + position: relative; content: url('/icon/xclip.svg'); - margin-left: 1rem; + vertical-align: middle; height: 24x; width: 24x; - vertical-align: top; + opacity: 1; +} + +.xclip { + /*position: relative;*/ + text-decoration: underline dotted; } .xclip:hover { @@ -284,10 +297,11 @@ form.search button { .clicked:hover::after { content: url('/icon/xclipdone.svg'); - margin-left: 1rem; - height: 24px; + vertical-align: middle; + right: 16px; + height: 24x; width: 24x; - vertical-align: top; + opacity: 1; } nav[role="tab-control"] {