@circuitwall/jarela 1.4.0 → 1.4.1
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/.next/standalone/.next/BUILD_ID +1 -1
- package/.next/standalone/.next/build-manifest.json +3 -3
- package/.next/standalone/.next/prerender-manifest.json +3 -3
- package/.next/standalone/.next/server/app/_global-error/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/_global-error.html +1 -1
- package/.next/standalone/.next/server/app/_global-error.rsc +1 -1
- package/.next/standalone/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_global-error.segments/_global-error/__PAGE__.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_global-error.segments/_global-error.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/_not-found.html +2 -2
- package/.next/standalone/.next/server/app/_not-found.rsc +1 -1
- package/.next/standalone/.next/server/app/_not-found.segments/_full.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_not-found.segments/_head.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_not-found.segments/_index.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_not-found.segments/_not-found.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/_not-found.segments/_tree.segment.rsc +1 -1
- package/.next/standalone/.next/server/app/api/v1/builtin-tools/route.js +10 -1
- package/.next/standalone/.next/server/app/api/v1/builtin-tools/route.js.map +1 -1
- package/.next/standalone/.next/server/app/api/v1/dashboard/currency/route.js +10 -5
- package/.next/standalone/.next/server/app/api/v1/dashboard/currency/route.js.map +1 -1
- package/.next/standalone/.next/server/app/api/v1/providers/[provider]/probe/route.js +9 -1
- package/.next/standalone/.next/server/app/api/v1/providers/[provider]/probe/route.js.map +1 -1
- package/.next/standalone/.next/server/app/api/v1/threads/[thread_id]/run/route.js +33 -8
- package/.next/standalone/.next/server/app/api/v1/threads/[thread_id]/run/route.js.map +1 -1
- package/.next/standalone/.next/server/app/page.js +63 -202
- package/.next/standalone/.next/server/app/page.js.map +1 -1
- package/.next/standalone/.next/server/app/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/app/setup/page.js +1 -1
- package/.next/standalone/.next/server/app/setup/page.js.nft.json +1 -1
- package/.next/standalone/.next/server/app/setup/page_client-reference-manifest.js +1 -1
- package/.next/standalone/.next/server/chunks/1718.js +159 -0
- package/.next/standalone/.next/server/chunks/1718.js.map +1 -0
- package/.next/standalone/.next/server/chunks/2082.js +6 -3
- package/.next/standalone/.next/server/chunks/2082.js.map +1 -1
- package/.next/standalone/.next/server/chunks/210.js +28 -0
- package/.next/standalone/.next/server/chunks/210.js.map +1 -1
- package/.next/standalone/.next/server/chunks/423.js +6 -3
- package/.next/standalone/.next/server/chunks/423.js.map +1 -1
- package/.next/standalone/.next/server/chunks/4631.js +37 -5
- package/.next/standalone/.next/server/chunks/4631.js.map +1 -1
- package/.next/standalone/.next/server/chunks/8167.js +255 -204
- package/.next/standalone/.next/server/chunks/8167.js.map +1 -1
- package/.next/standalone/.next/server/chunks/8866.js +38 -5
- package/.next/standalone/.next/server/chunks/8866.js.map +1 -1
- package/.next/standalone/.next/server/chunks/9032.js +8 -0
- package/.next/standalone/.next/server/chunks/9032.js.map +1 -1
- package/.next/standalone/.next/server/chunks/{7883.js → 9557.js} +15 -3
- package/.next/standalone/.next/server/chunks/9557.js.map +1 -0
- package/.next/standalone/.next/server/middleware-build-manifest.js +3 -3
- package/.next/standalone/.next/server/middleware.js +6 -3
- package/.next/standalone/.next/server/pages/404.html +2 -2
- package/.next/standalone/.next/server/pages/500.html +1 -1
- package/.next/standalone/.next/server/proxy.js.map +1 -1
- package/.next/standalone/.next/server/server-reference-manifest.json +1 -1
- package/.next/standalone/.next/static/chunks/{2351-68d8987bbe17ba2d.js → 2351-1ab119fb3b48f4c9.js} +258 -205
- package/.next/standalone/.next/static/chunks/2351-1ab119fb3b48f4c9.js.map +1 -0
- package/.next/standalone/.next/static/chunks/{9209-0d46118e502f8bf5.js → 4097-64691f9110cf167c.js} +14 -2
- package/.next/standalone/.next/static/chunks/4097-64691f9110cf167c.js.map +1 -0
- package/.next/standalone/.next/static/chunks/app/{page-74846c864241b96d.js → page-145150e0468544e7.js} +64 -203
- package/.next/standalone/.next/static/chunks/app/page-145150e0468544e7.js.map +1 -0
- package/.next/standalone/.next/static/chunks/app/setup/{page-9a465b5fa755b3c3.js → page-a1463a9ace439ff7.js} +2 -2
- package/.next/standalone/.next/static/chunks/app/setup/{page-9a465b5fa755b3c3.js.map → page-a1463a9ace439ff7.js.map} +1 -1
- package/.next/standalone/.next/static/chunks/{webpack-ff5627013a5e3842.js → webpack-f4ac5c5f92cfd1c1.js} +13 -1
- package/.next/standalone/.next/static/chunks/webpack-f4ac5c5f92cfd1c1.js.map +1 -0
- package/.next/standalone/package.json +1 -1
- package/CHANGELOG.md +60 -0
- package/README.md +1 -1
- package/api/client.ts +10 -9
- package/app/api/v1/dashboard/currency/route.ts +7 -2
- package/app/api/v1/providers/[provider]/probe/route.ts +12 -1
- package/app/api/v1/threads/[thread_id]/run/route.ts +22 -8
- package/components/layout/AppShell.tsx +53 -17
- package/components/setup/PinKeypad.tsx +238 -0
- package/components/setup/ScreenLock.tsx +8 -173
- package/components/setup/UnlockScreen.tsx +25 -192
- package/lib/documents/remote/github.ts +16 -2
- package/lib/documents/remote/mail.ts +11 -2
- package/lib/lifecycle/shutdown.ts +9 -0
- package/lib/providers/github-copilot-auth.ts +2 -0
- package/lib/providers/github-copilot.ts +1 -0
- package/lib/tools/async-results.ts +11 -0
- package/package.json +1 -1
- package/scripts/install-to-system.ps1 +2 -2
- package/scripts/installed-launcher.ps1 +81 -17
- package/.next/standalone/.next/server/chunks/7883.js.map +0 -1
- package/.next/standalone/.next/static/chunks/2351-68d8987bbe17ba2d.js.map +0 -1
- package/.next/standalone/.next/static/chunks/9209-0d46118e502f8bf5.js.map +0 -1
- package/.next/standalone/.next/static/chunks/app/page-74846c864241b96d.js.map +0 -1
- package/.next/standalone/.next/static/chunks/webpack-ff5627013a5e3842.js.map +0 -1
- /package/.next/standalone/.next/static/{AV5AO0yTRABo-NgwxhDe7 → WQdcnm9NyqpeNc0Z8_woo}/_buildManifest.js +0 -0
- /package/.next/standalone/.next/static/{AV5AO0yTRABo-NgwxhDe7 → WQdcnm9NyqpeNc0Z8_woo}/_ssgManifest.js +0 -0
|
@@ -182,7 +182,10 @@ async function indexGmailMail(row: DocumentSourceRow): Promise<RemoteIndexStats>
|
|
|
182
182
|
const batch = list.messages ?? [];
|
|
183
183
|
if (batch.length === 0) break;
|
|
184
184
|
|
|
185
|
-
|
|
185
|
+
// Use allSettled so a single 404/transient 5xx on one message
|
|
186
|
+
// doesn't bin the whole page (and stall the cursor on the next
|
|
187
|
+
// run). Failures get counted into stats.errors instead.
|
|
188
|
+
const settled = await Promise.allSettled(batch.slice(0, limit).map(async (entry) => {
|
|
186
189
|
const msg = await googleFetch(
|
|
187
190
|
auth,
|
|
188
191
|
"Gmail",
|
|
@@ -212,10 +215,16 @@ async function indexGmailMail(row: DocumentSourceRow): Promise<RemoteIndexStats>
|
|
|
212
215
|
});
|
|
213
216
|
}));
|
|
214
217
|
|
|
215
|
-
for (const [index,
|
|
218
|
+
for (const [index, outcome] of settled.entries()) {
|
|
216
219
|
const id = batch[index]?.id ?? "";
|
|
217
220
|
if (id) keep.add(`gmail://${id}`);
|
|
218
221
|
stats.scanned++;
|
|
222
|
+
if (outcome.status === "rejected") {
|
|
223
|
+
stats.errors++;
|
|
224
|
+
console.warn(`[mail-indexer] message ${id} failed:`, outcome.reason);
|
|
225
|
+
continue;
|
|
226
|
+
}
|
|
227
|
+
const item = outcome.value;
|
|
219
228
|
stats.added += item.status === "added" ? 1 : 0;
|
|
220
229
|
stats.updated += item.status === "updated" ? 1 : 0;
|
|
221
230
|
stats.unchanged += item.status === "unchanged" ? 1 : 0;
|
|
@@ -131,6 +131,15 @@ async function runShutdown(): Promise<void> {
|
|
|
131
131
|
console.error("[jarela] waiting for runs failed:", err);
|
|
132
132
|
}
|
|
133
133
|
|
|
134
|
+
// 4b. Stop the async-tool-results sweeper. Holds a setInterval that
|
|
135
|
+
// would otherwise keep the event loop alive past closeDb().
|
|
136
|
+
try {
|
|
137
|
+
const { stopAsyncResults } = await import("@/lib/tools/async-results");
|
|
138
|
+
stopAsyncResults();
|
|
139
|
+
} catch (err) {
|
|
140
|
+
console.error("[jarela] stopping async-results sweeper failed:", err);
|
|
141
|
+
}
|
|
142
|
+
|
|
134
143
|
// 5. Close the DB. WAL is checkpointed so the next boot is fast and we
|
|
135
144
|
// leave no stale -shm/-wal sidecars on disk.
|
|
136
145
|
try {
|
|
@@ -44,6 +44,7 @@ export async function startDeviceFlow(): Promise<DeviceCodeResponse> {
|
|
|
44
44
|
"User-Agent": "Jarela/1.0",
|
|
45
45
|
},
|
|
46
46
|
body: JSON.stringify({ client_id: COPILOT_CLIENT_ID, scope: SCOPE }),
|
|
47
|
+
signal: AbortSignal.timeout(30_000),
|
|
47
48
|
});
|
|
48
49
|
if (!res.ok) {
|
|
49
50
|
const body = await res.text().catch(() => res.statusText);
|
|
@@ -69,6 +70,7 @@ export async function pollDeviceFlow(device_code: string): Promise<PollResult> {
|
|
|
69
70
|
device_code,
|
|
70
71
|
grant_type: "urn:ietf:params:oauth:grant-type:device_code",
|
|
71
72
|
}),
|
|
73
|
+
signal: AbortSignal.timeout(30_000),
|
|
72
74
|
});
|
|
73
75
|
if (!res.ok) {
|
|
74
76
|
return { status: "error", error: `HTTP ${res.status}` };
|
|
@@ -57,6 +57,17 @@ function ensureSweeper(): void {
|
|
|
57
57
|
(sweeper as unknown as { unref?: () => void }).unref?.();
|
|
58
58
|
}
|
|
59
59
|
|
|
60
|
+
/**
|
|
61
|
+
* Tear down the sweeper. Called from the shutdown drain so the timer
|
|
62
|
+
* isn't keeping the event loop alive past close-time. Idempotent.
|
|
63
|
+
*/
|
|
64
|
+
export function stopAsyncResults(): void {
|
|
65
|
+
if (sweeper) {
|
|
66
|
+
clearInterval(sweeper);
|
|
67
|
+
sweeper = null;
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
|
|
60
71
|
/**
|
|
61
72
|
* Carve out a slot for a new async tool call and return its key.
|
|
62
73
|
* The key is opaque and URL-safe — the agent treats it as a token.
|
package/package.json
CHANGED
|
@@ -245,8 +245,8 @@ $settings = New-ScheduledTaskSettingsSet `
|
|
|
245
245
|
-StartWhenAvailable `
|
|
246
246
|
-Hidden `
|
|
247
247
|
-ExecutionTimeLimit (New-TimeSpan -Seconds 0) `
|
|
248
|
-
-RestartInterval (New-TimeSpan -Minutes
|
|
249
|
-
-RestartCount
|
|
248
|
+
-RestartInterval (New-TimeSpan -Minutes 5) `
|
|
249
|
+
-RestartCount 3 `
|
|
250
250
|
-MultipleInstances IgnoreNew
|
|
251
251
|
|
|
252
252
|
$task = New-ScheduledTask `
|
|
@@ -120,41 +120,105 @@ $env:PORT = "$Port"
|
|
|
120
120
|
$env:HOSTNAME = '127.0.0.1'
|
|
121
121
|
$env:NODE_ENV = 'production'
|
|
122
122
|
|
|
123
|
-
# Separate files for the node child's stdout/stderr.
|
|
124
|
-
#
|
|
125
|
-
#
|
|
123
|
+
# Separate files for the node child's stdout/stderr. We append (>>) instead
|
|
124
|
+
# of truncating each spawn so a crash-and-respawn cycle keeps the prior
|
|
125
|
+
# stderr lines around for diagnosis.
|
|
126
126
|
$ServerOut = Join-Path $LogDir 'server.out.log'
|
|
127
127
|
$ServerErr = Join-Path $LogDir 'server.err.log'
|
|
128
128
|
|
|
129
|
+
# Spawn node and reliably capture stdout/stderr to files. Background:
|
|
130
|
+
# `Start-Process -NoNewWindow -RedirectStandardOutput X -RedirectStandardError Y`
|
|
131
|
+
# silently drops both streams when the parent chain is wscript -> powershell
|
|
132
|
+
# (i.e. when there is no console attached to the PowerShell host). Under that
|
|
133
|
+
# setup, server.out.log / server.err.log stay 0 bytes forever, hiding crash
|
|
134
|
+
# reasons. Switching to a raw `[System.Diagnostics.Process]` with async
|
|
135
|
+
# `BeginOutputReadLine`/`BeginErrorReadLine` event handlers works regardless
|
|
136
|
+
# of console attachment because the read loop runs on a .NET worker thread.
|
|
137
|
+
function Start-NodeChild([string]$nodeExe, [string]$workDir, [string]$outFile, [string]$errFile) {
|
|
138
|
+
$psi = New-Object System.Diagnostics.ProcessStartInfo
|
|
139
|
+
$psi.FileName = $nodeExe
|
|
140
|
+
$psi.Arguments = 'server.js'
|
|
141
|
+
$psi.WorkingDirectory = $workDir
|
|
142
|
+
$psi.UseShellExecute = $false
|
|
143
|
+
$psi.RedirectStandardOutput = $true
|
|
144
|
+
$psi.RedirectStandardError = $true
|
|
145
|
+
$psi.CreateNoWindow = $true
|
|
146
|
+
# Env (PORT, HOSTNAME, NODE_ENV set above) is inherited by default.
|
|
147
|
+
|
|
148
|
+
$proc = New-Object System.Diagnostics.Process
|
|
149
|
+
$proc.StartInfo = $psi
|
|
150
|
+
$proc.EnableRaisingEvents = $true
|
|
151
|
+
|
|
152
|
+
# StreamWriters with AutoFlush=true so every line lands on disk immediately.
|
|
153
|
+
$outFs = [System.IO.File]::Open($outFile, [System.IO.FileMode]::Append, [System.IO.FileAccess]::Write, [System.IO.FileShare]::Read)
|
|
154
|
+
$errFs = [System.IO.File]::Open($errFile, [System.IO.FileMode]::Append, [System.IO.FileAccess]::Write, [System.IO.FileShare]::Read)
|
|
155
|
+
$outSw = New-Object System.IO.StreamWriter($outFs, [System.Text.Encoding]::UTF8)
|
|
156
|
+
$errSw = New-Object System.IO.StreamWriter($errFs, [System.Text.Encoding]::UTF8)
|
|
157
|
+
$outSw.AutoFlush = $true
|
|
158
|
+
$errSw.AutoFlush = $true
|
|
159
|
+
|
|
160
|
+
$outEvent = Register-ObjectEvent -InputObject $proc -EventName OutputDataReceived -MessageData $outSw -Action {
|
|
161
|
+
if ($EventArgs.Data -ne $null) { $Event.MessageData.WriteLine($EventArgs.Data) }
|
|
162
|
+
}
|
|
163
|
+
$errEvent = Register-ObjectEvent -InputObject $proc -EventName ErrorDataReceived -MessageData $errSw -Action {
|
|
164
|
+
if ($EventArgs.Data -ne $null) { $Event.MessageData.WriteLine($EventArgs.Data) }
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
if (-not $proc.Start()) { return $null }
|
|
168
|
+
$proc.BeginOutputReadLine()
|
|
169
|
+
$proc.BeginErrorReadLine()
|
|
170
|
+
|
|
171
|
+
return [PSCustomObject]@{
|
|
172
|
+
Process = $proc
|
|
173
|
+
OutWriter = $outSw
|
|
174
|
+
ErrWriter = $errSw
|
|
175
|
+
OutFs = $outFs
|
|
176
|
+
ErrFs = $errFs
|
|
177
|
+
OutEvent = $outEvent
|
|
178
|
+
ErrEvent = $errEvent
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
|
|
129
182
|
# Supervisor loop: respawn server.js if it exits. Bail after too many rapid
|
|
130
|
-
# restarts so Task Scheduler can
|
|
183
|
+
# restarts (3 in 60s) so Task Scheduler can decide. With an encrypted master
|
|
184
|
+
# key, every restart costs the user a manual PIN entry, so we prefer to fail
|
|
185
|
+
# loudly rather than churn silently.
|
|
131
186
|
$restartCount = 0
|
|
132
187
|
$windowStart = Get-Date
|
|
133
188
|
|
|
134
189
|
while ($true) {
|
|
135
190
|
Write-Log "Starting 'node server.js' on http://127.0.0.1:$Port (out=$ServerOut)"
|
|
136
|
-
$
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
-NoNewWindow `
|
|
140
|
-
-PassThru `
|
|
141
|
-
-RedirectStandardOutput $ServerOut `
|
|
142
|
-
-RedirectStandardError $ServerErr
|
|
143
|
-
if (-not $proc) {
|
|
144
|
-
Write-Log "FATAL: Start-Process returned null for node server.js"
|
|
191
|
+
$child = Start-NodeChild -nodeExe $node -workDir $InstallDir -outFile $ServerOut -errFile $ServerErr
|
|
192
|
+
if (-not $child -or -not $child.Process) {
|
|
193
|
+
Write-Log "FATAL: failed to start node server.js"
|
|
145
194
|
Start-Sleep -Seconds 5
|
|
146
195
|
exit 1
|
|
147
196
|
}
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
197
|
+
$childPid = $child.Process.Id
|
|
198
|
+
Write-Log "spawned node PID $childPid"
|
|
199
|
+
|
|
200
|
+
Wait-ProcessExit $childPid
|
|
201
|
+
$exitCode = $null
|
|
202
|
+
try { $exitCode = $child.Process.ExitCode } catch {}
|
|
203
|
+
|
|
204
|
+
# Drain remaining async reads, then unregister handlers and close files.
|
|
205
|
+
try { $child.Process.WaitForExit() } catch {}
|
|
206
|
+
try { Unregister-Event -SourceIdentifier $child.OutEvent.Name -ErrorAction SilentlyContinue } catch {}
|
|
207
|
+
try { Unregister-Event -SourceIdentifier $child.ErrEvent.Name -ErrorAction SilentlyContinue } catch {}
|
|
208
|
+
try { $child.OutWriter.Dispose() } catch {}
|
|
209
|
+
try { $child.ErrWriter.Dispose() } catch {}
|
|
210
|
+
try { $child.OutFs.Dispose() } catch {}
|
|
211
|
+
try { $child.ErrFs.Dispose() } catch {}
|
|
212
|
+
try { $child.Process.Dispose() } catch {}
|
|
213
|
+
|
|
214
|
+
Write-Log "server.js exited (PID $childPid, exit=$exitCode)"
|
|
151
215
|
|
|
152
216
|
if (((Get-Date) - $windowStart).TotalSeconds -gt 60) {
|
|
153
217
|
$restartCount = 0
|
|
154
218
|
$windowStart = Get-Date
|
|
155
219
|
}
|
|
156
220
|
$restartCount++
|
|
157
|
-
if ($restartCount -ge
|
|
221
|
+
if ($restartCount -ge 3) {
|
|
158
222
|
Write-Log "Too many rapid restarts ($restartCount in <60s). Exiting; Task Scheduler will retry."
|
|
159
223
|
exit 1
|
|
160
224
|
}
|