{-# LANGUAGE CPP #-}
{-# LANGUAGE PatternSynonyms #-}

module Distribution.Compat.Binary
       ( decodeOrFailIO
       , decodeFileOrFail'
       , module Data.Binary
       ) where

import Control.Exception (ErrorCall (..), catch, evaluate)
import Data.ByteString.Lazy (ByteString)

import Data.Binary

-- | Lazily reconstruct a value previously written to a file.
decodeFileOrFail' :: Binary a => FilePath -> IO (Either String a)
decodeFileOrFail' :: forall a. Binary a => FilePath -> IO (Either FilePath a)
decodeFileOrFail' FilePath
f = forall a c b. (a -> c) -> (b -> c) -> Either a b -> c
either (forall a b. a -> Either a b
Left forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a, b) -> b
snd) forall a b. b -> Either a b
Right forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
`fmap` forall a.
Binary a =>
FilePath -> IO (Either (ByteOffset, FilePath) a)
decodeFileOrFail FilePath
f

decodeOrFailIO :: Binary a => ByteString -> IO (Either String a)
decodeOrFailIO :: forall a. Binary a => ByteString -> IO (Either FilePath a)
decodeOrFailIO ByteString
bs =
    forall e a. Exception e => IO a -> (e -> IO a) -> IO a
catch (forall a. a -> IO a
evaluate (forall a. Binary a => ByteString -> a
decode ByteString
bs) forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= forall (m :: * -> *) a. Monad m => a -> m a
return forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. b -> Either a b
Right) forall {m :: * -> *} {b}.
Monad m =>
ErrorCall -> m (Either FilePath b)
handler
  where
    handler :: ErrorCall -> m (Either FilePath b)
handler (ErrorCallWithLocation FilePath
str FilePath
_) = forall (m :: * -> *) a. Monad m => a -> m a
return forall a b. (a -> b) -> a -> b
$ forall a b. a -> Either a b
Left FilePath
str