utility-identity — Unified Temp-Email & Identity CLI (SONJJ + Boomlify)
One CLI that wraps the SONJJ and Boomlify APIs for disposable email, OTP capture, email/phone validation, IP geolocation, BIN lookup, and fake test profiles. Every command emits a single JSON object to stdout so other skills can pipe it. Part of Dr. Wael's Utility / Automation arsenal.
- Tool:
utility_identity.py(Python 3 stdlib +requests; falls back tourllib) - Run with
/usr/bin/python3.
⚖️ ETHICAL RED LINE (read first)
This tool is for legitimate use only:
- ✅ Protecting your own privacy with disposable inboxes
- ✅ Capturing OTPs for your own signups / account verification
- ✅ Software / QA testing with throwaway identities
- ✅ Email/phone validation, IP geolocation, BIN informational lookup
- ❌ Fraud of any kind
- ❌ Using BIN / card data to charge, test, or transact against anyone
- ❌ Impersonation of real people or organizations
- ❌ Spam, mass-signup abuse, bypassing anti-abuse on services you don't own
gen-profile and bin-lookup commands return synthetic / informational
data only. Do not use them to deceive, defraud, or impersonate.---
🔑 Authentication
Keys live in /data/.openclaw/secrets/env.sh:
| Provider | Env var | Header | Base URL |
|---|---|---|---|
| SONJJ | SONJJ_API_KEY (64-char) | X-Api-Key | https://app.sonjj.com |
| Boomlify | BOOMLIFY_API_KEY | X-API-Key | https://v1.boomlify.com |
How keys are resolved (robust):
1. First from os.environ.
2. If missing, the script parses env.sh directly (handles the dash-subshell
gotcha where source ... 2>/dev/null silently empties vars).
Recommended invocation (sources env.sh into the parent shell first):
bash
bash -c 'source /data/.openclaw/secrets/env.sh; \
/usr/bin/python3 skills/utility-identity/utility_identity.py <subcommand> ...'
…but the tool also works with a clean environment (env -i) because of the
env.sh fallback. Keys are never printed; mask() shows only 9ebc…6947.---
Output contract
- Success →
{"ok": true, ...}(exit 0) - Failure →
{"ok": false, "error": "...", "status": <int|null>, "detail": ...}(exit ≠ 0) - 429 → honors
Retry-After, exponential backoff, up to 4 retries. - 5xx / network → backoff + retry. 401/402/403 → fail fast (no point retrying).
- Every HTTP call has a 20s timeout (
DEFAULT_TIMEOUT).
Subcommands
1. create-email — create a temp inbox
create-email [--provider sonjj|boomlify|auto] [--expiry MIN] [--username NAME]
autotries SONJJ first, falls back to Boomlify (records the SONJJ error).- SONJJ picks the first available domain automatically;
--usernamesets the
u<epoch>).
- Boomlify maps
--expiry: ≤10→10min, ≤60→1hour, else→1day.
bash
$ ... create-email --provider sonjj --expiry 60
{"provider": "sonjj", "email": "u1781707296@storegmail.net",
"id": "u1781707296@storegmail.net", "expires_at": 1781710897,
"raw": {"email": "...", "expired_at": 1781710897, "action": "created"}, "ok": true}
Boomlify example:
bash
$ ... create-email --provider boomlify --expiry 10
{"provider": "boomlify", "email": "ikcn6lnu@starlight.store",
"id": "17f9ae67-7726-4310-92c0-55c77e6ad1af",
"expires_at": "2026-06-17T14:51:40.911Z", "raw": {...}, "ok": true}
> Note: for Boomlify, id is the UUID you pass to inbox/message ops; the
> address also works (the tool resolves address→id automatically).2. read-inbox — list messages
read-inbox --email ADDR [--provider sonjj|boomlify|auto]
bash
$ ... read-inbox --provider sonjj --email u1781707296@storegmail.net
{"provider": "sonjj", "email": "...", "count": 0, "messages": [], "ok": true}
For Boomlify you may pass either the address or the UUID.3. read-message — full message body (for manual OTP capture)
read-message --email ADDR --mid ID [--provider ...]
- SONJJ:
GET /v1/temp_email/message?email=&mid= - Boomlify:
GET /api/v1/emails/<id>/messages/<mid>
4. wait-otp — poll until a code arrives
wait-otp --email ADDR [--provider ...] [--timeout 120] [--regex '\b(\d{4,8})\b']
- Polls every 5s, backing off up to 15s, honoring
Retry-Afteron 429. - Scans subject/body/html/content/snippet of each message; for SONJJ it fetches
- Prints the extracted code or a clean timeout error.
bash
$ ... wait-otp --provider sonjj --email <addr> --timeout 8
{"ok": false, "error": "timeout: no OTP matched within 8s",
"status": null, "detail": {"polls": 2, "provider": "sonjj"}}
on success:
{"ok": true, "provider": "sonjj", "email": "<addr>", "otp": "482913",
"polls": 3, "matched_in": {...}}
Custom regex example (6-digit only): --regex '\b(\d{6})\b'.5. check-email — validate an email (SONJJ)
bash
$ ... check-email --email test@gmail.com
{"provider": "sonjj", "email": "test@gmail.com",
"result": {"type": "Gmail", "disposable": "No", "status": "Disable", "avatar": ""}, "ok": true}
6. bin-lookup — card BIN information (SONJJ) — lookup only
bash
$ ... bin-lookup --bin 411111
{"provider": "sonjj", "bin": "411111",
"result": {"type": "CREDIT", "country": "US", "brand": "VISA",
"level": "", "bin": 411111, "bank": "JPMORGAN CHASE BANK, N.A."}, "ok": true}
Informational only — see red line above.7. gen-profile — synthetic test profile (SONJJ)
gen-profile [--age 25-35] [--gender male|female] [--domain D] [--password-length N]
> ⚠️ --age must be a range like 25-35 (API regex ^\d{1,2}-\d{1,2}$).
bash
$ ... gen-profile --age 25-35 --gender male
{"provider": "sonjj", "profile": {"name": "Ronald Lindsey", "gender": "male",
"dob": {...}, "address_real": {...}, "email_for_verification": {...},
"username": "ronaldbro991015", "password": "NmaPWet@", "payment": {"bin": 429645}}, "ok": true}
8. domains — list temp domains
bash
$ ... domains --provider sonjj
{"domains": {"sonjj": ["storegmail.net", "corhash.net", ... "appbott.com"]}, "ok": true}
Boomlify auto-assigns a domain on create (no public list endpoint); --provider
auto returns SONJJ domains plus a Boomlify note.9. ip-lookup — IP geolocation (SONJJ)
bash
$ ... ip-lookup --address 8.8.8.8
{"provider": "sonjj", "result": {"is_valid": true, "country": "United States",
"city": "Mountain View", "isp": "Google LLC", ...}, "ok": true}
10. validate-phone — phone validation (SONJJ v2)
bash
$ ... validate-phone --phone "+16265785546"
{"provider": "sonjj", "result": {"is_valid": true, "country": "United States",
"location": "Pasadena, CA", "format_e164": "+16265785546", "country_code": 1}, "ok": true}
> Uses GET /v2/validate_phone/?number=... (param is number, not phone).---
End-to-end OTP recipe
bash
bash -c 'source /data/.openclaw/secrets/env.sh
T=skills/utility-identity/utility_identity.py
ADDR=$(/usr/bin/python3 $T create-email --provider sonjj --expiry 30 \
| python3 -c "import sys,json;print(json.load(sys.stdin)[\"email\"])")
echo "Use $ADDR to sign up, then:"
/usr/bin/python3 $T wait-otp --provider sonjj --email "$ADDR" --timeout 120 --regex "\b(\d{6})\b"'
---
Implementation notes / gotchas (verified 2026-06-17)
- SONJJ
user_generatorrejects a bare age (30) — needs a range (25-35). - SONJJ phone validation lives at
/v2/validate_phone/with paramnumber. - Boomlify messages endpoint that returns 200:
GET /api/v1/emails/<id>/messages
?email_id= and /inbox → 404; kept the working one).
- Boomlify create is POST with query params
time=10min|1hour|1day|permanent,
custom_username, domain.
- All keys masked in any diagnostic output; nothing secret is printed.
Files
utility_identity.py— the CLI (chmod +x)SKILL.md— this doc
🔗 n8n Integration — signup→OTP→activate (LIVE, verified 2026-06-17)
Workflow: "Signup → OTP → Activate (utility-identity + evolink)" (active). Pipeline: n8n webhook → auth-token gate → arsenal-hooks bridge172.16.1.1:8910/signup (runs signup_flow.py) → OTP-captured branch → bridge /activate → respond. Includes LLM fallback for OTP extraction when regex misses.Trigger (FLAT payload — no body wrapper):
bash
curl -X POST "$N8N_BASE_URL/webhook/signup-flow" \
-H "Content-Type: application/json" \
-H "X-Signup-Token: $SIGNUP_FLOW_TOKEN" \
-d '{"signup_cmd":"<shell using {EMAIL}>","provider":"sonjj","timeout":180,"regex":"\\d{4,8}"}'
signup_cmd= YOUR command that triggers the target service to email the OTP ({EMAIL} substituted).- Returns JSON:
{ok, email, provider, signup:{...}, otp:{ok,otp,...}}. - Direct (no n8n):
python3 signup_flow.py run --provider sonjj --signup-cmd '...{EMAIL}...' --timeout 180. - Bridge direct:
POST 172.16.1.1:8910/signupwith headerX-Signup-Token.
SIGNUP_FLOW_TOKEN.
Ethics: legitimate signups/privacy/testing only.