First-run chooser, node shutdown on switch, file picker, export path fix
- First-run: show Start Fresh / Import chooser only when single auto-created identity with no profile (not on every boot without a display name). - Identity switch: shut down old node's endpoint before starting new one. Fixes lockup after multiple switches (zombie background tasks). - File picker: native Browse buttons on export (folder) and import (ZIP file) via tauri-plugin-dialog. - Export path: resolve relative paths against home dir (was using process cwd). - Lightbox close: only close on overlay/image click, not inner form content. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
a349d33422
commit
ec731fdb4b
6 changed files with 171 additions and 15 deletions
|
|
@ -3372,7 +3372,10 @@ $('#export-btn').addEventListener('click', () => {
|
|||
</div>
|
||||
<div style="margin-bottom:0.75rem">
|
||||
<label style="font-size:0.75rem;color:#888">Save to folder:</label>
|
||||
<input id="export-output-dir" type="text" value="Downloads" style="width:100%;margin-top:0.25rem;font-size:0.8rem" />
|
||||
<div style="display:flex;gap:0.25rem;margin-top:0.25rem">
|
||||
<input id="export-output-dir" type="text" value="Downloads" style="flex:1;font-size:0.8rem" />
|
||||
<button class="btn btn-ghost btn-sm" id="export-browse">Browse</button>
|
||||
</div>
|
||||
<p style="font-size:0.65rem;color:#555;margin-top:0.2rem">Relative to your home directory, or absolute path</p>
|
||||
</div>
|
||||
<div style="display:flex;gap:0.5rem;justify-content:center">
|
||||
|
|
@ -3406,6 +3409,12 @@ $('#export-btn').addEventListener('click', () => {
|
|||
overlay.querySelector('#export-go').disabled = false;
|
||||
}
|
||||
});
|
||||
overlay.querySelector('#export-browse').addEventListener('click', async () => {
|
||||
try {
|
||||
const path = await invoke('pick_folder', { title: 'Choose export folder' });
|
||||
if (path) overlay.querySelector('#export-output-dir').value = path;
|
||||
} catch (_) {}
|
||||
});
|
||||
overlay.querySelector('#export-cancel').addEventListener('click', () => overlay.remove());
|
||||
overlay.addEventListener('click', (e) => { if (e.target === overlay) overlay.remove(); });
|
||||
});
|
||||
|
|
@ -3418,8 +3427,11 @@ $('#import-btn').addEventListener('click', () => {
|
|||
overlay.innerHTML = `
|
||||
<div style="background:#1a1a2e;border:1px solid #333;border-radius:12px;padding:1.5rem;max-width:420px;width:90%;text-align:center">
|
||||
<h3 style="color:#7fdbca;margin:0 0 0.75rem">Import Data</h3>
|
||||
<p style="font-size:0.75rem;color:#888;margin-bottom:0.75rem">Enter the path to an ItsGoin export ZIP file.</p>
|
||||
<input id="import-zip-path" type="text" placeholder="/path/to/itsgoin-export.zip" style="width:100%;margin-bottom:0.75rem;font-size:0.8rem" />
|
||||
<p style="font-size:0.75rem;color:#888;margin-bottom:0.75rem">Select an ItsGoin export ZIP file.</p>
|
||||
<div style="display:flex;gap:0.25rem;margin-bottom:0.75rem">
|
||||
<input id="import-zip-path" type="text" placeholder="/path/to/itsgoin-export.zip" style="flex:1;font-size:0.8rem" />
|
||||
<button class="btn btn-ghost btn-sm" id="import-browse">Browse</button>
|
||||
</div>
|
||||
<div id="import-summary-box" style="display:none;text-align:left;background:#111;border-radius:8px;padding:0.75rem;margin-bottom:0.75rem;font-size:0.75rem"></div>
|
||||
<div id="import-action-box" style="display:none;text-align:left;margin-bottom:0.75rem">
|
||||
<label class="checkbox-label" style="font-size:0.8rem"><input type="radio" name="import-action" value="add_identity" /> Add as new identity (requires key in export)</label>
|
||||
|
|
@ -3438,6 +3450,13 @@ $('#import-btn').addEventListener('click', () => {
|
|||
</div>`;
|
||||
document.body.appendChild(overlay);
|
||||
|
||||
overlay.querySelector('#import-browse').addEventListener('click', async () => {
|
||||
try {
|
||||
const path = await invoke('pick_file', { title: 'Select export ZIP', filterName: 'ZIP files', filterExt: ['zip'] });
|
||||
if (path) overlay.querySelector('#import-zip-path').value = path;
|
||||
} catch (_) {}
|
||||
});
|
||||
|
||||
overlay.querySelector('#import-preview').addEventListener('click', async () => {
|
||||
const zipPath = overlay.querySelector('#import-zip-path').value.trim();
|
||||
if (!zipPath) { toast('Enter a ZIP path'); return; }
|
||||
|
|
@ -3646,9 +3665,39 @@ async function init() {
|
|||
}
|
||||
}
|
||||
const info = await loadNodeInfo();
|
||||
// Show first-run chooser only if no profile AND only one identity (auto-created)
|
||||
let isFirstRun = false;
|
||||
if (info && !info.hasProfile) {
|
||||
setupOverlay.classList.remove('hidden');
|
||||
setupName.focus();
|
||||
try {
|
||||
const ids = await invoke('list_identities');
|
||||
isFirstRun = ids.length <= 1;
|
||||
} catch (_) {}
|
||||
}
|
||||
if (isFirstRun) {
|
||||
// First-run chooser: start fresh or import
|
||||
const chooser = document.createElement('div');
|
||||
chooser.className = 'image-lightbox';
|
||||
chooser.style.cursor = 'default';
|
||||
chooser.innerHTML = `
|
||||
<div style="background:#1a1a2e;border:1px solid #333;border-radius:12px;padding:2rem;max-width:360px;width:90%;text-align:center">
|
||||
<h2 style="color:#7fdbca;margin:0 0 0.5rem">Welcome to ItsGoin</h2>
|
||||
<p style="color:#888;font-size:0.85rem;margin-bottom:1.5rem">How would you like to get started?</p>
|
||||
<div style="display:flex;flex-direction:column;gap:0.75rem">
|
||||
<button id="first-run-new" class="btn btn-primary" style="padding:0.75rem">Start Fresh</button>
|
||||
<button id="first-run-import" class="btn btn-ghost" style="padding:0.75rem">Import an Identity</button>
|
||||
</div>
|
||||
</div>`;
|
||||
document.body.appendChild(chooser);
|
||||
chooser.querySelector('#first-run-new').addEventListener('click', () => {
|
||||
chooser.remove();
|
||||
setupOverlay.classList.remove('hidden');
|
||||
setupName.focus();
|
||||
});
|
||||
chooser.querySelector('#first-run-import').addEventListener('click', () => {
|
||||
chooser.remove();
|
||||
// Open the import wizard
|
||||
document.getElementById('import-btn')?.click();
|
||||
});
|
||||
}
|
||||
// Pre-load feed + messages from local DB (instant — no network needed)
|
||||
await loadFeed(true).catch(() => {});
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue