← Commit history

Publish 0.7.9

John Lauer ·a2f7b0887b ·3mo ago ·parent ae366d9
4 files changed +40−23
SKILL.md+7−14
@@ -15,20 +15,6 @@ adom-google        modular wrapper: gmail · contacts · (drive/calendar = +1 sc Google REST APIs   called directly (gmail.googleapis.com, people.googleapis.com, …) ``` --## Displaying this app (REQUIRED — read before showing anything)--When showing the user a Sheet/Doc/Slide/email, open it on a proper Adom surface: the user's real signed-in browser (Adom browser extension) is BEST for Google URLs; a Hydrogen webview (`webview` skill) works for share-link previews.-- **NEVER open this app in VS Code's "Simple Browser"** — that is NOT what "webview" means-  in the Adom ecosystem. Simple Browser has no live channel, no console read-back, and no-  AI drivability; using it is a bug.-- The Adom surfaces for showing an app are: **wv** — a Hydrogen webview panel (load the-  `webview` skill from adom-workspace-control and follow it; inside HD this is HD's pane-  tab), **pup** — a pup window (`pup` skill), **nb** — the user's real signed-in browser (Adom browser-  extension), and **hdbw** — HD's standalone built-in Tauri browser window-  (picker: "HD Browser Window", destination id `webview-window`, only under Hydrogen-  Desktop). Pick per the situation; Simple Browser is NEVER one of them.- ## Why REST-direct (not a base-CLI shim)  We evaluated wrapping a base CLI — Google's `googleworkspace/cli` (`gws`, Rust,@@ -87,6 +73,13 @@ presentations, calendar, tasks, chat.messages, chat.spaces.readonly`) plus the g `adom-google api <url>` passthrough for **any** Google API. It prints a Google consent URL; the user clicks **Allow** once. +> ⚠ **Open the consent URL as ONE value — never unquoted in a shell.** It contains `&`; if you+> drop it into an unquoted shell/open command the shell truncates it at the first `&`, Google+> receives only `client_id`, and shows *"Error 400: invalid_request — missing response_type"*+> (this bit real users). Safe: hand the URL to a browser tool with the URL **inside JSON**+> (`adom-desktop nbrowser_open_window '{"sessionId":"gauth","url":"<URL>"}'`), or single-quote the+> whole URL. The `adom-google auth` output prints the ready-to-paste safe command for you.+ > ⏱ **The user has ~10 minutes to click Allow.** The gateway keeps the sign-in session alive > with a WebSocket heartbeat, so there's no rush. If they ever see a "Session Expired" page, just > re-run `adom-google auth`.
bin/adom-google+28−4
@@ -258,6 +258,9 @@ Hint: Check the current provider any time with: adom-google provider show""" SETUP_HINT = """ERROR: adom-google is not authorized yet (no Google token for this container). Hint: Just run:  adom-google auth Hint: It prints a Google consent URL — open it in the user's browser; they click Allow ONCE.+Hint: ⚠ That URL contains '&'. Open it as ONE value (a browser tool with the URL inside JSON, or a+Hint:   SINGLE-QUOTED shell arg). If you drop it UNQUOTED into a shell, it truncates at the first+Hint:   '&' and Google shows "Error 400: missing response_type". The auth output shows the safe way. Hint: Default access is FULL Workspace (Gmail, Contacts, Drive, Sheets, Docs, Slides, Calendar, Hint: Tasks, Chat + any Google API). There is NO mode question to ask the user — full is the Hint: default so the tool "just works".@@ -869,6 +872,25 @@ def _store_broker_tokens(cfg, tokens, scopes, mode):     _save(cfg)  +def _print_open_url(auth_link, step="1"):+    """Present the consent URL so an AI/shell can't mangle it. The URL is full of '&'; dropped+    UNQUOTED into a shell/open command the shell cuts it at the first '&', Google then receives+    only client_id and errors 'invalid_request: missing response_type' (issue #3). So lead with a+    browser-tool one-liner that carries the URL inside a JSON string (safe), and loudly warn to+    single-quote it otherwise."""+    safe = json.dumps({"sessionId": "gauth", "url": auth_link})+    print(f"{step}) Open this consent URL in the user's browser and have them click Allow.\n")+    print("   ⚠ The URL contains '&'. Open it as ONE whole value. Do NOT drop it UNQUOTED into a")+    print("     shell/open command — the shell cuts it at the first '&', Google then gets only")+    print("     client_id and shows \"Error 400: invalid_request — missing response_type\".")+    print("   SAFEST (URL rides inside JSON, so '&' can't truncate it) — paste this as-is:\n")+    print("     adom-desktop nbrowser_open_window '" + safe + "'")+    print("     # opens the user's real logged-in Chrome (add --target <name> if >1 Adom Desktop).")+    print("     # logged-out window instead: browser_open_window (add \"profile\":\"default\").\n")+    print("   Or paste the URL into the browser by hand (if via a shell, SINGLE-QUOTE the whole URL):\n")+    print("   " + auth_link + "\n")++ def cmd_auth(a):     cfg = _maybe_load_raw() or {}     # FULL is the default (no first-run mode quiz — issue #2). `--safe` is an advanced opt-in@@ -896,8 +918,7 @@ def cmd_auth(a):     print(f"OAuth Gateway flow — {mode.upper()} access"           + ("  (full Workspace: Gmail/Contacts/Drive/Sheets/Docs/Slides/Calendar/Tasks/Chat + delete)"              if mode == "full" else "  (safe: only files this app makes; no 'delete all')") + ".\n")-    print("1) Open this URL and approve with your Google Workspace account:\n")-    print("   " + auth_link + "\n")+    _print_open_url(auth_link)     # The gateway keeps the sign-in session alive for the full 10 min via a WS heartbeat     # (gateway fix for issue #1), so the client waits the same 10 min.     print("2) Waiting for your approval — you have ~10 minutes, no rush.")@@ -944,9 +965,12 @@ def _auth_manual(cfg, scopes, mode):         "client_id": cid, "redirect_uri": MANUAL_REDIRECT, "response_type": "code",         "scope": " ".join(scopes), "access_type": "offline", "prompt": "consent",     }+    manual_link = AUTH_URL + "?" + urllib.parse.urlencode(params)     print(f"Manual (desktop-client) flow — {mode.upper()} mode.\n")-    print("1) Open this URL and approve:\n")-    print("   " + AUTH_URL + "?" + urllib.parse.urlencode(params))+    print("1) Open this URL and approve. ⚠ It contains '&' — SINGLE-QUOTE the whole URL if you use")+    print("   any shell/open command, or the shell truncates it at the first '&' and Google shows")+    print("   \"Error 400: invalid_request — missing response_type\":\n")+    print("   " + manual_link)     print("\n2) The page will fail to load (expected). Copy the `code` value from the address")     print("   bar, then run:\n\n   adom-google auth-code '<paste-code-here>'") 
package.json+4−4
@@ -1,9 +1,9 @@ {   "slug": "adom-google",-  "version": "0.7.8",+  "version": "0.7.9",   "type": "app",   "license": "MIT",-  "description": "Drive your whole Google Workspace from the terminal \u2014 Gmail, Contacts, Drive, Sheets, Docs, Slides, Calendar, Tasks, Google Chat, plus a generic `api` passthrough to hit ANY Google API. Open source, ships with NO OAuth provider baked in: point it at your own token-broker gateway (`provider set`), buy a managed one, or \u2014 Adom staff \u2014 install the private adom-google-adom provider. One-click OAuth, no client secret on your machine. Full Workspace access by default (one Allow click, no mode quiz).",+  "description": "Drive your whole Google Workspace from the terminal — Gmail, Contacts, Drive, Sheets, Docs, Slides, Calendar, Tasks, Google Chat, plus a generic `api` passthrough to hit ANY Google API. Open source, ships with NO OAuth provider baked in: point it at your own token-broker gateway (`provider set`), buy a managed one, or — Adom staff — install the private adom-google-adom provider. One-click OAuth, no client secret on your machine. Full Workspace access by default (one Allow click, no mode quiz).",   "keywords": [     "adom-google",     "google-workspace",@@ -32,7 +32,7 @@   "hero": {     "path": "screenshots/hero-grid-v4.png"   },-  "discovery_pitch": "Drive your whole Google Workspace from the terminal through your AI \u2014 read Gmail (and its attachments), search Drive, build Sheets/Docs/Slides, manage Calendar & Tasks, and post to Google Chat as yourself. One OAuth, any Google API.",+  "discovery_pitch": "Drive your whole Google Workspace from the terminal through your AI — read Gmail (and its attachments), search Drive, build Sheets/Docs/Slides, manage Calendar & Tasks, and post to Google Chat as yourself. One OAuth, any Google API.",   "discovery_triggers": [     "read my gmail",     "read my email",@@ -114,4 +114,4 @@       "prompt": "post to Google Chat that the boards shipped"     }   ]-}\ No newline at end of file+}
page.json+1−1
@@ -4,7 +4,7 @@   "slug": "adom-google",   "title": "Adom Google",   "brief": "Drive your whole Google Workspace from the terminal — Gmail, Drive, Sheets, Docs, Slides, Calendar, Tasks, Chat + any Google API.",-  "version": "0.7.8",+  "version": "0.7.9",   "visibility": "public",   "install": {     "binary_name": "adom-google"