From cf3fc18aeca80b5c24ee2495cbd38fdf2ae96851 Mon Sep 17 00:00:00 2001 From: "Liberty.Chris" <82896265+Liberty-Chris@users.noreply.github.com> Date: Tue, 9 Jul 2024 01:02:51 -0400 Subject: [PATCH 1/4] Create Aiken_Design_Module 1) Data Structure: The Design data type encapsulates all necessary information about a design. 2) Minting Policy: The designPolicy function ensures that the minting conditions are met. 3) NFT Minting Function: The designNFT function creates an NFT with the design's name. 4) Minting Policy Script: The mkPolicy function combines the design policy and minting function. 5) Serialization: The minting policy is serialized for deployment. --- .../marketplace-scripts/Aiken_Design_Module | 71 +++++++++++++++++++ 1 file changed, 71 insertions(+) create mode 100644 space-printer/scripts/marketplace-scripts/Aiken_Design_Module diff --git a/space-printer/scripts/marketplace-scripts/Aiken_Design_Module b/space-printer/scripts/marketplace-scripts/Aiken_Design_Module new file mode 100644 index 0000000..fcb3496 --- /dev/null +++ b/space-printer/scripts/marketplace-scripts/Aiken_Design_Module @@ -0,0 +1,71 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE NoImplicitPrelude #-} +{-# LANGUAGE TemplateHaskell #-} +{-# LANGUAGE ScopedTypeVariables #-} + +module Designer where + +import Plutus.V2.Ledger.Api +import Plutus.V2.Ledger.Contexts +import Plutus.V2.Ledger.Tx +import Plutus.V2.Ledger.Value +import PlutusTx +import PlutusTx.Prelude hiding (Semigroup(..), unless) +import Prelude (IO, Semigroup(..)) + +-- Define the data structure for a Design +data Design = Design + { category :: ByteString + , name :: ByteString + , thumbnail :: ByteString + , model :: ByteString + , stlFiles :: [ByteString] + , royalty :: Maybe Integer + } + +PlutusTx.unstableMakeIsData ''Design + +-- Define the minting policy for design NFTs +{-# INLINABLE designPolicy #-} +designPolicy :: Design -> ScriptContext -> Bool +designPolicy design ctx = traceIfFalse "Invalid minting context" validMinting + where + txInfo :: TxInfo + txInfo = scriptContextTxInfo ctx + + validMinting :: Bool + validMinting = all (\i -> txOutValue (txInInfoResolved i) `geq` Ada.lovelaceValueOf 0) (txInfoInputs txInfo) + +-- Define the NFT minting function +{-# INLINABLE designNFT #-} +designNFT :: Design -> (ByteString, TxOut) +designNFT design = + let + nft = ByteString.append "nft-" (name design) + value = singleton (policyId design) (TokenName nft) 1 + txOut = TxOut (pubKeyHashAddress (txOutAddress output)) value Nothing + in + (nft, txOut) + +-- Minting policy script +{-# INLINABLE mkPolicy #-} +mkPolicy :: Design -> () -> ScriptContext -> Bool +mkPolicy design () ctx = designPolicy design ctx + +policy :: Design -> MintingPolicy +policy design = mkMintingPolicyScript $ + $$(PlutusTx.compile [|| mkPolicy ||]) + `PlutusTx.applyCode` + PlutusTx.liftCode design + +-- Serialize the minting policy +import Plutus.V2.Ledger.Scripts +import Plutus.V2.Ledger.Api + +mintingPolicy :: MintingPolicy +mintingPolicy = policy yourDesign + +serializedPolicy :: Script +serializedPolicy = unMintingPolicyScript mintingPolicy + +-- Save the serialized policy to a file or use it in a transaction From b64b696dae3da3fa5ba0c32b928fd5524340f6fe Mon Sep 17 00:00:00 2001 From: "Liberty.Chris" <82896265+Liberty-Chris@users.noreply.github.com> Date: Tue, 9 Jul 2024 01:07:59 -0400 Subject: [PATCH 2/4] Create Aiken_Consumer_Module 1) Data Structure: The Purchase data type encapsulates all necessary information about a purchase. 2) Validator: The purchaseValidator function ensures that the correct price is paid and the design NFT is valid. 3)Purchase Logic: The processPurchase function processes the purchase transaction. 4)Validator Script: The mkValidator function combines the purchase logic and validator. 5) Serialization: The validator is serialized for deployment on the blockchain. --- .../marketplace-scripts/Aiken_Consumer_Module | 76 +++++++++++++++++++ 1 file changed, 76 insertions(+) create mode 100644 space-printer/scripts/marketplace-scripts/Aiken_Consumer_Module diff --git a/space-printer/scripts/marketplace-scripts/Aiken_Consumer_Module b/space-printer/scripts/marketplace-scripts/Aiken_Consumer_Module new file mode 100644 index 0000000..2334141 --- /dev/null +++ b/space-printer/scripts/marketplace-scripts/Aiken_Consumer_Module @@ -0,0 +1,76 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE NoImplicitPrelude #-} +{-# LANGUAGE TemplateHaskell #-} +{-# LANGUAGE ScopedTypeVariables #-} + +module Consumer where + +import Plutus.V2.Ledger.Api +import Plutus.V2.Ledger.Contexts +import Plutus.V2.Ledger.Tx +import Plutus.V2.Ledger.Value +import PlutusTx +import PlutusTx.Prelude hiding (Semigroup(..), unless) +import Prelude (IO, Semigroup(..)) + +-- Define the data structure for a Purchase +data Purchase = Purchase + { designNFT :: ByteString + , price :: Integer + } + +PlutusTx.unstableMakeIsData ''Purchase + +-- Define the validator for purchase transactions +{-# INLINABLE purchaseValidator #-} +purchaseValidator :: Purchase -> () -> ScriptContext -> Bool +purchaseValidator purchase () ctx = traceIfFalse "Incorrect price paid" validPrice && + traceIfFalse "Invalid design NFT" validDesignNFT + where + txInfo :: TxInfo + txInfo = scriptContextTxInfo ctx + + -- Check that the correct price is paid + validPrice :: Bool + validPrice = any (\i -> txOutValue (txInInfoResolved i) `geq` Ada.lovelaceValueOf (price purchase)) (txInfoInputs txInfo) + + -- Check that the design NFT is valid + validDesignNFT :: Bool + validDesignNFT = any (\o -> txOutValue o `geq` singleton (policyId designNFT) (TokenName (designNFT purchase)) 1) (txInfoOutputs txInfo) + +-- Define the function to handle purchase logic +{-# INLINABLE processPurchase #-} +processPurchase :: Purchase -> ScriptContext -> Bool +processPurchase purchase ctx = + let + txInfo = scriptContextTxInfo ctx + inputs = txInfoInputs txInfo + outputs = txInfoOutputs txInfo + pricePaid = any (\i -> txOutValue (txInInfoResolved i) `geq` Ada.lovelaceValueOf (price purchase)) inputs + validNFT = any (\o -> txOutValue o `geq` singleton (policyId designNFT) (TokenName (designNFT purchase)) 1) outputs + in + traceIfFalse "Incorrect price paid" pricePaid && + traceIfFalse "Invalid design NFT" validNFT + +-- Validator script +{-# INLINABLE mkValidator #-} +mkValidator :: Purchase -> () -> ScriptContext -> Bool +mkValidator purchase () ctx = purchaseValidator purchase () ctx + +validator :: Purchase -> Validator +validator purchase = mkValidatorScript $ + $$(PlutusTx.compile [|| mkValidator ||]) + `PlutusTx.applyCode` + PlutusTx.liftCode purchase + +-- Serialize the validator +import Plutus.V2.Ledger.Scripts +import Plutus.V2.Ledger.Api + +purchaseValidator :: Validator +purchaseValidator = validator yourPurchase + +serializedValidator :: Script +serializedValidator = unValidatorScript purchaseValidator + +-- Save the serialized validator to a file or use it in a transaction From ca2516e5550c1e3ffab47fe39ebfc9a5158f7496 Mon Sep 17 00:00:00 2001 From: "Liberty.Chris" <82896265+Liberty-Chris@users.noreply.github.com> Date: Tue, 9 Jul 2024 01:11:06 -0400 Subject: [PATCH 3/4] Create Aiken_Printer_Operator_Module 1) Data Structure: The PrintJob data type encapsulates all necessary information about a print job. 2) Validator: The printJobValidator function ensures that the bid is valid, the design NFT is valid, and the shipping cost is non-negative. 3) Print Job Logic: The processPrintJob function processes the print job transaction. 4) Validator Script: The mkValidator function combines the print job logic and validator. 5) Serialization: The validator is serialized for deployment on the blockchain. --- .../Aiken_Printer_Operator_Module | 84 +++++++++++++++++++ 1 file changed, 84 insertions(+) create mode 100644 space-printer/scripts/marketplace-scripts/Aiken_Printer_Operator_Module diff --git a/space-printer/scripts/marketplace-scripts/Aiken_Printer_Operator_Module b/space-printer/scripts/marketplace-scripts/Aiken_Printer_Operator_Module new file mode 100644 index 0000000..264e4e3 --- /dev/null +++ b/space-printer/scripts/marketplace-scripts/Aiken_Printer_Operator_Module @@ -0,0 +1,84 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE NoImplicitPrelude #-} +{-# LANGUAGE TemplateHaskell #-} +{-# LANGUAGE ScopedTypeVariables #-} + +module PrinterOperator where + +import Plutus.V2.Ledger.Api +import Plutus.V2.Ledger.Contexts +import Plutus.V2.Ledger.Tx +import Plutus.V2.Ledger.Value +import PlutusTx +import PlutusTx.Prelude hiding (Semigroup(..), unless) +import Prelude (IO, Semigroup(..)) + +-- Define the data structure for a Print Job +data PrintJob = PrintJob + { designNFT :: ByteString + , bid :: Integer + , eta :: Integer + , shippingCost :: Integer + } + +PlutusTx.unstableMakeIsData ''PrintJob + +-- Define the validator for print job bids +{-# INLINABLE printJobValidator #-} +printJobValidator :: PrintJob -> () -> ScriptContext -> Bool +printJobValidator job () ctx = traceIfFalse "Invalid bid" validBid && + traceIfFalse "Invalid design NFT" validDesignNFT && + traceIfFalse "Invalid shipping cost" validShippingCost + where + txInfo :: TxInfo + txInfo = scriptContextTxInfo ctx + + -- Check that the bid is valid + validBid :: Bool + validBid = any (\i -> txOutValue (txInInfoResolved i) `geq` Ada.lovelaceValueOf (bid job)) (txInfoInputs txInfo) + + -- Check that the design NFT is valid + validDesignNFT :: Bool + validDesignNFT = any (\o -> txOutValue o `geq` singleton (policyId designNFT) (TokenName (designNFT job)) 1) (txInfoOutputs txInfo) + + -- Check that the shipping cost is valid + validShippingCost :: Bool + validShippingCost = shippingCost job >= 0 + +-- Define the function to handle print job logic +{-# INLINABLE processPrintJob #-} +processPrintJob :: PrintJob -> ScriptContext -> Bool +processPrintJob job ctx = + let + txInfo = scriptContextTxInfo ctx + inputs = txInfoInputs txInfo + outputs = txInfoOutputs txInfo + bidPaid = any (\i -> txOutValue (txInInfoResolved i) `geq` Ada.lovelaceValueOf (bid job)) inputs + validNFT = any (\o -> txOutValue o `geq` singleton (policyId designNFT) (TokenName (designNFT job)) 1) outputs + in + traceIfFalse "Invalid bid" bidPaid && + traceIfFalse "Invalid design NFT" validNFT && + traceIfFalse "Invalid shipping cost" (shippingCost job >= 0) + +-- Validator script +{-# INLINABLE mkValidator #-} +mkValidator :: PrintJob -> () -> ScriptContext -> Bool +mkValidator job () ctx = printJobValidator job () ctx + +validator :: PrintJob -> Validator +validator job = mkValidatorScript $ + $$(PlutusTx.compile [|| mkValidator ||]) + `PlutusTx.applyCode` + PlutusTx.liftCode job + +-- Serialize the validator +import Plutus.V2.Ledger.Scripts +import Plutus.V2.Ledger.Api + +printJobValidator :: Validator +printJobValidator = validator yourPrintJob + +serializedValidator :: Script +serializedValidator = unValidatorScript printJobValidator + +-- Save the serialized validator to a file or use it in a transaction From c6c99f457ff4a498e55ad93529401820ee3a5d18 Mon Sep 17 00:00:00 2001 From: "Liberty.Chris" <82896265+Liberty-Chris@users.noreply.github.com> Date: Tue, 9 Jul 2024 01:15:36 -0400 Subject: [PATCH 4/4] Create Aiken_Order_Finalization_Module 1) Data Structure: The OrderConfirmation data type encapsulates all necessary information for confirming an order. 2) Validator: The finalizeValidator function ensures that the final payment, design NFT, job NFT, and royalty payment are valid. 3) Order Finalization Logic: The processOrderFinalization function processes the order finalization transaction. 4) Validator Script: The mkValidator function combines the order finalization logic and validator. 5) Serialization: The validator is serialized for deployment on the blockchain. --- .../Aiken_Order_Finalization_Module | 92 +++++++++++++++++++ 1 file changed, 92 insertions(+) create mode 100644 space-printer/scripts/marketplace-scripts/Aiken_Order_Finalization_Module diff --git a/space-printer/scripts/marketplace-scripts/Aiken_Order_Finalization_Module b/space-printer/scripts/marketplace-scripts/Aiken_Order_Finalization_Module new file mode 100644 index 0000000..e9d9c6c --- /dev/null +++ b/space-printer/scripts/marketplace-scripts/Aiken_Order_Finalization_Module @@ -0,0 +1,92 @@ +{-# LANGUAGE DataKinds #-} +{-# LANGUAGE NoImplicitPrelude #-} +{-# LANGUAGE TemplateHaskell #-} +{-# LANGUAGE ScopedTypeVariables #-} + +module OrderFinalization where + +import Plutus.V2.Ledger.Api +import Plutus.V2.Ledger.Contexts +import Plutus.V2.Ledger.Tx +import Plutus.V2.Ledger.Value +import PlutusTx +import PlutusTx.Prelude hiding (Semigroup(..), unless) +import Prelude (IO, Semigroup(..)) + +-- Define the data structure for Order Confirmation +data OrderConfirmation = OrderConfirmation + { designNFT :: ByteString + , jobNFT :: ByteString + , finalPayment :: Integer + , royalty :: Integer + } + +PlutusTx.unstableMakeIsData ''OrderConfirmation + +-- Define the validator for order finalization +{-# INLINABLE finalizeValidator #-} +finalizeValidator :: OrderConfirmation -> () -> ScriptContext -> Bool +finalizeValidator confirmation () ctx = traceIfFalse "Invalid final payment" validFinalPayment && + traceIfFalse "Invalid design NFT" validDesignNFT && + traceIfFalse "Invalid job NFT" validJobNFT && + traceIfFalse "Invalid royalty payment" validRoyaltyPayment + where + txInfo :: TxInfo + txInfo = scriptContextTxInfo ctx + + -- Check that the final payment is valid + validFinalPayment :: Bool + validFinalPayment = any (\i -> txOutValue (txInInfoResolved i) `geq` Ada.lovelaceValueOf (finalPayment confirmation)) (txInfoInputs txInfo) + + -- Check that the design NFT is valid + validDesignNFT :: Bool + validDesignNFT = any (\o -> txOutValue o `geq` singleton (policyId designNFT) (TokenName (designNFT confirmation)) 1) (txInfoOutputs txInfo) + + -- Check that the job NFT is valid + validJobNFT :: Bool + validJobNFT = any (\o -> txOutValue o `geq` singleton (policyId jobNFT) (TokenName (jobNFT confirmation)) 1) (txInfoOutputs txInfo) + + -- Check that the royalty payment is valid + validRoyaltyPayment :: Bool + validRoyaltyPayment = any (\o -> txOutValue o `geq` Ada.lovelaceValueOf (royalty confirmation)) (txInfoOutputs txInfo) + +-- Define the function to handle order finalization logic +{-# INLINABLE processOrderFinalization #-} +processOrderFinalization :: OrderConfirmation -> ScriptContext -> Bool +processOrderFinalization confirmation ctx = + let + txInfo = scriptContextTxInfo ctx + inputs = txInfoInputs txInfo + outputs = txInfoOutputs txInfo + finalPaymentValid = any (\i -> txOutValue (txInInfoResolved i) `geq` Ada.lovelaceValueOf (finalPayment confirmation)) inputs + validDesignNFT = any (\o -> txOutValue o `geq` singleton (policyId designNFT) (TokenName (designNFT confirmation)) 1) outputs + validJobNFT = any (\o -> txOutValue o `geq` singleton (policyId jobNFT) (TokenName (jobNFT confirmation)) 1) outputs + validRoyaltyPayment = any (\o -> txOutValue o `geq` Ada.lovelaceValueOf (royalty confirmation)) outputs + in + traceIfFalse "Invalid final payment" finalPaymentValid && + traceIfFalse "Invalid design NFT" validDesignNFT && + traceIfFalse "Invalid job NFT" validJobNFT && + traceIfFalse "Invalid royalty payment" validRoyaltyPayment + +-- Validator script +{-# INLINABLE mkValidator #-} +mkValidator :: OrderConfirmation -> () -> ScriptContext -> Bool +mkValidator confirmation () ctx = finalizeValidator confirmation () ctx + +validator :: OrderConfirmation -> Validator +validator confirmation = mkValidatorScript $ + $$(PlutusTx.compile [|| mkValidator ||]) + `PlutusTx.applyCode` + PlutusTx.liftCode confirmation + +-- Serialize the validator +import Plutus.V2.Ledger.Scripts +import Plutus.V2.Ledger.Api + +orderFinalizationValidator :: Validator +orderFinalizationValidator = validator yourOrderConfirmation + +serializedValidator :: Script +serializedValidator = unValidatorScript orderFinalizationValidator + +-- Save the serialized validator to a file or use it in a transaction