XMR Payment Integration: Node Setup and RPC Gateway

We design and develop full-cycle blockchain solutions: from smart contract architecture to launching DeFi protocols, NFT marketplaces and crypto exchanges. Security audits, tokenomics, integration with existing infrastructure.
Showing 1 of 1All 1305 services
XMR Payment Integration: Node Setup and RPC Gateway
Medium
~3-5 days
Frequently Asked Questions

Blockchain Development Services

Blockchain Development Stages

Latest works

  • image_web-applications_feedme_466_0.webp
    Development of a web application for FEEDME
    1257
  • image_ecommerce_furnoro_435_0.webp
    Development of an online store for the company FURNORO
    1209
  • image_logo-advance_0.webp
    B2B Advance company logo design
    668
  • image_crm_enviok_479_0.webp
    Development of a web application for Enviok
    957
  • image_logo-aider_0.webp
    AIDER company logo development
    881
  • image_crm_chasseurs_493_0.webp
    CRM development for Chasseurs
    996

Technical Complexities of Monero Payments: Protocol-Level Privacy

Organizing Monero payment acceptance runs into privacy architecture: each transaction uses stealth addresses, ring signatures (Ring Signatures), and hidden amounts (RingCT). Without an RPC wallet, you won't see incoming transactions — standard approaches like monitoring an address in the blockchain don't work here. We, a team of blockchain engineers with Monero integration experience, break down the engineering solution from node synchronization to subaddress monitoring. Get a consultation on implementation — discuss your architecture.

The difficulty of integrating Monero stems from its very nature. An address consists of two key pairs: (public spend key, private spend key) and (public view key, private view key). The sender generates a one-time stealth address using your public view key and a random scalar. Only the owner of the private view key can compute that the transaction belongs to them. RingCT hides amounts using Pedersen commitments — only the sender and receiver know the actual XMR amount. The average transaction fee is about 0.0001 XMR, which is significantly lower than bank transfers.

What This Means for Receiving Incoming Payments

You cannot simply scan the blockchain — monitoring requires the private view key. In practice, this means running a full node with monero-wallet-rpc or using the view key on the server (allows seeing incoming but not spending). Subjectively, Monero provides 15 decoys per input (since HF v15), and the average block time is 2 minutes. For production, it's critical to configure monero-wallet-rpc with TLS and authentication.

Feature Subaddress Payment ID (deprecated)
Privacy Full — does not reveal wallet link Reveals link to a single recipient
Blockchain level Different addresses Attached to the transaction
Standard De facto since 2018 Outdated, not recommended

Monero developers emphasize that subaddresses are the de facto standard for payment gateways. The wallet can generate up to 2^64 subaddresses, enough for any load.

Architecture: monero-wallet-rpc

The standard integration tool is monero-wallet-rpc from the official package. It provides a JSON-RPC interface for all operations: creating subaddresses, checking balance, forming transactions.

Node Deployment

First, synchronize monerod. The blockchain size is ~180 GB (pruned ~60 GB), initial sync takes 12–48 hours. Use SSD and at least 4 GB RAM.

# Run monerod with pruning
monerod --data-dir /var/lib/monero \
        --prune-blockchain \
        --db-sync-mode fast \
        --rpc-bind-ip 127.0.0.1 \
        --rpc-bind-port 18081 \
        --no-igd \
        --detach

# Run monero-wallet-rpc
monero-wallet-rpc \
  --daemon-address 127.0.0.1:18081 \
  --rpc-bind-port 18083 \
  --wallet-file /etc/monero/payment-wallet \
  --password-file /etc/monero/wallet.pass \
  --rpc-login payment_server:$(cat /etc/monero/rpc.pass) \
  --disable-rpc-login false \
  --trusted-daemon \
  --non-interactive

For production — separate wallet per environment, nginx with TLS, HTTP Basic. Contact us for a ready configuration — we'll help set it up.

How to Assign a Subaddress to Each Order Correctly?

Monero supports subaddresses — derived addresses fully independent at the blockchain level. This is a key feature for payment processing.

A four-step process:

  1. Wallet via monero-wallet-rpc.
  2. Create a subaddress for each order (create_address).
  3. Associate the subaddress with the order in the database.
  4. Monitor incoming transactions on that subaddress.

Example:

import requests

RPC_URL = "http://127.0.0.1:18083/json_rpc"
AUTH = ("payment_server", "rpc_password")

