From 98329e0a3dd4f78b5d815ac3896272ec70904901 Mon Sep 17 00:00:00 2001 From: Eugen Wissner Date: Thu, 11 Dec 2025 10:28:11 +0100 Subject: Add remaining haskell book exercises --- Haskell-book/26/Exercises/app/Main.hs | 61 +++++++++++++++++++++++++++++++++++ 1 file changed, 61 insertions(+) create mode 100644 Haskell-book/26/Exercises/app/Main.hs (limited to 'Haskell-book/26/Exercises/app') diff --git a/Haskell-book/26/Exercises/app/Main.hs b/Haskell-book/26/Exercises/app/Main.hs new file mode 100644 index 0000000..6bfe6bb --- /dev/null +++ b/Haskell-book/26/Exercises/app/Main.hs @@ -0,0 +1,61 @@ +{-# LANGUAGE OverloadedStrings #-} + +module Main where + +import Control.Monad.IO.Class +import Control.Monad.Trans.Class +import Control.Monad.Trans.Reader +import Data.IORef +import qualified Data.Map as M +import Data.Maybe (fromMaybe) +import Data.Text.Lazy (Text) +import qualified Data.Text.Lazy as TL +import System.Environment (getArgs) +import Web.Scotty.Trans ( ScottyT(..) + , ActionT(..) + , scottyT + , get + , html + , param ) + +data Config = + Config { + -- that's one, one click! + -- two...two clicks! + -- Three BEAUTIFUL clicks! ah ah ahhhh + counts :: IORef (M.Map Text Integer) + , prefix :: Text + } + +type Scotty = ScottyT Text (ReaderT Config IO) + +bumpBoomp :: Text + -> M.Map Text Integer + -> (M.Map Text Integer, Integer) +bumpBoomp k m = + let (maybeCount, newMap) = M.insertLookupWithKey (\_ _ oldCount -> oldCount + 1) k 1 m + in case maybeCount of + Nothing -> (newMap, 1) + Just oldCount -> (newMap, oldCount + 1) + +app :: Scotty () +app = + get "/:key" $ do + unprefixed <- param "key" + prefix <- lift $ asks prefix + let key' = mappend prefix unprefixed + counts <- lift $ asks counts + (newMap, newInteger) <- liftIO $ bumpBoomp key' <$> readIORef counts + liftIO $ writeIORef counts newMap + html $ mconcat [ "

Success! Count was: " + , TL.pack $ show (newInteger :: Integer) + , "

" + ] + +main :: IO () +main = do + [prefixArg] <- getArgs + counter <- newIORef M.empty + let config = Config {counts = counter, prefix = TL.pack prefixArg} + runR = flip runReaderT config + scottyT 3000 runR app -- cgit v1.2.3