mirror of
https://github.com/0xrsydn/idx-cli.git
synced 2026-11-07 09:45:36 +00:00
feat(stockbit): one browser sign-in in idx-core for the CLI and MCP
`stockbit::signin` is now the single sign-in flow. `idx stockbit login` waits on it in the foreground; the `stockbit_login` MCP tool runs it on a thread and `stockbit_status` reports `sign_in.state`, so an agent knows when to stop polling. Auto uses a browser unless the shell is over SSH or has no display, and falls back to the local page only when the browser cannot start. The browser way opens Stockbit's sign-in page in a profile only idx uses and reads the session cookie over DevTools. What a real sign-in showed: - The cookie is host-only on stockbit.com, so deleting by the assumed .stockbit.com removed nothing and left live tokens in the profile. It is now deleted by its own domain and path, with every other tab closed first, and read back to confirm. - A signed-out page writes the cookie without tokens; it no longer counts. - A profile belongs to one browser, so it records the executable that made it. - On macOS the config directory depends on XDG_CONFIG_HOME, so a shell and an app started from the Dock disagreed; both default locations are now checked. - A thread does not outlive main, so idx-mcp closes a waiting browser when stdin closes or on SIGTERM or Ctrl-C. Progress goes to stderr, which keeps `-o json` to one document on stdout. Google refused its own sign-in in this window on 2026-10-31, most likely over the debugging flag; password sign-in works, and the docs and roadmap say so. Claude-Session: https://claude.ai/code/session_01RqPPVaoFxLToGAXXBEoCtH
This commit is contained in:
parent
cb532b670b
commit
ca4d3d09c2
21 changed files with 2799 additions and 212 deletions
|
|
@ -80,44 +80,114 @@ idx --provider stockbit stocks history BBCA --period 1y # Stockbit's daily
|
|||
idx stockbit logout
|
||||
```
|
||||
|
||||
**Logging in.** `idx stockbit login` opens a small page on your own machine
|
||||
(127.0.0.1, a fresh port each run). With stockbit.com open and logged in,
|
||||
click the page's **Send my Stockbit session** bookmarklet: it reads
|
||||
Stockbit's `credentialStorage` cookie in your browser and hands it to the
|
||||
page, which checks it with one request and says "Connected". If bookmarklets
|
||||
are blocked, click **Paste from clipboard** after copying the cookie, or
|
||||
paste it into the box. Without a browser, `--no-browser` prints the page URL
|
||||
instead, and `--port 7878` pins the port for `ssh -L 7878:127.0.0.1:7878`.
|
||||
Piping the value in still works (`pbpaste | idx stockbit login`), as does a
|
||||
refresh token on its own. On a server, set `IDX_STOCKBIT_REFRESH_TOKEN`.
|
||||
**Logging in.** `idx stockbit login` opens Chrome (or Chromium, Edge, Brave,
|
||||
Helium) on Stockbit's own sign-in page, in a browser profile only idx uses. Sign in
|
||||
there as usual, including any one-time code: idx reads the
|
||||
session cookie over the DevTools protocol, checks it with one request, and
|
||||
closes the window. Your password never reaches idx. The profile sits beside
|
||||
`config.toml`; idx takes the session cookie out of it once the session is
|
||||
stored, so the profile keeps only Stockbit's device cookies. The profile
|
||||
stays with the browser that made it: idx opens the same one next time, unless
|
||||
`IDX_STOCKBIT_BROWSER` names another. Choose your browser that way on the
|
||||
first sign-in if you have several.
|
||||
|
||||
Use your Stockbit password in that window. Google can refuse to sign in there
|
||||
with "This browser or app may not be secure", most likely because idx starts
|
||||
the browser with remote debugging on. If you only sign in with Google, use the
|
||||
local page below: sign in from a private window, paste the cookie, then close
|
||||
that window.
|
||||
|
||||
Run `login` again while the session is still good and there is nothing to
|
||||
do: idx checks it with one request and exits without opening a browser. The
|
||||
window it does open waits 15 minutes, and closes at once if you close it
|
||||
yourself.
|
||||
|
||||
**How long a session lasts.** Stockbit's refresh token is good for about a
|
||||
week, and idx spends it on every refresh, which extends the session. Use idx
|
||||
at least once a week and you stay signed in. A longer gap, a `logout`, or
|
||||
another tool spending the same token means one more sign-in.
|
||||
|
||||
Over SSH, on a machine with no display, without such a browser, or with
|
||||
`--no-browser`, idx serves a small page on your own machine (127.0.0.1, port
|
||||
7878 when it is free) instead. With
|
||||
stockbit.com open and logged in, click the page's **Send my Stockbit
|
||||
session** bookmarklet: it reads Stockbit's `credentialStorage` cookie in your
|
||||
browser and hands it to the page, which checks it with one request and says
|
||||
"Connected". If bookmarklets are blocked, click **Paste from clipboard**
|
||||
after copying the cookie, or paste it into the box. `--port` picks another
|
||||
port. Piping the value in still works
|
||||
(`pbpaste | idx stockbit login`), as does a refresh token on its own. On a
|
||||
server, set `IDX_STOCKBIT_REFRESH_TOKEN`. Set `IDX_STOCKBIT_BROWSER` to use a
|
||||
browser idx does not find on its own.
|
||||
|
||||
The session lands in `~/.config/idx/stockbit-session.json`, readable only by
|
||||
you. Tokens never appear in output, logs or errors. The page takes only the
|
||||
you. On macOS without `XDG_CONFIG_HOME` that is
|
||||
`~/Library/Application Support/idx/` instead; idx finds a session in either
|
||||
one, so the CLI and an MCP client started from the Dock share it. Tokens never appear in output, logs or errors. The page takes only the
|
||||
session value, keeps it in memory, and closes when it is done (or after five
|
||||
minutes). A session Stockbit refuses leaves a previously stored one in place.
|
||||
|
||||
The page listens on this machine's loopback interface only, so the browser
|
||||
must run on the same machine: from another host over SSH, or from a browser
|
||||
outside a container or WSL distro, `127.0.0.1` is a different machine and the
|
||||
page will not load. idx notices an SSH session (`SSH_CONNECTION`) and prints
|
||||
the exact command to run on the machine with the browser, on port 7878:
|
||||
## Remote and headless
|
||||
|
||||
The page listens on this machine's loopback interface only, and the browser
|
||||
handoff needs a browser on this machine too. On a server, in a container, or
|
||||
in a WSL distro, `127.0.0.1` is a different machine and neither will load.
|
||||
Three ways around that, in order of how little they ask of you.
|
||||
|
||||
**Pipe the cookie over SSH.** No tunnel, one command. Copy the
|
||||
`credentialStorage` value on the machine with the browser (DevTools,
|
||||
Application, Cookies), then:
|
||||
|
||||
```bash
|
||||
ssh -L 7878:127.0.0.1:7878 <this-host> # run where the browser is, keep it open
|
||||
pbpaste | ssh <host> "idx stockbit login"
|
||||
```
|
||||
|
||||
Elsewhere, pin the port yourself and forward it the same way:
|
||||
idx reads stdin, verifies the session, and stores it on the server. The value
|
||||
never reaches a shell history or a file.
|
||||
|
||||
**Forward the page.** Run the page on the server and forward its port from the
|
||||
machine with the browser:
|
||||
|
||||
```bash
|
||||
idx stockbit login --no-browser --port 7878
|
||||
idx stockbit login # on the server: over SSH, it serves the page
|
||||
ssh -L 7878:127.0.0.1:7878 <host> # where the browser is, keep it open
|
||||
```
|
||||
|
||||
Then open the printed URL there and click the bookmarklet. Over SSH, idx
|
||||
notices `SSH_CONNECTION`, skips the browser, and prints the exact forward
|
||||
itself.
|
||||
|
||||
**Seed a token.** For anything unattended, keep the refresh token in a secret
|
||||
store and pass it at run time:
|
||||
|
||||
```bash
|
||||
op run --env-file=stockbit.env -- idx stocks orderbook BBCA
|
||||
```
|
||||
|
||||
where the file holds `IDX_STOCKBIT_REFRESH_TOKEN=op://Private/stockbit/refresh`.
|
||||
Only the refresh token is needed; idx mints its own access token.
|
||||
|
||||
**Agents.** Over MCP, an agent calls `stockbit_login`, which answers at once
|
||||
and does the same as `idx stockbit login`. Where idx-mcp runs on your desktop,
|
||||
a browser window opens on Stockbit's sign-in page (`"method": "browser"`) and
|
||||
you sign in there. Over SSH or without a display, the answer carries the page
|
||||
URL and its `ssh -L` forward (`"method": "page"`) for the agent to hand you.
|
||||
The agent then polls `stockbit_status` until `sign_in.state` is `signed_in`
|
||||
or `failed`. A session that already works answers `signed_in` without opening
|
||||
anything, a second call while one is waiting returns it again, and
|
||||
`{"method": "page"}` or `{"method": "browser"}` picks the way. If the server
|
||||
stops while the window waits, the window closes with it.
|
||||
|
||||
One rule for all three: only one machine may own a session. Stockbit retires
|
||||
the refresh token on every refresh, so a token copied to two machines signs the
|
||||
other one out. Two machines need two sign-ins.
|
||||
|
||||
**One refresher per session.** Stockbit replaces the refresh token every time
|
||||
it is used. Once idx refreshes your session, a browser holding the same
|
||||
session has to log in again, and two tools sharing one session log each
|
||||
other out. Log in through a separate browser profile (or a private window
|
||||
you then close) for idx. idx processes on one machine take turns through a
|
||||
lock, so they never spend the token twice.
|
||||
other out. `idx stockbit login` keeps its own browser profile, so this only
|
||||
affects a browser you use yourself. idx processes on one machine take turns
|
||||
through a lock, so they never spend the token twice.
|
||||
|
||||
What the login adds:
|
||||
|
||||
|
|
@ -139,7 +209,8 @@ candles explicitly; windows it charts only weekly or hourly (`2y`, `5y`,
|
|||
|
||||
Stockbit's [terms](https://stockbit.com/terms) allow its content for personal,
|
||||
non-commercial use. They prohibit data mining, robots and redistribution
|
||||
without Stockbit's written consent. idx is not affiliated with or endorsed by
|
||||
without Stockbit's written consent, which includes serving the data to other
|
||||
people through `idx-mcp`. idx is not affiliated with or endorsed by
|
||||
Stockbit. Use this for looking at a stock now and then, not for crawling the
|
||||
market or republishing prices. With your login, automated use is tied to your
|
||||
account: keep it human-paced.
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue