Skip to content

Deploy and Operate an Aspens Markets Stack

This comprehensive guide shows you how to deploy and configure your own Aspens Markets Stack (AMS). Follow these steps to set up a complete cross-chain trading infrastructure that enables seamless trading between different blockchain networks.

Table of Contents

  1. Set Up Infrastructure
  2. Deploy Smart Contracts
  3. Deploy the Stack
  4. Configure Blockchain Networks
  5. Configure Tokens
  6. Create Markets
  7. Implement Security and Monitoring
  8. Go Live
  9. Maintain and Update Your Stack
  10. Enable Application Development

1. Set Up Infrastructure

Check Prerequisites

Before beginning, ensure you have:

  • Docker and Docker Compose installed
  • Domain name for your AMS instance
  • Access to blockchain node endpoints (RPC URLs) for each chain you'll support
  • Private key for the AMS deployer wallet (will control the AMS configuration)

Prepare the Environment

# Create a dedicated directory for your AMS deployment
mkdir -p ~/aspens-stack
cd ~/aspens-stack

# Clone the Aspens Markets Stack repository
git clone https://github.com/aspensprotocol/markets-stack.git .

# Create configuration directories
mkdir -p config data logs

2. Deploy Smart Contracts

Before deploying the stack, you need to deploy the smart contracts that will power your Aspens Markets Stack instance. The deployment process involves deploying a ContractFactory on each supported chain and then creating an AppInstance through the TEE (Trusted Execution Environment).

Contract Deployment Flow

graph TD
    A[ContractFactory Deployed<br>on Multiple Chains] --> B[AppStack Defined,<br>Configured, and<br>Instantiated in TEE]

    subgraph User_Interactions
        C1[gRPC: AddChain base]
        C2[gRPC: AddChain quote]
        C1 --> B
        C2 --> B

        D[gRPC: CreateInstance]
        D --> B
    end

    B -->|Calls| E[ContractFactory SC]
    E -->|Returns AppInstance<br>at 0x... with AppStack<br>as owner| F[AppInstance]

    subgraph Post_Instance_Setup
        G1[gRPC: Add Token<br>to BaseChain]
        G2[gRPC: Add Token<br>to QuoteChain]
        G1 --> F
        G2 --> F

        H[gRPC: Create Markets<br>for Token Pairs]
        H --> F
    end

Deployment Steps

  1. Deploy ContractFactory
  2. Deploy the ContractFactory smart contract on each chain you plan to support
  3. Keep track of the deployed addresses for each chain

  4. Configure AppStack in TEE

  5. Define your AppStack configuration in the TEE
  6. Add base and quote chains using the gRPC interface
  7. Create an instance through the TEE

  8. Create AppInstance

  9. The TEE will interact with the ContractFactory to create your AppInstance
  10. The AppInstance will be deployed at a new address on each chain
  11. Your AppStack will be set as the owner of these instances

  12. Post-Deployment Setup

  13. Add tokens to each chain through the gRPC interface
  14. Create markets for the token pairs you want to support
  15. Configure market parameters and fees

Security Considerations

  • Ensure the TEE is properly configured and secured
  • Keep private keys for contract deployment secure
  • Verify contract addresses and ownership after deployment
  • Monitor contract events for any unexpected behavior

3. Deploy the Stack

Configure the Stack via gRPC

The Aspens Markets Stack is configured through a series of gRPC calls. You'll need to use a gRPC client (like grpcurl) to make these calls. Here's the step-by-step process:

1. Add Base Chain

First, add your base chain (e.g., Ethereum):

grpcurl -plaintext -d '{
  "chain": {
    "chainId": "1",
    "name": "Ethereum",
    "rpcUrl": "https://your-ethereum-rpc-endpoint",
    "contractAddress": "0xYourContractFactoryAddress",
    "confirmations": 12
  }
}' localhost:50051 aspens.v1.AdminService/AddChain

2. Add Quote Chain

Next, add your quote chain (e.g., Hedera):

grpcurl -plaintext -d '{
  "chain": {
    "chainId": "hedera:mainnet",
    "name": "Hedera",
    "rpcUrl": "https://your-hedera-endpoint",
    "contractAddress": "0.0.yourContractFactoryAddress",
    "confirmations": 5
  }
}' localhost:50051 aspens.v1.AdminService/AddChain

3. Add Tokens to Base Chain

Add the tokens you want to support on the base chain:

# Add USDT on Ethereum
grpcurl -plaintext -d '{
  "token": {
    "chainId": "1",
    "symbol": "USDT",
    "name": "Tether USD",
    "address": "0xdAC17F958D2ee523a2206206994597C13D831ec7",
    "decimals": 6,
    "isNative": false
  }
}' localhost:50051 aspens.v1.AdminService/AddToken

# Add WETH on Ethereum
grpcurl -plaintext -d '{
  "token": {
    "chainId": "1",
    "symbol": "WETH",
    "name": "Wrapped Ether",
    "address": "0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2",
    "decimals": 18,
    "isNative": false
  }
}' localhost:50051 aspens.v1.AdminService/AddToken

4. Add Tokens to Quote Chain

Add the corresponding tokens on the quote chain:

# Add USDC on Hedera
grpcurl -plaintext -d '{
  "token": {
    "chainId": "hedera:mainnet",
    "symbol": "USDC",
    "name": "USD Coin",
    "address": "0.0.yourUsdcTokenId",
    "decimals": 6,
    "isNative": false
  }
}' localhost:50051 aspens.v1.AdminService/AddToken

# Add HBAR on Hedera
grpcurl -plaintext -d '{
  "token": {
    "chainId": "hedera:mainnet",
    "symbol": "HBAR",
    "name": "Hedera",
    "address": "0.0.0",
    "decimals": 8,
    "isNative": true
  }
}' localhost:50051 aspens.v1.AdminService/AddToken

5. Create Markets

Create markets for the token pairs you want to support:

# Create USDT/USDC market
grpcurl -plaintext -d '{
  "market": {
    "baseTokenId": "1:USDT",
    "quoteTokenId": "hedera:mainnet:USDC",
    "displayName": "USDT/USDC",
    "description": "Trade USDT on Ethereum for USDC on Hedera",
    "minOrderSize": "10",
    "maxOrderSize": "1000000",
    "priceDecimals": 6,
    "quantityDecimals": 2,
    "makerFee": "0.0010",
    "takerFee": "0.0020"
  }
}' localhost:50051 aspens.v1.AdminService/CreateMarket

# Create WETH/HBAR market
grpcurl -plaintext -d '{
  "market": {
    "baseTokenId": "1:WETH",
    "quoteTokenId": "hedera:mainnet:HBAR",
    "displayName": "WETH/HBAR",
    "description": "Trade WETH on Ethereum for HBAR on Hedera",
    "minOrderSize": "0.01",
    "maxOrderSize": "100",
    "priceDecimals": 8,
    "quantityDecimals": 8,
    "makerFee": "0.0010",
    "takerFee": "0.0020"
  }
}' localhost:50051 aspens.v1.AdminService/CreateMarket

Verify Configuration

After completing the configuration, verify that everything is set up correctly:

# List configured chains
grpcurl -plaintext localhost:50051 aspens.v1.AdminService/ListChains

# List configured tokens
grpcurl -plaintext localhost:50051 aspens.v1.AdminService/ListTokens

# List configured markets
grpcurl -plaintext localhost:50051 aspens.v1.AdminService/ListMarkets

Start the Stack

Once configuration is complete, start the stack services:

# Start all services
docker-compose up -d

# Verify services are running
docker-compose ps

You should see the following services running: - arborter (core service) - journal (trade log database) - frontend (UI service)

4. Configure Blockchain Networks

You must configure the blockchain networks your AMS will interact with through the Admin API.

Add Blockchain Networks

For each blockchain network, make an API call with the network details:

Add Ethereum Mainnet

curl -X POST https://api.your-ams-instance.com/admin/chains \
  -H "Content-Type: application/json" \
  -d '{
    "chainId": 1,
    "name": "Ethereum",
    "symbol": "ETH",
    "rpcUrl": "https://your-ethereum-rpc-endpoint",
    "blockExplorerUrl": "https://etherscan.io",
    "contractAddress": "0xYourAspensContractOnEthereum",
    "gasPrice": {
      "slow": 30,
      "standard": 40,
      "fast": 60
    },
    "confirmations": 12
  }'

