# `Onchain.Tempo.Faucet`
[🔗](https://github.com/ZenHive/onchain-stack/blob/onchain_tempo-v0.10.0/packages/onchain_tempo/lib/onchain/tempo/faucet.ex#L1)

Moderato testnet faucet — wraps the non-standard `tempo_fundAddress` JSON-RPC.

Moderato exposes a custom JSON-RPC method, `tempo_fundAddress`, that funds an
address with native gas + pathUSD in a single call. This module provides a
thin wrapper plus a convenience helper for spinning up a fresh, funded
keypair — useful for writing integration tests against Moderato without
re-deriving the recipe.

Only Moderato (chain `42_431`) supports this RPC. Mainnet (`4_217`) does not.

## Usage

    # Fund an existing address.
    {:ok, [tx_hash | _]} = Onchain.Tempo.Faucet.fund_address("0xabc...")

    # Generate + fund a fresh keypair (polls for confirmation before returning).
    {:ok, %{private_key: priv, address_hex: hex, address_bin: bin}} =
      Onchain.Tempo.Faucet.fresh_funded_wallet()

    # Override the endpoint (defaults to https://rpc.moderato.tempo.xyz, or
    # the TEMPO_RPC_URL env var if set).
    Onchain.Tempo.Faucet.fund_address("0xabc...", rpc_url: "https://my-mirror")

## Options

Both `fund_address/2` and `fresh_funded_wallet/1` accept:

  * `:rpc_url` — RPC endpoint URL. Defaults to `rpc_url/0`.
  * `:req_options` — keyword list passed to `Req.request/2` (timeouts,
    adapters, `Req.Test` plug, etc.)

`fresh_funded_wallet/1` additionally accepts:

  * `:settle_ms` — maximum milliseconds to wait for the funding transaction
    to confirm. Defaults to `10_000`. Set to `0` to skip the wait entirely
    (used by unit tests that mock the RPC layer).
  * `:poll_interval_ms` — interval between balance polls. Defaults to `200`.
  * `:fee_token` — hex address of the fee token to poll for funding (via an
    `eth_call` of `balanceOf`). Defaults to Moderato's pathUSD. The faucet
    funds native gas *and* the fee token, but gas can land first; polling the
    fee token confirms the balance the caller actually needs has arrived.

# `fresh_funded_wallet`

```elixir
@spec fresh_funded_wallet(keyword()) ::
  {:ok,
   %{private_key: binary(), address_hex: String.t(), address_bin: binary()}}
  | {:error, String.t()}
```

Generate a fresh 32-byte keypair, fund it via `tempo_fundAddress`, and poll
the fee token's `balanceOf` (via `eth_call`) until the funding lands on-chain.
The faucet credits native gas *and* the fee token, but gas can confirm first;
polling the fee token (pathUSD by default) confirms the balance callers
actually need has arrived. Override the token with `:fee_token`.

Returns the wallet as a map with `:private_key` (32 bytes), `:address_hex`
(`"0x"` + 40 hex), and `:address_bin` (20 bytes).

Polling is bounded by `:settle_ms` (default `10_000` ms); pass `0` to skip
the wait entirely. The interval between polls is controlled by
`:poll_interval_ms` (default `200` ms).

# `fund_address`

```elixir
@spec fund_address(
  String.t(),
  keyword()
) :: {:ok, [String.t()]} | {:error, String.t()}
```

Fund an existing address via Moderato's `tempo_fundAddress` RPC.

Returns `{:ok, hashes}` where `hashes` is the list of funding transaction
hashes returned by the node.

# `rpc_url`

```elixir
@spec rpc_url() :: String.t()
```

RPC URL used by the faucet by default — `TEMPO_RPC_URL` env var if set,
otherwise `https://rpc.moderato.tempo.xyz`.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