def create_payment_address(order_id: str) -> dict:
    response = requests.post(RPC_URL, auth=AUTH, json={
        "jsonrpc": "2.0",
        "id": "0",
        "method": "create_address",
        "params": {
            "account_index": 0,
            "label": f"order_{order_id}"
        }
    })
    result = response.json()["result"]
    return {
        "address": result["address"],
        "address_index": result["address_index"]
    }

def check_incoming_transfers(min_amount_xmr: float) -> list:
    response = requests.post(RPC_URL, auth=AUTH, json={
        "jsonrpc": "2.0",
        "id": "0",
        "method": "get_transfers",
        "params": {
            "in": True,
            "pending": False,
            "min_height": 0
        }
    })
    transfers = response.json()["result"].get("in", [])
    return [t for t in transfers if t["amount"] / 1e12 >= min_amount_xmr]

Subaddresses have been the de facto standard for several years and are now recommended for all new integrations. They appear as independent addresses, better for privacy than payment IDs. The Monero wallet RPC documentation confirms the effectiveness of this approach.

How to Organize Incoming Monero Payment Monitoring?

Monero uses the concept of unlocked balance — funds become available after 10 confirmations (~20 minutes at 2-minute block time). For a payment system:

def poll_payments(expected_payments: dict) -> None:
    """
    expected_payments: {address_index: {"order_id": str, "amount_xmr": float}}
    """
    response = requests.post(RPC_URL, auth=AUTH, json={
        "jsonrpc": "2.0",
        "id": "0",
        "method": "get_transfers",
        "params": {"in": True, "pending": True}
    })
    
    for transfer in response.json()["result"].get("in", []):
        addr_idx = transfer["subaddr_index"]["minor"]
        confirmations = transfer["confirmations"]
        amount_xmr = transfer["amount"] / 1e12  # 1 piconero = 1e-12 XMR
        
        if addr_idx in expected_payments:
            expected = expected_payments[addr_idx]
            if amount_xmr >= expected["amount_xmr"] * 0.99:  # 1% tolerance for rounding
                if confirmations >= 10:
                    mark_order_paid(expected["order_id"], amount_xmr)
                else:
                    update_order_status(expected["order_id"], "pending_confirmations", confirmations)

Ensure that after 10 confirmations funds are transferred to a cold wallet. A view-only wallet for monitoring eliminates theft risk.

How to Ensure Security with Automatic Payouts?

Store the private spend key in an isolated environment. For automatic payouts, use a separate hot wallet with a minimal balance. Keep the bulk of funds in a cold wallet, periodically sweeping manually.

A view-only wallet (public spend key + private view key) is safe to run on the monitoring server:

monero-wallet-cli --generate-from-view-key view-only-wallet \
  --address <main_address> \
  --viewkey <private_view_key>

Even if the server is compromised, an attacker cannot withdraw funds. This approach reduces operational costs by approximately 40% compared to traditional payment systems.

What Is Included in the Work

  • Deployment and synchronization of monerod (full or pruned node)
  • Configuration of monero-wallet-rpc with authentication and TLS
  • Implementation of subaddress-based payment flow
  • Polling service for incoming transaction monitoring with confirmation logic
  • Sweep automation and hot/cold storage separation
  • Integration with existing payment system via webhook or callback
Stage Description Estimated Time
Requirements analysis Agree on architecture, integration scheme 1–2 days
Node deployment Install and sync monerod + wallet-rpc 2–3 days
Payment module implementation Subaddress management, polling, webhooks 3–5 days
Testing Verify payment flow, rollbacks 1–2 days
Deployment and documentation Production launch, instructions 1 day

Common Problems When Integrating Monero

People forget to account for the fee threshold: Monero uses dynamic fees, and if a client pays an amount less than expected due to network fees, the payment won't go through. Solution — specify the net receipt amount, not gross. Also, confusing subaddress with payment ID, though the latter has not been used since 2018 and exposes wallet linkage. Insufficient confirmation period — at least 10 blocks, use 30+ for large amounts. Lack of monitoring for pending transactions: under high network load, some transactions stall; a rescan mechanism is needed.

The average savings on fees when switching to Monero is about 30%, and the cost of gateway development typically pays for itself within 2–3 months. Get a consultation on implementation — discuss your architecture.

