From b2a8fcf6c9e641b2306db7328120b597629430ae Mon Sep 17 00:00:00 2001 From: kwxm Date: Thu, 20 Nov 2025 04:00:41 +0000 Subject: [PATCH 01/10] End-to-end test scripts for dropList --- .../PlutusScripts/Batch6/DropList.hs | 158 ++++++++++++++++++ plutus-scripts/PlutusScripts/Batch6/V_1_0.hs | 32 ++++ plutus-scripts/PlutusScripts/Batch6/V_1_1.hs | 27 +++ plutus-scripts/app/Main.hs | 19 ++- plutus-scripts/plutus-scripts.cabal | 3 + 5 files changed, 234 insertions(+), 5 deletions(-) create mode 100644 plutus-scripts/PlutusScripts/Batch6/DropList.hs create mode 100644 plutus-scripts/PlutusScripts/Batch6/V_1_0.hs create mode 100644 plutus-scripts/PlutusScripts/Batch6/V_1_1.hs diff --git a/plutus-scripts/PlutusScripts/Batch6/DropList.hs b/plutus-scripts/PlutusScripts/Batch6/DropList.hs new file mode 100644 index 0000000..1b9e010 --- /dev/null +++ b/plutus-scripts/PlutusScripts/Batch6/DropList.hs @@ -0,0 +1,158 @@ +{-| Simple end-to-end tests for the Plutus Core `dropList` builtin. These are +adapted from the `plutus-conformance` tests. -} + +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE TemplateHaskell #-} +{-# LANGUAGE ViewPatterns #-} + +module PlutusScripts.Batch6.DropList + {- + ( + mkCountSetBitsPolicy, + mkFindFirstSetBitPolicy, + succeedingCountSetBitsParams, + succeedingFindFirstSetBitParams + ) +-} +where + +import PlutusTx.Prelude qualified as P +import PlutusTx qualified +import PlutusTx (Data (B,I)) +import PlutusTx.Builtins qualified as BI +import PlutusTx.Builtins.HasOpaque () +import PlutusTx.Builtins.Internal qualified as BI (unitval, BuiltinInteger) + +import PlutusScripts.Helpers (hxs) + +data Params = Params + { count :: Integer + , input :: [Integer] + , output :: [Integer] + } +PlutusTx.unstableMakeIsData ''Params +PlutusTx.makeLift ''Params + +{-# INLINEABLE bilEq #-} +bilEq :: P.BuiltinList Integer -> P.BuiltinList Integer -> Bool +bilEq as bs = + if BI.null as && BI.null bs + then True + else (BI.head as P.== BI.head bs) && bilEq (BI.tail as) (BI.tail bs) + +{-# INLINEABLE mkDropListPolicy #-} +mkDropListPolicy :: [Params] -> P.BuiltinData -> P.BuiltinUnit +mkDropListPolicy l _ctx = go l + where go [] = BI.unitval + go (Params{..}:rest) = + if BI.drop count (P.toOpaque input) `bilEq` (P.toOpaque output) + then go rest + else P.traceError "mkCountSetBitsPolicyI" + +-- Succeeding inputs for lists of UPLC integers; `dropList` can only fail for cost reasons. +succeedingDropListParams :: [Params] +succeedingDropListParams = + [ Params -- Dropping zero elements has no effect. + { count = 0 + , input = [11,22,33,44,55,66,77,88,99] + , output = [11,22,33,44,55,66,77,88,99] + }, + Params -- A typical case where you really drop some elements. + { count = 7 + , input = [11,22,33,44,55,66,77,88,99] + , output = [88,99] + }, + Params -- Dropping more elements than the length of the list succeeds and returns the empty list. + { count = 17 + , input = [11,22,33,44,55,66,77,88,99] + , output = [] + }, + Params -- Dropping a negative number of elements succeeds and returns the list unchanged. + { count = 07 + , input = [11,22,33,44,55,66,77,88,99] + , output = [11,22,33,44,55,66,77,88,99] + }, + -- Dropping any number of elements from an empty list always succeeds (and + -- returns the empty list). + Params + { count = -1234 + , input = [] + , output = [] + }, + -- Dropping any number of elements from an empty list always succeeds (and + -- returns the empty list). + Params + { count = 0 + , input = [] + , output = [] + }, + -- Dropping any number of elements from an empty list always succeeds (and + -- returns the empty list). + Params + { count = 1234 + , input = [] + , output = [] + } + ] + +-- Failing inputs for lists of UPLC integers. +---These should return the empty list. However, if run in restricting mode they +-- will (probably, depending on the cost model) attempt to consume the maxmimum +-- budget and fail because the cost depends on the absolute value of the `count` +-- argument, irrespective of the size of the list. +failingDropListParams :: [Params] +failingDropListParams = + [ Params + { count = 10000000000000000000 + , input = [11,22,33,44,55,66,77,88,99] + , output = [] + }, + Params + { count = -12345678901234567890 + , input = [11,22,33,44,55,66,77,88,99] + , output = [] + } , + Params -- Drop (maxBound::Int)-1 elements + { count = 9223372036854775806 + , input = [ 20, 21, 22, 23, 24, 25, 26, 27, 28, 29 + , 30, 31, 32, 33, 34, 35, 36, 37, 38, 39 + , 40, 41, 42, 43, 44, 45, 46, 47, 48, 49 + , 50, 51, 52, 53, 54, 55, 56, 57, 58, 59 + , 60, 61, 62, 63, 64, 65, 66, 67, 68, 69 + , 70, 71, 72, 73, 74, 75, 76, 77, 78, 79 + , 80, 81, 82, 83, 84, 85, 86, 87, 88, 89 + , 90, 91, 92, 93, 94, 95, 96, 97, 98, 99 + , 100, 101, 102, 103, 104, 105, 106, 107 + , 108, 109, 110, 111 ] + , output = [] + }, + Params -- Drop (maxBound::Int) elements + { count = 9223372036854775807 + , input = [ 20, 21, 22, 23, 24, 25, 26, 27, 28, 29 + , 30, 31, 32, 33, 34, 35, 36, 37, 38, 39 + , 40, 41, 42, 43, 44, 45, 46, 47, 48, 49 + , 50, 51, 52, 53, 54, 55, 56, 57, 58, 59 + , 60, 61, 62, 63, 64, 65, 66, 67, 68, 69 + , 70, 71, 72, 73, 74, 75, 76, 77, 78, 79 + , 80, 81, 82, 83, 84, 85, 86, 87, 88, 89 + , 90, 91, 92, 93, 94, 95, 96, 97, 98, 99 + , 100, 101, 102, 103, 104, 105, 106, 107 + , 108, 109, 110, 111 ] + , output = [] + }, + Params -- Drop (maxBound::Int)+1 elements + { count = 9223372036854775808 + , input = [ 20, 21, 22, 23, 24, 25, 26, 27, 28, 29 + , 30, 31, 32, 33, 34, 35, 36, 37, 38, 39 + , 40, 41, 42, 43, 44, 45, 46, 47, 48, 49 + , 50, 51, 52, 53, 54, 55, 56, 57, 58, 59 + , 60, 61, 62, 63, 64, 65, 66, 67, 68, 69 + , 70, 71, 72, 73, 74, 75, 76, 77, 78, 79 + , 80, 81, 82, 83, 84, 85, 86, 87, 88, 89 + , 90, 91, 92, 93, 94, 95, 96, 97, 98, 99 + , 100, 101, 102, 103, 104, 105, 106, 107 + , 108, 109, 110, 111 ] + , output = [] + } + ] diff --git a/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs b/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs new file mode 100644 index 0000000..ed142bd --- /dev/null +++ b/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs @@ -0,0 +1,32 @@ +{-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=1.0.0 #-} + +module PlutusScripts.Batch6.V_1_0 where + +import PlutusCore.Default (DefaultFun, DefaultUni) +import PlutusCore.Version (plcVersion100) +import PlutusScripts.Batch6.DropList qualified as DropList +import PlutusTx (compile, liftCode, unsafeApplyCode) +import PlutusTx.Code (CompiledCodeIn) +import PlutusTx.Prelude qualified as P +import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) + +-- Tests for `dropList` with PlutusV2 and Plutus 1.0.0 + +-- FIXME: these are currently unused until we work out how to deal with the fact +-- that SoPs and all builtins will be enabled in PlutusV1 and PlutusV2 at PV11. + +-- Compiled code values with parameters already applied for succeeding tests +succeedingDropListPolicyCompiledV2 + :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +succeedingDropListPolicyCompiledV2 = + $$(compile [|| DropList.mkDropListPolicy ||]) + `unsafeApplyCode` liftCode plcVersion100 DropList.succeedingDropListParams + +failingDropListScriptGroupV2 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +failingDropListScriptGroupV2 = ScriptGroup + { sgBaseName = "failingDropListPolicyScriptV2" + , sgScripts = map compileDropList DropList.failingDropListParams + } + where compileDropList param = + $$(compile [|| DropList.mkDropListPolicy ||]) + `unsafeApplyCode` liftCode plcVersion100 [param] diff --git a/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs b/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs new file mode 100644 index 0000000..535bb4b --- /dev/null +++ b/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs @@ -0,0 +1,27 @@ +{-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=1.1.0 #-} + +module PlutusScripts.Batch6.V_1_1 where + +import PlutusCore.Default (DefaultFun, DefaultUni) +import PlutusCore.Version (plcVersion110) +import PlutusScripts.Batch6.DropList qualified as DropList +import PlutusTx (compile, liftCode, unsafeApplyCode) +import PlutusTx.Code (CompiledCodeIn) +import PlutusTx.Prelude qualified as P +import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) + +-- Compiled code values with parameters already applied for succeeding tests +succeedingDropListPolicyCompiledV3 + :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +succeedingDropListPolicyCompiledV3 = + $$(compile [|| DropList.mkDropListPolicy ||]) + `unsafeApplyCode` liftCode plcVersion110 DropList.succeedingDropListParams + +failingDropListScriptGroupV3 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +failingDropListScriptGroupV3 = ScriptGroup + { sgBaseName = "failingDropListPolicyScriptV3" + , sgScripts = map compileDropList DropList.failingDropListParams + } + where compileDropList param = + $$(compile [|| DropList.mkDropListPolicy ||]) + `unsafeApplyCode` liftCode plcVersion110 [param] diff --git a/plutus-scripts/app/Main.hs b/plutus-scripts/app/Main.hs index dee96c2..f44b210 100644 --- a/plutus-scripts/app/Main.hs +++ b/plutus-scripts/app/Main.hs @@ -12,6 +12,8 @@ import PlutusScripts.Bitwise.V_1_0 qualified as BitwiseV0 import PlutusScripts.Bitwise.V_1_1 qualified as BitwiseV1 import PlutusScripts.Hashing.V_1_1 qualified as Hashing import PlutusScripts.SECP256k1.V_1_1 qualified as SECP +-- import PlutusScripts.Batch6.V_1_0 qualified as Batch6_1_0 +import PlutusScripts.Batch6.V_1_1 qualified as Batch6_1_1 import PlutusTx.Code (CompiledCode) import System.Directory (createDirectoryIfMissing) @@ -36,15 +38,15 @@ main = withUtf8 do BitwiseV0.byteStringToIntegerRoundtripPolicyCompiledV2 -- Basic scripts (PlutusV3) - writeEnvelopeV3 "alwaysSucceedPolicyScriptV3" Basic.alwaysSucceedPolicyCompiled - writeEnvelopeV3 "alwaysFailsPolicyScriptV3" Basic.alwaysFailsPolicyCompiled - writeEnvelopeV3 "mintTokenNamePolicyScriptV3" Basic.mintTokenNamePolicyCompiledV3 - writeEnvelopeV3 "timeRangePolicyScriptV3" Basic.timeRangePolicyCompiledV3 + writeEnvelopeV3 "alwaysSucceedPolicyScriptV3" Basic.alwaysSucceedPolicyCompiled + writeEnvelopeV3 "alwaysFailsPolicyScriptV3" Basic.alwaysFailsPolicyCompiled + writeEnvelopeV3 "mintTokenNamePolicyScriptV3" Basic.mintTokenNamePolicyCompiledV3 + writeEnvelopeV3 "timeRangePolicyScriptV3" Basic.timeRangePolicyCompiledV3 writeEnvelopeV3 "witnessRedeemerPolicyScriptV3" Basic.witnessRedeemerPolicyCompiledV3 -- SECP256k1 scripts (PlutusV3) writeEnvelopeV3 "verifySchnorrPolicyScriptV3" SECP.verifySchnorrPolicyCompiledV3 - writeEnvelopeV3 "verifyEcdsaPolicyScriptV3" SECP.verifyEcdsaPolicyCompiledV3 + writeEnvelopeV3 "verifyEcdsaPolicyScriptV3" SECP.verifyEcdsaPolicyCompiledV3 -- Hashing scripts (PlutusV3) writeEnvelopeV3 "succeedingRipemd_160Policy" Hashing.succeedingRipemd_160PolicyCompiled @@ -87,6 +89,13 @@ main = withUtf8 do -- Failing Bitwise Tests (ReadBit, WriteBits, ReplicateByte variants) mapM_ writeScriptGroup BitwiseV1.failingBitwiseScriptGroupsV3 + -- Batch 6 (protocol version 11) + writeEnvelopeV3 + "succeedingDropListPolicyScriptV3" + Batch6_1_1.succeedingDropListPolicyCompiledV3 + + writeScriptGroup Batch6_1_1.failingDropListScriptGroupV3 + -------------------------------------------------------------------------------- -- IO helpers ------------------------------------------------------------------ diff --git a/plutus-scripts/plutus-scripts.cabal b/plutus-scripts/plutus-scripts.cabal index 217bfe5..b7f9300 100644 --- a/plutus-scripts/plutus-scripts.cabal +++ b/plutus-scripts/plutus-scripts.cabal @@ -118,6 +118,9 @@ library scripts PlutusScripts.SECP256k1.Common PlutusScripts.SECP256k1.V_1_0 PlutusScripts.SECP256k1.V_1_1 + PlutusScripts.Batch6.DropList + PlutusScripts.Batch6.V_1_0 + PlutusScripts.Batch6.V_1_1 executable envelopes import: ghc-options From 8365fd110b8b4c262b7eb53a7a8b9576919f7337 Mon Sep 17 00:00:00 2001 From: kwxm Date: Thu, 20 Nov 2025 04:11:40 +0000 Subject: [PATCH 02/10] End-to-end test scripts for dropList --- .../PlutusScripts/Batch6/DropList.hs | 32 ++++++------------- plutus-scripts/PlutusScripts/Batch6/V_1_0.hs | 9 +++--- plutus-scripts/PlutusScripts/Batch6/V_1_1.hs | 9 +++--- plutus-scripts/app/Main.hs | 4 +-- 4 files changed, 22 insertions(+), 32 deletions(-) diff --git a/plutus-scripts/PlutusScripts/Batch6/DropList.hs b/plutus-scripts/PlutusScripts/Batch6/DropList.hs index 1b9e010..52581b4 100644 --- a/plutus-scripts/PlutusScripts/Batch6/DropList.hs +++ b/plutus-scripts/PlutusScripts/Batch6/DropList.hs @@ -6,25 +6,13 @@ adapted from the `plutus-conformance` tests. -} {-# LANGUAGE TemplateHaskell #-} {-# LANGUAGE ViewPatterns #-} -module PlutusScripts.Batch6.DropList - {- - ( - mkCountSetBitsPolicy, - mkFindFirstSetBitPolicy, - succeedingCountSetBitsParams, - succeedingFindFirstSetBitParams - ) --} +module PlutusScripts.Batch6.DropList ( mkDropListPolicy, succeedingDropListParams, expensiveDropListParams) where import PlutusTx.Prelude qualified as P import PlutusTx qualified -import PlutusTx (Data (B,I)) import PlutusTx.Builtins qualified as BI -import PlutusTx.Builtins.HasOpaque () -import PlutusTx.Builtins.Internal qualified as BI (unitval, BuiltinInteger) - -import PlutusScripts.Helpers (hxs) +import PlutusTx.Builtins.Internal qualified as BI (unitval) data Params = Params { count :: Integer @@ -34,21 +22,21 @@ data Params = Params PlutusTx.unstableMakeIsData ''Params PlutusTx.makeLift ''Params -{-# INLINEABLE bilEq #-} -bilEq :: P.BuiltinList Integer -> P.BuiltinList Integer -> Bool -bilEq as bs = +{-# INLINEABLE eqIntList #-} +eqIntList :: P.BuiltinList Integer -> P.BuiltinList Integer -> Bool +eqIntList as bs = if BI.null as && BI.null bs then True - else (BI.head as P.== BI.head bs) && bilEq (BI.tail as) (BI.tail bs) + else (BI.head as P.== BI.head bs) && eqIntList (BI.tail as) (BI.tail bs) {-# INLINEABLE mkDropListPolicy #-} mkDropListPolicy :: [Params] -> P.BuiltinData -> P.BuiltinUnit mkDropListPolicy l _ctx = go l where go [] = BI.unitval go (Params{..}:rest) = - if BI.drop count (P.toOpaque input) `bilEq` (P.toOpaque output) + if BI.drop count (P.toOpaque input) `eqIntList` (P.toOpaque output) then go rest - else P.traceError "mkCountSetBitsPolicyI" + else P.traceError "mkCountSetBitsPolicy" -- Succeeding inputs for lists of UPLC integers; `dropList` can only fail for cost reasons. succeedingDropListParams :: [Params] @@ -101,8 +89,8 @@ succeedingDropListParams = -- will (probably, depending on the cost model) attempt to consume the maxmimum -- budget and fail because the cost depends on the absolute value of the `count` -- argument, irrespective of the size of the list. -failingDropListParams :: [Params] -failingDropListParams = +expensiveDropListParams :: [Params] +expensiveDropListParams = [ Params { count = 10000000000000000000 , input = [11,22,33,44,55,66,77,88,99] diff --git a/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs b/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs index ed142bd..9c3d15e 100644 --- a/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs +++ b/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs @@ -22,10 +22,11 @@ succeedingDropListPolicyCompiledV2 = $$(compile [|| DropList.mkDropListPolicy ||]) `unsafeApplyCode` liftCode plcVersion100 DropList.succeedingDropListParams -failingDropListScriptGroupV2 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -failingDropListScriptGroupV2 = ScriptGroup - { sgBaseName = "failingDropListPolicyScriptV2" - , sgScripts = map compileDropList DropList.failingDropListParams +-- These should fail due to exceeding the budget. +expensiveDropListScriptGroupV2 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +expensiveDropListScriptGroupV2 = ScriptGroup + { sgBaseName = "expensiveDropListPolicyScriptV2" + , sgScripts = map compileDropList DropList.expensiveDropListParams } where compileDropList param = $$(compile [|| DropList.mkDropListPolicy ||]) diff --git a/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs b/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs index 535bb4b..c744597 100644 --- a/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs +++ b/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs @@ -17,10 +17,11 @@ succeedingDropListPolicyCompiledV3 = $$(compile [|| DropList.mkDropListPolicy ||]) `unsafeApplyCode` liftCode plcVersion110 DropList.succeedingDropListParams -failingDropListScriptGroupV3 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -failingDropListScriptGroupV3 = ScriptGroup - { sgBaseName = "failingDropListPolicyScriptV3" - , sgScripts = map compileDropList DropList.failingDropListParams +-- These should fail due to exceeding the budget. +expensiveDropListScriptGroupV3 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +expensiveDropListScriptGroupV3 = ScriptGroup + { sgBaseName = "expensiveDropListPolicyScriptV3" + , sgScripts = map compileDropList DropList.expensiveDropListParams } where compileDropList param = $$(compile [|| DropList.mkDropListPolicy ||]) diff --git a/plutus-scripts/app/Main.hs b/plutus-scripts/app/Main.hs index f44b210..9aa8f09 100644 --- a/plutus-scripts/app/Main.hs +++ b/plutus-scripts/app/Main.hs @@ -89,12 +89,12 @@ main = withUtf8 do -- Failing Bitwise Tests (ReadBit, WriteBits, ReplicateByte variants) mapM_ writeScriptGroup BitwiseV1.failingBitwiseScriptGroupsV3 - -- Batch 6 (protocol version 11) + -- ** Batch 6 (protocol version 11) ** writeEnvelopeV3 "succeedingDropListPolicyScriptV3" Batch6_1_1.succeedingDropListPolicyCompiledV3 - writeScriptGroup Batch6_1_1.failingDropListScriptGroupV3 + writeScriptGroup Batch6_1_1.expensiveDropListScriptGroupV3 -------------------------------------------------------------------------------- -- IO helpers ------------------------------------------------------------------ From 93eff7d43a97d952b9fdc8a6f412fbb26d580b10 Mon Sep 17 00:00:00 2001 From: kwxm Date: Thu, 20 Nov 2025 04:13:54 +0000 Subject: [PATCH 03/10] Remove commented-out import --- plutus-scripts/app/Main.hs | 1 - 1 file changed, 1 deletion(-) diff --git a/plutus-scripts/app/Main.hs b/plutus-scripts/app/Main.hs index 9aa8f09..4077c98 100644 --- a/plutus-scripts/app/Main.hs +++ b/plutus-scripts/app/Main.hs @@ -12,7 +12,6 @@ import PlutusScripts.Bitwise.V_1_0 qualified as BitwiseV0 import PlutusScripts.Bitwise.V_1_1 qualified as BitwiseV1 import PlutusScripts.Hashing.V_1_1 qualified as Hashing import PlutusScripts.SECP256k1.V_1_1 qualified as SECP --- import PlutusScripts.Batch6.V_1_0 qualified as Batch6_1_0 import PlutusScripts.Batch6.V_1_1 qualified as Batch6_1_1 import PlutusTx.Code (CompiledCode) import System.Directory (createDirectoryIfMissing) From cccb968a4f9e93391950dc463ae1bb3c6b8a4037 Mon Sep 17 00:00:00 2001 From: kwxm Date: Mon, 24 Nov 2025 10:36:20 +0000 Subject: [PATCH 04/10] Fix formatting --- CLAUDE.md | 6 +- README.md | 11 + plutus-scripts/Helpers/ScriptUtils.hs | 4 +- .../PlutusScripts/Batch6/DropList.hs | 457 ++++++++++++++---- plutus-scripts/PlutusScripts/Batch6/V_1_0.hs | 20 +- plutus-scripts/PlutusScripts/Batch6/V_1_1.hs | 20 +- plutus-scripts/PlutusScripts/Bitwise/V_1_1.hs | 10 +- plutus-scripts/app/Main.hs | 20 +- plutus-scripts/plutus-scripts.cabal | 6 +- 9 files changed, 415 insertions(+), 139 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index 4fe0a9d..556f8d5 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -124,6 +124,7 @@ mapM_ writeScriptGroup BitwiseV1.failingBitwiseScriptGroupsV3 ``` This pattern: + - ✅ Encapsulates parameter iteration in the library - ✅ Keeps executable unaware of Params types - ✅ Generates numbered script files automatically @@ -242,6 +243,7 @@ cabal run envelopes Output: Multiple `.plutus` files in `serialised-plutus-scripts/` (git-ignored) **Generated Scripts**: + - PlutusV2 scripts (bytestring/integer conversions) - Basic PlutusV3 scripts (always succeed/fail, token names, time ranges, redeemers) - SECP256k1 scripts (Schnorr and ECDSA signature verification) @@ -267,12 +269,14 @@ To add a simple script: For parameterized tests (e.g., failing tests with multiple edge cases): 1. Define test parameters in the `Common` module: + ```haskell data Params = Params { input :: ByteString, expected :: Bool } testParams :: [Params] ``` 2. Create a `ScriptGroup` in the versioned module: + ```haskell myScriptGroup :: [ScriptGroup DefaultUni DefaultFun (BuiltinData -> BuiltinUnit)] myScriptGroup = [ScriptGroup @@ -282,7 +286,7 @@ For parameterized tests (e.g., failing tests with multiple edge cases): ``` 3. Use `mapM_ writeScriptGroup` in `app/Main.hs` -4. Run `cabal run envelopes` - generates numbered files (myTestScript_1.plutus, _2.plutus, ...) +4. Run `cabal run envelopes` - generates numbered files (myTestScript_1.plutus, \_2.plutus, ...) ## Nix Binary Cache diff --git a/README.md b/README.md index cedfacf..e9bb6fa 100644 --- a/README.md +++ b/README.md @@ -9,6 +9,7 @@ Originally based on the [Antaeus repository](https://github.com/IntersectMBO/ant This repository provides serialized Plutus scripts compiled for **Plutus Core 1.0.0 and 1.1.0** targeting **PlutusV2** and **PlutusV3** ledger APIs. The scripts are generated as `.plutus` envelope files consumed by the [cardano-node-tests](https://github.com/IntersectMBO/cardano-node-tests) E2E test suite. **Key Features:** + - Comprehensive script library covering basic validators, bitwise operations, cryptography, and governance - Plutus Core 1.0.0 and 1.1.0 support with PlutusV2 and PlutusV3 targeting - Modular architecture with Common/Versioned module pattern @@ -40,6 +41,7 @@ cabal run envelopes The generated `.plutus` files are JSON envelopes containing the serialized Plutus scripts, ready for use in cardano-node-tests. **Generated Scripts**: + - PlutusV2 scripts (bytestring/integer conversions) - Basic PlutusV3 scripts (always succeed/fail, token names, time ranges, redeemers) - SECP256k1 scripts (Schnorr and ECDSA signature verification) @@ -87,12 +89,14 @@ Core testing scripts for fundamental blockchain operations: Scripts demonstrating Plutus bitwise primitives (Plutus Core 1.1.0+): **Succeeding Tests**: + - Logical operations: `andByteString`, `orByteString`, `xorByteString`, `complementByteString` - Shifts and rotates: `shiftByteString`, `rotateByteString` - Bit manipulation: `readBit`, `writeBits`, `countSetBits`, `findFirstSetBit` - Byte operations: `replicateByte`, conversions between integers and bytestrings **Failing Tests**: + - ReadBit edge cases: empty bytestring, negative indices, out of bounds, Int64 limits - WriteBits edge cases: empty bytestring, negative indices, out of bounds - ReplicateByte edge cases: negative count, invalid byte values, size limits @@ -145,17 +149,20 @@ alwaysSucceedPolicyCompiled = $$(PlutusTx.compile [||mkAlwaysSucceedPolicyV3||]) Scripts are compiled for both **Plutus Core 1.0.0** (PlutusV2) and **Plutus Core 1.1.0** (PlutusV3): **Plutus Core 1.0.0 scripts:** + ```haskell {-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=1.0.0 #-} ``` **Plutus Core 1.1.0 scripts:** + ```haskell {-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:conservative-optimisation #-} {-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=1.1.0 #-} ``` PlutusV3 (1.1.0) validators receive enhanced `ScriptContext` with governance support: + - Committee actions and voting - Proposal transactions - Constitutional committee hot key operations @@ -292,6 +299,7 @@ Example envelope structure: 5. **Validation**: Cardano node validates scripts during E2E tests The scripts enable comprehensive testing of: + - Plutus V2 and V3 features (including governance) - Bitwise operations introduced in Plutus Core 1.1.0 - Cryptographic primitives (BLS, SECP256k1) @@ -302,18 +310,21 @@ The scripts enable comprehensive testing of: ### Adding New Scripts 1. **Create validator logic** in `PlutusScripts//Common.hs`: + ```haskell {-# INLINEABLE myValidator #-} myValidator :: BuiltinData -> BuiltinData -> BuiltinData -> () ``` 2. **Add versioned module** `PlutusScripts//V_1_1.hs`: + ```haskell myValidatorCompiled :: CompiledCode (BuiltinData -> BuiltinData -> BuiltinData -> ()) myValidatorCompiled = $$(PlutusTx.compile [||myValidator||]) ``` 3. **Update envelopes executable** in `app/Main.hs`: + ```haskell writeEnvelopeV3 "myValidatorScript" MyCategory.myValidatorCompiled ``` diff --git a/plutus-scripts/Helpers/ScriptUtils.hs b/plutus-scripts/Helpers/ScriptUtils.hs index 17c4018..26f5e14 100644 --- a/plutus-scripts/Helpers/ScriptUtils.hs +++ b/plutus-scripts/Helpers/ScriptUtils.hs @@ -38,9 +38,9 @@ The executable can iterate over 'sgScripts' and generate files named -} data ScriptGroup uni fun a = ScriptGroup { sgBaseName :: String - -- ^ Base name for the script group (e.g., "failingReadBitPolicyScriptV3") + -- ^ Base name for the script group (e.g., "failingReadBitPolicyScriptV3") , sgScripts :: [CompiledCodeIn uni fun a] - -- ^ List of compiled scripts, will be numbered from 1 + -- ^ List of compiled scripts, will be numbered from 1 } {-# INLINEABLE tracedUnsafeFrom #-} diff --git a/plutus-scripts/PlutusScripts/Batch6/DropList.hs b/plutus-scripts/PlutusScripts/Batch6/DropList.hs index 52581b4..9ef5037 100644 --- a/plutus-scripts/PlutusScripts/Batch6/DropList.hs +++ b/plutus-scripts/PlutusScripts/Batch6/DropList.hs @@ -1,18 +1,18 @@ -{-| Simple end-to-end tests for the Plutus Core `dropList` builtin. These are -adapted from the `plutus-conformance` tests. -} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE TemplateHaskell #-} +{-# LANGUAGE ViewPatterns #-} -{-# LANGUAGE OverloadedStrings #-} -{-# LANGUAGE RecordWildCards #-} -{-# LANGUAGE TemplateHaskell #-} -{-# LANGUAGE ViewPatterns #-} - -module PlutusScripts.Batch6.DropList ( mkDropListPolicy, succeedingDropListParams, expensiveDropListParams) +{- | Simple end-to-end tests for the Plutus Core `dropList` builtin. These are +adapted from the `plutus-conformance` tests. +-} +module PlutusScripts.Batch6.DropList (mkDropListPolicy, succeedingDropListParams, expensiveDropListParams) where -import PlutusTx.Prelude qualified as P import PlutusTx qualified import PlutusTx.Builtins qualified as BI import PlutusTx.Builtins.Internal qualified as BI (unitval) +import PlutusTx.Prelude qualified as P data Params = Params { count :: Integer @@ -26,62 +26,63 @@ PlutusTx.makeLift ''Params eqIntList :: P.BuiltinList Integer -> P.BuiltinList Integer -> Bool eqIntList as bs = if BI.null as && BI.null bs - then True - else (BI.head as P.== BI.head bs) && eqIntList (BI.tail as) (BI.tail bs) + then True + else (BI.head as P.== BI.head bs) && eqIntList (BI.tail as) (BI.tail bs) {-# INLINEABLE mkDropListPolicy #-} mkDropListPolicy :: [Params] -> P.BuiltinData -> P.BuiltinUnit mkDropListPolicy l _ctx = go l - where go [] = BI.unitval - go (Params{..}:rest) = - if BI.drop count (P.toOpaque input) `eqIntList` (P.toOpaque output) - then go rest - else P.traceError "mkCountSetBitsPolicy" + where + go [] = BI.unitval + go (Params{..} : rest) = + if BI.drop count (P.toOpaque input) `eqIntList` (P.toOpaque output) + then go rest + else P.traceError "mkCountSetBitsPolicy" -- Succeeding inputs for lists of UPLC integers; `dropList` can only fail for cost reasons. succeedingDropListParams :: [Params] succeedingDropListParams = - [ Params -- Dropping zero elements has no effect. - { count = 0 - , input = [11,22,33,44,55,66,77,88,99] - , output = [11,22,33,44,55,66,77,88,99] - }, - Params -- A typical case where you really drop some elements. - { count = 7 - , input = [11,22,33,44,55,66,77,88,99] - , output = [88,99] - }, - Params -- Dropping more elements than the length of the list succeeds and returns the empty list. - { count = 17 - , input = [11,22,33,44,55,66,77,88,99] - , output = [] - }, - Params -- Dropping a negative number of elements succeeds and returns the list unchanged. - { count = 07 - , input = [11,22,33,44,55,66,77,88,99] - , output = [11,22,33,44,55,66,77,88,99] - }, - -- Dropping any number of elements from an empty list always succeeds (and + [ Params -- Dropping zero elements has no effect. + { count = 0 + , input = [11, 22, 33, 44, 55, 66, 77, 88, 99] + , output = [11, 22, 33, 44, 55, 66, 77, 88, 99] + } + , Params -- A typical case where you really drop some elements. + { count = 7 + , input = [11, 22, 33, 44, 55, 66, 77, 88, 99] + , output = [88, 99] + } + , Params -- Dropping more elements than the length of the list succeeds and returns the empty list. + { count = 17 + , input = [11, 22, 33, 44, 55, 66, 77, 88, 99] + , output = [] + } + , Params -- Dropping a negative number of elements succeeds and returns the list unchanged. + { count = 07 + , input = [11, 22, 33, 44, 55, 66, 77, 88, 99] + , output = [11, 22, 33, 44, 55, 66, 77, 88, 99] + } + , -- Dropping any number of elements from an empty list always succeeds (and -- returns the empty list). Params - { count = -1234 - , input = [] - , output = [] - }, - -- Dropping any number of elements from an empty list always succeeds (and + { count = -1234 + , input = [] + , output = [] + } + , -- Dropping any number of elements from an empty list always succeeds (and -- returns the empty list). Params - { count = 0 - , input = [] - , output = [] - }, - -- Dropping any number of elements from an empty list always succeeds (and + { count = 0 + , input = [] + , output = [] + } + , -- Dropping any number of elements from an empty list always succeeds (and -- returns the empty list). Params - { count = 1234 - , input = [] - , output = [] - } + { count = 1234 + , input = [] + , output = [] + } ] -- Failing inputs for lists of UPLC integers. @@ -92,55 +93,307 @@ succeedingDropListParams = expensiveDropListParams :: [Params] expensiveDropListParams = [ Params - { count = 10000000000000000000 - , input = [11,22,33,44,55,66,77,88,99] - , output = [] - }, - Params - { count = -12345678901234567890 - , input = [11,22,33,44,55,66,77,88,99] - , output = [] - } , - Params -- Drop (maxBound::Int)-1 elements - { count = 9223372036854775806 - , input = [ 20, 21, 22, 23, 24, 25, 26, 27, 28, 29 - , 30, 31, 32, 33, 34, 35, 36, 37, 38, 39 - , 40, 41, 42, 43, 44, 45, 46, 47, 48, 49 - , 50, 51, 52, 53, 54, 55, 56, 57, 58, 59 - , 60, 61, 62, 63, 64, 65, 66, 67, 68, 69 - , 70, 71, 72, 73, 74, 75, 76, 77, 78, 79 - , 80, 81, 82, 83, 84, 85, 86, 87, 88, 89 - , 90, 91, 92, 93, 94, 95, 96, 97, 98, 99 - , 100, 101, 102, 103, 104, 105, 106, 107 - , 108, 109, 110, 111 ] - , output = [] - }, - Params -- Drop (maxBound::Int) elements - { count = 9223372036854775807 - , input = [ 20, 21, 22, 23, 24, 25, 26, 27, 28, 29 - , 30, 31, 32, 33, 34, 35, 36, 37, 38, 39 - , 40, 41, 42, 43, 44, 45, 46, 47, 48, 49 - , 50, 51, 52, 53, 54, 55, 56, 57, 58, 59 - , 60, 61, 62, 63, 64, 65, 66, 67, 68, 69 - , 70, 71, 72, 73, 74, 75, 76, 77, 78, 79 - , 80, 81, 82, 83, 84, 85, 86, 87, 88, 89 - , 90, 91, 92, 93, 94, 95, 96, 97, 98, 99 - , 100, 101, 102, 103, 104, 105, 106, 107 - , 108, 109, 110, 111 ] - , output = [] - }, - Params -- Drop (maxBound::Int)+1 elements - { count = 9223372036854775808 - , input = [ 20, 21, 22, 23, 24, 25, 26, 27, 28, 29 - , 30, 31, 32, 33, 34, 35, 36, 37, 38, 39 - , 40, 41, 42, 43, 44, 45, 46, 47, 48, 49 - , 50, 51, 52, 53, 54, 55, 56, 57, 58, 59 - , 60, 61, 62, 63, 64, 65, 66, 67, 68, 69 - , 70, 71, 72, 73, 74, 75, 76, 77, 78, 79 - , 80, 81, 82, 83, 84, 85, 86, 87, 88, 89 - , 90, 91, 92, 93, 94, 95, 96, 97, 98, 99 - , 100, 101, 102, 103, 104, 105, 106, 107 - , 108, 109, 110, 111 ] - , output = [] - } + { count = 10000000000000000000 + , input = [11, 22, 33, 44, 55, 66, 77, 88, 99] + , output = [] + } + , Params + { count = -12345678901234567890 + , input = [11, 22, 33, 44, 55, 66, 77, 88, 99] + , output = [] + } + , Params -- Drop (maxBound::Int)-1 elements + { count = 9223372036854775806 + , input = + [ 20 + , 21 + , 22 + , 23 + , 24 + , 25 + , 26 + , 27 + , 28 + , 29 + , 30 + , 31 + , 32 + , 33 + , 34 + , 35 + , 36 + , 37 + , 38 + , 39 + , 40 + , 41 + , 42 + , 43 + , 44 + , 45 + , 46 + , 47 + , 48 + , 49 + , 50 + , 51 + , 52 + , 53 + , 54 + , 55 + , 56 + , 57 + , 58 + , 59 + , 60 + , 61 + , 62 + , 63 + , 64 + , 65 + , 66 + , 67 + , 68 + , 69 + , 70 + , 71 + , 72 + , 73 + , 74 + , 75 + , 76 + , 77 + , 78 + , 79 + , 80 + , 81 + , 82 + , 83 + , 84 + , 85 + , 86 + , 87 + , 88 + , 89 + , 90 + , 91 + , 92 + , 93 + , 94 + , 95 + , 96 + , 97 + , 98 + , 99 + , 100 + , 101 + , 102 + , 103 + , 104 + , 105 + , 106 + , 107 + , 108 + , 109 + , 110 + , 111 + ] + , output = [] + } + , Params -- Drop (maxBound::Int) elements + { count = 9223372036854775807 + , input = + [ 20 + , 21 + , 22 + , 23 + , 24 + , 25 + , 26 + , 27 + , 28 + , 29 + , 30 + , 31 + , 32 + , 33 + , 34 + , 35 + , 36 + , 37 + , 38 + , 39 + , 40 + , 41 + , 42 + , 43 + , 44 + , 45 + , 46 + , 47 + , 48 + , 49 + , 50 + , 51 + , 52 + , 53 + , 54 + , 55 + , 56 + , 57 + , 58 + , 59 + , 60 + , 61 + , 62 + , 63 + , 64 + , 65 + , 66 + , 67 + , 68 + , 69 + , 70 + , 71 + , 72 + , 73 + , 74 + , 75 + , 76 + , 77 + , 78 + , 79 + , 80 + , 81 + , 82 + , 83 + , 84 + , 85 + , 86 + , 87 + , 88 + , 89 + , 90 + , 91 + , 92 + , 93 + , 94 + , 95 + , 96 + , 97 + , 98 + , 99 + , 100 + , 101 + , 102 + , 103 + , 104 + , 105 + , 106 + , 107 + , 108 + , 109 + , 110 + , 111 + ] + , output = [] + } + , Params -- Drop (maxBound::Int)+1 elements + { count = 9223372036854775808 + , input = + [ 20 + , 21 + , 22 + , 23 + , 24 + , 25 + , 26 + , 27 + , 28 + , 29 + , 30 + , 31 + , 32 + , 33 + , 34 + , 35 + , 36 + , 37 + , 38 + , 39 + , 40 + , 41 + , 42 + , 43 + , 44 + , 45 + , 46 + , 47 + , 48 + , 49 + , 50 + , 51 + , 52 + , 53 + , 54 + , 55 + , 56 + , 57 + , 58 + , 59 + , 60 + , 61 + , 62 + , 63 + , 64 + , 65 + , 66 + , 67 + , 68 + , 69 + , 70 + , 71 + , 72 + , 73 + , 74 + , 75 + , 76 + , 77 + , 78 + , 79 + , 80 + , 81 + , 82 + , 83 + , 84 + , 85 + , 86 + , 87 + , 88 + , 89 + , 90 + , 91 + , 92 + , 93 + , 94 + , 95 + , 96 + , 97 + , 98 + , 99 + , 100 + , 101 + , 102 + , 103 + , 104 + , 105 + , 106 + , 107 + , 108 + , 109 + , 110 + , 111 + ] + , output = [] + } ] diff --git a/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs b/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs index 9c3d15e..62ff02d 100644 --- a/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs +++ b/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs @@ -2,13 +2,13 @@ module PlutusScripts.Batch6.V_1_0 where +import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) import PlutusCore.Default (DefaultFun, DefaultUni) import PlutusCore.Version (plcVersion100) import PlutusScripts.Batch6.DropList qualified as DropList import PlutusTx (compile, liftCode, unsafeApplyCode) import PlutusTx.Code (CompiledCodeIn) import PlutusTx.Prelude qualified as P -import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) -- Tests for `dropList` with PlutusV2 and Plutus 1.0.0 @@ -19,15 +19,17 @@ import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) succeedingDropListPolicyCompiledV2 :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) succeedingDropListPolicyCompiledV2 = - $$(compile [|| DropList.mkDropListPolicy ||]) + $$(compile [||DropList.mkDropListPolicy||]) `unsafeApplyCode` liftCode plcVersion100 DropList.succeedingDropListParams -- These should fail due to exceeding the budget. expensiveDropListScriptGroupV2 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -expensiveDropListScriptGroupV2 = ScriptGroup - { sgBaseName = "expensiveDropListPolicyScriptV2" - , sgScripts = map compileDropList DropList.expensiveDropListParams - } - where compileDropList param = - $$(compile [|| DropList.mkDropListPolicy ||]) - `unsafeApplyCode` liftCode plcVersion100 [param] +expensiveDropListScriptGroupV2 = + ScriptGroup + { sgBaseName = "expensiveDropListPolicyScriptV2" + , sgScripts = map compileDropList DropList.expensiveDropListParams + } + where + compileDropList param = + $$(compile [||DropList.mkDropListPolicy||]) + `unsafeApplyCode` liftCode plcVersion100 [param] diff --git a/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs b/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs index c744597..5b9f47a 100644 --- a/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs +++ b/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs @@ -2,27 +2,29 @@ module PlutusScripts.Batch6.V_1_1 where +import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) import PlutusCore.Default (DefaultFun, DefaultUni) import PlutusCore.Version (plcVersion110) import PlutusScripts.Batch6.DropList qualified as DropList import PlutusTx (compile, liftCode, unsafeApplyCode) import PlutusTx.Code (CompiledCodeIn) import PlutusTx.Prelude qualified as P -import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) -- Compiled code values with parameters already applied for succeeding tests succeedingDropListPolicyCompiledV3 :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) succeedingDropListPolicyCompiledV3 = - $$(compile [|| DropList.mkDropListPolicy ||]) + $$(compile [||DropList.mkDropListPolicy||]) `unsafeApplyCode` liftCode plcVersion110 DropList.succeedingDropListParams -- These should fail due to exceeding the budget. expensiveDropListScriptGroupV3 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -expensiveDropListScriptGroupV3 = ScriptGroup - { sgBaseName = "expensiveDropListPolicyScriptV3" - , sgScripts = map compileDropList DropList.expensiveDropListParams - } - where compileDropList param = - $$(compile [|| DropList.mkDropListPolicy ||]) - `unsafeApplyCode` liftCode plcVersion110 [param] +expensiveDropListScriptGroupV3 = + ScriptGroup + { sgBaseName = "expensiveDropListPolicyScriptV3" + , sgScripts = map compileDropList DropList.expensiveDropListParams + } + where + compileDropList param = + $$(compile [||DropList.mkDropListPolicy||]) + `unsafeApplyCode` liftCode plcVersion110 [param] diff --git a/plutus-scripts/PlutusScripts/Bitwise/V_1_1.hs b/plutus-scripts/PlutusScripts/Bitwise/V_1_1.hs index 97ed1fd..bebeef4 100644 --- a/plutus-scripts/PlutusScripts/Bitwise/V_1_1.hs +++ b/plutus-scripts/PlutusScripts/Bitwise/V_1_1.hs @@ -2,7 +2,10 @@ module PlutusScripts.Bitwise.V_1_1 where -import Helpers.ScriptUtils (IsScriptContext (mkUntypedMintingPolicy), ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) +import Helpers.ScriptUtils ( + IsScriptContext (mkUntypedMintingPolicy), + ScriptGroup (ScriptGroup, sgBaseName, sgScripts), + ) import PlutusCore.Default (DefaultFun, DefaultUni) import PlutusCore.Version (plcVersion110) import PlutusLedgerApi.V3 qualified as V3 @@ -155,8 +158,9 @@ succeedingReplicateBytePolicyCompiledV3 = -------------------------------------------------------------------------------- -- Failing Tests --------------------------------------------------------------- --- | All failing bitwise test script groups --- Each group generates numbered scripts (e.g., failingReadBit_1.plutus, failingReadBit_2.plutus) +{- | All failing bitwise test script groups +Each group generates numbered scripts (e.g., failingReadBit_1.plutus, failingReadBit_2.plutus) +-} failingBitwiseScriptGroupsV3 :: [ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit)] failingBitwiseScriptGroupsV3 = [ -- ReadBit failing tests diff --git a/plutus-scripts/app/Main.hs b/plutus-scripts/app/Main.hs index 4077c98..f9bbc89 100644 --- a/plutus-scripts/app/Main.hs +++ b/plutus-scripts/app/Main.hs @@ -1,18 +1,18 @@ module Main (main) where +import Control.Monad (zipWithM_) import Data.Text qualified as T +import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) import Main.Utf8 (withUtf8) +import PlutusCore.Default (DefaultFun, DefaultUni) import PlutusLedgerApi.Common.Versions (PlutusLedgerLanguage (PlutusV2, PlutusV3)) import PlutusLedgerApi.Envelope qualified as Envelope import PlutusScripts.Basic.V_1_1 qualified as Basic -import Control.Monad (zipWithM_) -import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) -import PlutusCore.Default (DefaultFun, DefaultUni) +import PlutusScripts.Batch6.V_1_1 qualified as Batch6_1_1 import PlutusScripts.Bitwise.V_1_0 qualified as BitwiseV0 import PlutusScripts.Bitwise.V_1_1 qualified as BitwiseV1 import PlutusScripts.Hashing.V_1_1 qualified as Hashing import PlutusScripts.SECP256k1.V_1_1 qualified as SECP -import PlutusScripts.Batch6.V_1_1 qualified as Batch6_1_1 import PlutusTx.Code (CompiledCode) import System.Directory (createDirectoryIfMissing) @@ -37,15 +37,15 @@ main = withUtf8 do BitwiseV0.byteStringToIntegerRoundtripPolicyCompiledV2 -- Basic scripts (PlutusV3) - writeEnvelopeV3 "alwaysSucceedPolicyScriptV3" Basic.alwaysSucceedPolicyCompiled - writeEnvelopeV3 "alwaysFailsPolicyScriptV3" Basic.alwaysFailsPolicyCompiled - writeEnvelopeV3 "mintTokenNamePolicyScriptV3" Basic.mintTokenNamePolicyCompiledV3 - writeEnvelopeV3 "timeRangePolicyScriptV3" Basic.timeRangePolicyCompiledV3 + writeEnvelopeV3 "alwaysSucceedPolicyScriptV3" Basic.alwaysSucceedPolicyCompiled + writeEnvelopeV3 "alwaysFailsPolicyScriptV3" Basic.alwaysFailsPolicyCompiled + writeEnvelopeV3 "mintTokenNamePolicyScriptV3" Basic.mintTokenNamePolicyCompiledV3 + writeEnvelopeV3 "timeRangePolicyScriptV3" Basic.timeRangePolicyCompiledV3 writeEnvelopeV3 "witnessRedeemerPolicyScriptV3" Basic.witnessRedeemerPolicyCompiledV3 -- SECP256k1 scripts (PlutusV3) writeEnvelopeV3 "verifySchnorrPolicyScriptV3" SECP.verifySchnorrPolicyCompiledV3 - writeEnvelopeV3 "verifyEcdsaPolicyScriptV3" SECP.verifyEcdsaPolicyCompiledV3 + writeEnvelopeV3 "verifyEcdsaPolicyScriptV3" SECP.verifyEcdsaPolicyCompiledV3 -- Hashing scripts (PlutusV3) writeEnvelopeV3 "succeedingRipemd_160Policy" Hashing.succeedingRipemd_160PolicyCompiled @@ -88,7 +88,7 @@ main = withUtf8 do -- Failing Bitwise Tests (ReadBit, WriteBits, ReplicateByte variants) mapM_ writeScriptGroup BitwiseV1.failingBitwiseScriptGroupsV3 - -- ** Batch 6 (protocol version 11) ** + -- \** Batch 6 (protocol version 11) ** writeEnvelopeV3 "succeedingDropListPolicyScriptV3" Batch6_1_1.succeedingDropListPolicyCompiledV3 diff --git a/plutus-scripts/plutus-scripts.cabal b/plutus-scripts/plutus-scripts.cabal index b7f9300..4963028 100644 --- a/plutus-scripts/plutus-scripts.cabal +++ b/plutus-scripts/plutus-scripts.cabal @@ -78,6 +78,9 @@ library scripts PlutusScripts.Basic.Common PlutusScripts.Basic.V_1_0 PlutusScripts.Basic.V_1_1 + PlutusScripts.Batch6.DropList + PlutusScripts.Batch6.V_1_0 + PlutusScripts.Batch6.V_1_1 PlutusScripts.Bitwise.Complement PlutusScripts.Bitwise.Conversions PlutusScripts.Bitwise.CountFindFirstSet @@ -118,9 +121,6 @@ library scripts PlutusScripts.SECP256k1.Common PlutusScripts.SECP256k1.V_1_0 PlutusScripts.SECP256k1.V_1_1 - PlutusScripts.Batch6.DropList - PlutusScripts.Batch6.V_1_0 - PlutusScripts.Batch6.V_1_1 executable envelopes import: ghc-options From 5b434c9fcb3c879abbbd76911f46412e23c01c6a Mon Sep 17 00:00:00 2001 From: Yuriy Lazaryev Date: Thu, 20 Nov 2025 12:58:47 +0100 Subject: [PATCH 05/10] refactor: adopt compacted Core version naming (V3_110) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Align dropList with array builtin naming convention: - Old: V_1_1 → New: V3_110 - Old: V_1_0 → New: V3_100 Uses compacted Plutus Core version digits for clarity: - Underscore: separates Plutus version from Core version - No separator: within Core version digits (110, 100) Changes: - Rename modules: V_X_Y.hs → V3_{XY0}.hs - Update identifiers: ...V3 → ..._V3_110 - Update script outputs: ...V3.plutus → ..._V3_110.plutus - Qualified imports: Batch6_V3_110 - Add CLAUDE.md with naming convention documentation Generated scripts (6 total): - succeedingDropListPolicyScript_V3_110.plutus - expensiveDropListPolicyScript_V3_110_{1-5}.plutus Benefits: - Less verbose: V3_110 vs V_1_1 (clearer separation) - Consistent with array builtins convention (PR #12) - Clear hierarchy: version concepts (separated) vs digits (compact) Convention documented in CLAUDE.md for project-wide consistency. Related: PR #12 (array builtins), issue #14 --- CLAUDE.md | 86 +++++++++++++++---- .../Batch6/{V_1_0.hs => V3_100.hs} | 12 +-- .../Batch6/{V_1_1.hs => V3_110.hs} | 12 +-- plutus-scripts/app/Main.hs | 8 +- plutus-scripts/plutus-scripts.cabal | 3 + 5 files changed, 87 insertions(+), 34 deletions(-) rename plutus-scripts/PlutusScripts/Batch6/{V_1_0.hs => V3_100.hs} (78%) rename plutus-scripts/PlutusScripts/Batch6/{V_1_1.hs => V3_110.hs} (75%) diff --git a/CLAUDE.md b/CLAUDE.md index 556f8d5..a032987 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -66,18 +66,68 @@ plutus-scripts/ ### Plutus Version Targeting -All scripts target **Plutus Core 1.1.0** and use **PlutusV3** ledger API: +Scripts support multiple Plutus Ledger versions (V1, V2, V3) and Plutus Core language versions (1.0.0, 1.1.0): -- Scripts use `{-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=1.1.0 #-}` +- Scripts use `{-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=X.Y.Z #-}` - V3 validators receive `ScriptContext` with enhanced governance support -- Scripts are organized by Plutus version: `V_1_0.hs` and `V_1_1.hs` modules +- Scripts are organized by version matrix using explicit naming convention (see below) + +### Plutus Script Versioning Naming Convention + +**Module Naming Pattern:** `V{LedgerVersion}_{CoreCompact}.hs` + +Where `CoreCompact` is Plutus Core version with digits compacted (no separators): +- 1.0.0 → 100 +- 1.1.0 → 110 + +**Examples:** +- `V1_100.hs` = PlutusV1 + Plutus Core 1.0.0 +- `V2_110.hs` = PlutusV2 + Plutus Core 1.1.0 +- `V3_100.hs` = PlutusV3 + Plutus Core 1.0.0 +- `V3_110.hs` = PlutusV3 + Plutus Core 1.1.0 + +**Identifier Naming:** `{function}_V{LedgerVersion}_{CoreCompact}` + +```haskell +succeedingIndexArrayPolicyCompiled_V3_110 +succeedingLengthOfArrayPolicyScript_V1_100 +expensiveDropListScriptGroup_V3_110 +``` + +**Script Output Files:** `{scriptName}_V{LedgerVersion}_{CoreCompact}.plutus` + +``` +succeedingIndexArrayPolicyScript_V3_110.plutus +succeedingDropListPolicyScript_V3_100.plutus +expensiveDropListPolicyScript_V3_110_1.plutus +``` + +**Qualified Import Aliases:** `{Category}_V{LedgerVersion}_{CoreCompact}` + +```haskell +import PlutusScripts.Array.V3_110 qualified as Array_V3_110 +import PlutusScripts.Batch6.V3_100 qualified as Batch6_V3_100 +``` + +**Rationale:** + +This convention provides clear separation of concerns: +- **Underscore** separates distinct version concepts (Plutus Ledger vs Core) +- **No separator** within Core version digits (compacted for clarity) +- Removes ambiguity about which separator indicates what + +**Benefits:** +- Visual clarity: `V3_110` vs verbose `V3_1_1_0` +- Less verbose: 6 characters vs 8 characters +- Clear hierarchy: version concepts (separated) vs version digits (compact) +- Easy grepping: `V3_*` finds all V3 scripts, `*_110` finds all 1.1.0 scripts ### Script Organization Pattern Each script category follows a consistent pattern: 1. **Common module** (`Common.hs`): Contains `INLINEABLE` validator logic and test parameters -2. **Versioned modules** (`V_1_0.hs`, `V_1_1.hs`): Compile scripts with Plutus Core target versions +2. **Versioned modules** (e.g., `V3_100.hs`, `V3_110.hs`): Compile scripts with specific Plutus version combinations 3. **Library exports**: Pure `CompiledCode` values (no IO operations) 4. **Executable serialization**: `app/Main.hs` handles all file writing @@ -87,15 +137,15 @@ For simple scripts without test variants: ```haskell -- PlutusScripts/Basic/Common.hs -{-# INLINEABLE mkAlwaysSucceedPolicyV3 #-} -mkAlwaysSucceedPolicyV3 :: P.BuiltinData -> P.BuiltinUnit +{-# INLINEABLE mkAlwaysSucceedPolicy #-} +mkAlwaysSucceedPolicy :: P.BuiltinData -> P.BuiltinUnit --- PlutusScripts/Basic/V_1_1.hs -alwaysSucceedPolicyCompiled :: CompiledCode (P.BuiltinData -> P.BuiltinUnit) -alwaysSucceedPolicyCompiled = $$(compile [||mkAlwaysSucceedPolicyV3||]) +-- PlutusScripts/Basic/V3_110.hs +alwaysSucceedPolicyCompiled_V3_110 :: CompiledCode (P.BuiltinData -> P.BuiltinUnit) +alwaysSucceedPolicyCompiled_V3_110 = $$(compile [||mkAlwaysSucceedPolicy||]) -- app/Main.hs -writeEnvelopeV3 "alwaysSucceedPolicyScriptV3" Basic.alwaysSucceedPolicyCompiled +writeEnvelopeV3 "alwaysSucceedPolicyScript_V3_110" Basic_V3_110.alwaysSucceedPolicyCompiled_V3_110 ``` #### Script Group Pattern (For Test Variants) @@ -107,11 +157,11 @@ For scripts with multiple parameter combinations (e.g., failing tests): data Params = Params { s :: BuiltinByteString, i :: Integer, output :: Bool } failingReadBitParams :: [Params] -- Test cases for edge conditions --- PlutusScripts/Bitwise/V_1_1.hs -failingBitwiseScriptGroupsV3 :: [ScriptGroup DefaultUni DefaultFun (BuiltinData -> BuiltinUnit)] -failingBitwiseScriptGroupsV3 = +-- PlutusScripts/Bitwise/V3_110.hs +failingBitwiseScriptGroups_V3_110 :: [ScriptGroup DefaultUni DefaultFun (BuiltinData -> BuiltinUnit)] +failingBitwiseScriptGroups_V3_110 = [ ScriptGroup - { sgBaseName = "failingReadBitPolicyScriptV3" + { sgBaseName = "failingReadBitPolicyScript_V3_110" , sgScripts = map compileReadBit failingReadBitParams -- Iteration in library } ] @@ -119,8 +169,8 @@ failingBitwiseScriptGroupsV3 = compileReadBit param = $$(compile [||mkReadBitPolicy||]) `unsafeApplyCode` liftCode plcVersion110 [param] -- app/Main.hs -mapM_ writeScriptGroup BitwiseV1.failingBitwiseScriptGroupsV3 --- Generates: failingReadBitPolicyScriptV3_1.plutus, _2.plutus, ..., _14.plutus +mapM_ writeScriptGroup Bitwise_V3_110.failingBitwiseScriptGroups_V3_110 +-- Generates: failingReadBitPolicyScript_V3_110_1.plutus, _2.plutus, ..., _14.plutus ``` This pattern: @@ -260,8 +310,8 @@ These serialized scripts are consumed by external E2E tests (e.g., `cardano-node To add a simple script: 1. Create the validator logic in a `Common.hs` module with `INLINEABLE` pragma -2. Add versioned modules (`V_1_0.hs`, `V_1_1.hs`) that compile and export the script as `CompiledCode` -3. Update `app/Main.hs` to add a `writeEnvelopeV3` call +2. Add versioned modules (e.g., `V3_100.hs`, `V3_110.hs`) that compile and export the script as `CompiledCode` +3. Update `app/Main.hs` to add a `writeEnvelopeV3` call with versioned filename 4. Run `cabal run envelopes` to generate the `.plutus` file #### Multiple Test Variants (Script Group Pattern) diff --git a/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs b/plutus-scripts/PlutusScripts/Batch6/V3_100.hs similarity index 78% rename from plutus-scripts/PlutusScripts/Batch6/V_1_0.hs rename to plutus-scripts/PlutusScripts/Batch6/V3_100.hs index 62ff02d..ce24411 100644 --- a/plutus-scripts/PlutusScripts/Batch6/V_1_0.hs +++ b/plutus-scripts/PlutusScripts/Batch6/V3_100.hs @@ -1,6 +1,6 @@ {-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=1.0.0 #-} -module PlutusScripts.Batch6.V_1_0 where +module PlutusScripts.Batch6.V3_100 where import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) import PlutusCore.Default (DefaultFun, DefaultUni) @@ -16,17 +16,17 @@ import PlutusTx.Prelude qualified as P -- that SoPs and all builtins will be enabled in PlutusV1 and PlutusV2 at PV11. -- Compiled code values with parameters already applied for succeeding tests -succeedingDropListPolicyCompiledV2 +succeedingDropListPolicyCompiled_V2_100 :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -succeedingDropListPolicyCompiledV2 = +succeedingDropListPolicyCompiled_V2_100 = $$(compile [||DropList.mkDropListPolicy||]) `unsafeApplyCode` liftCode plcVersion100 DropList.succeedingDropListParams -- These should fail due to exceeding the budget. -expensiveDropListScriptGroupV2 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -expensiveDropListScriptGroupV2 = +expensiveDropListScriptGroup_V2_100 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +expensiveDropListScriptGroup_V2_100 = ScriptGroup - { sgBaseName = "expensiveDropListPolicyScriptV2" + { sgBaseName = "expensiveDropListPolicyScript_V2_100" , sgScripts = map compileDropList DropList.expensiveDropListParams } where diff --git a/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs b/plutus-scripts/PlutusScripts/Batch6/V3_110.hs similarity index 75% rename from plutus-scripts/PlutusScripts/Batch6/V_1_1.hs rename to plutus-scripts/PlutusScripts/Batch6/V3_110.hs index 5b9f47a..e98ec34 100644 --- a/plutus-scripts/PlutusScripts/Batch6/V_1_1.hs +++ b/plutus-scripts/PlutusScripts/Batch6/V3_110.hs @@ -1,6 +1,6 @@ {-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=1.1.0 #-} -module PlutusScripts.Batch6.V_1_1 where +module PlutusScripts.Batch6.V3_110 where import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) import PlutusCore.Default (DefaultFun, DefaultUni) @@ -11,17 +11,17 @@ import PlutusTx.Code (CompiledCodeIn) import PlutusTx.Prelude qualified as P -- Compiled code values with parameters already applied for succeeding tests -succeedingDropListPolicyCompiledV3 +succeedingDropListPolicyCompiled_V3_110 :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -succeedingDropListPolicyCompiledV3 = +succeedingDropListPolicyCompiled_V3_110 = $$(compile [||DropList.mkDropListPolicy||]) `unsafeApplyCode` liftCode plcVersion110 DropList.succeedingDropListParams -- These should fail due to exceeding the budget. -expensiveDropListScriptGroupV3 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -expensiveDropListScriptGroupV3 = +expensiveDropListScriptGroup_V3_110 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +expensiveDropListScriptGroup_V3_110 = ScriptGroup - { sgBaseName = "expensiveDropListPolicyScriptV3" + { sgBaseName = "expensiveDropListPolicyScript_V3_110" , sgScripts = map compileDropList DropList.expensiveDropListParams } where diff --git a/plutus-scripts/app/Main.hs b/plutus-scripts/app/Main.hs index f9bbc89..907f48a 100644 --- a/plutus-scripts/app/Main.hs +++ b/plutus-scripts/app/Main.hs @@ -8,7 +8,7 @@ import PlutusCore.Default (DefaultFun, DefaultUni) import PlutusLedgerApi.Common.Versions (PlutusLedgerLanguage (PlutusV2, PlutusV3)) import PlutusLedgerApi.Envelope qualified as Envelope import PlutusScripts.Basic.V_1_1 qualified as Basic -import PlutusScripts.Batch6.V_1_1 qualified as Batch6_1_1 +import PlutusScripts.Batch6.V3_110 qualified as Batch6_V3_110 import PlutusScripts.Bitwise.V_1_0 qualified as BitwiseV0 import PlutusScripts.Bitwise.V_1_1 qualified as BitwiseV1 import PlutusScripts.Hashing.V_1_1 qualified as Hashing @@ -90,10 +90,10 @@ main = withUtf8 do -- \** Batch 6 (protocol version 11) ** writeEnvelopeV3 - "succeedingDropListPolicyScriptV3" - Batch6_1_1.succeedingDropListPolicyCompiledV3 + "succeedingDropListPolicyScript_V3_110" + Batch6_V3_110.succeedingDropListPolicyCompiled_V3_110 - writeScriptGroup Batch6_1_1.expensiveDropListScriptGroupV3 + writeScriptGroup Batch6_V3_110.expensiveDropListScriptGroup_V3_110 -------------------------------------------------------------------------------- -- IO helpers ------------------------------------------------------------------ diff --git a/plutus-scripts/plutus-scripts.cabal b/plutus-scripts/plutus-scripts.cabal index 4963028..d9e8496 100644 --- a/plutus-scripts/plutus-scripts.cabal +++ b/plutus-scripts/plutus-scripts.cabal @@ -121,6 +121,9 @@ library scripts PlutusScripts.SECP256k1.Common PlutusScripts.SECP256k1.V_1_0 PlutusScripts.SECP256k1.V_1_1 + PlutusScripts.Batch6.DropList + PlutusScripts.Batch6.V3_100 + PlutusScripts.Batch6.V3_110 executable envelopes import: ghc-options From cb983755b295a345b35c477d62ab394e8cee69d8 Mon Sep 17 00:00:00 2001 From: Yuriy Lazaryev Date: Mon, 24 Nov 2025 12:36:15 +0100 Subject: [PATCH 06/10] refactor: reorganize dropList into Batch6/DropList/ subdirectory MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Move dropList to subdirectory structure for consistency with batch6 organization pattern, following Kenneth's feedback. Directory structure: Batch6/ └── DropList/ ├── Common.hs (was DropList.hs) ├── V3_100.hs └── V3_110.hs Changes: - DropList.hs → DropList/Common.hs - V3_100.hs → DropList/V3_100.hs - V3_110.hs → DropList/V3_110.hs - Update module paths: Batch6.DropList.V3_110 - Update imports: DropList_V3_110 - Update cabal exposed-modules This structure enables clean organization of all batch6 builtins (arrays, dropList, etc.) with each builtin in its own subdirectory. Generated scripts (6 total): - succeedingDropListPolicyScript_V3_110.plutus - expensiveDropListPolicyScript_V3_110_{1-5}.plutus Related: Kenneth's feedback on PR #15, PR #12 (arrays) --- .../Batch6/{DropList.hs => DropList/Common.hs} | 2 +- .../PlutusScripts/Batch6/{ => DropList}/V3_100.hs | 4 ++-- .../PlutusScripts/Batch6/{ => DropList}/V3_110.hs | 4 ++-- plutus-scripts/app/Main.hs | 6 +++--- plutus-scripts/plutus-scripts.cabal | 9 +++------ 5 files changed, 11 insertions(+), 14 deletions(-) rename plutus-scripts/PlutusScripts/Batch6/{DropList.hs => DropList/Common.hs} (98%) rename plutus-scripts/PlutusScripts/Batch6/{ => DropList}/V3_100.hs (92%) rename plutus-scripts/PlutusScripts/Batch6/{ => DropList}/V3_110.hs (91%) diff --git a/plutus-scripts/PlutusScripts/Batch6/DropList.hs b/plutus-scripts/PlutusScripts/Batch6/DropList/Common.hs similarity index 98% rename from plutus-scripts/PlutusScripts/Batch6/DropList.hs rename to plutus-scripts/PlutusScripts/Batch6/DropList/Common.hs index 9ef5037..4083262 100644 --- a/plutus-scripts/PlutusScripts/Batch6/DropList.hs +++ b/plutus-scripts/PlutusScripts/Batch6/DropList/Common.hs @@ -6,7 +6,7 @@ {- | Simple end-to-end tests for the Plutus Core `dropList` builtin. These are adapted from the `plutus-conformance` tests. -} -module PlutusScripts.Batch6.DropList (mkDropListPolicy, succeedingDropListParams, expensiveDropListParams) +module PlutusScripts.Batch6.DropList.Common (mkDropListPolicy, succeedingDropListParams, expensiveDropListParams) where import PlutusTx qualified diff --git a/plutus-scripts/PlutusScripts/Batch6/V3_100.hs b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_100.hs similarity index 92% rename from plutus-scripts/PlutusScripts/Batch6/V3_100.hs rename to plutus-scripts/PlutusScripts/Batch6/DropList/V3_100.hs index ce24411..a242586 100644 --- a/plutus-scripts/PlutusScripts/Batch6/V3_100.hs +++ b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_100.hs @@ -1,11 +1,11 @@ {-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=1.0.0 #-} -module PlutusScripts.Batch6.V3_100 where +module PlutusScripts.Batch6.DropList.V3_100 where import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) import PlutusCore.Default (DefaultFun, DefaultUni) import PlutusCore.Version (plcVersion100) -import PlutusScripts.Batch6.DropList qualified as DropList +import PlutusScripts.Batch6.DropList.Common qualified as DropList import PlutusTx (compile, liftCode, unsafeApplyCode) import PlutusTx.Code (CompiledCodeIn) import PlutusTx.Prelude qualified as P diff --git a/plutus-scripts/PlutusScripts/Batch6/V3_110.hs b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs similarity index 91% rename from plutus-scripts/PlutusScripts/Batch6/V3_110.hs rename to plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs index e98ec34..d9232dc 100644 --- a/plutus-scripts/PlutusScripts/Batch6/V3_110.hs +++ b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs @@ -1,11 +1,11 @@ {-# OPTIONS_GHC -fplugin-opt PlutusTx.Plugin:target-version=1.1.0 #-} -module PlutusScripts.Batch6.V3_110 where +module PlutusScripts.Batch6.DropList.V3_110 where import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) import PlutusCore.Default (DefaultFun, DefaultUni) import PlutusCore.Version (plcVersion110) -import PlutusScripts.Batch6.DropList qualified as DropList +import PlutusScripts.Batch6.DropList.Common qualified as DropList import PlutusTx (compile, liftCode, unsafeApplyCode) import PlutusTx.Code (CompiledCodeIn) import PlutusTx.Prelude qualified as P diff --git a/plutus-scripts/app/Main.hs b/plutus-scripts/app/Main.hs index 907f48a..ec3e030 100644 --- a/plutus-scripts/app/Main.hs +++ b/plutus-scripts/app/Main.hs @@ -8,7 +8,7 @@ import PlutusCore.Default (DefaultFun, DefaultUni) import PlutusLedgerApi.Common.Versions (PlutusLedgerLanguage (PlutusV2, PlutusV3)) import PlutusLedgerApi.Envelope qualified as Envelope import PlutusScripts.Basic.V_1_1 qualified as Basic -import PlutusScripts.Batch6.V3_110 qualified as Batch6_V3_110 +import PlutusScripts.Batch6.DropList.V3_110 qualified as DropList_V3_110 import PlutusScripts.Bitwise.V_1_0 qualified as BitwiseV0 import PlutusScripts.Bitwise.V_1_1 qualified as BitwiseV1 import PlutusScripts.Hashing.V_1_1 qualified as Hashing @@ -91,9 +91,9 @@ main = withUtf8 do -- \** Batch 6 (protocol version 11) ** writeEnvelopeV3 "succeedingDropListPolicyScript_V3_110" - Batch6_V3_110.succeedingDropListPolicyCompiled_V3_110 + DropList_V3_110.succeedingDropListPolicyCompiled_V3_110 - writeScriptGroup Batch6_V3_110.expensiveDropListScriptGroup_V3_110 + writeScriptGroup DropList_V3_110.expensiveDropListScriptGroup_V3_110 -------------------------------------------------------------------------------- -- IO helpers ------------------------------------------------------------------ diff --git a/plutus-scripts/plutus-scripts.cabal b/plutus-scripts/plutus-scripts.cabal index d9e8496..a222f50 100644 --- a/plutus-scripts/plutus-scripts.cabal +++ b/plutus-scripts/plutus-scripts.cabal @@ -78,9 +78,6 @@ library scripts PlutusScripts.Basic.Common PlutusScripts.Basic.V_1_0 PlutusScripts.Basic.V_1_1 - PlutusScripts.Batch6.DropList - PlutusScripts.Batch6.V_1_0 - PlutusScripts.Batch6.V_1_1 PlutusScripts.Bitwise.Complement PlutusScripts.Bitwise.Conversions PlutusScripts.Bitwise.CountFindFirstSet @@ -121,9 +118,9 @@ library scripts PlutusScripts.SECP256k1.Common PlutusScripts.SECP256k1.V_1_0 PlutusScripts.SECP256k1.V_1_1 - PlutusScripts.Batch6.DropList - PlutusScripts.Batch6.V3_100 - PlutusScripts.Batch6.V3_110 + PlutusScripts.Batch6.DropList.Common + PlutusScripts.Batch6.DropList.V3_100 + PlutusScripts.Batch6.DropList.V3_110 executable envelopes import: ghc-options From 66128bbb376685dff0242b3b790de25e7db1ae6f Mon Sep 17 00:00:00 2001 From: Yuriy Lazaryev Date: Mon, 24 Nov 2025 12:42:34 +0100 Subject: [PATCH 07/10] docs: update CLAUDE.md examples for Batch6 subdirectory structure Update examples to reflect reorganization: - PlutusScripts.Batch6.Array.V3_110 - PlutusScripts.Batch6.DropList.V3_110 Matches PR #12 documentation updates. --- CLAUDE.md | 10 +++------- 1 file changed, 3 insertions(+), 7 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index a032987..ab7fbdc 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -105,8 +105,8 @@ expensiveDropListPolicyScript_V3_110_1.plutus **Qualified Import Aliases:** `{Category}_V{LedgerVersion}_{CoreCompact}` ```haskell -import PlutusScripts.Array.V3_110 qualified as Array_V3_110 -import PlutusScripts.Batch6.V3_100 qualified as Batch6_V3_100 +import PlutusScripts.Batch6.Array.V3_110 qualified as Array_V3_110 +import PlutusScripts.Batch6.DropList.V3_110 qualified as DropList_V3_110 ``` **Rationale:** @@ -174,7 +174,6 @@ mapM_ writeScriptGroup Bitwise_V3_110.failingBitwiseScriptGroups_V3_110 ``` This pattern: - - ✅ Encapsulates parameter iteration in the library - ✅ Keeps executable unaware of Params types - ✅ Generates numbered script files automatically @@ -293,7 +292,6 @@ cabal run envelopes Output: Multiple `.plutus` files in `serialised-plutus-scripts/` (git-ignored) **Generated Scripts**: - - PlutusV2 scripts (bytestring/integer conversions) - Basic PlutusV3 scripts (always succeed/fail, token names, time ranges, redeemers) - SECP256k1 scripts (Schnorr and ECDSA signature verification) @@ -319,14 +317,12 @@ To add a simple script: For parameterized tests (e.g., failing tests with multiple edge cases): 1. Define test parameters in the `Common` module: - ```haskell data Params = Params { input :: ByteString, expected :: Bool } testParams :: [Params] ``` 2. Create a `ScriptGroup` in the versioned module: - ```haskell myScriptGroup :: [ScriptGroup DefaultUni DefaultFun (BuiltinData -> BuiltinUnit)] myScriptGroup = [ScriptGroup @@ -336,7 +332,7 @@ For parameterized tests (e.g., failing tests with multiple edge cases): ``` 3. Use `mapM_ writeScriptGroup` in `app/Main.hs` -4. Run `cabal run envelopes` - generates numbered files (myTestScript_1.plutus, \_2.plutus, ...) +4. Run `cabal run envelopes` - generates numbered files (myTestScript_1.plutus, _2.plutus, ...) ## Nix Binary Cache From 301e53219367640b59fd37b32a9399e5815f5d97 Mon Sep 17 00:00:00 2001 From: Yuriy Lazaryev Date: Mon, 24 Nov 2025 14:11:23 +0100 Subject: [PATCH 08/10] refactor: simplify identifiers by removing version repetition Remove version suffix from identifiers to avoid repetition: - Old: DropList_V3_110.succeedingDropListPolicyCompiled_V3_110 - New: DropList_V3_110.succeedingDropListPolicy Changes: - Remove version suffix from all exported identifiers - Version info already clear from qualified import Example usage: DropList_V3_110.succeedingDropListPolicy DropList_V3_110.expensiveDropListScriptGroup Benefits: cleaner code, no excessive repetition, version still clear. Matches array builtin pattern from PR #12. --- plutus-scripts/PlutusScripts/Batch6/DropList/V3_100.hs | 8 ++++---- plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs | 8 ++++---- plutus-scripts/app/Main.hs | 4 ++-- 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/plutus-scripts/PlutusScripts/Batch6/DropList/V3_100.hs b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_100.hs index a242586..6b10f5b 100644 --- a/plutus-scripts/PlutusScripts/Batch6/DropList/V3_100.hs +++ b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_100.hs @@ -16,15 +16,15 @@ import PlutusTx.Prelude qualified as P -- that SoPs and all builtins will be enabled in PlutusV1 and PlutusV2 at PV11. -- Compiled code values with parameters already applied for succeeding tests -succeedingDropListPolicyCompiled_V2_100 +succeedingDropListPolicy :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -succeedingDropListPolicyCompiled_V2_100 = +succeedingDropListPolicy = $$(compile [||DropList.mkDropListPolicy||]) `unsafeApplyCode` liftCode plcVersion100 DropList.succeedingDropListParams -- These should fail due to exceeding the budget. -expensiveDropListScriptGroup_V2_100 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -expensiveDropListScriptGroup_V2_100 = +expensiveDropListScriptGroup :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +expensiveDropListScriptGroup = ScriptGroup { sgBaseName = "expensiveDropListPolicyScript_V2_100" , sgScripts = map compileDropList DropList.expensiveDropListParams diff --git a/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs index d9232dc..6187347 100644 --- a/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs +++ b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs @@ -11,15 +11,15 @@ import PlutusTx.Code (CompiledCodeIn) import PlutusTx.Prelude qualified as P -- Compiled code values with parameters already applied for succeeding tests -succeedingDropListPolicyCompiled_V3_110 +succeedingDropListPolicy :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -succeedingDropListPolicyCompiled_V3_110 = +succeedingDropListPolicy = $$(compile [||DropList.mkDropListPolicy||]) `unsafeApplyCode` liftCode plcVersion110 DropList.succeedingDropListParams -- These should fail due to exceeding the budget. -expensiveDropListScriptGroup_V3_110 :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) -expensiveDropListScriptGroup_V3_110 = +expensiveDropListScriptGroup :: ScriptGroup DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +expensiveDropListScriptGroup = ScriptGroup { sgBaseName = "expensiveDropListPolicyScript_V3_110" , sgScripts = map compileDropList DropList.expensiveDropListParams diff --git a/plutus-scripts/app/Main.hs b/plutus-scripts/app/Main.hs index ec3e030..a8903ce 100644 --- a/plutus-scripts/app/Main.hs +++ b/plutus-scripts/app/Main.hs @@ -91,9 +91,9 @@ main = withUtf8 do -- \** Batch 6 (protocol version 11) ** writeEnvelopeV3 "succeedingDropListPolicyScript_V3_110" - DropList_V3_110.succeedingDropListPolicyCompiled_V3_110 + DropList_V3_110.succeedingDropListPolicy - writeScriptGroup DropList_V3_110.expensiveDropListScriptGroup_V3_110 + writeScriptGroup DropList_V3_110.expensiveDropListScriptGroup -------------------------------------------------------------------------------- -- IO helpers ------------------------------------------------------------------ From 9435ff3f4aa5fcb0377fd03840048d654ab2dbbc Mon Sep 17 00:00:00 2001 From: Yuriy Lazaryev Date: Mon, 24 Nov 2025 16:21:52 +0100 Subject: [PATCH 09/10] refactor: introduce VersionedScript pattern for batch6 builtins Apply same pattern as array builtins (PR #12) to reduce boilerplate. New pattern: - Added Helpers/Envelopes with VersionedScript types - Created PlutusScripts/Batch6/DropList overarching module - Exports allDropListScripts and allDropListScriptGroups lists - Main.hs: mapM_ writeVersionedScript/writeVersionedScriptGroup Benefits: - Main.hs scales: 2 lines for dropList (not 7 lines) - No version repetition: DropList_V3_110.succeedingDropListPolicy - Type-safe version tracking with proper PlutusCore type - Matches array builtin pattern for consistency Example: Old: writeEnvelopeV3 "succeedingDropListPolicyScript_V3_110" DropList_V3_110.succeedingDropListPolicy writeScriptGroup DropList_V3_110.expensiveDropListScriptGroup New: mapM_ writeVersionedScript DropList.allDropListScripts mapM_ writeVersionedScriptGroup DropList.allDropListScriptGroups Generated scripts (6 total): - succeedingDropListPolicyScript_V3_110.plutus - expensiveDropListPolicyScript_V3_110_{1-5}.plutus Related: PR #12 (array pattern), Kenneth's feedback --- CLAUDE.md | 10 ++- plutus-scripts/Helpers/Envelopes.hs | 61 +++++++++++++++++++ .../PlutusScripts/Batch6/DropList.hs | 32 ++++++++++ .../PlutusScripts/Batch6/DropList/V3_110.hs | 3 +- plutus-scripts/app/Main.hs | 35 ++++++++--- plutus-scripts/plutus-scripts.cabal | 9 ++- 6 files changed, 136 insertions(+), 14 deletions(-) create mode 100644 plutus-scripts/Helpers/Envelopes.hs create mode 100644 plutus-scripts/PlutusScripts/Batch6/DropList.hs diff --git a/CLAUDE.md b/CLAUDE.md index ab7fbdc..48c232a 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -77,10 +77,12 @@ Scripts support multiple Plutus Ledger versions (V1, V2, V3) and Plutus Core lan **Module Naming Pattern:** `V{LedgerVersion}_{CoreCompact}.hs` Where `CoreCompact` is Plutus Core version with digits compacted (no separators): + - 1.0.0 → 100 - 1.1.0 → 110 **Examples:** + - `V1_100.hs` = PlutusV1 + Plutus Core 1.0.0 - `V2_110.hs` = PlutusV2 + Plutus Core 1.1.0 - `V3_100.hs` = PlutusV3 + Plutus Core 1.0.0 @@ -112,11 +114,13 @@ import PlutusScripts.Batch6.DropList.V3_110 qualified as DropList_V3_110 **Rationale:** This convention provides clear separation of concerns: + - **Underscore** separates distinct version concepts (Plutus Ledger vs Core) - **No separator** within Core version digits (compacted for clarity) - Removes ambiguity about which separator indicates what **Benefits:** + - Visual clarity: `V3_110` vs verbose `V3_1_1_0` - Less verbose: 6 characters vs 8 characters - Clear hierarchy: version concepts (separated) vs version digits (compact) @@ -174,6 +178,7 @@ mapM_ writeScriptGroup Bitwise_V3_110.failingBitwiseScriptGroups_V3_110 ``` This pattern: + - ✅ Encapsulates parameter iteration in the library - ✅ Keeps executable unaware of Params types - ✅ Generates numbered script files automatically @@ -292,6 +297,7 @@ cabal run envelopes Output: Multiple `.plutus` files in `serialised-plutus-scripts/` (git-ignored) **Generated Scripts**: + - PlutusV2 scripts (bytestring/integer conversions) - Basic PlutusV3 scripts (always succeed/fail, token names, time ranges, redeemers) - SECP256k1 scripts (Schnorr and ECDSA signature verification) @@ -317,12 +323,14 @@ To add a simple script: For parameterized tests (e.g., failing tests with multiple edge cases): 1. Define test parameters in the `Common` module: + ```haskell data Params = Params { input :: ByteString, expected :: Bool } testParams :: [Params] ``` 2. Create a `ScriptGroup` in the versioned module: + ```haskell myScriptGroup :: [ScriptGroup DefaultUni DefaultFun (BuiltinData -> BuiltinUnit)] myScriptGroup = [ScriptGroup @@ -332,7 +340,7 @@ For parameterized tests (e.g., failing tests with multiple edge cases): ``` 3. Use `mapM_ writeScriptGroup` in `app/Main.hs` -4. Run `cabal run envelopes` - generates numbered files (myTestScript_1.plutus, _2.plutus, ...) +4. Run `cabal run envelopes` - generates numbered files (myTestScript_1.plutus, \_2.plutus, ...) ## Nix Binary Cache diff --git a/plutus-scripts/Helpers/Envelopes.hs b/plutus-scripts/Helpers/Envelopes.hs new file mode 100644 index 0000000..d3c95ab --- /dev/null +++ b/plutus-scripts/Helpers/Envelopes.hs @@ -0,0 +1,61 @@ +module Helpers.Envelopes ( + PlutusCore (..), + VersionedScript (..), + VersionedScriptGroup (..), + plc100, + plc110, + formatCoreVersion, + formatPlutusVersion, +) +where + +import Data.Text (Text) +import Data.Text qualified as T +import Helpers.ScriptUtils (ScriptGroup) +import PlutusCore.Default (DefaultFun, DefaultUni) +import PlutusLedgerApi.Common.Versions ( + PlutusLedgerLanguage (PlutusV1, PlutusV2, PlutusV3), + ) +import PlutusTx.Code (CompiledCode) + +-------------------------------------------------------------------------------- +-- Types ----------------------------------------------------------------------- + +-- | Plutus Core language version +data PlutusCore = PlutusCore Int Int Int + deriving (Eq, Show) + +-- | Common Plutus Core versions +plc100, plc110 :: PlutusCore +plc100 = PlutusCore 1 0 0 +plc110 = PlutusCore 1 1 0 + +-- | A compiled script with version metadata +data VersionedScript a = VersionedScript + { vsPlutusVersion :: PlutusLedgerLanguage + , vsCoreVersion :: PlutusCore + , vsScriptName :: Text + , vsCompiledCode :: CompiledCode a + } + +-- | A script group with version metadata +data VersionedScriptGroup a = VersionedScriptGroup + { vsgPlutusVersion :: PlutusLedgerLanguage + , vsgCoreVersion :: PlutusCore + , vsgBaseName :: Text + , vsgScriptGroup :: ScriptGroup DefaultUni DefaultFun a + } + +-------------------------------------------------------------------------------- +-- Formatting ------------------------------------------------------------------ + +-- | Format Plutus Core version as compact string (e.g., "100", "110") +formatCoreVersion :: PlutusCore -> Text +formatCoreVersion (PlutusCore major minor micro) = + T.pack $ show major ++ show minor ++ show micro + +-- | Format Plutus ledger version as string (e.g., "V1", "V2", "V3") +formatPlutusVersion :: PlutusLedgerLanguage -> Text +formatPlutusVersion PlutusV1 = "V1" +formatPlutusVersion PlutusV2 = "V2" +formatPlutusVersion PlutusV3 = "V3" diff --git a/plutus-scripts/PlutusScripts/Batch6/DropList.hs b/plutus-scripts/PlutusScripts/Batch6/DropList.hs new file mode 100644 index 0000000..951aaae --- /dev/null +++ b/plutus-scripts/PlutusScripts/Batch6/DropList.hs @@ -0,0 +1,32 @@ +module PlutusScripts.Batch6.DropList ( + allDropListScripts, + allDropListScriptGroups, +) +where + +import Helpers.Envelopes ( + VersionedScript (VersionedScript), + VersionedScriptGroup (VersionedScriptGroup), + plc110, + ) +import PlutusLedgerApi.Common.Versions (PlutusLedgerLanguage (PlutusV3)) +import PlutusScripts.Batch6.DropList.V3_110 qualified as V3_110 +import PlutusTx.Prelude qualified as P + +allDropListScripts :: [VersionedScript (P.BuiltinData -> P.BuiltinUnit)] +allDropListScripts = + [ VersionedScript + PlutusV3 + plc110 + "succeedingDropListPolicyScript" + V3_110.succeedingDropListPolicy + ] + +allDropListScriptGroups :: [VersionedScriptGroup (P.BuiltinData -> P.BuiltinUnit)] +allDropListScriptGroups = + [ VersionedScriptGroup + PlutusV3 + plc110 + "expensiveDropListPolicyScript" + V3_110.expensiveDropListScriptGroup + ] diff --git a/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs index 6187347..122f1b6 100644 --- a/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs +++ b/plutus-scripts/PlutusScripts/Batch6/DropList/V3_110.hs @@ -11,8 +11,7 @@ import PlutusTx.Code (CompiledCodeIn) import PlutusTx.Prelude qualified as P -- Compiled code values with parameters already applied for succeeding tests -succeedingDropListPolicy - :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) +succeedingDropListPolicy :: CompiledCodeIn DefaultUni DefaultFun (P.BuiltinData -> P.BuiltinUnit) succeedingDropListPolicy = $$(compile [||DropList.mkDropListPolicy||]) `unsafeApplyCode` liftCode plcVersion110 DropList.succeedingDropListParams diff --git a/plutus-scripts/app/Main.hs b/plutus-scripts/app/Main.hs index a8903ce..024669c 100644 --- a/plutus-scripts/app/Main.hs +++ b/plutus-scripts/app/Main.hs @@ -2,13 +2,19 @@ module Main (main) where import Control.Monad (zipWithM_) import Data.Text qualified as T +import Helpers.Envelopes ( + VersionedScript (VersionedScript), + VersionedScriptGroup (VersionedScriptGroup), + formatCoreVersion, + formatPlutusVersion, + ) import Helpers.ScriptUtils (ScriptGroup (ScriptGroup, sgBaseName, sgScripts)) import Main.Utf8 (withUtf8) import PlutusCore.Default (DefaultFun, DefaultUni) import PlutusLedgerApi.Common.Versions (PlutusLedgerLanguage (PlutusV2, PlutusV3)) import PlutusLedgerApi.Envelope qualified as Envelope import PlutusScripts.Basic.V_1_1 qualified as Basic -import PlutusScripts.Batch6.DropList.V3_110 qualified as DropList_V3_110 +import PlutusScripts.Batch6.DropList qualified as DropList import PlutusScripts.Bitwise.V_1_0 qualified as BitwiseV0 import PlutusScripts.Bitwise.V_1_1 qualified as BitwiseV1 import PlutusScripts.Hashing.V_1_1 qualified as Hashing @@ -19,12 +25,28 @@ import System.Directory (createDirectoryIfMissing) -------------------------------------------------------------------------------- -- Script Group Helpers -------------------------------------------------------- +-- | Write versioned script with automatic filename generation +writeVersionedScript :: VersionedScript a -> IO () +writeVersionedScript (VersionedScript lang coreVer name code) = do + let versionSuffix = formatPlutusVersion lang <> "_" <> formatCoreVersion coreVer + let filename = T.unpack (name <> "_" <> versionSuffix) + writeEnvelope lang filename code + +-- | Write versioned script group with automatic base name generation +writeVersionedScriptGroup :: VersionedScriptGroup a -> IO () +writeVersionedScriptGroup (VersionedScriptGroup lang coreVer baseName scriptGroup) = do + let versionSuffix = formatPlutusVersion lang <> "_" <> formatCoreVersion coreVer + let baseWithVersion = T.unpack (baseName <> "_" <> versionSuffix) + zipWithM_ (writeNumbered lang baseWithVersion) [1 :: Integer ..] (sgScripts scriptGroup) + where + writeNumbered l base n = writeEnvelope l (base ++ "_" ++ show n) + -- | Write a group of numbered scripts (e.g., script_1.plutus, script_2.plutus, ...) writeScriptGroup :: ScriptGroup DefaultUni DefaultFun a -> IO () writeScriptGroup ScriptGroup{..} = zipWithM_ writeNumbered [1 :: Integer ..] sgScripts where - writeNumbered n code = writeEnvelopeV3 (sgBaseName ++ "_" ++ show n) code + writeNumbered n = writeEnvelopeV3 (sgBaseName ++ "_" ++ show n) -------------------------------------------------------------------------------- -- Main ------------------------------------------------------------------------ @@ -88,12 +110,9 @@ main = withUtf8 do -- Failing Bitwise Tests (ReadBit, WriteBits, ReplicateByte variants) mapM_ writeScriptGroup BitwiseV1.failingBitwiseScriptGroupsV3 - -- \** Batch 6 (protocol version 11) ** - writeEnvelopeV3 - "succeedingDropListPolicyScript_V3_110" - DropList_V3_110.succeedingDropListPolicy - - writeScriptGroup DropList_V3_110.expensiveDropListScriptGroup + -- Batch6 (PV11) builtins + mapM_ writeVersionedScript DropList.allDropListScripts + mapM_ writeVersionedScriptGroup DropList.allDropListScriptGroups -------------------------------------------------------------------------------- -- IO helpers ------------------------------------------------------------------ diff --git a/plutus-scripts/plutus-scripts.cabal b/plutus-scripts/plutus-scripts.cabal index a222f50..16d1706 100644 --- a/plutus-scripts/plutus-scripts.cabal +++ b/plutus-scripts/plutus-scripts.cabal @@ -72,12 +72,18 @@ library scripts , plutus-ledger-api ^>=1.53.1.0 , plutus-tx ^>=1.53.1.0 , plutus-tx-plugin ^>=1.53.1.0 + , text exposed-modules: + Helpers.Envelopes Helpers.ScriptUtils PlutusScripts.Basic.Common PlutusScripts.Basic.V_1_0 PlutusScripts.Basic.V_1_1 + PlutusScripts.Batch6.DropList + PlutusScripts.Batch6.DropList.Common + PlutusScripts.Batch6.DropList.V3_100 + PlutusScripts.Batch6.DropList.V3_110 PlutusScripts.Bitwise.Complement PlutusScripts.Bitwise.Conversions PlutusScripts.Bitwise.CountFindFirstSet @@ -118,9 +124,6 @@ library scripts PlutusScripts.SECP256k1.Common PlutusScripts.SECP256k1.V_1_0 PlutusScripts.SECP256k1.V_1_1 - PlutusScripts.Batch6.DropList.Common - PlutusScripts.Batch6.DropList.V3_100 - PlutusScripts.Batch6.DropList.V3_110 executable envelopes import: ghc-options From 6aa806da697da0b5a42d3a679e1790f216e1d68e Mon Sep 17 00:00:00 2001 From: kwxm Date: Tue, 25 Nov 2025 06:27:00 +0000 Subject: [PATCH 10/10] Restore writeVersionedScriptGroup --- plutus-scripts/app/Main.hs | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/plutus-scripts/app/Main.hs b/plutus-scripts/app/Main.hs index 27cd877..1089afe 100644 --- a/plutus-scripts/app/Main.hs +++ b/plutus-scripts/app/Main.hs @@ -133,3 +133,10 @@ writeScriptGroup ScriptGroup{..} = writeNumbered n = writeEnvelopeV3 (sgBaseName ++ "_" ++ show n) -- | Write versioned script group with automatic base name generation +writeVersionedScriptGroup :: VersionedScriptGroup a -> IO () +writeVersionedScriptGroup (VersionedScriptGroup lang coreVer baseName scriptGroup) = do + let versionSuffix = formatPlutusVersion lang <> "_" <> formatCoreVersion coreVer + let baseWithVersion = T.unpack (baseName <> "_" <> versionSuffix) + zipWithM_ (writeNumbered lang baseWithVersion) [1 :: Integer ..] (sgScripts scriptGroup) + where + writeNumbered l base n = writeEnvelope l (base ++ "_" ++ show n)