devantler-tech / devantler-tech/ksail
Make Copilot authentication tokenless by default across every KSail interface
- Dominant language
- Go
- Stars
- 165
- Forks
- 12
- Avg merge
- 5h 41m
- Merged PRs (30d)
- 337
Description
> 🤖 Generated by the Agentic Engineer
## Evidence
Other Copilot-backed apps do not ask the user for a token, and KSail does. The reason is visible in
the code, and it is **not** that the no-token path is missing — it is that it is second in line, and
absent entirely from most interfaces.
| Interface | Source | Today |
|---|---|---|
| CLI — `ksail open chat` | `pkg/cli/cmd/open/chat/client.go` | Token **first**, Copilot CLI OAuth (device flow) as *fallback* |
| Desktop (Wails) | `desktop/main.go` | **Token-only** — assistant "stays hidden in the UI until a Copilot token … is configured" |
| Web UI / webchat | `pkg/svc/webchat/webchat.go` | **Token-only** — `Available == false` with no token |
The CLI already documents the ordering explicitly:
```go
// Authentication precedence:
// 1. KSAIL_COPILOT_TOKEN / COPILOT_TOKEN — explicit Copilot token
// 2. Copilot CLI's own OAuth credentials (device flow via `copilot auth login`)
```
and its failure message leads with the token:
```
- Set KSAIL_COPILOT_TOKEN or COPILOT_TOKEN for token-based authentication
```
So a user who has already run `copilot auth login` — the normal state for anyone with the Copilot
CLI installed — is still told to go and mint a token.
## Why the no-token path exists already
KSail consumes the **official `github.com/github/copilot-sdk/go`**, whose architecture delegates
authentication to the Copilot CLI:
```
Your Application → SDK Client → JSON-RPC → Copilot CLI (server mode) → GitHub (models, auth)
```
The SDK's stated prerequisite is a Copilot CLI that is *installed and authenticated*. That is
exactly the mechanism the other apps use, and KSail is already on it. The CLI interface proves it
works here — nothing new has to be invented for the common case.
## On authenticating as an *app*
Worth stating plainly, because it shapes the design: Copilot entitlement is attached to a **user
seat**, not to an installation. A GitHub App installation token authenticates an *app acting on a
repository*, which is a different subject, so it is not expected to carry a Copilot seat. The
supported "no token" mechanism is therefore a **user OAuth flow**, which is precisely what the
Copilot CLI performs once and stores — and what the SDK then reuses.
That gives two candidate mechanisms, in preference order:
1. **Delegate to the Copilot CLI's existing OAuth** — zero new credentials, zero new consent
screens, already working in the CLI interface.
2. **A KSail-owned OAuth app device flow** — only if we want KSail to own the login when the Copilot
CLI is absent.
Confirming (1) is sufficient, and whether (2) is worth owning, is the first child below — it is a
decision to record before code is written, not an assumption to build on.
## Target
**The default is no token.** Where an interactive user is present and the Copilot CLI is
authenticated, KSail uses that. A token remains fully supported as an **explicit override**, and
stays genuinely required for the case that cannot do better: a headless or remote server with no
interactive consent channel.
That distinction matters and is currently blurred. The webchat comment — *"a server cannot drive the
interactive device login"* — is sound for a **remote** server, but the **desktop app** and a
**locally-served** web UI both run on the user's own machine with the user right there. They inherit
the server-shaped restriction without needing it, which is the single biggest gap here.
## Success signal
A user with the Copilot CLI authenticated reaches a working assistant in **every** interface without
being asked for a token, and no existing token-based setup breaks.
## Guardrail
Token support is not removed, deprecated, or made harder — only demoted from default. Any change
must keep a token-configured environment working exactly as it does today.
Contributor guide
Research direction
Start by reading pkg/cli/cmd/open/chat/client.go, desktop/main.go, and pkg/svc/webchat/webchat.go, then verify how the Copilot SDK delegates authentication to the installed Copilot CLI. Record whether KSail should rely on that OAuth path or own a device flow. Done means authenticated interactive users reach the assistant through every interface, while explicit token configuration and headless operation continue to work.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- github, go
- Domain
- authentication, cli, desktop, web-dev
- Issue type
- Feature
- Difficulty
- 5/5
- Estimated time
- Over a week
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 45/100