packages feed

wai-app-static 3.1.1 → 3.1.2

raw patch · 6 files changed

+84/−51 lines, 6 filesdep +temporaryPVP: major bump suggested

API removals or changes: PVP suggests a major version bump

Dependencies added: temporary

API changes (from Hackage documentation)

- WaiAppStatic.CmdLine: docroot :: Args -> FilePath
- WaiAppStatic.CmdLine: host :: Args -> String
- WaiAppStatic.CmdLine: index :: Args -> [FilePath]
- WaiAppStatic.CmdLine: mime :: Args -> [(String, String)]
- WaiAppStatic.CmdLine: noindex :: Args -> Bool
- WaiAppStatic.CmdLine: port :: Args -> Int
- WaiAppStatic.CmdLine: quiet :: Args -> Bool
- WaiAppStatic.CmdLine: verbose :: Args -> Bool
- WaiAppStatic.Storage.Embedded: eContent :: EmbeddableEntry -> Either (Etag, ByteString) ExpQ
- WaiAppStatic.Storage.Embedded: eLocation :: EmbeddableEntry -> Text
- WaiAppStatic.Storage.Embedded: eMimeType :: EmbeddableEntry -> MimeType
- WaiAppStatic.Types: fileGetHash :: File -> IO (Maybe ByteString)
- WaiAppStatic.Types: fileGetModified :: File -> Maybe EpochTime
- WaiAppStatic.Types: fileGetSize :: File -> Int
- WaiAppStatic.Types: fileName :: File -> Piece
- WaiAppStatic.Types: fileToResponse :: File -> Status -> ResponseHeaders -> Response
- WaiAppStatic.Types: folderContents :: Folder -> [Either FolderName File]
- WaiAppStatic.Types: instance Eq Piece
- WaiAppStatic.Types: instance Ord Piece
- WaiAppStatic.Types: instance Show Piece
- WaiAppStatic.Types: ssAddTrailingSlash :: StaticSettings -> Bool
- WaiAppStatic.Types: ssGetMimeType :: StaticSettings -> File -> IO MimeType
- WaiAppStatic.Types: ssIndices :: StaticSettings -> [Piece]
- WaiAppStatic.Types: ssListing :: StaticSettings -> Maybe Listing
- WaiAppStatic.Types: ssLookupFile :: StaticSettings -> Pieces -> IO LookupResult
- WaiAppStatic.Types: ssMaxAge :: StaticSettings -> MaxAge
- WaiAppStatic.Types: ssMkRedirect :: StaticSettings -> Pieces -> ByteString -> ByteString
- WaiAppStatic.Types: ssRedirectToIndex :: StaticSettings -> Bool
- WaiAppStatic.Types: ssUseHash :: StaticSettings -> Bool
+ WaiAppStatic.CmdLine: [docroot] :: Args -> FilePath
+ WaiAppStatic.CmdLine: [host] :: Args -> String
+ WaiAppStatic.CmdLine: [index] :: Args -> [FilePath]
+ WaiAppStatic.CmdLine: [mime] :: Args -> [(String, String)]
+ WaiAppStatic.CmdLine: [noindex] :: Args -> Bool
+ WaiAppStatic.CmdLine: [port] :: Args -> Int
+ WaiAppStatic.CmdLine: [quiet] :: Args -> Bool
+ WaiAppStatic.CmdLine: [verbose] :: Args -> Bool
+ WaiAppStatic.Storage.Embedded: [eContent] :: EmbeddableEntry -> Either (Etag, ByteString) ExpQ
+ WaiAppStatic.Storage.Embedded: [eLocation] :: EmbeddableEntry -> Text
+ WaiAppStatic.Storage.Embedded: [eMimeType] :: EmbeddableEntry -> MimeType
+ WaiAppStatic.Types: [fileGetHash] :: File -> IO (Maybe ByteString)
+ WaiAppStatic.Types: [fileGetModified] :: File -> Maybe EpochTime
+ WaiAppStatic.Types: [fileGetSize] :: File -> Int
+ WaiAppStatic.Types: [fileName] :: File -> Piece
+ WaiAppStatic.Types: [fileToResponse] :: File -> Status -> ResponseHeaders -> Response
+ WaiAppStatic.Types: [folderContents] :: Folder -> [Either FolderName File]
+ WaiAppStatic.Types: [ssAddTrailingSlash] :: StaticSettings -> Bool
+ WaiAppStatic.Types: [ssGetMimeType] :: StaticSettings -> File -> IO MimeType
+ WaiAppStatic.Types: [ssIndices] :: StaticSettings -> [Piece]
+ WaiAppStatic.Types: [ssListing] :: StaticSettings -> Maybe Listing
+ WaiAppStatic.Types: [ssLookupFile] :: StaticSettings -> Pieces -> IO LookupResult
+ WaiAppStatic.Types: [ssMaxAge] :: StaticSettings -> MaxAge
+ WaiAppStatic.Types: [ssMkRedirect] :: StaticSettings -> Pieces -> ByteString -> ByteString
+ WaiAppStatic.Types: [ssRedirectToIndex] :: StaticSettings -> Bool
+ WaiAppStatic.Types: [ssUseHash] :: StaticSettings -> Bool
+ WaiAppStatic.Types: instance GHC.Classes.Eq WaiAppStatic.Types.Piece
+ WaiAppStatic.Types: instance GHC.Classes.Ord WaiAppStatic.Types.Piece
+ WaiAppStatic.Types: instance GHC.Show.Show WaiAppStatic.Types.Piece

