Start of implementation of wireframe

This commit is contained in:
Chris Done 2014-06-01 13:35:10 +02:00
parent 841c9f5c81
commit 4814d994dc
13 changed files with 141 additions and 78 deletions

View File

@ -39,6 +39,7 @@ import qualified Echo
-- Import all relevant handler modules here.
-- Don't forget to add new modules to your cabal file!
import Handler.Home
import Handler.Snapshots
import Handler.Profile
import Handler.Email
import Handler.ResetToken
@ -152,7 +153,7 @@ makeFoundation useEcho conf = do
(messageLoggerSource foundation logger)
-- Start the cabal file loader
void $ forkIO $ forever $ flip runLoggingT (messageLoggerSource foundation logger) $ do
{-void $ forkIO $ forever $ flip runLoggingT (messageLoggerSource foundation logger) $ do
$logInfoS "CLEANUP" "Cleaning up /tmp"
now <- liftIO getCurrentTime
runResourceT $ sourceDirectory "/tmp" $$ mapM_C (cleanupTemp now)
@ -180,8 +181,7 @@ makeFoundation useEcho conf = do
case eres of
Left e -> $logError $ tshow e
Right () -> return ()
liftIO $ threadDelay $ 30 * 60 * 1000000
liftIO $ threadDelay $ 30 * 60 * 1000000 -}
return foundation
cleanupTemp :: UTCTime -> FilePath -> ResourceT (LoggingT IO) ()

View File