Add Hedera Mainnet

curl -X POST https://api.your-ams-instance.com/admin/chains \
  -H "Content-Type: application/json" \
  -d '{
    "chainId": "hedera:mainnet",
    "name": "Hedera",
    "symbol": "HBAR",
    "rpcUrl": "https://your-hedera-endpoint",
    "blockExplorerUrl": "https://hashscan.io",
    "contractAddress": "0.0.yourAspensContractOnHedera",
    "gasPrice": {
      "slow": 1000000,
      "standard": 2000000,
      "fast": 5000000
    },
    "confirmations": 5
  }'

Verify Blockchain Configuration

List all configured blockchain networks to verify they were added correctly:

curl -X GET https://api.your-ams-instance.com/config/chains 

5. Configure Tokens

After configuring blockchain networks, add the tokens that will be tradable on your AMS.

Add Tokens

For each token on each blockchain network:

Add USDT on Ethereum

curl -X POST https://api.your-ams-instance.com/admin/tokens \
  -H "Content-Type: application/json" \
  -d '{
    "chainId": 1,
    "symbol": "USDT",
    "name": "Tether USD",
    "address": "0xdAC17F958D2ee523a2206206994597C13D831ec7",
    "decimals": 6,
    "isNative": false,
    "iconUrl": "https://assets.example.com/tokens/usdt.png"
  }'

Add USDC on Hedera

curl -X POST https://api.your-ams-instance.com/admin/tokens \
  -H "Content-Type: application/json" \
  -d '{
    "chainId": "hedera:mainnet",
    "symbol": "USDC",
    "name": "USD",
    "address": "0.0.yourUsdtTokenIdOnHedera",
    "decimals": 6,
    "isNative": false,
    "iconUrl": "https://assets.example.com/tokens/usdc.png"
  }'

Verify Token Configuration

List all configured tokens to verify they were added correctly:

curl -X GET https://api.your-ams-instance.com/admin/tokens 

6. Create Markets

Now that you have configured the networks and tokens, create markets for trading these tokens across chains.

Create a Market

Create a USDT/USDT Cross-Chain Market

curl -X POST https://api.your-ams-instance.com/admin/markets \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "baseTokenId": "ethereum:USDT",
    "quoteTokenId": "hedera:USDC",
    "displayName": "USDT:USDC,
    "description": "Trade USDT on Ethereum and USDC on Hedera",
    "minOrderSize": "10",
    "maxOrderSize": "1000000",
    "priceDecimals": 6,
    "quantityDecimals": 2,
    "makerFee": "0.0010",
    "takerFee": "0.0020",
    "status": "active"
  }'

Adjust Market Parameters

Modify market parameters such as fees, minimum and maximum order sizes:

curl -X PUT https://api.your-ams-instance.com/admin/markets/ethereum:USDT-hedera:USDC \
  -H "Content-Type: application/json" \
  -d '{
    "makerFee": "0.0005",
    "takerFee": "0.0015",
    "minOrderSize": "50",
    "status": "active"
  }'

Verify Market Configuration

List all configured markets to verify they were created correctly:

curl -X GET https://api.your-ams-instance.com/admin/markets 

7. Implement Security and Monitoring

Set Up Monitoring

Configure monitoring to keep track of your AMS performance and security:

# Install monitoring stack (if not included in your docker-compose)
docker-compose -f monitoring-stack.yaml up -d

# Configure Prometheus endpoints in monitoring/prometheus.yml
cat > monitoring/prometheus.yml << 'EOF'
global:
  scrape_interval: 15s

scrape_configs:
  - job_name: 'aspens-metrics'
    static_configs:
      - targets: ['api-gateway:9090', 'arborter:9090', 'blockchain-watcher:9090']
EOF

# Restart monitoring services
docker-compose -f monitoring-stack.yaml restart

Harden Your Security

Enhance the security of your AMS:

  1. Configure a firewall to only allow necessary ports:
# Allow SSH, HTTP, HTTPS, and the AMS API port
sudo ufw allow 22/tcp
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp
sudo ufw allow 50051/tcp
sudo ufw enable
  1. Set up SSL certificates with Let's Encrypt:
