Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Verifier plugin interface #1324

Merged
merged 14 commits into from
Jan 30, 2024
Merged
Show file tree
Hide file tree
Changes from 5 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 31 additions & 9 deletions docs/en/pact-functions.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,14 +5,14 @@

Constant denoting the ASCII charset

Constant:
Constant:
  `CHARSET_ASCII:integer = 0`

### CHARSET_LATIN1 {#CHARSET_LATIN1}

Constant denoting the Latin-1 charset ISO-8859-1

Constant:
Constant:
  `CHARSET_LATIN1:integer = 1`

### at {#at}
Expand Down Expand Up @@ -461,7 +461,7 @@ Return ID if called during current pact execution, failing if not.
Obtain current pact build version.
```lisp
pact> (pact-version)
"4.9"
"4.10"
```

Top level only: this function will fail if used in module code.
Expand Down Expand Up @@ -765,7 +765,7 @@ Top level only: this function will fail if used in module code.

Select rows from TABLE using QRY as a predicate with both key and value, and then accumulate results of the query in CONSUMER. Output is sorted by the ordering of keys.
```lisp
(let*
(let*
((qry (lambda (k obj) true)) ;; select all rows
(f (lambda (k obj) [(at 'firstName obj), (at 'b obj)]))
)
Expand Down Expand Up @@ -924,7 +924,7 @@ pact> (add-time (time "2016-07-22T12:00:00Z") 15)
*n* `integer` *→* `decimal`


N days, for use with 'add-time'
N days, for use with 'add-time'
```lisp
pact> (add-time (time "2016-07-22T12:00:00Z") (days 1))
"2016-07-23T12:00:00Z"
Expand Down Expand Up @@ -962,7 +962,7 @@ pact> (format-time "%F" (time "2016-07-22T12:00:00Z"))
*n* `integer` *→* `decimal`


N hours, for use with 'add-time'
N hours, for use with 'add-time'
```lisp
pact> (add-time (time "2016-07-22T12:00:00Z") (hours 1))
"2016-07-22T13:00:00Z"
Expand All @@ -976,7 +976,7 @@ pact> (add-time (time "2016-07-22T12:00:00Z") (hours 1))
*n* `integer` *→* `decimal`


N minutes, for use with 'add-time'.
N minutes, for use with 'add-time'.
```lisp
pact> (add-time (time "2016-07-22T12:00:00Z") (minutes 1))
"2016-07-22T12:01:00Z"
Expand All @@ -1000,7 +1000,7 @@ pact> (parse-time "%F" "2016-09-12")
*utcval* `string` *→* `time`


Construct time from UTCVAL using ISO8601 format (%Y-%m-%dT%H:%M:%SZ).
Construct time from UTCVAL using ISO8601 format (%Y-%m-%dT%H:%M:%SZ).
```lisp
pact> (time "2016-07-22T11:26:35Z")
"2016-07-22T11:26:35Z"
Expand Down Expand Up @@ -1498,6 +1498,17 @@ Execute GUARD, or defined keyset KEYSETNAME, to enforce desired predicate logic.
```


### enforce-verifier {#enforce-verifier}

*verifiername* `string` *→* `bool`


Enforce that a verifier is in scope.
```lisp
(enforce-verifier 'COOLZK)
```


### keys-2 {#keys-2}

*count* `integer` *matched* `integer` *→* `bool`
Expand Down Expand Up @@ -1947,7 +1958,7 @@ Retreive any accumulated events and optionally clear event state. Object returne
*→* `[string]`


