@bacnh85/pi-web 0.10.4 → 0.10.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,15 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.10.5 (2026-09-13)
4
+
5
+ ### Added
6
+
7
+ - **`GEMINI_WEB_SECURE_1PSIDTS` env** — the rotating `__Secure-1PSIDTS`
8
+ session cookie, injected into the client jar pre-init. Google stopped
9
+ serving SNlM0e/cookie rotations to plain clients; without it the session
10
+ is partially authed (chat works, `accessToken` unresolved, sensitive
11
+ surfaces refuse). With it: full auth (`accessToken` resolves).
12
+
3
13
  ## 0.10.4 (2026-09-13)
4
14
 
5
15
  ### Fixed
@@ -254,3 +264,11 @@ All notable changes to `pi-web` will be documented in this file.
254
264
 
255
265
  - Consolidated 14 backend-specific tools into 7 unified tools (`web_search`, `web_extract`, `web_map`, `web_crawl`, `web_screenshot`, `web_pdf`, `web_status`).
256
266
  - Auto-selection and adaptive fallback between static (JSDOM), dynamic (Firecrawl), and full (Crawl4AI) backends.
267
+ ## 0.10.6
268
+
269
+ Docs correction: Deep Research is **not** Gemini-Advanced-gated. Live
270
+ verification (2026-09-13, free-tier account): Deep Research plan creation
271
+ succeeds via a browser-impersonating client, while this package's Node
272
+ transport is refused with 1184/FEATURE_NOT_AVAILABLE on the same fresh
273
+ session. The 1184 error is a client-transport artifact; README,
274
+ `web_research` descriptions, and troubleshooting updated accordingly.
package/README.md CHANGED
@@ -32,6 +32,7 @@ Variables:
32
32
  | `CRAWL4AI_API_TOKEN` | No (3) | — | Required if Crawl4AI auth enabled |
33
33
  | `GEMINI_WEB_SECURE_1PSID` | No (4) | — | `__Secure-1PSID` cookie from gemini.google.com — enables authed `web_research` (Deep Research) |
34
34
  | `GEMINI_WEB_PROXY` | No | — | Proxy URL for Gemini web calls (escape hatch if Google blocks the IP) |
35
+ | `GEMINI_WEB_SECURE_1PSIDTS` | No (6) | — | Rotating `__Secure-1PSIDTS` cookie — restores full auth when Google withholds SNlM0e from plain clients (recommended for image surfaces) |
35
36
  | `ZAI_API_KEY` | No (5) | — | Z.ai API key — enables the `web_image` `zai` provider (GLM-Image via the official `api.z.ai`); `Z_AI_API_KEY` also accepted |
36
37
  | `WEB_IMAGE_API_BASE_URL` | No | — | `web_image` `custom` provider: any OpenAI-compatible images endpoint (e.g. `https://api.openai.com/v1`) |
37
38
  | `WEB_IMAGE_API_KEY` | No | — | Bearer key for the `custom` endpoint |
@@ -45,6 +46,7 @@ Variables:
45
46
  > (2) Required for hosted Firecrawl; optional for self-hosted instances without auth.
46
47
  > (3) Required for Crawl4AI v0.9+ default config.
47
48
  > (4) Without it `web_research mode=ask` still works in guest mode (Flash-only); `mode=research` errors with setup steps.
49
+ > (6) Copy the current value from DevTools (Application → Cookies) alongside `__Secure-1PSID`; it rotates, so refresh it when auth degrades.
48
50
  > (5) `web_image` works with zero config via Gemini guest mode (availability varies by region/account); `zai` activates when `ZAI_API_KEY` is present, `custom` when `WEB_IMAGE_API_BASE_URL` is set.
49
51
 
50
52
  Secrets are never printed; `web_status` reports only presence/source.
@@ -227,8 +229,12 @@ web_research(query="compare the top 3 cloud providers' AI offerings", mode="rese
227
229
  Google Search). Works **without any cookie** in guest mode (Flash-only).
228
230
  Sent as a temporary chat so your Gemini history stays clean.
229
231
  - **`mode: "research"`** — full Gemini **Deep Research**: plan → autonomous web
230
- browsing (minutes) → cited report. Requires the cookie **and a Gemini
231
- Advanced subscription** on the account. Default timeout 600 s, cap 1 800 000.
232
+ browsing (minutes) → cited report. Requires the cookie and a **fresh session**.
233
+ **Known limitation (2026-09):** Gemini refuses Deep Research for non-browser
234
+ clients, so this mode currently fails with 1184/FEATURE_NOT_AVAILABLE even on
235
+ free-tier accounts that *can* run Deep Research (proven via a
236
+ browser-impersonating client — it is not an Advanced-entitlement gate).
237
+ Default timeout 600 s, cap 1 800 000.
232
238
 
233
239
  Both modes return the text plus **Sources** — URLs extracted from the
234
240
  answer/report markdown (the web protocol exposes no structured citations field).
@@ -263,10 +269,12 @@ Troubleshooting:
263
269
 
264
270
  - *"cookie expired or invalid"* — re-copy `__Secure-1PSID` (it rotates).
