Nu vil vi se på smarte aktiver og flere tilfælde af deres brug, herunder indefrysning af aktiver og oprettelse af begrænsninger for transaktioner på specificerede adresser.
Waves Smart Assets giver brugerne mulighed for at overlejre scripts på aktiver efter samme mekanik som Smart Accounts. Hver ny transaktion, der oprettes ved hjælp af et smart aktiv, bekræftes først af scriptet og først derefter af blockchain.
Det er værd at bemærke følgende forskelle mellem smarte aktiver og smarte konti:
I koden for et smart aktiv er det umuligt at kontrollere beviser (vi talte om dem i den første artikel).
I den smarte kontokode kan du kun tjekke ExchangeTransaction, hvis din konto er en matcherkonto. Ellers er det kun ordren, der kontrolleres. I den smarte aktivkode kan du ikke kontrollere ordren direkte; du kan kontrollere ExchangeTransactionen og om nødvendigt udtrække en ordre fra den.
Et smart aktiv, i modsætning til en smart konto, har ikke en tilstand, men vi har stadig adgang til kontotilstande fra scriptet.
Smarte aktiver forenkler i høj grad skrivningen af kontrakter, hvilket gør implementeringen af mange sager kortfattet og elegant.
Fastfrysning af aktiver
At fryse aktiver til en bestemt blokhøjde målhøjde, kan du blot indstille denne værdi i scriptet for følgende smarte aktiv:
let targetHeight = 1500000
height >= targetHeight
height - функция языка, возращающая текущую высоту.
Matcher specifik tilstand
For at indstille en specifik matcher som den ønskede, kan du indstille dens adresse som afsender i et smart asset script, der ser sådan ud:
match tx {
case t : ExchangeTransaction =>
t.sender == addressFromString("3PJaDyprvekvPXPuAtxrapacuDJopgJRaU3")
case _ => true
}
"Hvid liste" over modtagere
For at tillade, at tokens kun sendes til bestemte konti - for at oprette en "hvid liste" over modtagere - kan du bruge et smart aktiv med følgende skema, der kontrollerer for medtagelse på listen:
match tx {
case t : TransferTransaction =>
let trustedRecipient1 = addressFromString("3P6ms9EotRX8JwSrebeTXYVnzpsGCrKWLv4")
let trustedRecipient2 = addressFromString("3PLZcCJyYQnfWfzhKXRA4rteCQC9J1ewf5K")
let trustedRecipient3 = addressFromString("3PHrS6VNPRtUD8MHkfkmELavL8JnGtSq5sx")
t.recipient == trustedRecipient1 || t.recipient == trustedRecipient2 || t.recipient == trustedRecipient3
case _ => false
}
Af sikkerhedsmæssige årsager og beviselig fuldstændighed af sproget indeholder listen ikke en iteratorimplementering. Derfor er det defineret som et sæt af betonelementer.
"Sort liste" over modtagere
Tilsvarende, for at forbyde at sende tokens til visse konti, kan du oprette en "sort liste". I dette tilfælde bruges nøjagtig det samme smarte aktiv, men med adressen markeret for at sikre, at den ikke er på sortlisten:
match tx {
case t : TransferTransaction =>
let bannedRecipient1 = addressFromString("3P6ms9EotRX8JwSrebeTXYVnzpsGCrKWLv4")
let bannedRecipient2 = addressFromString("3PLZcCJyYQnfWfzhKXRA4rteCQC9J1ewf5K")
let bannedRecipient3 = addressFromString("3PHrS6VNPRtUD8MHkfkmELavL8JnGtSq5sx")
t.recipient != bannedRecipient1 && t.recipient != bannedRecipient2 && t.recipient != bannedRecipient3
case _ => false
}
Sendes med tilladelse fra udstederen
Ved at bruge et smart aktiv kan du også indstille muligheden for kun at sende et smart aktiv med tilladelse fra udstederen (tilsagn/gældsmærke). Udstederen udtrykker sit samtykke ved at placere transaktions-id'et i tilstanden på sin konto:
match tx {
case t : TransferTransaction =>
let issuer = extract(addressFromString("3P6ms9EotRX8JwSrebeTXYVnzpsGCrKWLv4"))
#убеждаемся, что в стейте эмитента содержится ID текущей транзакции
isDefined(getInteger(issuer, toBase58String(t.id)))
case _ => false
}
Byt kun til visse mønter
Et smart aktiv giver kun tilladelse til at bytte det til visse mønter. For eksempel, for kun at tillade udveksling af Bitcoins, kan du bruge følgende kode:
let BTCId = base58'8LQW8f7P5d5PZM7GtZEBgaqRPGSzS3DfPuiXrURJ4AJS'
match tx {
case t : ExchangeTransaction =>
t.sellOrder.assetPair.priceAsset == BTCId ||
t.sellOrder.assetPair.amountAsset == BTCId
case _ => true
}
Handel efter pris fra oraklet
I det smarte aktiv-script kan du indstille tilladelse til kun at handle til den pris, der er fastsat i et pålideligt orakel. Her er et eksempel på sådan et script:
let oracle = Address(base58'3PLNmokt22NrSiNvCLvwMUP84LCMJqbXwAD')
let assetId = toBase58String(base58'oWgJN6YGZFtZrV8BWQ1PGktZikgg7jzGmtm16Ktyvjd')
match tx {
#запрещаем передачу ассета
case t: TransferTransaction | MassTransferTransaction => false
case e: ExchangeTransaction =>
#убеждаемся, что торговля происходит по цене, заданной в стейте оракла для этого ассета
let correctPrice = e.price == extract(getInteger(oracle, assetId))
#убеждаемся, что торговля происходит в обмен на WAVES
let correctPriceAsset = !isDefined(e.sellOrder.assetPair.priceAsset)
correctPrice && correctPriceAsset
case _ => true
}
Her står vi over for et ikke-oplagt punkt, når vi tjekker ID'et på det aktiv, som handles med. Pointen er, at hvis aktiv-id'et ikke er defineret, så taler vi om WAVES. I scriptet sørger vi for, at handel udføres i tandem med WAVES, på præcis denne måde.
Fast prisstigning
Du kan sætte en fast pris for et smart aktiv, som vil stige trin for trin i en given andel. Her er et eksempel på et aktivscript, hvis pris vil stige med 5 % for hver 1000 blokke:
let startPrice = 10
let startHeight = 1000
let interval = 1000
#на сколько процентов цена увеличивается за один шаг
let raise = 5
match tx {
case t: TransferTransaction | MassTransferTransaction => false
case e: ExchangeTransaction =>
e.price == startPrice + ((height - startHeight) / interval) * (100 + raise) / 100
&& !isDefined(e.sellOrder.assetPair.priceAsset)
case _ => true
}
Interval handel
Takket være scriptet kan handel med et smart aktiv også begrænses til forudbestemte intervaller. Her er et eksempel på sådan et script:
let startHeight = 10000
let interval = 44000
let limit = 1500
match tx {
case t: TransferTransaction | MassTransferTransaction | ExchangeTransaction =>
(height - startHeight) % interval < limit
case _ => true
}
I scriptet sørger vi for, at fra starten af handel startHøjde ikke mere end begrænse intervaller. Længden af intervallet er lig med antallet af blokke angivet i feltet interval.