# Install certbot
sudo apt-get update
sudo apt-get install -y certbot python3-certbot-nginx

# Generate certificates
sudo certbot --nginx -d your-ams-instance.com -d api.yoursite.com

8. Go Live

Complete Pre-Launch Checklist

Before making your AMS available to users, complete these steps:

  1. Fund Owner Wallets: Ensure the owner wallets on each blockchain have enough native tokens for gas fees:
# For Ethereum
# Send at least 1 ETH to your owner address: 0xYourOwnerAddress

# For Hedera
# Send at least 100 HBAR to your owner address: 0.0.yourOwnerAddressOnHedera
  1. Initialize Contracts: Run the initialization command to set up the smart contracts:
curl -X POST https://api.your-ams-instance.com/admin/initialize \
  -H "Authorization: Bearer $TOKEN"
  1. Test Trading: Perform test trades on each market to ensure everything works correctly:
# Follow the steps in the testing script
./scripts/test-trading.sh

Launch Your AMS

After completing all the steps above, prepare for launch:

  1. Update DNS Records: Point your domain to your server's IP address:
your-ams-instance.com.    300    IN    A    your.server.ip.address
api.your-ams-instance.com.    300    IN    A    your.server.ip.address
  1. Announce Launch: Inform users that your AMS is now available for trading.

9. Maintain and Update Your Stack

Perform Regular Maintenance Tasks

Execute these tasks regularly to keep your AMS running smoothly:

  1. Back Up Your Database:
# Daily database backup
docker exec -t postgres pg_dumpall -c -U aspens > ~/aspens-stack/backups/backup_$(date +%Y-%m-%d).sql
  1. Update the Software:
# Pull the latest changes
git pull

# Rebuild and restart containers
docker-compose build
docker-compose up -d
  1. Monitor the Logs:
# Check service logs
docker-compose logs -f --tail=100

Troubleshoot Common Issues

If you encounter issues with your AMS, try these steps:

  1. Fix Unresponsive Services:
# Restart the specific service
docker-compose restart service-name

# Check logs for errors
docker-compose logs service-name
  1. Resolve Database Connection Issues:
# Check database status
docker exec -t postgres pg_isready -U aspens

# Restart database if needed
docker-compose restart postgres
  1. Solve Blockchain Synchronization Issues:
# Check blockchain-watcher logs
docker-compose logs blockchain-watcher

# Restart the watcher
docker-compose restart blockchain-watcher

10. Enable Application Development

Once your Aspens Markets Stack is operational, help developers build applications on top of it.

Create Developer Access

To allow developers to build on your stack:

Provide Documentation to Developers:

Share with developers: - API endpoint information - Links to developer documentation

Direct Developers to Resources

For developers interested in building applications on your AMS, point them to:

  • Application Developer Guide: The Application Developer Guide provides comprehensive instructions for building applications on top of an Aspens Markets Stack.

Suggest Application Types

Developers can build various applications on your AMS:

  1. Cross-Chain Wallets: Applications that allow users to hold and transfer assets across chains with a simplified UI.

  2. Cross-Chain DeFi Platforms: DeFi applications that leverage cross-chain liquidity for lending, borrowing, or yield farming.

  3. Cross-Chain NFT Marketplaces: Platforms where users can trade NFTs across different blockchain networks.

  4. Cross-Chain Gaming: Games where in-game assets can move seamlessly between blockchain networks.

  5. Enterprise Solutions: Business applications that require moving assets across different blockchain environments.

Support Your Developer Ecosystem

To foster a healthy ecosystem of developers:

  1. Create a Developer Dashboard: Build a dashboard where developers can monitor API usage, manage keys, and access documentation.

  2. Establish a Developer Community: Create a dedicated section in your community forum for developers.

  3. Provide Example Applications: Share sample code and reference implementations to help developers get started.

By supporting developers building on your AMS, you can expand your stack's utility and reach a wider audience.

Access Support and Resources

If you need additional help or have questions:


By following this guide, you've learned how to deploy, configure, and maintain an Aspens Markets Stack. Your stack is now ready to facilitate cross-chain trading for users, providing a seamless experience for exchanging assets across different blockchain networks.