# ARRR Scripts This repository contains helper tooling to bootstrap the Pirate Chain daemon stack and expose an `ARRRwallet` friendly gRPC endpoint. The primary entry point is `setup-arrr-lightwalletd.sh`, which compiles the upstream projects, configures systemd services, and (optionally) wires nginx/Certbot for TLS termination and gRPC proxying. ## Ironwood / Pirate 6.0.0 The script defaults to the released Pirate `v6.0.0` node and the matching ARRRwallet lightwalletd commit `43b29b4229cc68adae8a807931d26f9a5f5d98a6` (version `v1.0.0.0`). This lightwalletd version understands Pirate v6 Ironwood transactions, serves compact Ironwood actions, and supplies Ironwood tree state and subtree-root data to compatible clients. Pirate 6.0.0 raises its minimum index version, so an existing node automatically performs a full chain-index rebuild on its first start after the upgrade. It also zaps and rescans the daemon wallet transaction records as part of that migration. Keep the existing `~/.komodo/PIRATE` directory and block files in place; do not delete them. Reindexing may take days. The script stops `lited`, restarts `pirated`, then restarts `lited`, so an upgrade actually applies even when the services were already running. Upgrade before the new notary `requiredSigs` rule at block `4141650` (estimated 19 September 2026, 19:00 UTC) and the Ironwood activation on 3 October 2026, 19:00 UTC. These dates and the reindex requirement are from the [Pirate 6.0.0 release notes](https://github.com/PirateNetwork/pirate/blob/master/doc/release-notes/release-notes-6.0.0.md). Before rerunning the script on a customized node, remove these Pirate 6.0.0-incompatible `PIRATE.conf` settings if present: - `consolidation` / `consolidationtxfee` → `saplingconsolidation*` or `ironwoodconsolidation*` - `consolidateaddress` → `consolidatesaplingaddress` or `consolidateironwoodaddress` - `sweepsaplingaddress` / `sweepironwoodaddress` → `sweepaddress` The script detects those old settings and stops before replacing the running daemon. It intentionally retains the lightwalletd compact-block cache; the matching lightwalletd code can retain historical compact blocks and append Ironwood blocks. If that cache is corrupt, move only `/db` aside after stopping `lited` and let it rebuild from `pirated`—do not delete it automatically as part of an upgrade. ## What the script does - Installs development/runtime dependencies, Go, and clones pinned `Pirate` plus `lightwalletd` revisions. The current Pirate build dependencies include `bison`, `liblz4-dev`, `python3-zmq`, and `zip`. - Builds Pirate Chain (`pirated`) and `lightwalletd`, links them under `/usr/local/bin`, and writes a `PIRATE.conf` for RPC access. - Uses Pirate's current HTTPS, checksum-verified parameter downloader; the old insecure `bootstrap.arrr.black` HTTP workaround has been removed. - Sets up nginx when you pass `--hostname`: - First writes a minimal HTTP-only nginx site serving `/.well-known/acme-challenge/` so Certbot can start without certs. - Requests certificates via `certbot certonly --webroot`, then rewrites the nginx site with the full HTTPS/gRPC proxy block (including `/etc/letsencrypt` includes and gRPC headers). - Ensures nginx is tested and reloaded after each stage. - Creates systemd units for `pirated` and `lited` (the lightwalletd binary), wiring logs, data directories, and capabilities. - If you opt out of nginx, the script runs `lited` with the provided TLS cert/key (or `--no-tls-very-insecure` when not supplied) directly on the host. ## Optional public explorer and DNS seed The installer can now add the two public components from Pirate’s seed-node deployment, without adopting its PM2/Bitcore-owned-daemon layout. This is intentional: this repository continues to keep `pirated` under systemd and preserves the old `cash.z.wallet.sdk.rpc.CompactTxStreamer` → `pirate.wallet.sdk.rpc.CompactTxStreamer` nginx compatibility rewrite for older wallet clients. ### Insight explorer Pass `--explorer-hostname` to install Pirate’s pinned `bitcore-node-pirate`, `insight-api-pirate`, and `insight-ui-pirate` packages under `~/arrr-explorer` and publish the UI/API through its own HTTPS nginx server block. It requires `--lets-encrypt` and `--email`; ensure the explorer hostname already resolves to the VPS and TCP 80/443 can reach it for the ACME challenge. The `arrr-explorer` systemd service connects to the **existing** `pirated` through loopback RPC and ZMQ. It does not spawn, stop, or own a second daemon. The script adds these settings only when the explorer is enabled, retaining existing values when they already match: ```ini zmqpubrawtx=tcp://127.0.0.1:28332 zmqpubhashblock=tcp://127.0.0.1:28332 ``` Both notifications must use one loopback endpoint, as required by the Pirate Bitcore integration. Bitcore’s HTTP listener itself cannot be bound to loopback, so the script denies its direct local port (default TCP/3001) when UFW is already active and proxies it through nginx. If UFW is not active, block TCP/3001 in the VPS/cloud firewall so the explorer is available only through HTTPS. ### DNS seeder Pass all three DNS identity arguments to build and run the separate `pirate-seeder` service: ```sh --dnsseed-host dnsseed.example.com \ --dnsseed-ns ns-dnsseed.example.com \ --dnsseed-mbox admin.example.com ``` `--dnsseed-mbox` is the SOA contact written with `@` replaced by `.`, not a literal email address. Before running the installer, create the delegation at the DNS provider: 1. Create a DNS-only `A` (and optionally `AAAA`) record for `ns-dnsseed.example.com` pointing to the VPS. Do not put it behind an HTTP proxy. 2. Delegate `dnsseed.example.com` with an `NS` record to `ns-dnsseed.example.com`. 3. Make UDP/53 and Pirate P2P TCP/45452 reachable. Use `--dnsseed-port` or `--p2p-port` if this host uses different ports. The seeder stores its crawl database in `/var/lib/pirate-seeder/dnsseed.dat`, runs as the regular installer user, and receives `CAP_NET_BIND_SERVICE` from systemd only when binding a port below 1024. `--dnsseed-tor-proxy HOST:PORT` optionally enables crawling Tor peers through an existing SOCKS5 proxy. The script never enables UFW; if UFW is already active, it adds the DNS UDP and P2P TCP allowances. Example with lightwalletd, an explorer, and a DNS seed: ```sh ./setup-arrr-lightwalletd.sh \ --hostname lwd.example.com \ --explorer-hostname explorer.example.com \ --email admin@example.com \ --lets-encrypt \ --dnsseed-host dnsseed.example.com \ --dnsseed-ns ns-dnsseed.example.com \ --dnsseed-mbox admin.example.com ``` ## Usage ```sh ./setup-arrr-lightwalletd.sh \ --hostname \ --email admin@example.com \ --lets-encrypt \ --bind-addr 127.0.0.1:9067 \ --http-bind-addr 127.0.0.1:9068 \ --data-dir /var/lib/lightwalletd ``` - `--hostname` enables nginx/Certbot and proxies `127.0.0.1:9067` (or your `--bind-addr`) over gRPC. - `--lets-encrypt` pairs with `--email` so `certbot certonly --webroot` can obtain certs. The script keeps nginx challenge locations intact while the final config relies on `/etc/letsencrypt/live/`. - Without `--hostname`, nginx isn’t installed and `lited` runs with the TLS arguments you provide (`--tls-cert`/`--tls-key`) or falls back to `--no-tls-very-insecure`. - `--go-version`, `--data-dir`, and bind addresses are all optional overrides. The defaults are documented in the script. - `--pirate-ref` and `--lightwalletd-ref` let an operator deliberately test another compatible source ref. The defaults are pinned Ironwood-compatible revisions, not moving branch names. The script refuses to overwrite local changes in either source checkout. - `--explorer-hostname` enables the optional Insight UI/API on a separate hostname. Its Node.js runtime defaults to the same `24.19.0` release used by Pirate’s seed-node deployment; override it with `--node-version` if necessary. - `--dnsseed-host`, `--dnsseed-ns`, and `--dnsseed-mbox` must be supplied together. `--dnsseed-ref` is a pinned `pirate-seeder` revision; `--dnsseed-port` and `--p2p-port` default to 53/UDP and 45452/TCP. ## After the run - `systemctl status pirated lited` shows the daemon status; logs live under `/var/log/lited`. During the v6 migration, follow `journalctl -fu pirated` until reindexing and chain synchronization complete. - If enabled, use `systemctl status arrr-explorer pirate-seeder`, `journalctl -fu arrr-explorer`, and `journalctl -fu pirate-seeder`. The explorer needs a fully indexed, synchronized daemon before its data will be complete. - `sudo certbot certificates` confirms the issued certificate for your hostname. - Let’s Encrypt installs its own renew timer, so nothing else is required for automatic renewal. ## Troubleshooting - If nginx reports `host` variable errors, ensure the generated config keeps `\$host`/`\$request_uri` escaped; the script already does this in the heredoc. - If the Pirate parameter download fails, resolve connectivity to GitHub or use the script's supported IPFS fallback; do not replace the verified HTTPS source with an unencrypted mirror. - You can rerun the script after DNS is live—Certbot’s webroot challenge will reuse the shared `/var/www/certbot` directory and nginx rewrites happen in-place.