Files

ChangeLog.md view
@@ -1,3 +1,7 @@+## 3.1.2++* Honor ssIndices when used with defaultWebAppSettings [#460](https://github.com/yesodweb/wai/pull/460)+ ## 3.1.1  * Make adding a trailing slash optional [#327](https://github.com/yesodweb/wai/issues/327) [yesod#988](https://github.com/yesodweb/yesod/issues/988)
Network/Wai/Application/Static.hs view
@@ -40,9 +40,7 @@ import Data.Text (Text) import qualified Data.Text as T -import Data.Either (rights) import Network.HTTP.Date (parseHTTPDate, epochTimeToHTTPDate, formatHTTPDate)-import Data.Monoid (First (First, getFirst), mconcat)  import WaiAppStatic.Types import Util@@ -74,38 +72,20 @@  -- | Serve an appropriate response for a folder request. serveFolder :: StaticSettings -> Pieces -> W.Request -> Folder -> IO StaticResponse-serveFolder ss@StaticSettings {..} pieces req folder@Folder {..} =-    -- first check if there is an index file in this folder-    case getFirst $ mconcat $ map (findIndex $ rights folderContents) ssIndices of-        Just index ->-            let pieces' = setLast pieces index in-            case () of-              () | ssRedirectToIndex -> return $ Redirect pieces' Nothing-                 | Just path <- addTrailingSlash req, ssAddTrailingSlash ->-                    return $ RawRedirect path-                 | otherwise ->-                    -- start the checking process over, with a new set-                    checkPieces ss pieces' req-        Nothing ->-            case ssListing of-                Just _ | Just path <- addTrailingSlash req, ssAddTrailingSlash ->-                    return $ RawRedirect path-                Just listing -> do-                    -- directory listings turned on, display it-                    builder <- listing pieces folder-                    return $ WaiResponse $ W.responseBuilder H.status200-                        [ ("Content-Type", "text/html; charset=utf-8")-                        ] builder-                Nothing -> return $ WaiResponse $ W.responseLBS H.status403-                    [ ("Content-Type", "text/plain")-                    ] "Directory listings disabled"+serveFolder StaticSettings {..} pieces req folder@Folder {..} =+    case ssListing of+        Just _ | Just path <- addTrailingSlash req, ssAddTrailingSlash ->+            return $ RawRedirect path+        Just listing -> do+            -- directory listings turned on, display it+            builder <- listing pieces folder+            return $ WaiResponse $ W.responseBuilder H.status200+                [ ("Content-Type", "text/html; charset=utf-8")+                ] builder+        Nothing -> return $ WaiResponse $ W.responseLBS H.status403+            [ ("Content-Type", "text/plain")+            ] "Directory listings disabled"   where-    setLast :: Pieces -> Piece -> Pieces-    setLast [] x = [x]-    setLast [t] x-        | fromPiece t == "" = [x]-    setLast (a:b) x = a : setLast b x-     addTrailingSlash :: W.Request -> Maybe ByteString     addTrailingSlash req         | S8.null rp = Just "/"@@ -114,16 +94,6 @@       where         rp = W.rawPathInfo req -    noTrailingSlash :: Pieces -> Bool-    noTrailingSlash [] = False-    noTrailingSlash [x] = fromPiece x /= ""-    noTrailingSlash (_:xs) = noTrailingSlash xs--    findIndex :: [File] -> Piece -> First Piece-    findIndex files index-        | index `elem` map fileName files = First $ Just index-        | otherwise = First Nothing- checkPieces :: StaticSettings             -> Pieces                    -- ^ parsed request             -> W.Request@@ -134,11 +104,30 @@     return $ Redirect (filterButLast (not . T.null . fromPiece) pieces) Nothing  checkPieces ss@StaticSettings {..} pieces req = do-    res <- ssLookupFile pieces+    res <- lookupResult     case res of         LRNotFound -> return NotFound         LRFile file -> serveFile ss req file         LRFolder folder -> serveFolder ss pieces req folder+  where+    lookupResult :: IO LookupResult+    lookupResult = do+      nonIndexResult <- ssLookupFile pieces+      case nonIndexResult of+          LRFile{} -> return nonIndexResult+          _ -> do+              indexResult <- lookupIndices (map (\ index -> pieces ++ [index]) ssIndices)+              return $ case indexResult of+                  LRNotFound -> nonIndexResult+                  _ -> indexResult++    lookupIndices :: [Pieces] -> IO LookupResult+    lookupIndices (x : xs) = do+        res <- ssLookupFile x+        case res of+            LRNotFound -> lookupIndices xs+            _ -> return res+    lookupIndices [] = return LRNotFound  serveFile :: StaticSettings -> W.Request -> File -> IO StaticResponse serveFile StaticSettings {..} req file
test/EmbeddedTestEntries.hs view
@@ -42,4 +42,9 @@   , EmbeddableEntry "e6.txt"                     "text/plain"                     (Right [| return ("" :: T.Text, body 1000 'W') |] )++    -- An index file+  , EmbeddableEntry "index.html"+                    "text/html"+                    (Right [| return ("" :: T.Text, "index file") |] )   ]
test/WaiAppEmbeddedTest.hs view
@@ -8,16 +8,15 @@ import Network.Wai.Test import Test.Hspec import WaiAppStatic.Storage.Embedded--embApp :: Application-embApp = staticApp $(mkSettings mkEntries)+import WaiAppStatic.Types  defRequest :: Request defRequest = defaultRequest  embSpec :: Spec embSpec = do-    let embed = flip runSession embApp+    let embedSettings settings = flip runSession (staticApp settings)+    let embed = embedSettings $(mkSettings mkEntries)     describe "embedded, compressed entry" $ do         it "served correctly" $ embed $ do             req <- request (setRawPathInfo defRequest "e1.txt")@@ -33,6 +32,15 @@                              { requestHeaders = [("If-None-Match", "Etag 1")] }             assertStatus 304 req +        it "ssIndices works" $ do+            let testSettings = $(mkSettings mkEntries){+                    ssIndices = [unsafeToPiece "index.html"]+                }+            embedSettings testSettings $ do+              req <- request defRequest+              assertStatus 200 req+              assertBody "index file" req+     describe "embedded, uncompressed entry" $ do         it "too short" $ embed $ do             req <- request (setRawPathInfo defRequest "e2.txt")@@ -75,4 +83,3 @@             assertNoHeader "Content-Encoding" req             assertNoHeader "ETag" req             assertBody (body 1000 'W') req-
test/WaiAppStaticTest.hs view
@@ -2,11 +2,14 @@ module WaiAppStaticTest (spec) where  import Network.Wai.Application.Static+import WaiAppStatic.Types  import Test.Hspec import qualified Data.ByteString.Char8 as S8 -- import qualified Data.ByteString.Lazy.Char8 as L8 import System.PosixCompat.Files (getFileStatus, modificationTime)+import System.FilePath+import System.IO.Temp  import Network.HTTP.Date import Network.HTTP.Types (status500)@@ -25,7 +28,8 @@ spec :: Spec spec = do   let webApp = flip runSession $ staticApp $ defaultWebAppSettings "test"-  let fileServerApp = flip runSession $ staticApp (defaultFileServerSettings "test")+  let fileServerAppWithSettings settings = flip runSession $ staticApp settings+  let fileServerApp = fileServerAppWithSettings (defaultFileServerSettings "test")         { ssAddTrailingSlash = True         } @@ -145,3 +149,25 @@         req <- request (setRawPathInfo defRequest "/subPath")         assertStatus 301 req         assertHeader "Location" "/subPath/" req++    context "with defaultWebAppSettings" $ do+      it "ssIndices works" $ do+        withSystemTempDirectory "wai-app-static-test" $ \ dir -> do+          writeFile (dir </> "index.html") "foo"+          let testSettings = (defaultWebAppSettings dir) {+                ssIndices = [unsafeToPiece "index.html"]+              }+          fileServerAppWithSettings testSettings $ do+            resp <- request (setRawPathInfo defRequest "/")+            assertStatus 200 resp+            assertBody "foo" resp++    context "with defaultFileServerSettings" $ do+      it "prefers ssIndices over ssListing" $ do+        withSystemTempDirectory "wai-app-static-test" $ \ dir -> do+          writeFile (dir </> "index.html") "foo"+          let testSettings = defaultFileServerSettings dir+          fileServerAppWithSettings testSettings $ do+            resp <- request (setRawPathInfo defRequest "/")+            assertStatus 200 resp+            assertBody "foo" resp
wai-app-static.cabal view
@@ -1,5 +1,5 @@ name:            wai-app-static-version:         3.1.1+version:         3.1.2 license:         MIT license-file:    LICENSE author:          Michael Snoyman <michael@snoyman.com>@@ -102,6 +102,8 @@                    , transformers                    , mime-types                    , zlib+                   , filepath+                   , temporary                    -- , containers   ghc-options:   -Wall