{- | for reliable results with Utf8 pattern or body,
    use "Text.Regex.Do.Replace.Utf8"   -}

module Text.Regex.Do.Replace.Latin
    (Replace(..))  where

import Text.Regex.Base.RegexLike as R
import Prelude as P
import Text.Regex.Do.Type.Do
import Text.Regex.Do.Type.Reexport as R
import Text.Regex.Do.Match.Matchf
import qualified Text.Regex.Do.Replace.Open as O
import Text.Regex.Do.Match.Regex as T
import Text.Regex.Do.Type.Extract


{- | hint: 'All' | 'Once'

    pattern: 'R.Regex', 'String', 'ByteString'   
    
    String | ByteString pattern may contains regex
    
    body: 'String', 'ByteString'

    result is 'Either' String body: 'Left' String returns regex construction errors.   
-} 
class Replace hint pattern repl body out where
    replace::(Extract' body, RegexLike R.Regex body) => 
        hint pattern -> repl -> body -> out


instance (R.RegexLike R.Regex b, O.Replace Maybe repl b) =>
        Replace Once R.Regex repl b b where
    replace :: Once Regex -> repl -> b -> b
replace (Once p0 :: Regex
p0) = Regex -> (b -> Tagged Once b) -> repl -> b -> b
forall (hint :: * -> *) b (f :: * -> *) repl body arr a.
(Matchf hint, RegexLike Regex b, Replace f repl body,
 Extract' body, ToArray arr, H hint ~ Either a (f arr)) =>
Regex -> (body -> hint b) -> repl -> body -> body
replace_rx Regex
p0 b -> Tagged Once b
forall b. b -> Tagged Once b
tagOnce
{- ^ succeeds unless 'GroupReplacer' fails due to mismatched pattern etc 

    repl: 'String' | 'ByteString' | 'GroupReplacer' repl
-}


instance (R.RegexLike R.Regex b, O.Replace [] repl b) =>
        Replace All R.Regex repl b b where
    replace :: All Regex -> repl -> b -> b
replace (All p0 :: Regex
p0) = Regex -> (b -> Tagged All b) -> repl -> b -> b
forall (hint :: * -> *) b (f :: * -> *) repl body arr a.
(Matchf hint, RegexLike Regex b, Replace f repl body,
 Extract' body, ToArray arr, H hint ~ Either a (f arr)) =>
Regex -> (body -> hint b) -> repl -> body -> body
replace_rx Regex
p0 b -> Tagged All b
forall b. b -> Tagged All b
tagAll
{- ^ succeeds unless 'GroupReplacer' fails due to mismatched pattern etc 

    repl: 'String' | 'ByteString' | 'GroupReplacer' repl
-}



instance (R.RegexLike R.Regex b, T.Regex b) => 
    Replace Once b b b (E b) where
    replace :: Once b -> b -> b -> E b
replace (Once p0 :: b
p0) = b -> (b -> Tagged Once b) -> b -> b -> E b
forall (hint :: * -> *) b a (f :: * -> *) repl b arr a.
(Matchf hint, RegexLike Regex b, Regex a, Replace f repl b,
 Extract' b, ToArray arr, H hint ~ Either a (f arr)) =>
a -> (b -> hint b) -> repl -> b -> Either a b
replace_ b
p0 b -> Tagged Once b
forall b. b -> Tagged Once b
tagOnce
{- ^ b: 'String' | 'ByteString'-}


instance (R.RegexLike R.Regex b, T.Regex b) => 
    Replace Once b (GroupReplacer b) b (E b) where
    replace :: Once b -> GroupReplacer b -> b -> E b
replace (Once p0 :: b
p0) = b -> (b -> Tagged Once b) -> GroupReplacer b -> b -> E b
forall (hint :: * -> *) b a (f :: * -> *) repl b arr a.
(Matchf hint, RegexLike Regex b, Regex a, Replace f repl b,
 Extract' b, ToArray arr, H hint ~ Either a (f arr)) =>
a -> (b -> hint b) -> repl -> b -> Either a b
replace_ b
p0 b -> Tagged Once b
forall b. b -> Tagged Once b
tagOnce
{- ^ b: 'String' | 'ByteString'-}


instance (R.RegexLike R.Regex b, T.Regex b) => 
    Replace All b b b (E b) where
    replace :: All b -> b -> b -> E b
replace (All p0 :: b
p0) = b -> (b -> Tagged All b) -> b -> b -> E b
forall (hint :: * -> *) b a (f :: * -> *) repl b arr a.
(Matchf hint, RegexLike Regex b, Regex a, Replace f repl b,
 Extract' b, ToArray arr, H hint ~ Either a (f arr)) =>
a -> (b -> hint b) -> repl -> b -> Either a b
replace_ b
p0 b -> Tagged All b
forall b. b -> Tagged All b
tagAll
{- ^ b: 'String' | 'ByteString'-}


instance (R.RegexLike R.Regex b, T.Regex b) => 
    Replace All b (GroupReplacer b) b (E b) where
    replace :: All b -> GroupReplacer b -> b -> E b
replace (All p0 :: b
p0) = b -> (b -> Tagged All b) -> GroupReplacer b -> b -> E b
forall (hint :: * -> *) b a (f :: * -> *) repl b arr a.
(Matchf hint, RegexLike Regex b, Regex a, Replace f repl b,
 Extract' b, ToArray arr, H hint ~ Either a (f arr)) =>
a -> (b -> hint b) -> repl -> b -> Either a b
replace_ b
p0 b -> Tagged All b
forall b. b -> Tagged All b
tagAll
{- ^ b: 'String' | 'ByteString'-}


replace_rx :: Regex -> (body -> hint b) -> repl -> body -> body
replace_rx rx0 :: Regex
rx0 tag0 :: body -> hint b
tag0 r0 :: repl
r0 b0 :: body
b0 =
    let Right ma1 :: f arr
ma1 = E Regex -> hint b -> H hint
forall (hint :: * -> *) b.
(Matchf hint, R_ b) =>
E Regex -> hint b -> H hint
marray_ (Regex -> E Regex
forall a b. b -> Either a b
Right Regex
rx0) (body -> hint b
tag0 body
b0) 
    in f arr -> repl -> body -> body
forall (f :: * -> *) repl body arr.
(Replace f repl body, Extract' body, ToArray arr) =>
f arr -> repl -> body -> body
O.replace f arr
ma1 repl
r0 body
b0


replace_ :: a -> (b -> hint b) -> repl -> b -> Either a b
replace_ p0 :: a
p0 tag0 :: b -> hint b
tag0 r0 :: repl
r0 b0 :: b
b0 = 
    E Regex -> hint b -> H hint
forall (hint :: * -> *) b.
(Matchf hint, R_ b) =>
E Regex -> hint b -> H hint
marray_ (a -> E Regex
forall a. Regex a => a -> E Regex
T.makeRegex a
p0) (b -> hint b
tag0 b
b0) Either a (f arr) -> (f arr -> Either a b) -> Either a b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= \ma1 :: f arr
ma1 ->
    b -> Either a b
forall a b. b -> Either a b
Right (b -> Either a b) -> b -> Either a b
forall a b. (a -> b) -> a -> b
$ f arr -> repl -> b -> b
forall (f :: * -> *) repl body arr.
(Replace f repl body, Extract' body, ToArray arr) =>
f arr -> repl -> body -> body
O.replace f arr
ma1 repl
r0 b
b0