diff --git a/package-lock.json b/package-lock.json index 4d7fd3f..07a2313 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "astra", - "version": "2.2.218", + "version": "2.2.219", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "astra", - "version": "2.2.218", + "version": "2.2.219", "license": "MIT", "dependencies": { "@lmstudio/sdk": "^1.5.0", diff --git a/package.json b/package.json index 67fe063..734bc44 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,7 @@ "name": "astra", "displayName": "Astra", "description": "The personal intelligence layer for Antigravity and VS Code. A private cognitive partner for deep project context, memory, and proactive strategic decision-making.", - "version": "2.2.218", + "version": "2.2.219", "publisher": "g1nation", "license": "MIT", "icon": "assets/icon.png", diff --git a/src/features/calendar/calendarApi.ts b/src/features/calendar/calendarApi.ts index dc7ba6d..1bcfc15 100644 --- a/src/features/calendar/calendarApi.ts +++ b/src/features/calendar/calendarApi.ts @@ -196,7 +196,20 @@ export async function getFreshAccessToken( return { ok: true, accessToken: cfg.accessToken }; } const r = await refreshAccessToken(cfg.clientId, cfg.clientSecret, cfg.refreshToken); - if (!r.ok) return { ok: false, error: r.error }; + if (!r.ok) { + // 리프레시 토큰 자체가 만료/철회된 경우 — raw 구글 에러("Token has been + // expired or revoked.")만 보여주면 사용자가 복구 방법을 알 수 없다. + // 재연결 명령 + 흔한 근본 원인(OAuth 동의 화면 '테스트' 모드 = 7일 만료) 안내. + if (/expired|revoked|invalid_grant/i.test(r.error)) { + return { + ok: false, + error: 'Google OAuth 토큰이 만료/철회되었습니다 — "Astra: Google Calendar OAuth 연결 (쓰기)" 명령으로 재연결하세요. ' + + "(자주 반복되면: Google Cloud Console → OAuth 동의 화면이 '테스트' 모드인지 확인 — 테스트 모드는 리프레시 토큰이 7일마다 만료되며, '앱 게시'로 프로덕션 전환 시 만료되지 않습니다.) " + + `원인: ${r.error}`, + }; + } + return { ok: false, error: r.error }; + } await writeCalendarConfig(context, { accessToken: r.accessToken, accessTokenExpiresAt: r.expiresAt }); return { ok: true, accessToken: r.accessToken }; }