Queries, or with arguments, sets execution config flags. Valid flags: ["AllowReadInLocal","DisableHistoryInTransactionalMode","DisableInlineMemCheck","DisableModuleInstall","DisableNewTrans","DisablePact40","DisablePact410","DisablePact42","DisablePact43","DisablePact431","DisablePact44","DisablePact45","DisablePact46","DisablePact47","DisablePact48","DisablePact49","DisablePactEvents","DisableRuntimeReturnTypeChecking","EnforceKeyFormats","OldReadOnlyBehavior","PreserveModuleIfacesBug","PreserveModuleNameBug","PreserveNsModuleInstallBug","PreserveShowDefs"]
Queries, or with arguments, sets execution config flags. Valid flags: ["AllowReadInLocal","DisableHistoryInTransactionalMode","DisableInlineMemCheck","DisableModuleInstall","DisableNewTrans","DisablePact40","DisablePact410","DisablePact42","DisablePact43","DisablePact431","DisablePact44","DisablePact45","DisablePact46","DisablePact47","DisablePact48","DisablePact49","DisablePactEvents","DisableRuntimeReturnTypeChecking","DisableVerifiers","EnforceKeyFormats","OldReadOnlyBehavior","PreserveModuleIfacesBug","PreserveModuleNameBug","PreserveNsModuleInstallBug","PreserveShowDefs"]
```lisp
pact> (env-exec-config ['DisableHistoryInTransactionalMode]) (env-exec-config)
["DisableHistoryInTransactionalMode"]
Expand Down Expand Up @@ -2081,6 +2092,17 @@ Set a flag to simulate on-chain behavior that differs from the repl, in particul
```


### env-verifiers {#env-verifiers}

*verifiers* `[object:*]` *→* `string`


Set transaction verifier names and capabilities. VERIFIERS is a list of objects with "name" specifying the verifier name, and "caps" specifying a list of associated capabilities.
```lisp
(env-verifiers [({'name: "COOLZK", 'caps: [(accounts.USER_GUARD "my-account")]}, {'name: "HYPERCHAIN-BRIDGE", 'caps: [(bridge.MINT "mycoin" 20)]}])
```


### expect {#expect}

*doc*&nbsp;`string` *expected*&nbsp;`<a>` *actual*&nbsp;`<a>` *&rarr;*&nbsp;`string`
Expand Down
1 change: 1 addition & 0 deletions pact.cabal
Original file line number Diff line number Diff line change
Expand Up @@ -181,6 +181,7 @@ library
Pact.Types.Type
Pact.Types.Typecheck
Pact.Types.Util
Pact.Types.Verifier
Pact.Types.Version
Pact.Utils.Servant

