// Copyright: Ankitects Pty Ltd and contributors // License: GNU AGPL, version 3 or later; http://www.gnu.org/licenses/agpl.html import { postRequest } from "@tslib/postrequest"; import { Scheduler } from "@tslib/proto"; interface CustomDataStates { again: Record; hard: Record; good: Record; easy: Record; } async function getSchedulingStatesWithContext(): Promise { return Scheduler.SchedulingStatesWithContext.decode( await postRequest("/_anki/getSchedulingStatesWithContext", ""), ); } async function setSchedulingStates( key: string, states: Scheduler.SchedulingStates, ): Promise { const bytes = Scheduler.SchedulingStates.encode(states).finish(); await postRequest("/_anki/setSchedulingStates", bytes, { key }); } function unpackCustomData(states: Scheduler.SchedulingStates): CustomDataStates { const toObject = (s: string): Record => { try { return JSON.parse(s); } catch { return {}; } }; return { again: toObject(states.current!.customData!), hard: toObject(states.current!.customData!), good: toObject(states.current!.customData!), easy: toObject(states.current!.customData!), }; } function packCustomData( states: Scheduler.SchedulingStates, customData: CustomDataStates, ) { states.again!.customData = JSON.stringify(customData.again); states.hard!.customData = JSON.stringify(customData.hard); states.good!.customData = JSON.stringify(customData.good); states.easy!.customData = JSON.stringify(customData.easy); } export async function mutateNextCardStates( key: string, mutator: ( states: Scheduler.SchedulingStates, customData: CustomDataStates, ctx: Scheduler.SchedulingContext, ) => Promise, ): Promise { const statesWithContext = await getSchedulingStatesWithContext(); const states = statesWithContext.states!; const customData = unpackCustomData(states); await mutator(states, customData, statesWithContext.context!); packCustomData(states, customData); await setSchedulingStates(key, states); }