feat: add RecipeSearchEntry JSON encoding for search payload
This commit is contained in:
+37
-2
@@ -1,11 +1,17 @@
|
|||||||
|
{-# LANGUAGE DeriveGeneric #-}
|
||||||
|
|
||||||
-- | Scanning and indexing of Cooklang recipe files on disk.
|
-- | Scanning and indexing of Cooklang recipe files on disk.
|
||||||
module Roux.RecipeIndex (
|
module Roux.RecipeIndex (
|
||||||
RecipeInfo (..),
|
RecipeInfo (..),
|
||||||
|
RecipeSearchEntry (..),
|
||||||
scanRecipes,
|
scanRecipes,
|
||||||
|
toSearchEntry,
|
||||||
) where
|
) where
|
||||||
|
|
||||||
|
import Data.Aeson (ToJSON (..), camelTo2, defaultOptions, fieldLabelModifier, genericToJSON)
|
||||||
import Data.Text (Text)
|
import Data.Text (Text)
|
||||||
import qualified Data.Text as T
|
import qualified Data.Text as T
|
||||||
|
import GHC.Generics (Generic)
|
||||||
import System.Directory (listDirectory)
|
import System.Directory (listDirectory)
|
||||||
import System.FilePath (takeBaseName, takeExtension, (</>))
|
import System.FilePath (takeBaseName, takeExtension, (</>))
|
||||||
|
|
||||||
@@ -45,9 +51,38 @@ loadRecipe dir filename = do
|
|||||||
, riRecipe = parsed
|
, riRecipe = parsed
|
||||||
}
|
}
|
||||||
|
|
||||||
{- | Extract a display title from the recipe's metadata or fall back to the
|
-- | Search payload for type-ahead / recipe search.
|
||||||
filename.
|
data RecipeSearchEntry = RecipeSearchEntry
|
||||||
|
{ rseTitle :: !Text
|
||||||
|
, rseFilename :: !Text
|
||||||
|
, rseCourse :: !(Maybe Text)
|
||||||
|
, rseTags :: ![Text]
|
||||||
|
}
|
||||||
|
deriving stock (Generic)
|
||||||
|
|
||||||
|
instance ToJSON RecipeSearchEntry where
|
||||||
|
toJSON = genericToJSON defaultOptions{fieldLabelModifier = camelTo2 '_' . drop 3}
|
||||||
|
|
||||||
|
{- | Convert a 'RecipeInfo' into a 'RecipeSearchEntry', extracting course and
|
||||||
|
tags from the parsed recipe metadata when available.
|
||||||
-}
|
-}
|
||||||
|
toSearchEntry :: RecipeInfo -> RecipeSearchEntry
|
||||||
|
toSearchEntry info =
|
||||||
|
let (course, tags) = case riRecipe info of
|
||||||
|
Right r ->
|
||||||
|
( metaCourse (recipeMetadata r)
|
||||||
|
, metaTags (recipeMetadata r)
|
||||||
|
)
|
||||||
|
Left _ -> (Nothing, [])
|
||||||
|
in RecipeSearchEntry
|
||||||
|
{ rseTitle = riTitle info
|
||||||
|
, rseFilename = T.pack (riFilename info)
|
||||||
|
, rseCourse = course
|
||||||
|
, rseTags = tags
|
||||||
|
}
|
||||||
|
|
||||||
|
-- | Extract a display title from the recipe's metadata or fall back to the
|
||||||
|
-- filename.
|
||||||
extractTitle :: Recipe -> FilePath -> Text
|
extractTitle :: Recipe -> FilePath -> Text
|
||||||
extractTitle recipe filename =
|
extractTitle recipe filename =
|
||||||
case metaTitle (recipeMetadata recipe) of
|
case metaTitle (recipeMetadata recipe) of
|
||||||
|
|||||||
Reference in New Issue
Block a user