managarten/packages/shared-stores/src/toggle-field.ts
Till JS ead4e71af5 feat(shared-ui,shared-stores): add FavoriteButton component and toggleField utility
FavoriteButton: reusable heart/star/pin toggle with filled/outline states,
accessible labels, configurable colors. toggleField: generic boolean field
toggle for Dexie records (isFavorite, isPinned, etc.) with timestamp.
Includes 11 tests (6 FavoriteButton + 5 toggleField).

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-02 16:16:23 +02:00

42 lines
1.1 KiB
TypeScript

/**
* Generic boolean field toggle for Dexie tables.
*
* Standardizes the common pattern of toggling a boolean field (isFavorite, isPinned, etc.)
* on a record in IndexedDB. Reads current value, flips it, updates with timestamp.
*
* @example
* ```typescript
* import { toggleField } from '@manacore/shared-stores';
* import { db } from '$lib/data/database';
*
* // In your store:
* async function toggleFavorite(id: string) {
* return toggleField(db.table('contacts'), id, 'isFavorite');
* }
* ```
*/
import type { Table } from 'dexie';
/**
* Toggle a boolean field on a Dexie record.
* @returns The new value of the field after toggling.
*/
export async function toggleField<T>(
table: Table<T, string>,
id: string,
field: string
): Promise<boolean> {
const record = await table.get(id);
if (!record) throw new Error(`Record ${id} not found`);
const current = !!(record as Record<string, unknown>)[field];
const newValue = !current;
await table.update(id, {
[field]: newValue,
updatedAt: new Date().toISOString(),
} as Partial<T>);
return newValue;
}