Skip to content

Commit

Permalink
Merge branch 'main' into 10871-exciseReallocate
Browse files Browse the repository at this point in the history
  • Loading branch information
mergify[bot] authored Feb 18, 2025
2 parents 0156fd8 + 63ca7a2 commit 9693576
Show file tree
Hide file tree
Showing 12 changed files with 260 additions and 1,088 deletions.
95 changes: 4 additions & 91 deletions main/guides/dapps/index.md
Original file line number Diff line number Diff line change
@@ -1,94 +1,7 @@
# Agoric Dapps

**This is a generic guide to Agoric Dapp projects**
See

A dapp is a _decentralized application_ which typically has a browser-based user interface, a public API server, and a contract running on the Agoric blockchain.

## Using a Dapp

If you have installed the [Agoric CLI](../getting-started/) and you want to try running a dapp locally on a simulated Agoric VM (i.e., it won't be running on an actual public chain), do the following:

1. Checkout the latest beta release of the SDK.

```sh
cd agoric-sdk
git checkout beta
yarn && yarn build
```

2. Run `agoric init` to make a new local copy of a dapp template.

```sh
# Here we chose the Fungible Faucet Dapp.
# You can replace `my-fungible-faucet` with a name of your choice.
agoric init --dapp-template dapp-fungible-faucet --dapp-branch beta my-fungible-faucet
cd my-fungible-faucet
# Install the project dependencies
agoric install
# Start the Agoric VM
agoric start --reset
```

3. Leave this command running (it is your simulated environment).
4. In a separate terminal, deploy the contract and API to the VM.

```sh secondary style2
# Deploy a new instance of the contract to the VM
agoric deploy contract/deploy.js
# Reset the VM's API server
agoric deploy api/deploy.js
```

5. In a third terminal, run the following.

```sh secondary style3
# Start the user interface
cd ui && yarn start
```

6. You can now navigate to [http://localhost:3000](http://localhost:3000) to view your dapp.

## Modifying this Dapp

In the Agoric system, components are written in Javascript.

## Components

The following are the important directories in an Agoric dapp project:

- [`contract/`](#contract-directory) defines the on-chain smart contract.
- [`api/`](#api-directory) defines the chain-connected server's `/api` HTTP endpoint.
- [`ui/`](#ui-directory) defines the browser user interface connecting users' personal wallets and the API server.

Other files and directories in this top-level folder should not typically be modified.

### Contract Directory

In the `contract` directory, you can find the following files to edit:

- **src directory**: Contract source code, starting with `src/contract.js`.

There are also files and folders that you usually shouldn't edit:

- **deploy.js**: Generic Agoric contract deployment script.

### API Directory

In the `api` directory, you can find the following files to edit:

- **src directory**: Handler for API HTTP endpoints, starting with `src/handler.js`.

There are also files and folders that you usually shouldn't edit:

- **deploy.js**: Generic Agoric API handler deployment script.

### UI Directory

The `ui` directory is almost completely under your control. The only files and folders that you usually shouldn't edit are:

- **public/lib**: The Agoric UI library.
- **public/conf**: Configuration files that are generated by the `contract/deploy.js` script.

## More Information

You can [learn more about the Agoric smart contract platform](https://agoric.com).
- [Getting Started](/guides/getting-started/)
- [Building Client Dapps](/guides/getting-started/contract-rpc.html)
- [UI Tutorial](/guides/getting-started/ui-tutorial/)
58 changes: 32 additions & 26 deletions main/guides/orchestration/contract-walkthroughs/send-anywhere.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ The high-level flow of the contract is:
- Creates or ensures the existence of a local account (held by the contract) to handle temporary holding.
- Transfers the asset from the source address to the local account.
- Initiates a transfer to the destination address, which could reside on the remote blockchain.
- Gracefully handles the failures.
- Gracefully handles failures.

The contract is implemented in two separate files:

Expand All @@ -24,12 +24,12 @@ Let us walk through these files one by one.

The contract begins by importing various modules and utilities necessary for its functionality. These include:

- **State management**: `makeSharedStateRecord` is imported to create and manage the state across contract incarnations.
- **Type validation**: `AmountShape` and `InvitationShape` ensure that the contract works with correct data types, such as amounts and invitations.
- **State management**: `makeSharedStateRecord` is imported to create and manage state across contract incarnations.
- **Type validation**: `AnyNatAmountShape` and `InvitationShape` ensure that the contract works with correct data types, such as amounts and invitations.
- **Orchestration utilities**: `withOrchestration` is imported to facilitate interactions with Orchestration functions.
- **Flows**: The Orchestration flows for handling transfers are imported from `send-anywhere.flows.js` to be made available to Zoe.

These imports set up the contract for the validation, orchestration, and execution of transfers through Zoe API.
These imports set up the contract for the validation, orchestration, and execution of transfers through the Zoe API.

### Single Amount Record Validation

Expand All @@ -52,16 +52,14 @@ This validation ensures that the proposal shape submitted by users contains exac
The contract defines a shared state record as below:

```js
const contractState = makeSharedStateRecord(
/** @type {{ account: OrchestrationAccount<any> | undefined }} */ {
localAccount: undefined
}
const sharedLocalAccountP = zone.makeOnce('localAccount', () =>
makeLocalAccount()
);
```

This state keeps track of the local account that will hold the transferred assets temporarily before they are sent to the destination
address. The state starts with an undefined `localAccount`. This account will be created later during the offer handling process if
needed.
`sharedLocalAccountP` stores the local account that will hold the transferred assets temporarily before they
are sent to the destination address. Since this is initialized with a promise (`makeOnce` returns a promise, so
we add a `P` to the variable name), uses of `sharedLocalAccountP` will have to await it before making use of it.

### Logging setup

Expand All @@ -81,8 +79,8 @@ these functions with the necessary context (such as the contract state, logging,

```js
const orchFns = orchestrateAll(flows, {
contractState,
log,
sharedLocalAccountP,
zoeTools
});
```
Expand Down Expand Up @@ -111,7 +109,7 @@ const publicFacet = zone.exo(
```

The `makeSendInvitation` method creates an invitation for users, allowing them to initiate a transfer by submitting a proposal. The
proposal must match the structure defined by the `SingleNatAmountRecord`, ensuring that only one asset is transferred per transaction.
proposal must match the structure defined by `SingleNatAmountRecord`, ensuring that only one asset is transferred per transaction.
The invitation is connected to the `sendIt` function (explained later), which performs the asset transfer.

## 2. `send-anywhere.flows.js`
Expand All @@ -122,22 +120,26 @@ remote chains. The parameters passed to this function include:

- `orch`: The orchestrator object for managing chain/account interactions.
- `ctx`: The contract state and utility functions, including:
- `contractState`: Holds the local account for intermediate storage.
- `localTransfer`: The transfer function for moving assets between local accounts.
- `sharedLocalAccountP`: Holds the local account for intermediate storage.
- `log`: access to logging
- zoeTools: Helper functions for transferring assets. Contains
- `localTransfer`: Support for moving assets between local accounts.
- `withdrawToSeat`: Support for moving assets from a local account to an account on a remote chain.
- `seat`: The Zoe seat representing the assets to be transferred.
- `offerArgs`: Includes details about the destination chain and address.

The `sendIt` function performs following important steps:
The `sendIt` function performs the following important steps:

### Offer Validation and Setup

Upon receiving an offer, the `sendIt` function:

- Validates the offer arguments using [endo's pattern-matching library](https://github.com/endojs/endo/tree/master/packages/patterns) to ensure the correct structure is submitted.
- Retrieves the `proposal` from the seat, extracting the asset (`brand` and `amount`) being transferred.
- The contract ensures that the asset brand is registered on the local chain by querying the chain’s asset registry (`vbank`). If not
the contract throws an error and exits the transaction.
- If a local account for the contract doesn’t already exist, the function creates one.
- Retrieves the `proposal` from the seat, extracting (from `give`) the asset (`brand` and `amount`) being transferred.
- The contract ensures that the asset brand is registered on the local chain by querying the chain’s asset registry
(`vbank`). If not the contract throws an error and exits the transaction. It also gets the `denom` for the
destination chain from the `vbank`.
- retrieves the `chainId` for the remote chain.

```js
mustMatch(offerArgs, harden({ chainName: M.scalar(), destAddr: M.string() }));
Expand All @@ -149,17 +151,20 @@ void log(`sending {${amt.value}} from ${chainName} to ${destAddr}`);
const agoric = await orch.getChain('agoric');
const assets = await agoric.getVBankAssetInfo();
void log(`got info for denoms: ${assets.map(a => a.denom).join(', ')}`);

const { denom } = NonNullish(
assets.find(a => a.brand === amt.brand),
`${amt.brand} not registered in vbank`
);

if (!contractState.localAccount) {
contractState.localAccount = await agoric.makeAccount();
}
const chain = await orch.getChain(chainName);
const info = await chain.getChainInfo();
const { chainId } = info;
assert(typeof chainId === 'string', 'bad chainId');
void log(`got info for chain: ${chainName} ${chainId}`);
```

This setup phase ensures the transaction is valid and the contract is prepared to handle it.
This setup phase ensures the transaction is valid and the contract is prepared to handle it. Notice that all checks
are complete before any transfers are started.

### Assets Transfer

Expand All @@ -168,7 +173,8 @@ Once everything is validated, the contract performs the following steps:
- **Local transfer**: The assets are first transferred from the Zoe seat to the contract’s local account using `localTransfer` API.

```js
await localTransfer(seat, contractState.localAccount, give);
const sharedLocalAccount = await sharedLocalAccountP;
await localTransfer(seat, sharedLocalAccount, give);
```

- **Remote transfer**: The contract initiates the transfer to the destination address on the remote chain. This transfer includes
Expand Down
129 changes: 2 additions & 127 deletions main/reference/repl/index.md
Original file line number Diff line number Diff line change
@@ -1,129 +1,4 @@
# Agoric REPL

**Note**: This page describes the Agoric REPL.
If you are instead looking for information about `node` or the Node.js REPL, see
[Node.js documentation](https://nodejs.org/api/repl.html).

## Introduction

When you run `agoric start --reset`, you start a local _ag-solo_.

You use `agoric start` to start what we call an _ag-solo_, which is a
single personal local Agoric node. You need an ag-solo running on your
machine to interact with Agoric network services, whether a built-in
simulated chain (also started by `agoric start`), or a fully-decentralized public Agoric
blockchain.

All deployment happens via the local running Agoric process. This is usually the
ag-solo process, and frequently referred to as that or just as ag-solo. It is also
sometimes described as/called an Agoric VM or a local server.

An ag-solo communicates with either a locally running or remote chain. This local process (the ag-solo)
has a home object, which contains references to services on-chain, including Zoe, the
Board for sharing objects, and an application user's Wallet, among others. Developers can
use these service references to call the service's associated API commands.

Contract code starts in a file on a user's computer, either written by them or
imported from `agoric/zoe`. The code is _bundled_; turned into a particularly formatted
blob of code that exists in memory while a deploy script is running. When `E(zoe).install()` is
called, the blob is sent to and stored on-chain so that Zoe can access it.

An ag-solo has an associated REPL (_Read-Eval-Print Loop_). From the REPL and the `home`
object, developers can use all the on-chain commands that deployment scripts use to
deploy contracts and Dapps. In addition to the on-chain commands, they can also run
any other JavaScript commands from the REPL.

## Accessing the REPL

Once an ag-solo is running and on-chain, you can access its associated REPL
in two ways.

- In a browser tab, go to `localhost:8000`. Depending on the browser's width, you
will see the Wallet UI and REPL either in separate columns or separate rows.

![Wallet and REPL](./assets/walletAndREPLColumns.png)

![Wallet and REPL](./assets/walletAndREPLRows.png)

- From a shell, run `agoric open --repl` This opens the user's Wallet UI and its
associated REPL. To open only the REPL, run `agoric open --repl only`

![REPL](./assets/repl.png)

## Using the REPL

You can run JavaScript commands from the REPL. You can also use the REPL's
`home` object's predefined connections to other objects and services. To see what’s
available, just type `home` into the REPL:

![home](./assets/home.png)

```js
Command[1] home
History[1] {"chainTimerService":[Presence o-50],"contractHost":[Presence o-52],"ibcport":[Presence o-53],"registrar":[Presence o-54],"registry":[Presence o-55],"zoe":[Presence o-56],"localTimerService":[Presence o-57],"uploads":[Presence o-58],"spawner":[Presence o-59],"wallet":[Presence o-60],"network":[Presence o-61],"http":[Presence o-62]}
```

The results of what is entered into the REPL is saved under `history[N]`

The following sections describe the `home` objects developers can use. Click on the
section header to go to more detailed documentation about that object.
Several `home` objects are either for internal Agoric use only or have been deprecated. These
are listed together in the final section. External developers should ignore them and not try to use
them.

### [`wallet`](../wallet-api/)

Holds on-chain digital assets and object capabilities on behalf of the user.
The header link takes you to the standard non-REPL specific `wallet` API documentation. When calling
`wallet` API methods from the REPL, `wallet` must be prefaced by `home.` and use `E()`. For
example, `E(home.wallet).getPurses()`. [Full Wallet API documentation.](/guides/wallet/)

### [`chainTimerService`](./timerServices)

On-chain time authority used to schedule events. [Full `chainTimerService` documentation.](./timerServices)

### [`localTimerService`](./timerServices)

Local off-chain time authority used to schedule events. [Full `localTimerService` documentation.](./timerServices)

### [`board`](./board)

Shared on-chain location where users can post generally accessible values. [Full `board` documentation.](./board)

### [`ibcport`](./networking)

IBC implementation that lets vats open and close listening ports,
connect and disconnect to/from remote ports, and send and receive
data over those connections. [Full `ibcport` documentation.](./networking)

### [`zoe`](../zoe-api/zoe)

Deploy and interact with smart contracts. Zoe protects smart contract users by escrowing
digital assets and guaranteeing users get either what they want or get a refund of what
they escrowed. Even if the contract is buggy or malicious. The header link takes you to the
standard, non-REPL specific, `zoe` API documentation. When calling any of the `zoe` API
methods from the REPL, `zoe` must be prefaced by `home.` and use `E()`. For
example, `E(home.zoe).getFoo()`. [Full Zoe API documentation.](../zoe-api/zoe)

### [`priceAuthority`](./priceAuthority)

Get price quotes for pairs of digital assets. [Full `priceAuthority` documentation.](./priceAuthority)

### [`scratch`](./scratch)

An off-chain, private, place to store key-value pairs on your ag-solo for later use. [Full `scratch` documentation.](./scratch)

### Deprecated and Internal-Only Objects

- `contractHost`: Replaced by the `spawner` object.
- `faucet`: Internal for chain setup.
- `http`: `api/deploy.js` uses this to install new HTTP and WebSocket handlers in an
ag-solo. You should not need to use it.
- `network`: Privileged object for internal use. [Full Network documentation.](./networking)
- `plugin`: Privileged object for internal use.
- `priceAuthorityAdmin`: Privileged object for internal use.
- `registrar`: Deprecated.
- `registry`: Deprecated.
- `spawner`: Privileged object for internal use.
- `uploads`: Deprecated name for `scratch`.
- `vattp`: Privileged object for internal use.
**Note**: Agoric REPL has been deprecated. Please see [Testing a Contract](/guides/zoe/contract-hello#testing-a-contract)
for information on how to test your smart contracts using [AVA](https://github.com/avajs/ava).
3 changes: 3 additions & 0 deletions main/reference/zoe-api/user-seat.md
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,9 @@ redirecting escrowed assets in accordance with the result of the transaction.

The promise will be resolved promptly once the seat exits.

If there is no payment corresponding to the keyword, an error will be
thrown.

## E(UserSeat).getOfferResult()

- Returns: **Promise&lt;OfferResult>**
Expand Down
Loading

0 comments on commit 9693576

Please sign in to comment.