{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE DataKinds #-}
{-# LANGUAGE PolyKinds #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE TypeOperators #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE TypeApplications #-}
{-# OPTIONS_GHC -fwarn-incomplete-patterns #-}
module Knit.Effect.UnusedId
(
UnusedId
, getNextUnusedId
, runUnusedId
)
where
import qualified Polysemy as P
import qualified Polysemy.State as PS
import qualified Data.Map as M
import qualified Data.Text as T
import Data.Maybe ( fromMaybe )
type IdMap = M.Map T.Text Int
type UnusedId = PS.State IdMap
getNextUnusedId :: P.Member UnusedId r => T.Text -> P.Sem r T.Text
getNextUnusedId prefixT = do
idMap <- PS.get @IdMap
let nextId = fromMaybe 1 $ M.lookup prefixT idMap
PS.put $ M.insert prefixT (nextId + 1) idMap
return $ prefixT <> "_" <> (T.pack $ show nextId)
runUnusedId :: P.Sem (UnusedId ': r) a -> P.Sem r a
runUnusedId = fmap snd . PS.runState M.empty