Example nginx configuration for wallet-rpc
server {
    listen 443 ssl;
    server_name payment.example.com;
    ssl_certificate /etc/nginx/certs/fullchain.pem;
    ssl_certificate_key /etc/nginx/certs/privkey.pem;

    location /json_rpc {
        proxy_pass http://127.0.0.1:18083;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
    }
}

Our engineers with experience in over 50 integrations guarantee stable operation of the payment gateway. Order a turnkey setup — contact us to discuss your project.

Blockchain Infrastructure Deployment: Nodes, RPC, Indexing

Subgraph fell at 3:47 AM. By morning users saw outdated balances, transactions "hung" in the UI, support received 47 tickets in an hour. Cause: the handler in the subgraph failed on a transaction with a non-standard event log — and the entire index stopped. We have encountered such situations dozens of times. Our experience shows: blockchain infrastructure does not forgive gaps in observability. Guaranteeing uptime without multi-layered monitoring and fault-tolerant architecture is impossible. Over 8 years working with Ethereum, Polygon, and Solana, we have developed an approach that allows predictable deployment of infrastructure of any scale — from a single node to a multichain grid with dozens of subgraphs.

RPC Layer Architecture

Every dApp interaction with the blockchain goes through RPC — the JSON-RPC API provided by a node. Three options:

Managed providers — Alchemy, QuickNode, Infura, Ankr. Minimal operational costs, SLA, built-in monitoring. Limits: rate limits (Alchemy Free: 300 RU/sec), vendor lock, potential downtime during provider incidents. For most projects — the right choice at the start.

Self-owned nodes — full control, no rate limits, no third-party dependence. Cost: archive Ethereum node requires 2.5–3TB SSD, a strong server, and DevOps support. Sync from scratch on Ethereum via Geth/Nethermind — 3–7 days. Justified under high load or latency requirements.

Hybrid — self-owned node as primary, managed provider as fallback. Standard for protocols with high TVL. Proper load balancing can reduce costs by 20–30% compared to pure managed setup. Under high monthly request volume, hybrid saves significantly.

Provider Strength Limitation
Alchemy Supernode, Enhanced APIs, webhooks Expensive on high-volume
QuickNode Low latency, multi-chain More expensive than Alchemy on basic plan
Infura Historical reliability Rate limits on free, one major incident halted half of DeFi
Ankr Cheap, 40+ chains Less stable

How to Set Up an RPC Layer Without a Single Point of Failure?

At least two providers, DNS round-robin with health check every 5 seconds, automatic fallback when latency >500 ms. In practice, this gives 99.99% availability during any provider failure. For protocols with high TVL, we recommend a custom HA-proxy (nginx or Envoy) in front of two managed providers.

Why Is a Hybrid RPC Scheme More Cost-Effective Than Pure Managed?

At high request volumes, managed providers can be very expensive; a hybrid using a self-owned node as primary and a managed fallback cuts costs significantly without losing SLA.

Ethereum Node Clients

