1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
//! The login flow (DESIGN §8.3 as amended, §15 M6 Z8): bz's one interactive
//! surface, run as the **streamed-piped** spawn class (§8's third class).
//! `bz --login --provider <row> --browser` streams its sign-in lines live to the
//! invoking surface — the Login pane, and beside an auth-failed step —
//! verbatim (§5.3 instance-local RAM); on exit ONE outcome row lands in
//! `ops.jsonl` (§4.2, the stream never logged line-by-line), and a non-zero exit
//! carries the exact command as a run-by-hand fallback (§8.3). Credentials stay
//! bz's: yog renders the flow, never reads or writes a credential (§5.1 #22).
//!
//! **The flow follows the row** (§8.3 rule 1 as amended by bl-61bf; bl-b4e5 for
//! the rule it replaces). bz's default is the headless device flow and it
//! refuses one — exit 78, "this provider has no device endpoint; use
//! `--browser`" — on any row whose `oauth` block declares no `device` endpoint.
//! So the flag follows brazen's own `device` column
//! ([`ProviderRow::headless_login`](crate::config_edit::brazen::ProviderRow::headless_login)):
//! a row that declares one is fired headless — bz binds nothing and streams the
//! verification URL and user code down the lane, so the sign-in completes from
//! any seat, a phone's browser included — and every other row is fired
//! `--browser`, the loopback AuthCode flow (RFC 8252) whose
//! `authorize_url`/`token_url` are *required* of every `oauth` block and which
//! is therefore the floor. That branch is [`Flow`], and it is read ONCE at the
//! spawn ([`runs::Runs::start`]): still no flow selector on any surface, and
//! nothing yog guesses at.
//!
//! The selectable providers come from
//! [`BzRunner::providers`](crate::config_edit::brazen::BzRunner::providers) —
//! brazen's effective provider table, read in-process since §16.7 W10, so the
//! built-in rows (§5.1 #21) are listed rather than hinted at. Whether a row can
//! be signed in at all is that table's own `auth` column
//! ([`ProviderRow::login_blocked`](crate::config_edit::brazen::ProviderRow::login_blocked)):
//! a keyless or api-keyed row gets **no button at all**, only the reason there
//! is none (§8.3 rule 4, bl-402f) — never a verb that can only exit 78. [`LoginRun`] wraps the streamed child + the
//! pure [`LoginView`] the shell paints; [`auth`] classifies an auth-shaped step
//! failure so the Login affordance surfaces one click away.
//!
//! The spawn itself stays a process (§16.7: seams that are processes for a
//! reason stay processes) — only the binary on the far side is now yog's own
//! executable under the `bz` namespace, so the device flow is served by the
//! same linked brazen the config projection reads.
use ;
use crate;
use crate;
/// The engine's live-run holder (REMOTE §8.3, bl-c285): one `bz --login` child
/// per workspace × provider, read by lanes and settled by a thread of its own.
/// The standing's one JSON spelling, both directions — beside its own type.
/// bz's login subcommand flag, its provider selector (§8.2), and the one flag
/// that selects a flow — see the module note.
const LOGIN_FLAG: &str = "--login";
const PROVIDER_FLAG: &str = "--provider";
const BROWSER_FLAG: &str = "--browser";
/// **Which sign-in flow a row is fired with** (§8.3 rule 1 as amended by
/// bl-61bf). Not a choice any surface offers: the row's own `device` column
/// decides it, and [`runs::Runs::start`] is the one place that reads it.
/// The `bz` words one sign-in is fired with. **One spelling, three readers**:
/// the spawn's argv, the `ops.jsonl` row and the run-by-hand fallback all read
/// this, so what is logged and what is offered can never diverge from what ran.
/// The pure view-model the shell paints for a login run (§8.3). All three fields
/// are derived facts of the streamed child; the shell holds a [`LoginRun`] as its
/// §5.3 instance-local RAM and reads this each frame.
/// A live `bz --login` run: the streamed child (§8) plus the [`LoginView`] the
/// shell paints. Held at the invoking surface as instance-local RAM (§5.3); the
/// child is SIGTERM'd on drop (closing the surface aborts the device flow —
/// consistent with a device code being for the human at *this* keyboard).
/// The §8.3 **run-by-hand spelling** of one sign-in (bl-b589): the supported
/// workspace-bound command, built from the very consts the spawn uses and the
/// hatch's own subcommand words, so what the pane offers cannot drift from what
/// yog runs or from what the hatch accepts.
///
/// It is not the spawn's argv, and deliberately so: yog fires `bz` with the
/// wall already standing in the child's environment, which a human's shell has
/// no way to inherit. The command shown therefore has to *ask* for that wall by
/// name — which is exactly what `yog exec --ws <workspace>` is for. Outside any
/// workspace there is no lawful spelling at all, so the fallback says what to
/// fix rather than offering a command that would refuse.
/// Spawn `bz --login --provider <provider>` in `flow` as the streamed-piped
/// class (§8): stdin null (this verb never reads TTY input — the browser flow
/// completes through the loopback redirect and the device flow through a code
/// the human types elsewhere), stdout/stderr piped for live line-buffering.
/// A spawn failure (bz absent) appends a synthetic `ops.jsonl` line (§4.2) and
/// returns the error, so no attempt is ever un-logged (§7.3). `ts` is the
/// wall-clock stamp minted at the shell boundary, kept clock-free here.