Use cached widget for /package

This commit is contained in:
Michael Snoyman 2014-10-23 07:33:39 +03:00
parent 1d46dcf5d6
commit 765ed91767
3 changed files with 24 additions and 2 deletions

View File

@ -138,6 +138,7 @@ makeFoundation useEcho conf = do
let haddockRootDir' = "/tmp/stackage-server-haddocks" let haddockRootDir' = "/tmp/stackage-server-haddocks"
unpacker <- createHaddockUnpacker haddockRootDir' blobStore' unpacker <- createHaddockUnpacker haddockRootDir' blobStore'
widgetCache' <- newIORef mempty
let logger = Yesod.Core.Types.Logger loggerSet' getter let logger = Yesod.Core.Types.Logger loggerSet' getter
foundation = App foundation = App
@ -153,6 +154,7 @@ makeFoundation useEcho conf = do
, nextProgressKey = nextProgressKey' , nextProgressKey = nextProgressKey'
, haddockRootDir = haddockRootDir' , haddockRootDir = haddockRootDir'
, haddockUnpacker = unpacker , haddockUnpacker = unpacker
, widgetCache = widgetCache'
} }
-- Perform database migration using our application's logging settings. -- Perform database migration using our application's logging settings.

View File

@ -16,7 +16,7 @@ import Types
import Yesod.Auth import Yesod.Auth
import Yesod.Auth.BrowserId import Yesod.Auth.BrowserId
import Yesod.Auth.GoogleEmail import Yesod.Auth.GoogleEmail
import Yesod.Core.Types (Logger) import Yesod.Core.Types (Logger, GWData)
import Yesod.Default.Config import Yesod.Default.Config
import Yesod.Default.Util (addStaticContentExternal) import Yesod.Default.Util (addStaticContentExternal)
@ -41,6 +41,7 @@ data App = App
-- things at once, (2) we never unpack the same thing twice at the same -- things at once, (2) we never unpack the same thing twice at the same
-- time, and (3) so that even if the client connection dies, we finish the -- time, and (3) so that even if the client connection dies, we finish the
-- unpack job. -- unpack job.
, widgetCache :: !(IORef (HashMap Text (UTCTime, GWData (Route App))))
} }
data Progress = ProgressWorking !Text data Progress = ProgressWorking !Text

View File

@ -2,6 +2,8 @@ module Handler.PackageList where
import Import import Import
import qualified Database.Esqueleto as E import qualified Database.Esqueleto as E
import Yesod.Core.Types (WidgetT (WidgetT), unWidgetT)
import Data.Time (NominalDiffTime, addUTCTime)
getPackageListR :: Handler Html getPackageListR :: Handler Html
getPackageListR = do getPackageListR = do
@ -10,4 +12,21 @@ getPackageListR = do
return $ u E.^. UploadedName return $ u E.^. UploadedName
defaultLayout $ do defaultLayout $ do
setTitle "Package list" setTitle "Package list"
$(widgetFile "package-list") cachedWidget (5 * 60) "package-list" $(widgetFile "package-list")
-- FIXME move somewhere else, maybe even yesod-core
cachedWidget :: NominalDiffTime -> Text -> Widget -> Widget
cachedWidget diff key widget = do
ref <- widgetCache <$> getYesod
now <- liftIO getCurrentTime
mpair <- lookup key <$> readIORef ref
case mpair of
Just (expires, gw) | expires > now -> do
$logDebug "Using cached widget"
WidgetT $ \_ -> return ((), gw)
_ -> do
$logDebug "Not using cached widget"
WidgetT $ \hd -> do
((), gw) <- unWidgetT widget hd
atomicModifyIORef' ref $ \m -> (insertMap key (addUTCTime diff now, gw) m, ())
return ((), gw)