@ -87,6 +87,7 @@ instance Yesod App where
-- value passed to hamletToRepHtml cannot be a widget, this allows
-- you to use normal widget features in default-layout.
cur <- getCurrentRoute
pc <- widgetToPageContent $ do
$(combineStylesheets 'StaticR
[ css_normalize_css

29
Handler/Snapshots.hs Normal file
View File

@ -0,0 +1,29 @@
{-# LANGUAGE TupleSections, OverloadedStrings #-}
module Handler.Snapshots where
import Import
import qualified Database.Esqueleto as E
-- This is a handler function for the GET request method on the HomeR
-- resource pattern. All of your resource patterns are defined in
-- config/routes
--
-- The majority of the code you will write in Yesod lives in these handler
-- functions. You can spread them across multiple files if you are so
-- inclined, or create a single monolithic file.
getAllSnapshotsR :: Handler Html
getAllSnapshotsR = do
stackages <- runDB $ E.select $ E.from $ \(stackage `E.InnerJoin` user) -> do
E.on (stackage E.^. StackageUser E.==. user E.^. UserId)
E.orderBy [E.desc $ stackage E.^. StackageUploaded]
return
( stackage E.^. StackageIdent
, stackage E.^. StackageTitle
, stackage E.^. StackageUploaded
, user E.^. UserDisplay
, user E.^. UserHandle
)
defaultLayout $ do
setTitle "Stackage Server"
$(widgetFile "all-snapshots")

View File

@ -5,6 +5,7 @@
/robots.txt RobotsR GET
/ HomeR GET
/snapshots AllSnapshotsR GET
/profile ProfileR GET PUT
/email/#EmailId EmailR DELETE
/reset-token ResetTokenR POST

View File

@ -25,6 +25,7 @@ library
Data.Hackage.Views
Types
Handler.Home
Handler.Snapshots
Handler.Profile
Handler.Email
Handler.ResetToken

View File

@ -0,0 +1,7 @@
<div .container>
<ul>
$forall (E.Value ident, E.Value title, E.Value uploaded, E.Value display, E.Value handle) <- stackages
<li>
<a href=@{StackageHomeR ident}>
#{title}
<i>by #{display} (#{handle}) on #{show uploaded}

View File

@ -26,10 +26,9 @@ $newline never
<script>
document.documentElement.className = document.documentElement.className.replace(/\bno-js\b/,'js');
<body>
<div class="container">
<header>
<div id="main" role="main">
^{pageBody pc}
<header>
<div id="main" role="main">
^{pageBody pc}
\<!-- Prompt IE 6 users to install Chrome Frame. Remove this if you want to support IE 6. chromium.org/developers/how-tos/chrome-frame-getting-started -->
\<!--[if lt IE 7 ]>

View File

@ -1,22 +1,34 @@
<nav .navbar .navbar-default role=navigation>
<div .container>
<div .navbar-header>
<div .navbar-brand>
<a href=@{HomeR}>
Stackage
<ul .nav .navbar-nav>
<li>
<a href=@{HomeR}>Home
$maybe Entity _ user <- muser
<li>You are logged in as #{userDisplay user} (#{userHandle user}).
<div .container>
<div .navbar role=navigation>
<div .navbar-inner>
<a .brand href=@{HomeR}>
Stackage
<ul .nav>
<li>
<a href=@{ProfileR}>Edit profile
<a href=@{AllSnapshotsR}>
All Snapshots
<li>
<a href=@{AuthR LogoutR}>Logout
$nothing
<li>
<a href=@{AuthR LoginR}>Login
<a href=@{UploadStackageR}>
Upload
<ul .nav .pull-right>
$maybe Entity _ user <- muser
<li>
<a href=@{ProfileR}>
<span .user-handle>
#{userHandle user}
<li>
<a href=@{AuthR LogoutR}>Logout
$nothing
<li>
<a href=@{AuthR LoginR}>Login
$maybe msg <- mmsg
<div .alert .alter-info>#{msg}
^{widget}
<div .container>
<div .alert .alter-info>#{msg}
$case cur
$of Just (AuthR _)
<div .container>
^{widget}
$of _
^{widget}

View File

View File

@ -1,3 +1,16 @@
.brand {
.navbar .nav > li > a {
color: #0088cc
}
.navbar .navbar-inner {
border: 0;
background: inherit;
border-top-left-radius: 0;
border-top-right-radius: 0;
}
.navbar .user-handle {
max-width: 15em;
overflow: hidden;
white-space: nowrap;
display: inline-block;
text-overflow:ellipsis;
}

View File

@ -1,12 +1,10 @@
<h2>Browse stackages
<ul>
$forall (E.Value ident, E.Value title, E.Value uploaded, E.Value display, E.Value handle) <- stackages
<li>
<a href=@{StackageHomeR ident}>
#{title}
<i>by #{display} (#{handle}) on #{show uploaded}
<h2>Upload
<a href=@{UploadStackageR}>Upload
<div .container>
<p>
Stackage is an infrastructure to create stable builds of complete package sets. Think “stable Hackage”.
<h2>Recommended Snapshots
<ul>
$forall (E.Value ident, E.Value title, E.Value uploaded, E.Value display, E.Value handle) <- stackages
<li>
<a href=@{StackageHomeR ident}>
#{title}
<i>by #{display} (#{handle}) on #{show uploaded}

View File

@ -1,43 +1,44 @@
<h2>Email addresses
$if length emails <= 1
$forall Entity _ email <- emails
<p>#{emailEmail email}
$else
<ul>
$forall Entity eid email <- emails
<li .email>
#{emailEmail email}
<form method=post action=@{EmailR eid}?_method=DELETE>
<button .btn>Remove
<div .container>
<h2>Email addresses
$if length emails <= 1
$forall Entity _ email <- emails
<p>#{emailEmail email}
$else
<ul>
$forall Entity eid email <- emails
<li .email>
#{emailEmail email}
<form method=post action=@{EmailR eid}?_method=DELETE>
<button .btn>Remove
<p>
<a href=@{AuthR LoginR}>Add another email address.
<p>
<a href=@{AuthR LoginR}>Add another email address.
<h2>Profile
<h2>Profile
<form method=post action=@{ProfileR}?_method=PUT enctype=#{enctype} role=form>
<div .form-group>
^{userWidget}
<button .btn>Update
<form method=post action=@{ProfileR}?_method=PUT enctype=#{enctype} role=form>
<div .form-group>
^{userWidget}
<button .btn>Update
<h2>Aliases
<h2>Aliases
<form method=post action=@{AliasesR}?_method=PUT>
Format: alias name, package set ID
<textarea #aliases name=aliases>#{unlines $ map aliasToText aliases}
<button .btn>Update
<form method=post action=@{AliasesR}?_method=PUT>
Format: alias name, package set ID
<textarea #aliases name=aliases>#{unlines $ map aliasToText aliases}
<button .btn>Update
$if not $ null aliases
<dl>
$forall Entity _ alias <- aliases
<dt>#{aliasName alias}
<dd>
$with url <- AliasR (userHandle user) (aliasName alias) []
<a href=@{url}>@{url}
$if not $ null aliases
<dl>
$forall Entity _ alias <- aliases
<dt>#{aliasName alias}
<dd>
$with url <- AliasR (userHandle user) (aliasName alias) []
<a href=@{url}>@{url}
<h2>Security token
<h2>Security token
<p>
Your security token is #{userToken user}.
<form method=post action=@{ResetTokenR}>
<button>Reset token
<p>
Your security token is #{userToken user}.
<form method=post action=@{ResetTokenR}>
<button>Reset token

View File

@ -1,4 +1,5 @@
<form method=post action=@{UploadStackageR}?_method=PUT enctype=multipart/form-data>
Stackage file:
<input type=file name=#{fileKey}>
<button>Upload
<div .container>
<form method=post action=@{UploadStackageR}?_method=PUT enctype=multipart/form-data>
Stackage file:
<input type=file name=#{fileKey}>
<button>Upload