265
271
  - *"temporarily blocked this IP"* — set `GEMINI_WEB_PROXY`.
266
- - *research mode: "Unknown API error: 1184"* — on this account Deep Research
267
- was rejected; usually means no Gemini Advanced subscription on the account
268
- (Deep Research is Advanced-only), or Google changed the protocol. `ask`
269
- mode is unaffected.
272
+ - *research mode: "Unknown API error: 1184"* — **not** an entitlement error:
273
+ Deep Research plan creation succeeds on free-tier accounts via
274
+ browser-impersonating clients (verified 2026-09-13). Gemini refuses
275
+ privileged tools to non-browser clients; this tool's transport is plain
276
+ Node, so research currently fails regardless of plan. `ask` mode is
277
+ unaffected.
270
278
 
271
279
  ### `web_image` — free upstream image generation
272
280
 
@@ -114,7 +114,7 @@ const WEB_ROUTING_GUIDANCE = `## Web Tool Routing (pi-web)
114
114
  - **web_map** — discover site URLs (Firecrawl Map).
115
115
  - **web_crawl** — multi-page crawl: \`mode: "light"\` (Firecrawl, url) or \`mode: "full"\` (Crawl4AI, urls[]).
116
116
  - **web_screenshot** / **web_pdf** — page capture (Crawl4AI).
117
- - **web_research** — AI-synthesized research via Gemini web (mode "ask" = grounded answer, guest OK; mode "research" = Deep Research report, needs cookie + Gemini Advanced, takes minutes).
117
+ - **web_research** — AI-synthesized research via Gemini web (mode "ask" = grounded answer, guest OK; mode "research" = Deep Research report currently blocked by Gemini's non-browser-client refusal (1184), not by entitlement; takes minutes when available).
118
118
  - **web_image** — text→image generation via free upstreams (auto: Gemini web → Z.ai GLM-Image → custom OpenAI-images endpoint; \`model\`/\`n\` params).
119
119
  - **web_chat** — one-off chat completion via an OpenAI-compatible gateway (\`WEB_CHAT_API_BASE_URL\`; non-streaming).
120
120
  - **web_status** — provider config + health.
@@ -485,7 +485,7 @@ export default function piWebExtension(pi: ExtensionAPI) {
485
485
  name: "web_research",
486
486
  label: "Web Research (Gemini)",
487
487
  description:
488
- "AI-synthesized web research via Gemini (gemini.google.com web tier, cookie auth). Mode 'ask' returns a quick grounded answer with source links (works guest-mode, Flash only). Mode 'research' runs Gemini Deep Research — an autonomous agent browses the web for minutes and returns a comprehensive cited report (requires GEMINI_WEB_SECURE_1PSID cookie and a Gemini Advanced subscription).",
488
+ "AI-synthesized web research via Gemini (gemini.google.com web tier, cookie auth). Mode 'ask' returns a quick grounded answer with source links (works guest-mode, Flash only). Mode 'research' runs Gemini Deep Research — plan, autonomous web browsing, cited report. Requires GEMINI_WEB_SECURE_1PSID and a fresh session; note Gemini currently refuses Deep Research to non-browser clients (1184) the error is a transport artifact, not an entitlement gate.",
489
489
  promptSnippet: "AI-synthesized research with citations",
490
490
  promptGuidelines: [
491
491
  "Use for AI-synthesized research with sources (mode ask = quick grounded answer; mode research = multi-minute Deep Research report). NOT for URL-list searches (web_search) or single-URL extraction (web_extract). Cite the returned source URLs.",
@@ -494,7 +494,7 @@ export default function piWebExtension(pi: ExtensionAPI) {
494
494
  query: Type.String({ description: "Research question or topic." }),
495
495
  mode: Type.Optional(Type.Union(
496
496
  [Type.Literal("ask"), Type.Literal("research")],
497
- { default: "ask", description: "ask = quick grounded answer (guest OK); research = full Deep Research report (cookie + Gemini Advanced required, takes minutes)." },
497
+ { default: "ask", description: "ask = quick grounded answer (guest OK); research = full Deep Research report (fresh cookie required; currently refused to non-browser clients with 1184)." },
498
498
  )),
499
499
  model: Type.Optional(Type.String({ description: "Gemini model for ask mode (e.g. gemini-3-flash). Discovered from the account by default." })),
500
500
  ...sharedControlSchema,
@@ -14,13 +14,15 @@ import { findEnvValue } from "./config";
14
14
  export interface GeminiWebConfig {
15
15
  psid?: string;
16
16
  psidSource: string;
17
+ psidts?: string;
17
18
  proxy?: string;
18
19
  }
19
20
 
20
21
  export function loadGeminiWebConfig(cwd = process.cwd(), includeCwdEnv = false): GeminiWebConfig {
21
22
  const psid = findEnvValue("GEMINI_WEB_SECURE_1PSID", cwd, includeCwdEnv);
23
+ const psidts = findEnvValue("GEMINI_WEB_SECURE_1PSIDTS", cwd, includeCwdEnv);
22
24
  const proxy = findEnvValue("GEMINI_WEB_PROXY", cwd, includeCwdEnv);
23
- return { psid: psid.value, psidSource: psid.value ? psid.source : "not set", proxy: proxy.value };
25
+ return { psid: psid.value, psidSource: psid.value ? psid.source : "not set", psidts: psidts.value, proxy: proxy.value };
24
26
  }
25
27
 
26
28
  // ---------------------------------------------------------------------------
@@ -66,7 +68,7 @@ export interface GeminiClientLike {
66
68
  }
67
69
 
68
70
  export type GeminiClientFactory = (
69
- opts: { secure_1psid?: string; proxy?: string },
71
+ opts: { secure_1psid?: string; secure_1psidts?: string; proxy?: string },
70
72
  ) => GeminiClientLike | Promise<GeminiClientLike>;
71
73
 
72
74
  // Cached per config (psid|proxy) so a config change re-creates the client.
@@ -137,14 +139,24 @@ export async function loadDefaultFactory(): Promise<GeminiClientFactory> {
137
139
  }
138
140
  // ponytail: generous per-request cap (covers research); per-mode ask/research
139
141
  // timeouts are enforced by raceGuard below.
140
- return (opts) => new Gemini({ secure_1psid: opts.secure_1psid, proxy: opts.proxy ?? null, timeout: 1_800_000 });
142
+ // ponytail: Google's rotating __Secure-1PSIDTS is required for sensitive
143
+ // surfaces (image generation refuses with "You might be signed out" when it
144
+ // is missing); the page HTML no longer carries SNlM0e/rotations for plain
145
+ // clients, so the user passes it explicitly and we inject it pre-init.
146
+ return (opts) => {
147
+ const client = new Gemini({ secure_1psid: opts.secure_1psid, proxy: opts.proxy ?? null, timeout: 1_800_000 });
148
+ if (opts.secure_1psidts) {
149
+ (client as unknown as { cookies: Record<string, string> }).cookies["__Secure-1PSIDTS"] = opts.secure_1psidts;
150
+ }
151
+ return client;
152
+ };
141
153
  }
142
154
 
143
155
  async function getClient(config: GeminiWebConfig, factory?: GeminiClientFactory): Promise<GeminiClientLike> {
144
- const key = `${config.psid ?? ""}|${config.proxy ?? ""}`;
156
+ const key = `${config.psid ?? ""}|${config.psidts ?? ""}|${config.proxy ?? ""}`;
145
157
  if (cached?.key === key) return cached.client;
146
158
  const make = factory ?? (await loadDefaultFactory());
147
- const client = await make({ secure_1psid: config.psid, proxy: config.proxy });
159
+ const client = await make({ secure_1psid: config.psid, secure_1psidts: config.psidts, proxy: config.proxy });
148
160
  cached = { key, client };
149
161
  return client;
150
162
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@bacnh85/pi-web",
3
- "version": "0.10.4",
3
+ "version": "0.10.6",
4
4
  "description": "Pi extension for web search, page extraction, Firecrawl scraping/crawling, Crawl4AI headless browser crawling, Gemini web-tier research, free upstream image generation, and one-off gateway chat.",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -17,7 +17,7 @@ Use the **10 unified tools** from the `pi-web` extension for all web-related tas
17
17
  | `web_crawl` | Crawl multiple pages from a site | Light (Firecrawl) or Full (Crawl4AI) |
18
18
  | `web_screenshot` | Capture page screenshot as PNG | Crawl4AI daemon (public URLs) or local headless Chrome (localhost/LAN/file URLs — auto-detected) |
19
19
  | `web_pdf` | Generate page PDF | Crawl4AI daemon (public URLs) or local headless Chrome (localhost/LAN/file URLs — auto-detected) |
20
- | `web_research` | AI-synthesized research with sources | Gemini web tier: ask = grounded answer (guest OK); research = Deep Research report (cookie + Gemini Advanced) |
20
+ | `web_research` | AI-synthesized research with sources | Gemini web tier: ask = grounded answer (guest OK); research = Deep Research report (fresh cookie; currently refused to non-browser clients with 1184) |
21
21
  | `web_image` | Generate images from a text prompt | Gemini web (guest/cookie) → Z.ai GLM-Image (`ZAI_API_KEY`) → custom OpenAI-images endpoint |
22
22
  | `web_chat` | One-off chat via an OpenAI-compatible gateway | `WEB_CHAT_API_BASE_URL` (ChatGPT web bridge, official OpenAI, …) |
23
23
  | `web_status` | Check provider configuration and health | — |
@@ -59,7 +59,7 @@ What do you need?
59
59
  ├── AI-synthesized research with sources (synthesis, comparisons, reports)
60
60
  │ → web_research
61
61
  │ ├─ quick grounded answer: mode=ask (default; guest OK, Flash-only)
62
- │ └─ multi-minute Deep Research report: mode=research (needs cookie + Gemini Advanced)
62
+ │ └─ multi-minute Deep Research report: mode=research (fresh cookie; currently blocked by Gemini's non-browser refusal)
63
63
 
64
64
  ├── Generate an image from a text prompt (NOT capturing an existing page)
65
65
  │ → web_image