conformance
LicenseApache-2.0
Safe HaskellNone
LanguageGHC2021

Conformance.Refusal

Description

A refusal closes a refuse-row only when it is attributable: the node must have refused in phase 2 (PlutusFailure) naming the script that refused (marker, the applied script hash hex). A phase-1 refusal proves nothing about the binding, and a reason that does not name the script proves nothing about which guard held. This is the #41 discipline as offchain/journey/li-refusals/Main.hs applies it.

wrongReasonMarker arms the negative control: matched against a marker no node reason can ever contain, the matcher must fail naming what came back (CONFORMANCE_CONTROL=wrong-reason).

Synopsis

Documentation

data RefusalMismatch Source #

How a refusal failed to attribute.

Constructors

NotPhase2

The node refused outside phase 2: proves nothing about the script binding.

Fields

MarkerAbsent

The reason does not name the expected script.

Fields

Instances

Instances details
Show RefusalMismatch Source # 
Instance details

Defined in Conformance.Refusal

Methods

showsPrec :: Int -> RefusalMismatch -> ShowS Source #

show :: RefusalMismatch -> String Source #

showList :: [RefusalMismatch] -> ShowS Source #

Eq RefusalMismatch Source # 
Instance details

Defined in Conformance.Refusal

Methods

(==) :: RefusalMismatch -> RefusalMismatch -> Bool Source #

(/=) :: RefusalMismatch -> RefusalMismatch -> Bool Source #

data RefusalRole Source #

Whose refusal is being attributed: a refusal ROW's receipt IS the row outcome and is written; a refused CONTROL's outcome is run-log evidence under its own identity and must never overwrite the row's receipt.

Constructors

RefusalRow 
RefusalControl 

Instances

Instances details
Show RefusalRole Source # 
Instance details

Defined in Conformance.Refusal

Methods

showsPrec :: Int -> RefusalRole -> ShowS Source #

show :: RefusalRole -> String Source #

showList :: [RefusalRole] -> ShowS Source #

Eq RefusalRole Source # 
Instance details

Defined in Conformance.Refusal

Methods

(==) :: RefusalRole -> RefusalRole -> Bool Source #

(/=) :: RefusalRole -> RefusalRole -> Bool Source #

data TracedRefusal Source #

What the traced replay of a refused transaction established: the reason it admitted for the attributed script, when every purpose of that script admitted the same one; the replay of each failing purpose; and the traced build those reasons rely on.

Instances

Instances details
Show TracedRefusal Source # 
Instance details

Defined in Conformance.Refusal

Methods

showsPrec :: Int -> TracedRefusal -> ShowS Source #

show :: TracedRefusal -> String Source #

showList :: [TracedRefusal] -> ShowS Source #

Eq TracedRefusal Source # 
Instance details

Defined in Conformance.Refusal

Methods

(==) :: TracedRefusal -> TracedRefusal -> Bool Source #

(/=) :: TracedRefusal -> TracedRefusal -> Bool Source #

untraced :: TracedRefusal Source #

A refusal no traced replay recorded.

attributeRefusalReceipt Source #

Arguments

:: RefusalRole 
-> FilePath

receipts directory (only touched when the policy writes)

-> String

row id

-> Verdict

verdict the receipt would carry

-> String

attributed script label

-> String

expected marker (applied script hash hex)

-> String

the node's refusal reason, verbatim

-> String

the submitted transaction's id

-> String

base commit

-> Bool

dirty tree flag

-> String

node identity

-> String

blueprint identity

-> TracedRefusal

what the traced replay of the refused transaction established

-> IO (Either RefusalMismatch ()) 

Attribute a node-submit refusal and, when the role's policy writes, record the refused receipt under the row's id. Returns the attribution mismatch for the caller to fail on loudly — this function never swallows a refusal that does not attribute, and a control here can never silently pass: acceptance and wrong-reason both fail the run upstream of this call. The receipt carries the trimmed reason (volume trimmed, never the script identities), the submitted transaction's id under rejected, and the node-submit venue.

matchRefusal :: String -> String -> Either RefusalMismatch () Source #

Require reason to be a phase-2 script failure naming marker. marker is the applied refusing script's hash hex; reason is the node's refusal text verbatim. The marker must be AMONG the extracted failure script hashes (NOTE-071) — a hash appearing in unrelated diagnostic text must not satisfy the check.

Two vocabularies, one discipline. At submit the node speaks PlutusFailure (the li-refusals precedent). At build evaluation the story language reports the node's per-purpose failure, whose text speaks CekError: the CEK machine executed the script and it errored. Both are the node's word for script-execution failure, never for a phase-1 ledger refusal — and both must name the script.

refusalScriptHashes :: String -> [String] Source #

Every ScriptHash "..." value in the reason, ledger order, first occurrence wins. A malformed transaction can trip two validators in one submission and the ledger's failure-list order is not stable, so attribution keeps them all: trim volume — the script binary, the cost model, the whole context — never the identities that attribute the refusal. Both shapes name hashes this way: the eval shape via pwcScriptHash, the node-submit shape in its failure headers. Unquoted ledger credentials never match this pattern.

refusalWritesReceipt :: RefusalRole -> Bool Source #

The receipt policy per role. A control keeps its evidence in the run log and its failures loud — an accepted control fails the run as a FINDING and a refusal that does not attribute fails the run naming the mismatch — so writing nothing leaves it unable to pass silently, while the row's held verdict survives its own control.

trimRefusal :: String -> String Source #

Keep the parts that attribute a refusal and drop the rest. show on an evaluation context embeds the whole compiled validator (~30KB of base64) plus the cost model and script context; a receipt carrying that is unreadable. Kept: the failure class and redeemer pointer, the failed script hash, the CEK error. Everything else — plutusBinary, pwcCostModel, the full ScriptContext — comes out; every failed script hash in ledger order binds which scripts ran, and the receipt already carries the blueprint hashes.

wrongReasonMarker :: String Source #

The marker the wrong-reason control matches refusals against: by construction no node reason can contain it, so a matched reason can never close a row and the control must fail.