{-# LANGUAGE AllowAmbiguousTypes #-}
{-# LANGUAGE OverloadedStrings #-}
module HUnit.Credential where

import Control.Applicative (Applicative(..))
import Test.Tasty.HUnit
import qualified Control.Monad.Trans.State.Strict as S
import qualified System.Random as Random

import Protocol.Arithmetic
import Protocol.Credential
import Utils

hunit :: TestTree
hunit = testGroup "Credential"
 [ testGroup "randomCredential"
	 [ testCase "0" $
		S.evalState randomCredential (Random.mkStdGen 0) @?=
			Credential "xLcs7ev6Jy6FHHE"
	 ]
 , testGroup "randomUUID"
	 [ testCase "0" $
		S.evalState randomUUID (Random.mkStdGen 0) @?=
			UUID "xLcs7ev6Jy6FHH"
	 ]
 , testGroup "readCredential" $
		let (==>) inp exp =
			testCase (show inp) $ readCredential inp @?= exp in
	 [ "" ==> Left CredentialError_Length
	 , "xLcs7ev6Jy6FH_E"  ==> Left (CredentialError_BadChar '_')
	 , "xLcs7ev6Jy6FHIE"  ==> Left (CredentialError_BadChar 'I')
	 , "xLcs7ev6Jy6FH0E"  ==> Left (CredentialError_BadChar '0')
	 , "xLcs7ev6Jy6FHOE"  ==> Left (CredentialError_BadChar 'O')
	 , "xLcs7ev6Jy6FHlE"  ==> Left (CredentialError_BadChar 'l')
	 , "xLcs7ev6Jy6FH6"   ==> Left CredentialError_Length
	 , "xLcs7ev6Jy6FHHy1" ==> Left CredentialError_Length
	 , "xLcs7ev6Jy6FHHF"  ==> Left CredentialError_Checksum
	 , "xLcs7ev6Jy6FHHE"  ==> Right (Credential "xLcs7ev6Jy6FHHE")
	 ]
 , testGroup "credentialSecretKey" $
	 [ testSecretKey @WeakParams 0 $ E (F 122)
	 , testSecretKey @WeakParams 1 $ E (F 35)
	 , testSecretKey @BeleniosParams 0 $ E (F 2317630607062989137269685509390)
	 , testSecretKey @BeleniosParams 1 $ E (F 1968146140481358915910346867611)
	 ]
 ]

testSecretKey :: forall q. SubGroup q => Int -> E q -> TestTree
testSecretKey seed exp =
	let (uuid@(UUID u), cred@(Credential c)) =
		(`S.evalState` Random.mkStdGen seed) $
			(,) <$> randomUUID <*> randomCredential in
	testCase (show (u,c)) $
		credentialSecretKey @q uuid cred @?= exp