2

I'm trying to select all Events from the database that contain a Tag in the Event's tags column.

Event is a model with a column tags that is defined in Yesod's model file as tags [Tag]. Tag is a model that is simply newtype Tag = Tag Text with a lot of derivings including PersistField which should allow Tag types to be stored as Text types.

I would like to define a query that selects all events that contain a given tag in their tags column. Something like:

getEventsByTag :: Tag -> Handler Value
getEventsByTag tag = do
  events <- runDB findEvents :: Handler [Entity Event]
  return $ object ["events" ==. events]
 where
  findEvents =
    select $
      from $ \event -> do
        where_ $ (event ^. EventTags) `contains` (val tag)
        return event

The part I'm not sure how to do is the contains function. It doesn't seem likely that I can use any postgres array functions since Persistent stores arrays as varchars in postgres. In which case I could get fancy with like. I was actually able to get the result I wanted with this query in postgres: select * from events where tags like '%"tag"%'; But I'm not sure how to translate this into Esqueleto's language. I tried using the like function but it requires both arguments to be instances of SqlString which I made Tag derive but had trouble figuring out how to make [Tag] derive without overlapping instances.

0 Answers0