mirror of
https://github.com/MBombeck/HealthLog.git
synced 2026-11-08 20:42:43 +00:00
Google turns the legacy Fitbit Web API off on 30 October 2026 (support ended on 30 September). From that day the hourly poll, the backfill, the sleep repair and the token refresh make no call, the connect, sync and test routes refuse with `provider_retired`, and the connection reads as not connected to the health read and the watchdog, so the shutdown pages nobody and asks nobody to reconnect. The connection row and everything it imported stay. The status envelope publishes `retirement` on the Fitbit entry (the day, whether it has come, the successor), and the Fitbit card shows when the connection stops, how to move to Google Health (same devices, one more consent, tokens cannot be carried over) and that the data stays; sync and connect grey out after the day. Both integrations can run side by side meanwhile: every type Fitbit writes is laddered with Fitbit just above Google Health, so a day both deliver counts once. The test setups pin the turndown off, so the Fitbit suites do not turn red on the day; the turndown's own tests flip it.
56 lines
2.1 KiB
TypeScript
56 lines
2.1 KiB
TypeScript
import { afterEach, inject, vi } from "vitest";
|
|
|
|
declare module "vitest" {
|
|
export interface ProvidedContext {
|
|
integrationDatabaseUrl: string;
|
|
}
|
|
}
|
|
|
|
process.env.DATABASE_URL = inject("integrationDatabaseUrl");
|
|
process.env.ENCRYPTION_KEY =
|
|
"0000000000000000000000000000000000000000000000000000000000000000";
|
|
delete process.env.ENCRYPTION_KEYS;
|
|
delete process.env.ENCRYPTION_ACTIVE_KEY_ID;
|
|
process.env.API_TOKEN_HMAC_KEY = "integration-test-hmac-key-32-bytes-minimum";
|
|
process.env.SESSION_SECRET = "integration-test-session-secret-32-bytes";
|
|
|
|
/**
|
|
* Leave no background work in flight when an integration test ends — the same
|
|
* contract the unit setup keeps, for the same reason: detached background work
|
|
* logs on its own handle, and a console write that reaches vitest after the
|
|
* worker has begun closing its RPC channel fails the run with
|
|
* `EnvironmentTeardownError: Closing rpc while "onUserConsoleLog" was pending`.
|
|
* This suite has its own config and its own setup file, so the unit hook does
|
|
* not cover it.
|
|
*
|
|
* The import is deferred: this file's whole job is to bridge DATABASE_URL into
|
|
* the worker BEFORE any application module reads it at import time, and a
|
|
* static import here would pull part of the application tree in first.
|
|
*/
|
|
afterEach(async () => {
|
|
const { settleBackgroundTasks } =
|
|
await import("@/lib/logging/background-tasks");
|
|
await settleBackgroundTasks();
|
|
});
|
|
|
|
/**
|
|
* The same pin the unit setup applies (see `vitest.setup.ts`): the Fitbit
|
|
* suites run before the Web API turndown, whatever the real date, and a test
|
|
* about the turndown flips `isFitbitRetired` itself. The factory imports the
|
|
* module lazily, so nothing of the application loads before DATABASE_URL is
|
|
* bridged above.
|
|
*/
|
|
vi.mock("@/lib/fitbit/retirement", async (importOriginal) => {
|
|
const actual =
|
|
await importOriginal<typeof import("@/lib/fitbit/retirement")>();
|
|
const isFitbitRetired = vi.fn((_now?: Date) => false);
|
|
return {
|
|
...actual,
|
|
isFitbitRetired,
|
|
fitbitRetirement: vi.fn((now?: Date) => ({
|
|
...actual.fitbitRetirement(now),
|
|
ended: isFitbitRetired(now),
|
|
})),
|
|
};
|
|
});
|