Expand Down
33 changes: 24 additions & 9 deletions src/Pact/ApiReq.hs
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,7 @@ import Pact.Types.RPC
import Pact.Types.Runtime
import Pact.Types.SigData
import Pact.Types.SPV
import Pact.Types.Verifier
import qualified Pact.JSON.Encode as J
import Pact.JSON.Legacy.Value
import Pact.JSON.Yaml
Expand Down Expand Up @@ -196,6 +197,7 @@ data ApiReq = ApiReq {
_ylCodeFile :: Maybe FilePath,
_ylKeyPairs :: Maybe [ApiKeyPair],
_ylSigners :: Maybe [ApiSigner],
_ylVerifiers :: Maybe [Verifier ParsedVerifierArgs],
_ylNonce :: Maybe Text,
_ylPublicMeta :: Maybe ApiPublicMeta,
_ylNetworkId :: Maybe NetworkId
Expand All @@ -211,6 +213,7 @@ instance J.Encode ApiReq where
, "networkId" J..= _ylNetworkId o
, "rollback" J..= _ylRollback o
, "signers" J..= fmap J.Array (_ylSigners o)
, "verifiers" J..= fmap J.Array (_ylVerifiers o)
, "step" J..= fmap J.Aeson (_ylStep o)
, "code" J..= _ylCode o
, "pactTxHash" J..= _ylPactTxHash o
Expand All @@ -228,7 +231,7 @@ instance Arbitrary ApiReq where
<*> arbitrary <*> arbitraryValue <*> arbitrary
<*> arbitrary <*> arbitrary <*> arbitrary
<*> arbitrary <*> arbitrary <*> arbitrary
<*> arbitrary <*> arbitrary
<*> arbitrary <*> arbitrary <*> arbitrary
where
arbitraryValue = suchThat arbitrary (/= Just Null)

Expand Down Expand Up @@ -508,8 +511,8 @@ mkApiReqExec unsignedReq ar@ApiReq{..} fp = do
return (code,cdata)
pubMeta <- mkPubMeta _ylPublicMeta
cmd <- withKeypairsOrSigner unsignedReq ar
(\ks -> mkExec code cdata pubMeta ks _ylNetworkId _ylNonce)
(\ss -> mkUnsignedExec code cdata pubMeta ss _ylNetworkId _ylNonce)
(\ks -> mkExec code cdata pubMeta ks (fromMaybe [] _ylVerifiers) _ylNetworkId _ylNonce)
(\ss -> mkUnsignedExec code cdata pubMeta ss (fromMaybe [] _ylVerifiers) _ylNetworkId _ylNonce)
return ((ar,code,cdata,pubMeta), cmd)

mkPubMeta :: Maybe ApiPublicMeta -> IO PublicMeta
Expand Down Expand Up @@ -545,15 +548,18 @@ mkExec
-- ^ public metadata
-> [(DynKeyPair, [SigCapability])]
-- ^ signing keypairs + caplists
-> [Verifier ParsedVerifierArgs]
-- ^ verifiers
-> Maybe NetworkId
-- ^ optional 'NetworkId'
-> Maybe Text
-- ^ optional nonce
-> IO (Command Text)
mkExec code mdata pubMeta kps nid ridm = do
mkExec code mdata pubMeta kps ves nid ridm = do
rid <- mkNonce ridm
cmd <- mkCommandWithDynKeys
kps
ves
pubMeta
rid
nid
Expand All @@ -571,15 +577,18 @@ mkUnsignedExec
-- ^ public metadata
-> [Signer]
-- ^ payload signers
-> [Verifier ParsedVerifierArgs]
-- ^ payload verifiers
-> Maybe NetworkId
-- ^ optional 'NetworkId'
-> Maybe Text
-- ^ optional nonce
-> IO (Command Text)
mkUnsignedExec code mdata pubMeta kps nid ridm = do
mkUnsignedExec code mdata pubMeta kps ves nid ridm = do
rid <- mkNonce ridm
cmd <- mkUnsignedCommand
kps
ves
pubMeta
rid
nid
Expand Down Expand Up @@ -613,8 +622,8 @@ mkApiReqCont unsignedReq ar@ApiReq{..} fp = do
let pactId = toPactId apiPactId
pubMeta <- mkPubMeta _ylPublicMeta
cmd <- withKeypairsOrSigner unsignedReq ar
(\ks -> mkCont pactId step rollback cdata pubMeta ks _ylNonce _ylProof _ylNetworkId)
(\ss -> mkUnsignedCont pactId step rollback cdata pubMeta ss _ylNonce _ylProof _ylNetworkId)
(\ks -> mkCont pactId step rollback cdata pubMeta ks (fromMaybe [] _ylVerifiers) _ylNonce _ylProof _ylNetworkId)
(\ss -> mkUnsignedCont pactId step rollback cdata pubMeta ss (fromMaybe [] _ylVerifiers) _ylNonce _ylProof _ylNetworkId)
return ((ar,"",cdata,pubMeta), cmd)

-- | Construct a Cont request message
Expand All @@ -632,17 +641,20 @@ mkCont
-- ^ command public metadata
-> [(DynKeyPair, [SigCapability])]
-- ^ signing keypairs
-> [Verifier ParsedVerifierArgs]
-- ^ verifiers
-> Maybe Text
-- ^ optional nonce
-> Maybe ContProof
-- ^ optional continuation proof (required for cross-chain)
-> Maybe NetworkId
-- ^ optional network id
-> IO (Command Text)
mkCont txid step rollback mdata pubMeta kps ridm proof nid = do
mkCont txid step rollback mdata pubMeta kps ves ridm proof nid = do
rid <- mkNonce ridm
cmd <- mkCommandWithDynKeys
kps
ves
pubMeta
rid
nid
Expand All @@ -665,17 +677,20 @@ mkUnsignedCont
-- ^ command public metadata
-> [Signer]
-- ^ payload signers
-> [Verifier ParsedVerifierArgs]
-- ^ verifiers
-> Maybe Text
-- ^ optional nonce
-> Maybe ContProof
-- ^ optional continuation proof (required for cross-chain)
-> Maybe NetworkId
-- ^ optional network id
-> IO (Command Text)
mkUnsignedCont txid step rollback mdata pubMeta kps ridm proof nid = do
mkUnsignedCont txid step rollback mdata pubMeta kps ves ridm proof nid = do
rid <- mkNonce ridm
cmd <- mkUnsignedCommand
kps
ves
pubMeta
(pack $ show rid)
nid
Expand Down
7 changes: 4 additions & 3 deletions src/Pact/Bench.hs
Original file line number Diff line number Diff line change
Expand Up @@ -158,6 +158,7 @@ loadBenchModule db = do
Nothing
pactInitialHash
[Signer Nothing pk Nothing []]
[]
let ec = ExecutionConfig $ S.fromList [FlagDisablePact44]
e <- setupEvalEnv db entity Transactional md (versionedNativesRefStore ec)
freeGasEnv permissiveNamespacePolicy noSPVSupport def ec
Expand Down Expand Up @@ -185,7 +186,7 @@ benchNFIO bname = bench bname . nfIO
runPactExec :: Advice -> String -> [Signer] -> Value -> Maybe (ModuleData Ref) ->
PactDbEnv e -> ParsedCode -> IO [PactValue]
runPactExec pt msg ss cdata benchMod dbEnv pc = do
let md = MsgData (toLegacyJson cdata) Nothing pactInitialHash ss
let md = MsgData (toLegacyJson cdata) Nothing pactInitialHash ss []
ec = ExecutionConfig $ S.fromList [FlagDisablePact44]
e <- set eeAdvice pt <$> setupEvalEnv dbEnv entity Transactional md (versionedNativesRefStore ec)
prodGasEnv permissiveNamespacePolicy noSPVSupport def ec
Expand All @@ -197,7 +198,7 @@ runPactExec pt msg ss cdata benchMod dbEnv pc = do

execPure :: Advice -> PactDbEnv e -> (String,[Term Name]) -> IO [Term Name]
execPure pt dbEnv (n,ts) = do
let md = MsgData (toLegacyJson Null) Nothing pactInitialHash []
let md = MsgData (toLegacyJson Null) Nothing pactInitialHash [] []
ec = ExecutionConfig $ S.fromList [FlagDisablePact44]
env <- set eeAdvice pt <$> setupEvalEnv dbEnv entity Local md (versionedNativesRefStore ec)
prodGasEnv permissiveNamespacePolicy noSPVSupport def ec
Expand Down Expand Up @@ -238,7 +239,7 @@ mkBenchCmd :: [Ed25519KeyPairCaps] -> (String, Text) -> IO (String, Command Byte
mkBenchCmd kps (str, t) = do
cmd <- mkCommand' kps
$ J.encodeStrict
$ Payload payload "nonce" (J.Aeson ()) ss Nothing
$ Payload payload "nonce" (J.Aeson ()) ss Nothing Nothing
return (str, cmd)
where
payload = Exec $ ExecMsg t (toLegacyJson Null)
Expand Down
2 changes: 1 addition & 1 deletion src/Pact/Eval.hs
Original file line number Diff line number Diff line change
Expand Up @@ -173,7 +173,7 @@ enforceGuard i g = case g of
evalError' i $ "Pact guard failed, intended: " <> pretty pid <> ", active: " <> pretty currPid

getSizeOfVersion :: Eval e SizeOfVersion
getSizeOfVersion =
getSizeOfVersion =
ifExecutionFlagSet' FlagDisablePact45 SizeOfV0 SizeOfV1
{-# INLINABLE getSizeOfVersion #-}

Expand Down
1 change: 1 addition & 0 deletions src/Pact/Gas/Table.hs
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,7 @@ defaultGasTable =
,("enforce-keyset", 8)
,("enforce-one", 6)
,("enforce-pact-version", 1)
,("enforce-verifier", 10)
,("enumerate", 1)
,("exp", 5)
,("filter", 3)
Expand Down
2 changes: 1 addition & 1 deletion src/Pact/GasModel/GasTests.hs
Original file line number Diff line number Diff line change
Expand Up @@ -371,7 +371,7 @@ requireCapabilityTests = tests
defPactExpression [text| (require-capability ($acctModuleNameText.GOV)) |]

cap = SigCapability (QualifiedName acctModuleName "GOV" def) []
capSlot = CapSlot CapCallStack cap []
capSlot = CapSlot CapCallStack False cap []
updateGrantedCap = setState (set (evalCapabilities . capStack) [capSlot])

tests =
Expand Down
19 changes: 16 additions & 3 deletions src/Pact/Interpreter.hs
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@ import Pact.Types.Pretty
import Pact.Types.RPC
import Pact.Types.Runtime
import Pact.Types.SPV
import Pact.Types.Verifier

import Pact.JSON.Legacy.Value

Expand All @@ -91,12 +92,13 @@ data MsgData = MsgData {
mdData :: !LegacyValue,
mdStep :: !(Maybe PactStep),
mdHash :: !Hash,
mdSigners :: [Signer]
mdSigners :: [Signer],
mdVerifiers :: [Verifier ()]
}


initMsgData :: Hash -> MsgData
initMsgData h = MsgData (toLegacyJson Null) def h def
initMsgData h = MsgData (toLegacyJson Null) def h def def

-- | Describes either a ContMsg or ExecMsg.
-- ContMsg is represented as a 'Maybe PactExec'
Expand Down Expand Up @@ -192,6 +194,7 @@ setupEvalEnv dbEnv ent mode msgData refStore gasEnv np spv pd ec = do
pure EvalEnv {
_eeRefStore = refStore
, _eeMsgSigs = mkMsgSigs $ mdSigners msgData
, _eeMsgVerifiers = mkMsgVerifiers $ mdVerifiers msgData
, _eeMsgBody = mdData msgData
, _eeMode = mode
, _eeEntity = ent
Expand All @@ -216,6 +219,9 @@ setupEvalEnv dbEnv ent mode msgData refStore gasEnv np spv pd ec = do
toPair Signer{..} = (pk,S.fromList _siCapList)
where
pk = PublicKeyText $ fromMaybe _siPubKey _siAddress
mkMsgVerifiers vs = M.fromListWith S.union $ map toPair vs
where
toPair Verifier{..} = (_verifierName, S.fromList _verifierCaps)


disablePactNatives :: [Text] -> ExecutionFlag -> ExecutionConfig -> Endo RefStore
Expand Down Expand Up @@ -245,6 +251,9 @@ disablePact47Natives = disablePactNatives pact47Natives FlagDisablePact47
disablePact410Natives :: ExecutionConfig -> Endo RefStore
disablePact410Natives = disablePactNatives pact410Natives FlagDisablePact410

disableVerifierNatives :: ExecutionConfig -> Endo RefStore
disableVerifierNatives = disablePactNatives verifierNatives FlagDisableVerifiers

pact40Natives :: [Text]
pact40Natives = ["enumerate" , "distinct" , "emit-event" , "concat" , "str-to-list"]

Expand All @@ -266,6 +275,9 @@ pact47Natives = ["dec"]
pact410Natives :: [Text]
pact410Natives = ["poseidon-hash-hack-a-chain"]

verifierNatives :: [Text]
verifierNatives = ["enforce-verifier"]

initRefStore :: RefStore
initRefStore = RefStore nativeDefs

Expand All @@ -279,7 +291,8 @@ versionedNativesRefStore ec = versionNatives initRefStore
, disablePact431Natives ec
, disablePact46Natives ec
, disablePact47Natives ec
, disablePact410Natives ec ]
, disablePact410Natives ec
, disableVerifierNatives ec ]

mkSQLiteEnv :: Logger -> Bool -> PSL.SQLiteConfig -> Loggers -> IO (PactDbEnv (DbEnv PSL.SQLite))
mkSQLiteEnv initLog deleteOldFile c loggers = do
Expand Down
Loading