VATs
The Agoric framework uses the same event loop as web browsers and Node.js. Each event loop has a message queue, a call stack of frames, and a heap of objects.
Agoric refer’s to this combination of an event loop with a message queue, a stack, and a heap as a vat
. Vats are like containers for JavaScript code. Inside a vat, everything communicates synchronously. But when vats talk to each other, it’s asynchronous.
Eventual Send
When you want to get data from a server, like a list of products, you can use something called the fetch
API. This helps you make requests to a server and handle the responses. Something like this:
const init = fetch('products.json')
.then((response) => response.json())
.then((products) => initialize(products))
.catch((err) => {
console.log(`Fetch problem: ${err.message}`);
});
In the Agoric, you often need to talk to objects that aren’t on your local computer but are on the network or blockchain. To make this easier, Agoric uses a special function called E()
.
Let’s say you need to install a smart contract on a blockchain using a service called Zoe
. You don’t have direct access to Zoe. Instead, you have a remote reference to it. Here’s how you can send a command to Zoe using E()
:
import { E } from '@endo/eventual-send';
E(zoe)
.install(bundle) // Send a request to Zoe to install a bundle (smart contract)
.then((installationHandle) => {
// Once installed, handle the result
// Do something with the installation handle
})
.catch((err) => {
// If there is an error, catch it and log a message
// Handle the error
});
This way, you can communicate with objects in separate vats as easily as objects in the same vat.
Far()
To export objects such as to make them available to other vats, mark them as remotable using Far
.
import { Far, passStyleOf } from '@endo/marshal';
const makeCounter = () => {
let count = 0;
return Far('counter', {
incr: () => (count += 1),
decr: () => (count -= 1),
});
};
const publicFacet = Far('makeCounter', { makeCounter });
assert(passStyleOf(publicFacet) === 'remotable');
By making an object remoteable, you can invoke methods of the Remotable object from remote locations as if the object were local. Another vat can make and use the exported counters:
const counter = E(publicFacet).makeCounter();
const n = await E(counter).incr();
Purses
A purse
is an object that holds digital assets of a specific type (e.g., a specific token or currency). It can contain any amount of that asset, from zero to the maximum amount available.
Key Characteristics
Asset Type
: Each purse is associated with a specific asset type, such as a specific cryptocurrency or token.Deposit Only
: Purses are designed to be deposit-only, meaning you cannot directly spend from a purse. Instead, you withdraw assets to a payment object when you need to transfer or spend them.Balance Checking
: You can check the balance of a purse to see how much of the asset it contains.
Issuer
An issuer
is an object that validates and manages the lifecycle of digital assets of a specific type. It ensures that assets are authentic and can be trusted by participants in the system.
Payment
A payment
is an object that encapsulates a specific amount of digital assets that can be transferred from one party to another. It is a one-time-use object, meaning once it is used (e.g., deposited into a purse), it cannot be reused.
Key Characteristics
Transferable
: Payments are designed to be transferred between parties, representing the movement of assets.One-Time Use
: After a payment is used for a transaction (such as being deposited into a purse), it is no longer valid.Validated by Issuers
: The issuer associated with the payment’s asset type ensures the payment is valid and genuine.
Atomic Transfer
In databases, atomicity is one of the four ACID properties (Atomicity, Consistency, Isolation, Durability) that ensure reliable transaction processing. Atomicity guarantees that a series of operations within a transaction are treated as a single unit. If any operation within the transaction fails, the entire transaction is rolled back, and the database state is left unchanged.
Atomic Transfer
refers to a series of transactions or operations that are executed as a single, indivisible unit. In the context of smart contracts, this means that either all operations within the transaction succeed, or none of them do. This ensures that the state of the blockchain remains consistent and prevents partial updates that could lead to inconsistencies or vulnerabilities.
Atomic Rearrange
Atomic Rearrange extends the concept of atomicity to more complex operations involving multiple parties and assets. It allows for the reorganization or rearrangement of assets among multiple participants in a single, indivisible operation. This is particularly useful in scenarios like multi-party swaps or complex asset exchanges where the integrity of the entire set of operations must be maintained.
What Are Seats?
Think of a Seat Like a Ticket
Imagine you want to join a game or event. You get a ticket that shows you are a participant. In a Zoe contract, this ticket is called a “seat.”
Making an Offer
When you want to make an offer in a Zoe contract (like buying or selling something), you get a seat. This seat keeps track of what you are offering and what you want in return.
Your Spot in the Contract
A seat is your spot in the contract. It allows you to interact with the contract, check if your offer is accepted, and receive your payout (like getting your prize or purchase).