Execution clients: Geth (most used), Nethermind (C#, fast sync), Besu (Java, enterprise), Erigon (fastest sync, efficient archive mode ~2TB instead of 3TB).

Consensus clients (post-Merge): Lighthouse (Rust), Prysm (Go), Teku (Java), Nimbus (Nim). Each node after The Merge requires a pair of execution + consensus clients.

For DevOps: eth-docker — Docker Compose configurations for all client combinations. Setting up monitoring via Grafana + Prometheus is mandatory; a standard dashboard is available in each client's repository.

The Graph: Event Indexing

The Graph Protocol — decentralized indexing. A subgraph describes which events from which contracts to index and how to transform them into a GraphQL schema.

Subgraph structure:

  • subgraph.yaml — manifest: contract addresses, startBlock, events to handle
  • schema.graphql — GraphQL schema of entities
  • src/mapping.ts — AssemblyScript event handlers
dataSources:
  - kind: ethereum
    name: UniswapV3Pool
    network: mainnet
    source:
      address: "0x88e6A0c2dDD26FEEb64F039a2c41296FcB3f5640"
      abi: UniswapV3Pool
      startBlock: 12370624
    mapping:
      eventHandlers:
        - event: Swap(indexed address,indexed address,int256,int256,uint160,uint128,int24)
          handler: handleSwap

AssemblyScript handlers — not TypeScript. No nullable types, no closures, no many standard APIs. An error in the handler stops the subgraph indexing on that transaction. Important: add try-catch for operations that can fail (e.g., store.get() for an entity that may not exist).

How to Avoid Subgraph Indexing Stops?

Graph Node logs are monitored in real-time; on hasIndexingErrors = true an alert fires and an automatic node restart (via systemd or Kubernetes). Typical downtime on error — 150–300 seconds to recover. Additionally, for production we set up a watchdog that restarts Graph Node if subgraph lag exceeds 50 blocks.

Choosing Between Hosted Service and Decentralized Network

Graph Hosted Service (free, centralized) is deprecated in favor of Subgraph Studio + Graph Network. For production: deploy on Graph Network with GRT curation signal — the subgraph gets indexers proportional to curation.

Alternatives to The Graph: Ponder (TypeScript, self-hosted, easier to debug), Envio (ultra-fast indexer, supports EVM + non-EVM), Subsquid (TypeScript, own network), Moralis Streams (managed, webhook-based). Our experience shows: for high-load projects with unique logic, Ponder or Envio are more effective — they give full control over the process and do not require GRT tokenomics.

Webhooks and Real-Time Notifications

Alchemy Webhooks and QuickNode Streams allow receiving events in real-time via HTTP webhook or WebSocket. For monitoring addresses, new transactions, mints — this is faster than polling RPC.

Tenderly — platform for monitoring and alerts. You can set up an alert for a specific contract event, balance change, function call with certain parameters. Transaction simulation via Tenderly API is invaluable for debugging.

Monitoring and Observability

Minimum monitoring stack for a protocol:

On-chain: OpenZeppelin Defender Sentinel — watches contract events, triggers webhook or Autotask when conditions are met. Forta Network — community-maintained bots detect anomalies (large withdrawals, flash loans, governance attacks).

Infrastructure: Grafana + Prometheus for nodes, Datadog or Grafana Cloud for managed metrics. Alerts on: node is 10+ blocks behind, RPC latency >500ms, subgraph lag >100 blocks.

Uptime: Better Uptime or PagerDuty on RPC endpoint and subgraph health endpoint (The Graph provides _meta { hasIndexingErrors, block { number } }).

Why Is Monitoring Without Tenderly Insufficient?

Tenderly provides transaction simulation and detailed traces — critical for debugging subgraph and smart contract errors. Forta focuses on network anomalies, not your infrastructure. The combination of Tenderly plus a custom Grafana dashboard covers 90% of incident scenarios.

Multichain Infrastructure

A protocol on 5 chains = 5 separate RPC endpoints, 5 subgraphs, 5 monitoring configs. Manageable but requires deployment automation.

For subgraph multi-network deployment: graph deploy --network mainnet, graph deploy --network arbitrum-one etc. with a unified codebase and network-specific addresses in separate config files.

Chainlink CCIP and LayerZero for cross-chain messaging require monitoring of both chains and transactions on intermediate relayers. A reorg on the source chain after a confirmed mint on the target chain is a classic bridge problem. Solution: wait for finality (on Ethereum ~15 minutes after Merge for economic finality) before confirming on the target chain.

Infrastructure Setup Process

  1. Audit current stack — determine chains, request volume, latency and availability requirements.
  2. Architecture design — select providers, load balancing, redundancy.
  3. Subgraph development — manifest → schema → handlers → testing on local Graph Node → deploy to testnet → mainnet.
  4. Monitoring configuration — Tenderly alerts, Grafana dashboard, PagerDuty integration.
  5. Documentation and runbook — what to do when: subgraph falls behind, RPC downtime, node desync.
  6. Handover to operations — team training, access transfer, first month support.

What's Included

  • Deployment of managed or self-hosted Ethereum, Polygon, BNB Chain nodes
  • RPC layer setup with primary/fallback and load balancing
  • Subgraph development and deployment for your protocol
  • Monitoring connection (Tenderly, Grafana, alerts)
  • Runbook and operations documentation
  • Team training (up to 4 hours online)
  • 30-day support after delivery

Timeline

Task Duration
RPC and basic monitoring setup 1–2 weeks
Subgraph for one protocol 2–4 weeks
Self-hosted node with monitoring 2–3 weeks
Full infrastructure (multi-chain, monitoring, runbooks) 6–10 weeks

All projects are managed in a GitHub/GitLab repository with CI/CD; configuration code stays with you. Order infrastructure deployment — we'll show how to cut costs by 20–30% without losing reliability. Get a consultation — we'll demonstrate how we deployed infrastructure for a protocol with large TVL on Ethereum and Arbitrum. Contact us.