···107107 <script>
108108 (function() {
109109 try {
110110- // Prevent duplicate execution on mobile (when switching back to browser)
111111- const redirectKey = 'atmosphere_oauth_redirected';
112112- if (sessionStorage.getItem(redirectKey) === 'true') {
113113- // Already redirected, show completion message
114114- document.querySelector('.spinner').style.display = 'none';
115115- document.querySelector('h1').textContent = '✅ Redirected!';
116116- document.getElementById('status').textContent = 'Return to Obsidian to complete login.';
117117- document.getElementById('manual-link').classList.add('show');
118118- return;
119119- }
120120-121110 // extract OAuth parameters from URL hash (not search string)
122111 const params = new URLSearchParams(window.location.hash.slice(1));
123112···126115 // store the URI for manual copy
127116 document.getElementById('link-text').textContent = obsidianUri;
128117129129- // Mark as redirected BEFORE the redirect to prevent race conditions
130130- sessionStorage.setItem(redirectKey, 'true');
131131-132132- // Small delay to ensure any pending IndexedDB writes complete
133133- // This is important on mobile where the browser may suspend the tab
134134- setTimeout(function() {
135135- window.location.href = obsidianUri;
136136- }, 100);
118118+ window.location.href = obsidianUri;
137119138120 setTimeout(function() {
139121 const spinner = document.querySelector('.spinner');
+6-1
src/lib/oauth/oauth.ts
···6565 new Notice('Continue login in the browser');
66666767 const params = await waitForCallback;
6868- await new Promise((resolve) => setTimeout(resolve, 300));
6868+6969+ console.log('[OAuth] Callback received, params:', params.toString());
7070+ console.log('[OAuth] Waiting for IndexedDB to settle...');
7171+ await new Promise((resolve) => setTimeout(resolve, 1000));
69727373+ console.log('[OAuth] Starting token exchange...');
7074 const { session } = await finalizeAuthorization(params);
7575+ console.log('[OAuth] Token exchange successful!');
7176 return session;
7277 }
7378