module Crypto.Nonce
( Generator
, new
, delete
, withGenerator
, nonce128
, nonce128url
, nonce128urlT
) where
import Control.Monad (liftM)
import Control.Monad.IO.Class (MonadIO, liftIO)
import qualified System.Entropy as Entropy
import Data.Typeable (Typeable)
import Control.Monad.IO.Unlift (MonadUnliftIO)
import UnliftIO.Exception (bracket)
import qualified Data.ByteString as B
import qualified Data.ByteString.Base64.URL as B64URL
import qualified Data.Text as T
import qualified Data.Text.Encoding as TE
newtype Generator = G Entropy.CryptHandle
deriving (Typeable)
instance Show Generator where
show :: Generator -> String
show Generator
_ = String
"<NonceGenerator>"
new :: MonadIO m => m Generator
new :: forall (m :: * -> *). MonadIO m => m Generator
new = (CryptHandle -> Generator) -> m CryptHandle -> m Generator
forall (m :: * -> *) a1 r. Monad m => (a1 -> r) -> m a1 -> m r
liftM CryptHandle -> Generator
G (m CryptHandle -> m Generator)
-> (IO CryptHandle -> m CryptHandle)
-> IO CryptHandle
-> m Generator
forall b c a. (b -> c) -> (a -> b) -> a -> c
. IO CryptHandle -> m CryptHandle
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO CryptHandle -> m Generator) -> IO CryptHandle -> m Generator
forall a b. (a -> b) -> a -> b
$ IO CryptHandle
Entropy.openHandle
delete :: MonadIO m => Generator -> m ()
delete :: forall (m :: * -> *). MonadIO m => Generator -> m ()
delete (G CryptHandle
v) = IO () -> m ()
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> m ()) -> IO () -> m ()
forall a b. (a -> b) -> a -> b
$ CryptHandle -> IO ()
Entropy.closeHandle CryptHandle
v
withGenerator :: MonadUnliftIO m => (Generator -> m a) -> m a
withGenerator :: forall (m :: * -> *) a.
MonadUnliftIO m =>
(Generator -> m a) -> m a
withGenerator = m Generator -> (Generator -> m ()) -> (Generator -> m a) -> m a
forall (m :: * -> *) a b c.
MonadUnliftIO m =>
m a -> (a -> m b) -> (a -> m c) -> m c
bracket m Generator
forall (m :: * -> *). MonadIO m => m Generator
new Generator -> m ()
forall (m :: * -> *). MonadIO m => Generator -> m ()
delete
genBytes :: MonadIO m => Int -> Generator -> m B.ByteString
genBytes :: forall (m :: * -> *). MonadIO m => Int -> Generator -> m ByteString
genBytes Int
n (G CryptHandle
v) = IO ByteString -> m ByteString
forall a. IO a -> m a
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO ByteString -> m ByteString) -> IO ByteString -> m ByteString
forall a b. (a -> b) -> a -> b
$ CryptHandle -> Int -> IO ByteString
Entropy.hGetEntropy CryptHandle
v Int
n
nonce128 :: MonadIO m => Generator -> m B.ByteString
nonce128 :: forall (m :: * -> *). MonadIO m => Generator -> m ByteString
nonce128 = Int -> Generator -> m ByteString
forall (m :: * -> *). MonadIO m => Int -> Generator -> m ByteString
genBytes Int
16
nonce128url :: MonadIO m => Generator -> m B.ByteString
nonce128url :: forall (m :: * -> *). MonadIO m => Generator -> m ByteString
nonce128url = (ByteString -> ByteString) -> m ByteString -> m ByteString
forall (m :: * -> *) a1 r. Monad m => (a1 -> r) -> m a1 -> m r
liftM ByteString -> ByteString
B64URL.encode (m ByteString -> m ByteString)
-> (Generator -> m ByteString) -> Generator -> m ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Int -> Generator -> m ByteString
forall (m :: * -> *). MonadIO m => Int -> Generator -> m ByteString
genBytes Int
18
nonce128urlT :: MonadIO m => Generator -> m T.Text
nonce128urlT :: forall (m :: * -> *). MonadIO m => Generator -> m Text
nonce128urlT = (ByteString -> Text) -> m ByteString -> m Text
forall (m :: * -> *) a1 r. Monad m => (a1 -> r) -> m a1 -> m r
liftM ByteString -> Text
TE.decodeUtf8 (m ByteString -> m Text)
-> (Generator -> m ByteString) -> Generator -> m Text
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Generator -> m ByteString
forall (m :: * -> *). MonadIO m => Generator -> m ByteString
nonce128url