Skill: dougbtv/unofficial-urban-dictionary-api (version 0.1.0)

--- name: unofficial-urban-dictionary-api description: Query the Unofficial Urban Dictionary API for slang definitions. Use when asked to define slang/phrases, fetch random Urban Dictionary entries, browse by letter/new, or get entries by author/date. Supports endpoints /api/search, /api/random, /api/browse, /api/author, and /api/date. --- Use this skill to fetch Urban Dictionary-style definitions from: - Base URL: `https://unofficialurbandictionaryapi.com/api` ## Fast path Prefer running the bundled helper script for deterministic output: - `python3 scripts/ud_api.py search --term "yeet" --limit 3` - `python3 scripts/ud_api.py random --limit 1` - `python3 scripts/ud_api.py browse --character a --limit 5` - `python3 scripts/ud_api.py author --term "some_author" --limit 5` - `python3 scripts/ud_api.py date --term "2024-01-01" --limit 5` If script execution is unavailable, use direct HTTP GET calls to the same endpoints. ## Endpoint mapping - `search` -> `/search` - `random` -> `/random` - `browse` -> `/browse` - `author` -> `/author` - `date` -> `/date` ## Common query params - `term`: word/phrase/author/date (depends on endpoint) - `limit`: integer > 0 - `strict`: `true|false` (search) - `matchCase`: `true|false` (search) - `page`: integer >= 1 - `multiPage`: `min,max` page range string - `character`: browse target (example: `a`, `new`, `*`) ## Output behavior When reporting results to users: 1. Show top entries only (default 3–5 unless asked for more). 2. Include: - term/word - short definition - example (if present) - thumbs up/down (if present) - permalink (if present) 3. If no entries found, say so clearly and suggest a broader query (disable strict, remove matchCase, etc.). 4. Content can be NSFW/offensive; reflect results neutrally without adding extra slurs or escalation. ## Troubleshooting - Empty result: retry with `strict=false` and lower constraints. - Bad response: retry once, then report API/network failure. - Very long entries: truncate cleanly and offer full dump on request.

path: scripts/ud_api.py
content: #!/usr/bin/env python3
import argparse
import json
import sys
import urllib.parse
import urllib.request

BASE = "https://unofficialurbandictionaryapi.com/api"


def bool_str(v):
    if v is None:
        return None
    return "true" if v else "false"


def get_json(path, params):
    query = {k: v for k, v in params.items() if v is not None}
    url = f"{BASE}{path}?{urllib.parse.urlencode(query)}"
    req = urllib.request.Request(url, headers={"User-Agent": "openclaw-ud-skill/1.0"})
    with urllib.request.urlopen(req, timeout=20) as r:
        return json.loads(r.read().decode("utf-8", errors="replace"))


def parse_args():
    p = argparse.ArgumentParser(description="Unofficial Urban Dictionary API helper")
    sub = p.add_subparsers(dest="cmd", required=True)

    common = argparse.ArgumentParser(add_help=False)
    common.add_argument("--limit", type=int)
    common.add_argument("--page", type=int)
    common.add_argument("--multi-page")

    s = sub.add_parser("search", parents=[common])
    s.add_argument("--term", required=True)
    s.add_argument("--strict", action="store_true")
    s.add_argument("--match-case", action="store_true")

    r = sub.add_parser("random", parents=[common])
    r.add_argument("--term")

    b = sub.add_parser("browse", parents=[common])
    b.add_argument("--character", required=True)
    b.add_argument("--term")

    a = sub.add_parser("author", parents=[common])
    a.add_argument("--term", required=True)

    d = sub.add_parser("date", parents=[common])
    d.add_argument("--term", required=True, help="Date string expected by API")

    return p.parse_args()


def main():
    args = parse_args()

    params = {
        "term": getattr(args, "term", None),
        "limit": args.limit,
        "page": args.page,
        "multiPage": args.multi_page,
    }

    if args.cmd == "search":
        path = "/search"
        params["strict"] = bool_str(args.strict)
        params["matchCase"] = bool_str(args.match_case)
    elif args.cmd == "random":
        path = "/random"
    elif args.cmd == "browse":
        path = "/browse"
        params["character"] = args.character
    elif args.cmd == "author":
        path = "/author"
    elif args.cmd == "date":
        path = "/date"
    else:
        print("Unknown command", file=sys.stderr)
        return 2

    try:
        data = get_json(path, params)
    except Exception as e:
        print(json.dumps({"ok": False, "error": str(e)}, indent=2))
        return 1

    print(json.dumps(data, indent=2, ensure_ascii=False))
    return 0


if __name__ == "__main__":
    raise SystemExit(main())


Security scan verdicts — ClawScan: clean | static analysis: clean | VirusTotal: clean | SkillSpector: clean (LOW)