mirror of
https://github.com/ankitects/anki.git
synced 2025-09-18 22:12:21 -04:00
split out decks, deckconfig, notes, notetypes
This commit is contained in:
parent
18851ace47
commit
9e0a295ab9
20 changed files with 733 additions and 683 deletions
|
@ -7,34 +7,10 @@ package anki.backend;
|
||||||
|
|
||||||
import "anki/generic.proto";
|
import "anki/generic.proto";
|
||||||
import "anki/cards.proto";
|
import "anki/cards.proto";
|
||||||
|
import "anki/decks.proto";
|
||||||
import "anki/collection.proto";
|
import "anki/collection.proto";
|
||||||
|
import "anki/notes.proto";
|
||||||
// IDs used in RPC calls
|
import "anki/notetypes.proto";
|
||||||
///////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
message NotetypeId {
|
|
||||||
int64 ntid = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message NoteId {
|
|
||||||
int64 nid = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message NoteIds {
|
|
||||||
repeated int64 note_ids = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message DeckId {
|
|
||||||
int64 did = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message DeckIds {
|
|
||||||
repeated int64 dids = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message DeckConfigId {
|
|
||||||
int64 dcid = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Backend methods
|
// Backend methods
|
||||||
///////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////
|
||||||
|
@ -66,15 +42,15 @@ service SchedulingService {
|
||||||
rpc StudiedTodayMessage(StudiedTodayMessageRequest) returns (generic.String);
|
rpc StudiedTodayMessage(StudiedTodayMessageRequest) returns (generic.String);
|
||||||
rpc UpdateStats(UpdateStatsRequest) returns (generic.Empty);
|
rpc UpdateStats(UpdateStatsRequest) returns (generic.Empty);
|
||||||
rpc ExtendLimits(ExtendLimitsRequest) returns (generic.Empty);
|
rpc ExtendLimits(ExtendLimitsRequest) returns (generic.Empty);
|
||||||
rpc CountsForDeckToday(DeckId) returns (CountsForDeckTodayResponse);
|
rpc CountsForDeckToday(decks.DeckId) returns (CountsForDeckTodayResponse);
|
||||||
rpc CongratsInfo(generic.Empty) returns (CongratsInfoResponse);
|
rpc CongratsInfo(generic.Empty) returns (CongratsInfoResponse);
|
||||||
rpc RestoreBuriedAndSuspendedCards(cards.CardIds)
|
rpc RestoreBuriedAndSuspendedCards(cards.CardIds)
|
||||||
returns (collection.OpChanges);
|
returns (collection.OpChanges);
|
||||||
rpc UnburyDeck(UnburyDeckRequest) returns (collection.OpChanges);
|
rpc UnburyDeck(UnburyDeckRequest) returns (collection.OpChanges);
|
||||||
rpc BuryOrSuspendCards(BuryOrSuspendCardsRequest)
|
rpc BuryOrSuspendCards(BuryOrSuspendCardsRequest)
|
||||||
returns (collection.OpChangesWithCount);
|
returns (collection.OpChangesWithCount);
|
||||||
rpc EmptyFilteredDeck(DeckId) returns (collection.OpChanges);
|
rpc EmptyFilteredDeck(decks.DeckId) returns (collection.OpChanges);
|
||||||
rpc RebuildFilteredDeck(DeckId) returns (collection.OpChangesWithCount);
|
rpc RebuildFilteredDeck(decks.DeckId) returns (collection.OpChangesWithCount);
|
||||||
rpc ScheduleCardsAsNew(ScheduleCardsAsNewRequest)
|
rpc ScheduleCardsAsNew(ScheduleCardsAsNewRequest)
|
||||||
returns (collection.OpChanges);
|
returns (collection.OpChanges);
|
||||||
rpc SetDueDate(SetDueDateRequest) returns (collection.OpChanges);
|
rpc SetDueDate(SetDueDateRequest) returns (collection.OpChanges);
|
||||||
|
@ -88,49 +64,6 @@ service SchedulingService {
|
||||||
rpc GetQueuedCards(GetQueuedCardsRequest) returns (QueuedCards);
|
rpc GetQueuedCards(GetQueuedCardsRequest) returns (QueuedCards);
|
||||||
}
|
}
|
||||||
|
|
||||||
service DecksService {
|
|
||||||
rpc AddDeckLegacy(generic.Json) returns (collection.OpChangesWithId);
|
|
||||||
rpc AddOrUpdateDeckLegacy(AddOrUpdateDeckLegacyRequest) returns (DeckId);
|
|
||||||
rpc DeckTree(DeckTreeRequest) returns (DeckTreeNode);
|
|
||||||
rpc DeckTreeLegacy(generic.Empty) returns (generic.Json);
|
|
||||||
rpc GetAllDecksLegacy(generic.Empty) returns (generic.Json);
|
|
||||||
rpc GetDeckIdByName(generic.String) returns (DeckId);
|
|
||||||
rpc GetDeck(DeckId) returns (Deck);
|
|
||||||
rpc UpdateDeck(Deck) returns (collection.OpChanges);
|
|
||||||
rpc UpdateDeckLegacy(generic.Json) returns (collection.OpChanges);
|
|
||||||
rpc SetDeckCollapsed(SetDeckCollapsedRequest) returns (collection.OpChanges);
|
|
||||||
rpc GetDeckLegacy(DeckId) returns (generic.Json);
|
|
||||||
rpc GetDeckNames(GetDeckNamesRequest) returns (DeckNames);
|
|
||||||
rpc NewDeckLegacy(generic.Bool) returns (generic.Json);
|
|
||||||
rpc RemoveDecks(DeckIds) returns (collection.OpChangesWithCount);
|
|
||||||
rpc ReparentDecks(ReparentDecksRequest)
|
|
||||||
returns (collection.OpChangesWithCount);
|
|
||||||
rpc RenameDeck(RenameDeckRequest) returns (collection.OpChanges);
|
|
||||||
rpc GetOrCreateFilteredDeck(DeckId) returns (FilteredDeckForUpdate);
|
|
||||||
rpc AddOrUpdateFilteredDeck(FilteredDeckForUpdate)
|
|
||||||
returns (collection.OpChangesWithId);
|
|
||||||
rpc FilteredDeckOrderLabels(generic.Empty) returns (generic.StringList);
|
|
||||||
rpc SetCurrentDeck(DeckId) returns (collection.OpChanges);
|
|
||||||
rpc GetCurrentDeck(generic.Empty) returns (Deck);
|
|
||||||
}
|
|
||||||
|
|
||||||
service NotesService {
|
|
||||||
rpc NewNote(NotetypeId) returns (Note);
|
|
||||||
rpc AddNote(AddNoteRequest) returns (AddNoteResponse);
|
|
||||||
rpc DefaultsForAdding(DefaultsForAddingRequest) returns (DeckAndNotetype);
|
|
||||||
rpc DefaultDeckForNotetype(NotetypeId) returns (DeckId);
|
|
||||||
rpc UpdateNote(UpdateNoteRequest) returns (collection.OpChanges);
|
|
||||||
rpc GetNote(NoteId) returns (Note);
|
|
||||||
rpc RemoveNotes(RemoveNotesRequest) returns (collection.OpChangesWithCount);
|
|
||||||
rpc ClozeNumbersInNote(Note) returns (ClozeNumbersInNoteResponse);
|
|
||||||
rpc AfterNoteUpdates(AfterNoteUpdatesRequest)
|
|
||||||
returns (collection.OpChangesWithCount);
|
|
||||||
rpc FieldNamesForNotes(FieldNamesForNotesRequest)
|
|
||||||
returns (FieldNamesForNotesResponse);
|
|
||||||
rpc NoteFieldsCheck(Note) returns (NoteFieldsCheckResponse);
|
|
||||||
rpc CardsOfNote(NoteId) returns (cards.CardIds);
|
|
||||||
}
|
|
||||||
|
|
||||||
service SyncService {
|
service SyncService {
|
||||||
rpc SyncMedia(SyncAuth) returns (generic.Empty);
|
rpc SyncMedia(SyncAuth) returns (generic.Empty);
|
||||||
rpc AbortSync(generic.Empty) returns (generic.Empty);
|
rpc AbortSync(generic.Empty) returns (generic.Empty);
|
||||||
|
@ -158,28 +91,6 @@ service ConfigService {
|
||||||
rpc SetPreferences(Preferences) returns (collection.OpChanges);
|
rpc SetPreferences(Preferences) returns (collection.OpChanges);
|
||||||
}
|
}
|
||||||
|
|
||||||
service NotetypesService {
|
|
||||||
rpc AddNotetype(Notetype) returns (collection.OpChangesWithId);
|
|
||||||
rpc UpdateNotetype(Notetype) returns (collection.OpChanges);
|
|
||||||
rpc AddNotetypeLegacy(generic.Json) returns (collection.OpChangesWithId);
|
|
||||||
rpc UpdateNotetypeLegacy(generic.Json) returns (collection.OpChanges);
|
|
||||||
rpc AddOrUpdateNotetype(AddOrUpdateNotetypeRequest) returns (NotetypeId);
|
|
||||||
rpc GetStockNotetypeLegacy(StockNotetype) returns (generic.Json);
|
|
||||||
rpc GetNotetype(NotetypeId) returns (Notetype);
|
|
||||||
rpc GetNotetypeLegacy(NotetypeId) returns (generic.Json);
|
|
||||||
rpc GetNotetypeNames(generic.Empty) returns (NotetypeNames);
|
|
||||||
rpc GetNotetypeNamesAndCounts(generic.Empty) returns (NotetypeUseCounts);
|
|
||||||
rpc GetNotetypeIdByName(generic.String) returns (NotetypeId);
|
|
||||||
rpc RemoveNotetype(NotetypeId) returns (collection.OpChanges);
|
|
||||||
rpc GetAuxNotetypeConfigKey(GetAuxConfigKeyRequest) returns (generic.String);
|
|
||||||
rpc GetAuxTemplateConfigKey(GetAuxTemplateConfigKeyRequest)
|
|
||||||
returns (generic.String);
|
|
||||||
rpc GetSingleNotetypeOfNotes(NoteIds) returns (NotetypeId);
|
|
||||||
rpc GetChangeNotetypeInfo(GetChangeNotetypeInfoRequest)
|
|
||||||
returns (ChangeNotetypeInfo);
|
|
||||||
rpc ChangeNotetype(ChangeNotetypeRequest) returns (collection.OpChanges);
|
|
||||||
}
|
|
||||||
|
|
||||||
service CardRenderingService {
|
service CardRenderingService {
|
||||||
rpc ExtractAVTags(ExtractAVTagsRequest) returns (ExtractAVTagsResponse);
|
rpc ExtractAVTags(ExtractAVTagsRequest) returns (ExtractAVTagsResponse);
|
||||||
rpc ExtractLatex(ExtractLatexRequest) returns (ExtractLatexResponse);
|
rpc ExtractLatex(ExtractLatexRequest) returns (ExtractLatexResponse);
|
||||||
|
@ -194,18 +105,6 @@ service CardRenderingService {
|
||||||
rpc RenderMarkdown(RenderMarkdownRequest) returns (generic.String);
|
rpc RenderMarkdown(RenderMarkdownRequest) returns (generic.String);
|
||||||
}
|
}
|
||||||
|
|
||||||
service DeckConfigService {
|
|
||||||
rpc AddOrUpdateDeckConfigLegacy(generic.Json) returns (DeckConfigId);
|
|
||||||
rpc GetDeckConfig(DeckConfigId) returns (DeckConfig);
|
|
||||||
rpc AllDeckConfigLegacy(generic.Empty) returns (generic.Json);
|
|
||||||
rpc GetDeckConfigLegacy(DeckConfigId) returns (generic.Json);
|
|
||||||
rpc NewDeckConfigLegacy(generic.Empty) returns (generic.Json);
|
|
||||||
rpc RemoveDeckConfig(DeckConfigId) returns (generic.Empty);
|
|
||||||
rpc GetDeckConfigsForUpdate(DeckId) returns (DeckConfigsForUpdate);
|
|
||||||
rpc UpdateDeckConfigs(UpdateDeckConfigsRequest)
|
|
||||||
returns (collection.OpChanges);
|
|
||||||
}
|
|
||||||
|
|
||||||
service TagsService {
|
service TagsService {
|
||||||
rpc ClearUnusedTags(generic.Empty) returns (collection.OpChangesWithCount);
|
rpc ClearUnusedTags(generic.Empty) returns (collection.OpChangesWithCount);
|
||||||
rpc AllTags(generic.Empty) returns (generic.StringList);
|
rpc AllTags(generic.Empty) returns (generic.StringList);
|
||||||
|
@ -250,257 +149,6 @@ service MediaService {
|
||||||
rpc RestoreTrash(generic.Empty) returns (generic.Empty);
|
rpc RestoreTrash(generic.Empty) returns (generic.Empty);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Protobuf stored in .anki2 files
|
|
||||||
// These should be moved to a separate file in the future
|
|
||||||
///////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
message DeckConfig {
|
|
||||||
message Config {
|
|
||||||
enum NewCardInsertOrder {
|
|
||||||
NEW_CARD_INSERT_ORDER_DUE = 0;
|
|
||||||
NEW_CARD_INSERT_ORDER_RANDOM = 1;
|
|
||||||
}
|
|
||||||
enum NewCardGatherPriority {
|
|
||||||
NEW_CARD_GATHER_PRIORITY_DECK = 0;
|
|
||||||
NEW_CARD_GATHER_PRIORITY_LOWEST_POSITION = 1;
|
|
||||||
NEW_CARD_GATHER_PRIORITY_HIGHEST_POSITION = 2;
|
|
||||||
}
|
|
||||||
enum NewCardSortOrder {
|
|
||||||
NEW_CARD_SORT_ORDER_TEMPLATE_THEN_LOWEST_POSITION = 0;
|
|
||||||
NEW_CARD_SORT_ORDER_TEMPLATE_THEN_HIGHEST_POSITION = 1;
|
|
||||||
NEW_CARD_SORT_ORDER_TEMPLATE_THEN_RANDOM = 2;
|
|
||||||
NEW_CARD_SORT_ORDER_LOWEST_POSITION = 3;
|
|
||||||
NEW_CARD_SORT_ORDER_HIGHEST_POSITION = 4;
|
|
||||||
NEW_CARD_SORT_ORDER_RANDOM = 5;
|
|
||||||
}
|
|
||||||
enum ReviewCardOrder {
|
|
||||||
REVIEW_CARD_ORDER_DAY = 0;
|
|
||||||
REVIEW_CARD_ORDER_DAY_THEN_DECK = 1;
|
|
||||||
REVIEW_CARD_ORDER_DECK_THEN_DAY = 2;
|
|
||||||
REVIEW_CARD_ORDER_INTERVALS_ASCENDING = 3;
|
|
||||||
REVIEW_CARD_ORDER_INTERVALS_DESCENDING = 4;
|
|
||||||
// REVIEW_CARD_ORDER_RELATIVE_OVERDUE = 3;
|
|
||||||
}
|
|
||||||
enum ReviewMix {
|
|
||||||
REVIEW_MIX_MIX_WITH_REVIEWS = 0;
|
|
||||||
REVIEW_MIX_AFTER_REVIEWS = 1;
|
|
||||||
REVIEW_MIX_BEFORE_REVIEWS = 2;
|
|
||||||
}
|
|
||||||
enum LeechAction {
|
|
||||||
LEECH_ACTION_SUSPEND = 0;
|
|
||||||
LEECH_ACTION_TAG_ONLY = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
repeated float learn_steps = 1;
|
|
||||||
repeated float relearn_steps = 2;
|
|
||||||
|
|
||||||
reserved 3 to 8;
|
|
||||||
|
|
||||||
uint32 new_per_day = 9;
|
|
||||||
uint32 reviews_per_day = 10;
|
|
||||||
uint32 new_per_day_minimum = 29;
|
|
||||||
|
|
||||||
float initial_ease = 11;
|
|
||||||
float easy_multiplier = 12;
|
|
||||||
float hard_multiplier = 13;
|
|
||||||
float lapse_multiplier = 14;
|
|
||||||
float interval_multiplier = 15;
|
|
||||||
|
|
||||||
uint32 maximum_review_interval = 16;
|
|
||||||
uint32 minimum_lapse_interval = 17;
|
|
||||||
|
|
||||||
uint32 graduating_interval_good = 18;
|
|
||||||
uint32 graduating_interval_easy = 19;
|
|
||||||
|
|
||||||
NewCardInsertOrder new_card_insert_order = 20;
|
|
||||||
NewCardGatherPriority new_card_gather_priority = 34;
|
|
||||||
NewCardSortOrder new_card_sort_order = 32;
|
|
||||||
ReviewMix new_mix = 30;
|
|
||||||
|
|
||||||
ReviewCardOrder review_order = 33;
|
|
||||||
|
|
||||||
ReviewMix interday_learning_mix = 31;
|
|
||||||
|
|
||||||
LeechAction leech_action = 21;
|
|
||||||
uint32 leech_threshold = 22;
|
|
||||||
|
|
||||||
bool disable_autoplay = 23;
|
|
||||||
uint32 cap_answer_time_to_secs = 24;
|
|
||||||
bool show_timer = 25;
|
|
||||||
bool skip_question_when_replaying_answer = 26;
|
|
||||||
|
|
||||||
bool bury_new = 27;
|
|
||||||
bool bury_reviews = 28;
|
|
||||||
|
|
||||||
bytes other = 255;
|
|
||||||
}
|
|
||||||
|
|
||||||
int64 id = 1;
|
|
||||||
string name = 2;
|
|
||||||
int64 mtime_secs = 3;
|
|
||||||
int32 usn = 4;
|
|
||||||
Config config = 5;
|
|
||||||
}
|
|
||||||
|
|
||||||
message Deck {
|
|
||||||
message Common {
|
|
||||||
bool study_collapsed = 1;
|
|
||||||
bool browser_collapsed = 2;
|
|
||||||
|
|
||||||
uint32 last_day_studied = 3;
|
|
||||||
int32 new_studied = 4;
|
|
||||||
int32 review_studied = 5;
|
|
||||||
int32 milliseconds_studied = 7;
|
|
||||||
|
|
||||||
// previously set in the v1 scheduler,
|
|
||||||
// but not currently used for anything
|
|
||||||
int32 learning_studied = 6;
|
|
||||||
|
|
||||||
reserved 8 to 13;
|
|
||||||
|
|
||||||
bytes other = 255;
|
|
||||||
}
|
|
||||||
message Normal {
|
|
||||||
int64 config_id = 1;
|
|
||||||
uint32 extend_new = 2;
|
|
||||||
uint32 extend_review = 3;
|
|
||||||
string description = 4;
|
|
||||||
bool markdown_description = 5;
|
|
||||||
|
|
||||||
reserved 6 to 11;
|
|
||||||
}
|
|
||||||
message Filtered {
|
|
||||||
message SearchTerm {
|
|
||||||
enum Order {
|
|
||||||
OLDEST_REVIEWED_FIRST = 0;
|
|
||||||
RANDOM = 1;
|
|
||||||
INTERVALS_ASCENDING = 2;
|
|
||||||
INTERVALS_DESCENDING = 3;
|
|
||||||
LAPSES = 4;
|
|
||||||
ADDED = 5;
|
|
||||||
DUE = 6;
|
|
||||||
REVERSE_ADDED = 7;
|
|
||||||
DUE_PRIORITY = 8;
|
|
||||||
}
|
|
||||||
|
|
||||||
string search = 1;
|
|
||||||
uint32 limit = 2;
|
|
||||||
Order order = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool reschedule = 1;
|
|
||||||
repeated SearchTerm search_terms = 2;
|
|
||||||
// v1 scheduler only
|
|
||||||
repeated float delays = 3;
|
|
||||||
// v2 scheduler only
|
|
||||||
uint32 preview_delay = 4;
|
|
||||||
}
|
|
||||||
// a container to store the deck specifics in the DB
|
|
||||||
// as a tagged enum
|
|
||||||
message KindContainer {
|
|
||||||
oneof kind {
|
|
||||||
Normal normal = 1;
|
|
||||||
Filtered filtered = 2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int64 id = 1;
|
|
||||||
string name = 2;
|
|
||||||
int64 mtime_secs = 3;
|
|
||||||
int32 usn = 4;
|
|
||||||
Common common = 5;
|
|
||||||
// the specifics are inlined here when sending data to clients,
|
|
||||||
// as otherwise an extra level of indirection would be required
|
|
||||||
oneof kind {
|
|
||||||
Normal normal = 6;
|
|
||||||
Filtered filtered = 7;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
message Notetype {
|
|
||||||
message Config {
|
|
||||||
enum Kind {
|
|
||||||
KIND_NORMAL = 0;
|
|
||||||
KIND_CLOZE = 1;
|
|
||||||
}
|
|
||||||
message CardRequirement {
|
|
||||||
enum Kind {
|
|
||||||
KIND_NONE = 0;
|
|
||||||
KIND_ANY = 1;
|
|
||||||
KIND_ALL = 2;
|
|
||||||
}
|
|
||||||
uint32 card_ord = 1;
|
|
||||||
Kind kind = 2;
|
|
||||||
repeated uint32 field_ords = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
Kind kind = 1;
|
|
||||||
uint32 sort_field_idx = 2;
|
|
||||||
string css = 3;
|
|
||||||
/// This is now stored separately; retrieve with DefaultsForAdding()
|
|
||||||
int64 target_deck_id_unused = 4;
|
|
||||||
string latex_pre = 5;
|
|
||||||
string latex_post = 6;
|
|
||||||
bool latex_svg = 7;
|
|
||||||
repeated CardRequirement reqs = 8;
|
|
||||||
|
|
||||||
bytes other = 255;
|
|
||||||
}
|
|
||||||
message Field {
|
|
||||||
message Config {
|
|
||||||
bool sticky = 1;
|
|
||||||
bool rtl = 2;
|
|
||||||
string font_name = 3;
|
|
||||||
uint32 font_size = 4;
|
|
||||||
|
|
||||||
bytes other = 255;
|
|
||||||
}
|
|
||||||
generic.OptionalUInt32 ord = 1;
|
|
||||||
string name = 2;
|
|
||||||
Config config = 5;
|
|
||||||
}
|
|
||||||
message Template {
|
|
||||||
message Config {
|
|
||||||
string q_format = 1;
|
|
||||||
string a_format = 2;
|
|
||||||
string q_format_browser = 3;
|
|
||||||
string a_format_browser = 4;
|
|
||||||
int64 target_deck_id = 5;
|
|
||||||
string browser_font_name = 6;
|
|
||||||
uint32 browser_font_size = 7;
|
|
||||||
|
|
||||||
bytes other = 255;
|
|
||||||
}
|
|
||||||
|
|
||||||
generic.OptionalUInt32 ord = 1;
|
|
||||||
string name = 2;
|
|
||||||
int64 mtime_secs = 3;
|
|
||||||
sint32 usn = 4;
|
|
||||||
Config config = 5;
|
|
||||||
}
|
|
||||||
|
|
||||||
int64 id = 1;
|
|
||||||
string name = 2;
|
|
||||||
int64 mtime_secs = 3;
|
|
||||||
sint32 usn = 4;
|
|
||||||
Config config = 7;
|
|
||||||
repeated Field fields = 8;
|
|
||||||
repeated Template templates = 9;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Database objects
|
|
||||||
///////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
message Note {
|
|
||||||
int64 id = 1;
|
|
||||||
string guid = 2;
|
|
||||||
int64 notetype_id = 3;
|
|
||||||
uint32 mtime_secs = 4;
|
|
||||||
int32 usn = 5;
|
|
||||||
repeated string tags = 6;
|
|
||||||
repeated string fields = 7;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Backend
|
// Backend
|
||||||
///////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
@ -551,43 +199,20 @@ message SchedTimingTodayResponse {
|
||||||
int64 next_day_at = 2;
|
int64 next_day_at = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
message DeckTreeRequest {
|
|
||||||
// if non-zero, counts for the provided timestamp will be included
|
|
||||||
int64 now = 1;
|
|
||||||
int64 top_deck_id = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message DeckTreeNode {
|
|
||||||
int64 deck_id = 1;
|
|
||||||
string name = 2;
|
|
||||||
uint32 level = 4;
|
|
||||||
bool collapsed = 5;
|
|
||||||
|
|
||||||
uint32 review_count = 6;
|
|
||||||
uint32 learn_count = 7;
|
|
||||||
uint32 new_count = 8;
|
|
||||||
|
|
||||||
bool filtered = 16;
|
|
||||||
|
|
||||||
// low index so key can be packed into a byte, but at bottom
|
|
||||||
// to make debug output easier to read
|
|
||||||
repeated DeckTreeNode children = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
message RenderExistingCardRequest {
|
message RenderExistingCardRequest {
|
||||||
int64 card_id = 1;
|
int64 card_id = 1;
|
||||||
bool browser = 2;
|
bool browser = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
message RenderUncommittedCardRequest {
|
message RenderUncommittedCardRequest {
|
||||||
Note note = 1;
|
notes.Note note = 1;
|
||||||
uint32 card_ord = 2;
|
uint32 card_ord = 2;
|
||||||
Notetype.Template template = 3;
|
notetypes.Notetype.Template template = 3;
|
||||||
bool fill_empty = 4;
|
bool fill_empty = 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
message RenderUncommittedCardLegacyRequest {
|
message RenderUncommittedCardLegacyRequest {
|
||||||
Note note = 1;
|
notes.Note note = 1;
|
||||||
uint32 card_ord = 2;
|
uint32 card_ord = 2;
|
||||||
bytes template = 3;
|
bytes template = 3;
|
||||||
bool fill_empty = 4;
|
bool fill_empty = 4;
|
||||||
|
@ -782,53 +407,11 @@ message ReplaceSearchNodeRequest {
|
||||||
SearchNode replacement_node = 2;
|
SearchNode replacement_node = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
message DeckConfigsForUpdate {
|
|
||||||
message ConfigWithExtra {
|
|
||||||
DeckConfig config = 1;
|
|
||||||
uint32 use_count = 2;
|
|
||||||
}
|
|
||||||
message CurrentDeck {
|
|
||||||
string name = 1;
|
|
||||||
int64 config_id = 2;
|
|
||||||
repeated int64 parent_config_ids = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
repeated ConfigWithExtra all_config = 1;
|
|
||||||
CurrentDeck current_deck = 2;
|
|
||||||
DeckConfig defaults = 3;
|
|
||||||
bool schema_modified = 4;
|
|
||||||
bool v3_scheduler = 5;
|
|
||||||
bool have_addons = 6;
|
|
||||||
// only applies to v3 scheduler
|
|
||||||
string card_state_customizer = 7;
|
|
||||||
}
|
|
||||||
|
|
||||||
message UpdateDeckConfigsRequest {
|
|
||||||
int64 target_deck_id = 1;
|
|
||||||
/// Unchanged, non-selected configs can be omitted. Deck will
|
|
||||||
/// be set to whichever entry comes last.
|
|
||||||
repeated DeckConfig configs = 2;
|
|
||||||
repeated int64 removed_config_ids = 3;
|
|
||||||
bool apply_to_children = 4;
|
|
||||||
string card_state_customizer = 5;
|
|
||||||
}
|
|
||||||
|
|
||||||
message SetTagCollapsedRequest {
|
message SetTagCollapsedRequest {
|
||||||
string name = 1;
|
string name = 1;
|
||||||
bool collapsed = 2;
|
bool collapsed = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
message SetDeckCollapsedRequest {
|
|
||||||
enum Scope {
|
|
||||||
REVIEWER = 0;
|
|
||||||
BROWSER = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
int64 deck_id = 1;
|
|
||||||
bool collapsed = 2;
|
|
||||||
Scope scope = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
message GetChangedTagsResponse {
|
message GetChangedTagsResponse {
|
||||||
repeated string tags = 1;
|
repeated string tags = 1;
|
||||||
}
|
}
|
||||||
|
@ -856,57 +439,6 @@ message SetConfigJsonRequest {
|
||||||
bool undoable = 3;
|
bool undoable = 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
message StockNotetype {
|
|
||||||
enum Kind {
|
|
||||||
BASIC = 0;
|
|
||||||
BASIC_AND_REVERSED = 1;
|
|
||||||
BASIC_OPTIONAL_REVERSED = 2;
|
|
||||||
BASIC_TYPING = 3;
|
|
||||||
CLOZE = 4;
|
|
||||||
}
|
|
||||||
|
|
||||||
Kind kind = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message NotetypeNames {
|
|
||||||
repeated NotetypeNameId entries = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message NotetypeUseCounts {
|
|
||||||
repeated NotetypeNameIdUseCount entries = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message NotetypeNameId {
|
|
||||||
int64 id = 1;
|
|
||||||
string name = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message NotetypeNameIdUseCount {
|
|
||||||
int64 id = 1;
|
|
||||||
string name = 2;
|
|
||||||
uint32 use_count = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
message AddOrUpdateNotetypeRequest {
|
|
||||||
bytes json = 1;
|
|
||||||
bool preserve_usn_and_mtime = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message AddNoteRequest {
|
|
||||||
Note note = 1;
|
|
||||||
int64 deck_id = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message AddNoteResponse {
|
|
||||||
int64 note_id = 1;
|
|
||||||
collection.OpChanges changes = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message UpdateNoteRequest {
|
|
||||||
Note note = 1;
|
|
||||||
bool skip_undo_entry = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message EmptyCardsReport {
|
message EmptyCardsReport {
|
||||||
message NoteWithEmptyCards {
|
message NoteWithEmptyCards {
|
||||||
int64 note_id = 1;
|
int64 note_id = 1;
|
||||||
|
@ -917,28 +449,6 @@ message EmptyCardsReport {
|
||||||
repeated NoteWithEmptyCards notes = 2;
|
repeated NoteWithEmptyCards notes = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
message DeckNames {
|
|
||||||
repeated DeckNameId entries = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message DeckNameId {
|
|
||||||
int64 id = 1;
|
|
||||||
string name = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message AddOrUpdateDeckLegacyRequest {
|
|
||||||
bytes deck = 1;
|
|
||||||
bool preserve_usn_and_mtime = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message FieldNamesForNotesRequest {
|
|
||||||
repeated int64 nids = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message FieldNamesForNotesResponse {
|
|
||||||
repeated string fields = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message FindAndReplaceRequest {
|
message FindAndReplaceRequest {
|
||||||
repeated int64 nids = 1;
|
repeated int64 nids = 1;
|
||||||
string search = 2;
|
string search = 2;
|
||||||
|
@ -992,12 +502,6 @@ message BrowserRow {
|
||||||
uint32 font_size = 4;
|
uint32 font_size = 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
message AfterNoteUpdatesRequest {
|
|
||||||
repeated int64 nids = 1;
|
|
||||||
bool mark_notes_modified = 2;
|
|
||||||
bool generate_cards = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
message NoteIdsAndTagsRequest {
|
message NoteIdsAndTagsRequest {
|
||||||
repeated int64 note_ids = 1;
|
repeated int64 note_ids = 1;
|
||||||
string tags = 2;
|
string tags = 2;
|
||||||
|
@ -1049,33 +553,6 @@ message Preferences {
|
||||||
Editing editing = 3;
|
Editing editing = 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
message ClozeNumbersInNoteResponse {
|
|
||||||
repeated uint32 numbers = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message GetDeckNamesRequest {
|
|
||||||
bool skip_empty_default = 1;
|
|
||||||
// if unset, implies skip_empty_default
|
|
||||||
bool include_filtered = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message ReparentDecksRequest {
|
|
||||||
repeated int64 deck_ids = 1;
|
|
||||||
int64 new_parent = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message NoteFieldsCheckResponse {
|
|
||||||
enum State {
|
|
||||||
NORMAL = 0;
|
|
||||||
EMPTY = 1;
|
|
||||||
DUPLICATE = 2;
|
|
||||||
MISSING_CLOZE = 3;
|
|
||||||
NOTETYPE_NOT_CLOZE = 4;
|
|
||||||
FIELD_NOT_CLOZE = 5;
|
|
||||||
}
|
|
||||||
State state = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message SyncLoginRequest {
|
message SyncLoginRequest {
|
||||||
string username = 1;
|
string username = 1;
|
||||||
string password = 2;
|
string password = 2;
|
||||||
|
@ -1131,11 +608,6 @@ message SyncServerMethodRequest {
|
||||||
bytes data = 2;
|
bytes data = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
message RemoveNotesRequest {
|
|
||||||
repeated int64 note_ids = 1;
|
|
||||||
repeated int64 card_ids = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message UpdateStatsRequest {
|
message UpdateStatsRequest {
|
||||||
int64 deck_id = 1;
|
int64 deck_id = 1;
|
||||||
int32 new_delta = 2;
|
int32 new_delta = 2;
|
||||||
|
@ -1403,58 +875,3 @@ message QueuedCards {
|
||||||
uint32 learning_count = 3;
|
uint32 learning_count = 3;
|
||||||
uint32 review_count = 4;
|
uint32 review_count = 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
message DefaultsForAddingRequest {
|
|
||||||
int64 home_deck_of_current_review_card = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
message DeckAndNotetype {
|
|
||||||
int64 deck_id = 1;
|
|
||||||
int64 notetype_id = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message RenameDeckRequest {
|
|
||||||
int64 deck_id = 1;
|
|
||||||
string new_name = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message FilteredDeckForUpdate {
|
|
||||||
int64 id = 1;
|
|
||||||
string name = 2;
|
|
||||||
Deck.Filtered config = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
message GetAuxConfigKeyRequest {
|
|
||||||
int64 id = 1;
|
|
||||||
string key = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message GetAuxTemplateConfigKeyRequest {
|
|
||||||
int64 notetype_id = 1;
|
|
||||||
uint32 card_ordinal = 2;
|
|
||||||
string key = 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
message GetChangeNotetypeInfoRequest {
|
|
||||||
int64 old_notetype_id = 1;
|
|
||||||
int64 new_notetype_id = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
message ChangeNotetypeRequest {
|
|
||||||
repeated int64 note_ids = 1;
|
|
||||||
// -1 is used to represent null, as nullable repeated fields
|
|
||||||
// are unwieldy in protobuf
|
|
||||||
repeated int32 new_fields = 2;
|
|
||||||
repeated int32 new_templates = 3;
|
|
||||||
int64 old_notetype_id = 4;
|
|
||||||
int64 new_notetype_id = 5;
|
|
||||||
int64 current_schema = 6;
|
|
||||||
}
|
|
||||||
|
|
||||||
message ChangeNotetypeInfo {
|
|
||||||
repeated string old_field_names = 1;
|
|
||||||
repeated string old_template_names = 2;
|
|
||||||
repeated string new_field_names = 3;
|
|
||||||
repeated string new_template_names = 4;
|
|
||||||
ChangeNotetypeRequest input = 5;
|
|
||||||
}
|
|
||||||
|
|
145
proto/anki/deckconfig.proto
Normal file
145
proto/anki/deckconfig.proto
Normal file
|
@ -0,0 +1,145 @@
|
||||||
|
// Copyright: Ankitects Pty Ltd and contributors
|
||||||
|
// License: GNU AGPL, version 3 or later; http://www.gnu.org/licenses/agpl.html
|
||||||
|
|
||||||
|
syntax = "proto3";
|
||||||
|
|
||||||
|
package anki.deckconfig;
|
||||||
|
|
||||||
|
import "anki/generic.proto";
|
||||||
|
import "anki/collection.proto";
|
||||||
|
import "anki/decks.proto";
|
||||||
|
|
||||||
|
service DeckConfigService {
|
||||||
|
rpc AddOrUpdateDeckConfigLegacy(generic.Json) returns (DeckConfigId);
|
||||||
|
rpc GetDeckConfig(DeckConfigId) returns (DeckConfig);
|
||||||
|
rpc AllDeckConfigLegacy(generic.Empty) returns (generic.Json);
|
||||||
|
rpc GetDeckConfigLegacy(DeckConfigId) returns (generic.Json);
|
||||||
|
rpc NewDeckConfigLegacy(generic.Empty) returns (generic.Json);
|
||||||
|
rpc RemoveDeckConfig(DeckConfigId) returns (generic.Empty);
|
||||||
|
rpc GetDeckConfigsForUpdate(decks.DeckId) returns (DeckConfigsForUpdate);
|
||||||
|
rpc UpdateDeckConfigs(UpdateDeckConfigsRequest)
|
||||||
|
returns (collection.OpChanges);
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckConfigId {
|
||||||
|
int64 dcid = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckConfig {
|
||||||
|
message Config {
|
||||||
|
enum NewCardInsertOrder {
|
||||||
|
NEW_CARD_INSERT_ORDER_DUE = 0;
|
||||||
|
NEW_CARD_INSERT_ORDER_RANDOM = 1;
|
||||||
|
}
|
||||||
|
enum NewCardGatherPriority {
|
||||||
|
NEW_CARD_GATHER_PRIORITY_DECK = 0;
|
||||||
|
NEW_CARD_GATHER_PRIORITY_LOWEST_POSITION = 1;
|
||||||
|
NEW_CARD_GATHER_PRIORITY_HIGHEST_POSITION = 2;
|
||||||
|
}
|
||||||
|
enum NewCardSortOrder {
|
||||||
|
NEW_CARD_SORT_ORDER_TEMPLATE_THEN_LOWEST_POSITION = 0;
|
||||||
|
NEW_CARD_SORT_ORDER_TEMPLATE_THEN_HIGHEST_POSITION = 1;
|
||||||
|
NEW_CARD_SORT_ORDER_TEMPLATE_THEN_RANDOM = 2;
|
||||||
|
NEW_CARD_SORT_ORDER_LOWEST_POSITION = 3;
|
||||||
|
NEW_CARD_SORT_ORDER_HIGHEST_POSITION = 4;
|
||||||
|
NEW_CARD_SORT_ORDER_RANDOM = 5;
|
||||||
|
}
|
||||||
|
enum ReviewCardOrder {
|
||||||
|
REVIEW_CARD_ORDER_DAY = 0;
|
||||||
|
REVIEW_CARD_ORDER_DAY_THEN_DECK = 1;
|
||||||
|
REVIEW_CARD_ORDER_DECK_THEN_DAY = 2;
|
||||||
|
REVIEW_CARD_ORDER_INTERVALS_ASCENDING = 3;
|
||||||
|
REVIEW_CARD_ORDER_INTERVALS_DESCENDING = 4;
|
||||||
|
// REVIEW_CARD_ORDER_RELATIVE_OVERDUE = 3;
|
||||||
|
}
|
||||||
|
enum ReviewMix {
|
||||||
|
REVIEW_MIX_MIX_WITH_REVIEWS = 0;
|
||||||
|
REVIEW_MIX_AFTER_REVIEWS = 1;
|
||||||
|
REVIEW_MIX_BEFORE_REVIEWS = 2;
|
||||||
|
}
|
||||||
|
enum LeechAction {
|
||||||
|
LEECH_ACTION_SUSPEND = 0;
|
||||||
|
LEECH_ACTION_TAG_ONLY = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
repeated float learn_steps = 1;
|
||||||
|
repeated float relearn_steps = 2;
|
||||||
|
|
||||||
|
reserved 3 to 8;
|
||||||
|
|
||||||
|
uint32 new_per_day = 9;
|
||||||
|
uint32 reviews_per_day = 10;
|
||||||
|
uint32 new_per_day_minimum = 29;
|
||||||
|
|
||||||
|
float initial_ease = 11;
|
||||||
|
float easy_multiplier = 12;
|
||||||
|
float hard_multiplier = 13;
|
||||||
|
float lapse_multiplier = 14;
|
||||||
|
float interval_multiplier = 15;
|
||||||
|
|
||||||
|
uint32 maximum_review_interval = 16;
|
||||||
|
uint32 minimum_lapse_interval = 17;
|
||||||
|
|
||||||
|
uint32 graduating_interval_good = 18;
|
||||||
|
uint32 graduating_interval_easy = 19;
|
||||||
|
|
||||||
|
NewCardInsertOrder new_card_insert_order = 20;
|
||||||
|
NewCardGatherPriority new_card_gather_priority = 34;
|
||||||
|
NewCardSortOrder new_card_sort_order = 32;
|
||||||
|
ReviewMix new_mix = 30;
|
||||||
|
|
||||||
|
ReviewCardOrder review_order = 33;
|
||||||
|
|
||||||
|
ReviewMix interday_learning_mix = 31;
|
||||||
|
|
||||||
|
LeechAction leech_action = 21;
|
||||||
|
uint32 leech_threshold = 22;
|
||||||
|
|
||||||
|
bool disable_autoplay = 23;
|
||||||
|
uint32 cap_answer_time_to_secs = 24;
|
||||||
|
bool show_timer = 25;
|
||||||
|
bool skip_question_when_replaying_answer = 26;
|
||||||
|
|
||||||
|
bool bury_new = 27;
|
||||||
|
bool bury_reviews = 28;
|
||||||
|
|
||||||
|
bytes other = 255;
|
||||||
|
}
|
||||||
|
|
||||||
|
int64 id = 1;
|
||||||
|
string name = 2;
|
||||||
|
int64 mtime_secs = 3;
|
||||||
|
int32 usn = 4;
|
||||||
|
Config config = 5;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckConfigsForUpdate {
|
||||||
|
message ConfigWithExtra {
|
||||||
|
DeckConfig config = 1;
|
||||||
|
uint32 use_count = 2;
|
||||||
|
}
|
||||||
|
message CurrentDeck {
|
||||||
|
string name = 1;
|
||||||
|
int64 config_id = 2;
|
||||||
|
repeated int64 parent_config_ids = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
repeated ConfigWithExtra all_config = 1;
|
||||||
|
CurrentDeck current_deck = 2;
|
||||||
|
DeckConfig defaults = 3;
|
||||||
|
bool schema_modified = 4;
|
||||||
|
bool v3_scheduler = 5;
|
||||||
|
bool have_addons = 6;
|
||||||
|
// only applies to v3 scheduler
|
||||||
|
string card_state_customizer = 7;
|
||||||
|
}
|
||||||
|
|
||||||
|
message UpdateDeckConfigsRequest {
|
||||||
|
int64 target_deck_id = 1;
|
||||||
|
/// Unchanged, non-selected configs can be omitted. Deck will
|
||||||
|
/// be set to whichever entry comes last.
|
||||||
|
repeated DeckConfig configs = 2;
|
||||||
|
repeated int64 removed_config_ids = 3;
|
||||||
|
bool apply_to_children = 4;
|
||||||
|
string card_state_customizer = 5;
|
||||||
|
}
|
188
proto/anki/decks.proto
Normal file
188
proto/anki/decks.proto
Normal file
|
@ -0,0 +1,188 @@
|
||||||
|
// Copyright: Ankitects Pty Ltd and contributors
|
||||||
|
// License: GNU AGPL, version 3 or later; http://www.gnu.org/licenses/agpl.html
|
||||||
|
|
||||||
|
syntax = "proto3";
|
||||||
|
|
||||||
|
package anki.decks;
|
||||||
|
|
||||||
|
import "anki/generic.proto";
|
||||||
|
import "anki/collection.proto";
|
||||||
|
|
||||||
|
service DecksService {
|
||||||
|
rpc AddDeckLegacy(generic.Json) returns (collection.OpChangesWithId);
|
||||||
|
rpc AddOrUpdateDeckLegacy(AddOrUpdateDeckLegacyRequest) returns (DeckId);
|
||||||
|
rpc DeckTree(DeckTreeRequest) returns (DeckTreeNode);
|
||||||
|
rpc DeckTreeLegacy(generic.Empty) returns (generic.Json);
|
||||||
|
rpc GetAllDecksLegacy(generic.Empty) returns (generic.Json);
|
||||||
|
rpc GetDeckIdByName(generic.String) returns (DeckId);
|
||||||
|
rpc GetDeck(DeckId) returns (Deck);
|
||||||
|
rpc UpdateDeck(Deck) returns (collection.OpChanges);
|
||||||
|
rpc UpdateDeckLegacy(generic.Json) returns (collection.OpChanges);
|
||||||
|
rpc SetDeckCollapsed(SetDeckCollapsedRequest) returns (collection.OpChanges);
|
||||||
|
rpc GetDeckLegacy(DeckId) returns (generic.Json);
|
||||||
|
rpc GetDeckNames(GetDeckNamesRequest) returns (DeckNames);
|
||||||
|
rpc NewDeckLegacy(generic.Bool) returns (generic.Json);
|
||||||
|
rpc RemoveDecks(DeckIds) returns (collection.OpChangesWithCount);
|
||||||
|
rpc ReparentDecks(ReparentDecksRequest)
|
||||||
|
returns (collection.OpChangesWithCount);
|
||||||
|
rpc RenameDeck(RenameDeckRequest) returns (collection.OpChanges);
|
||||||
|
rpc GetOrCreateFilteredDeck(DeckId) returns (FilteredDeckForUpdate);
|
||||||
|
rpc AddOrUpdateFilteredDeck(FilteredDeckForUpdate)
|
||||||
|
returns (collection.OpChangesWithId);
|
||||||
|
rpc FilteredDeckOrderLabels(generic.Empty) returns (generic.StringList);
|
||||||
|
rpc SetCurrentDeck(DeckId) returns (collection.OpChanges);
|
||||||
|
rpc GetCurrentDeck(generic.Empty) returns (Deck);
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckId {
|
||||||
|
int64 did = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckIds {
|
||||||
|
repeated int64 dids = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Deck {
|
||||||
|
message Common {
|
||||||
|
bool study_collapsed = 1;
|
||||||
|
bool browser_collapsed = 2;
|
||||||
|
|
||||||
|
uint32 last_day_studied = 3;
|
||||||
|
int32 new_studied = 4;
|
||||||
|
int32 review_studied = 5;
|
||||||
|
int32 milliseconds_studied = 7;
|
||||||
|
|
||||||
|
// previously set in the v1 scheduler,
|
||||||
|
// but not currently used for anything
|
||||||
|
int32 learning_studied = 6;
|
||||||
|
|
||||||
|
reserved 8 to 13;
|
||||||
|
|
||||||
|
bytes other = 255;
|
||||||
|
}
|
||||||
|
message Normal {
|
||||||
|
int64 config_id = 1;
|
||||||
|
uint32 extend_new = 2;
|
||||||
|
uint32 extend_review = 3;
|
||||||
|
string description = 4;
|
||||||
|
bool markdown_description = 5;
|
||||||
|
|
||||||
|
reserved 6 to 11;
|
||||||
|
}
|
||||||
|
message Filtered {
|
||||||
|
message SearchTerm {
|
||||||
|
enum Order {
|
||||||
|
OLDEST_REVIEWED_FIRST = 0;
|
||||||
|
RANDOM = 1;
|
||||||
|
INTERVALS_ASCENDING = 2;
|
||||||
|
INTERVALS_DESCENDING = 3;
|
||||||
|
LAPSES = 4;
|
||||||
|
ADDED = 5;
|
||||||
|
DUE = 6;
|
||||||
|
REVERSE_ADDED = 7;
|
||||||
|
DUE_PRIORITY = 8;
|
||||||
|
}
|
||||||
|
|
||||||
|
string search = 1;
|
||||||
|
uint32 limit = 2;
|
||||||
|
Order order = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool reschedule = 1;
|
||||||
|
repeated SearchTerm search_terms = 2;
|
||||||
|
// v1 scheduler only
|
||||||
|
repeated float delays = 3;
|
||||||
|
// v2 scheduler only
|
||||||
|
uint32 preview_delay = 4;
|
||||||
|
}
|
||||||
|
// a container to store the deck specifics in the DB
|
||||||
|
// as a tagged enum
|
||||||
|
message KindContainer {
|
||||||
|
oneof kind {
|
||||||
|
Normal normal = 1;
|
||||||
|
Filtered filtered = 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int64 id = 1;
|
||||||
|
string name = 2;
|
||||||
|
int64 mtime_secs = 3;
|
||||||
|
int32 usn = 4;
|
||||||
|
Common common = 5;
|
||||||
|
// the specifics are inlined here when sending data to clients,
|
||||||
|
// as otherwise an extra level of indirection would be required
|
||||||
|
oneof kind {
|
||||||
|
Normal normal = 6;
|
||||||
|
Filtered filtered = 7;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
message AddOrUpdateDeckLegacyRequest {
|
||||||
|
bytes deck = 1;
|
||||||
|
bool preserve_usn_and_mtime = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckTreeRequest {
|
||||||
|
// if non-zero, counts for the provided timestamp will be included
|
||||||
|
int64 now = 1;
|
||||||
|
int64 top_deck_id = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckTreeNode {
|
||||||
|
int64 deck_id = 1;
|
||||||
|
string name = 2;
|
||||||
|
uint32 level = 4;
|
||||||
|
bool collapsed = 5;
|
||||||
|
|
||||||
|
uint32 review_count = 6;
|
||||||
|
uint32 learn_count = 7;
|
||||||
|
uint32 new_count = 8;
|
||||||
|
|
||||||
|
bool filtered = 16;
|
||||||
|
|
||||||
|
// low index so key can be packed into a byte, but at bottom
|
||||||
|
// to make debug output easier to read
|
||||||
|
repeated DeckTreeNode children = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message SetDeckCollapsedRequest {
|
||||||
|
enum Scope {
|
||||||
|
REVIEWER = 0;
|
||||||
|
BROWSER = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int64 deck_id = 1;
|
||||||
|
bool collapsed = 2;
|
||||||
|
Scope scope = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message GetDeckNamesRequest {
|
||||||
|
bool skip_empty_default = 1;
|
||||||
|
// if unset, implies skip_empty_default
|
||||||
|
bool include_filtered = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckNames {
|
||||||
|
repeated DeckNameId entries = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckNameId {
|
||||||
|
int64 id = 1;
|
||||||
|
string name = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message ReparentDecksRequest {
|
||||||
|
repeated int64 deck_ids = 1;
|
||||||
|
int64 new_parent = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message RenameDeckRequest {
|
||||||
|
int64 deck_id = 1;
|
||||||
|
string new_name = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message FilteredDeckForUpdate {
|
||||||
|
int64 id = 1;
|
||||||
|
string name = 2;
|
||||||
|
Deck.Filtered config = 3;
|
||||||
|
}
|
106
proto/anki/notes.proto
Normal file
106
proto/anki/notes.proto
Normal file
|
@ -0,0 +1,106 @@
|
||||||
|
// Copyright: Ankitects Pty Ltd and contributors
|
||||||
|
// License: GNU AGPL, version 3 or later; http://www.gnu.org/licenses/agpl.html
|
||||||
|
|
||||||
|
syntax = "proto3";
|
||||||
|
|
||||||
|
package anki.notes;
|
||||||
|
|
||||||
|
import "anki/notetypes.proto";
|
||||||
|
import "anki/collection.proto";
|
||||||
|
import "anki/decks.proto";
|
||||||
|
import "anki/cards.proto";
|
||||||
|
|
||||||
|
service NotesService {
|
||||||
|
rpc NewNote(notetypes.NotetypeId) returns (Note);
|
||||||
|
rpc AddNote(AddNoteRequest) returns (AddNoteResponse);
|
||||||
|
rpc DefaultsForAdding(DefaultsForAddingRequest) returns (DeckAndNotetype);
|
||||||
|
rpc DefaultDeckForNotetype(notetypes.NotetypeId) returns (decks.DeckId);
|
||||||
|
rpc UpdateNote(UpdateNoteRequest) returns (collection.OpChanges);
|
||||||
|
rpc GetNote(NoteId) returns (Note);
|
||||||
|
rpc RemoveNotes(RemoveNotesRequest) returns (collection.OpChangesWithCount);
|
||||||
|
rpc ClozeNumbersInNote(Note) returns (ClozeNumbersInNoteResponse);
|
||||||
|
rpc AfterNoteUpdates(AfterNoteUpdatesRequest)
|
||||||
|
returns (collection.OpChangesWithCount);
|
||||||
|
rpc FieldNamesForNotes(FieldNamesForNotesRequest)
|
||||||
|
returns (FieldNamesForNotesResponse);
|
||||||
|
rpc NoteFieldsCheck(Note) returns (NoteFieldsCheckResponse);
|
||||||
|
rpc CardsOfNote(NoteId) returns (cards.CardIds);
|
||||||
|
rpc GetSingleNotetypeOfNotes(notes.NoteIds) returns (notetypes.NotetypeId);
|
||||||
|
}
|
||||||
|
|
||||||
|
message NoteId {
|
||||||
|
int64 nid = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message NoteIds {
|
||||||
|
repeated int64 note_ids = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Note {
|
||||||
|
int64 id = 1;
|
||||||
|
string guid = 2;
|
||||||
|
int64 notetype_id = 3;
|
||||||
|
uint32 mtime_secs = 4;
|
||||||
|
int32 usn = 5;
|
||||||
|
repeated string tags = 6;
|
||||||
|
repeated string fields = 7;
|
||||||
|
}
|
||||||
|
|
||||||
|
message AddNoteRequest {
|
||||||
|
Note note = 1;
|
||||||
|
int64 deck_id = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message AddNoteResponse {
|
||||||
|
int64 note_id = 1;
|
||||||
|
collection.OpChanges changes = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message UpdateNoteRequest {
|
||||||
|
Note note = 1;
|
||||||
|
bool skip_undo_entry = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DefaultsForAddingRequest {
|
||||||
|
int64 home_deck_of_current_review_card = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeckAndNotetype {
|
||||||
|
int64 deck_id = 1;
|
||||||
|
int64 notetype_id = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message RemoveNotesRequest {
|
||||||
|
repeated int64 note_ids = 1;
|
||||||
|
repeated int64 card_ids = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message ClozeNumbersInNoteResponse {
|
||||||
|
repeated uint32 numbers = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message AfterNoteUpdatesRequest {
|
||||||
|
repeated int64 nids = 1;
|
||||||
|
bool mark_notes_modified = 2;
|
||||||
|
bool generate_cards = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message FieldNamesForNotesRequest {
|
||||||
|
repeated int64 nids = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message FieldNamesForNotesResponse {
|
||||||
|
repeated string fields = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message NoteFieldsCheckResponse {
|
||||||
|
enum State {
|
||||||
|
NORMAL = 0;
|
||||||
|
EMPTY = 1;
|
||||||
|
DUPLICATE = 2;
|
||||||
|
MISSING_CLOZE = 3;
|
||||||
|
NOTETYPE_NOT_CLOZE = 4;
|
||||||
|
FIELD_NOT_CLOZE = 5;
|
||||||
|
}
|
||||||
|
State state = 1;
|
||||||
|
}
|
176
proto/anki/notetypes.proto
Normal file
176
proto/anki/notetypes.proto
Normal file
|
@ -0,0 +1,176 @@
|
||||||
|
// Copyright: Ankitects Pty Ltd and contributors
|
||||||
|
// License: GNU AGPL, version 3 or later; http://www.gnu.org/licenses/agpl.html
|
||||||
|
|
||||||
|
syntax = "proto3";
|
||||||
|
|
||||||
|
package anki.notetypes;
|
||||||
|
|
||||||
|
import "anki/generic.proto";
|
||||||
|
import "anki/collection.proto";
|
||||||
|
|
||||||
|
service NotetypesService {
|
||||||
|
rpc AddNotetype(Notetype) returns (collection.OpChangesWithId);
|
||||||
|
rpc UpdateNotetype(Notetype) returns (collection.OpChanges);
|
||||||
|
rpc AddNotetypeLegacy(generic.Json) returns (collection.OpChangesWithId);
|
||||||
|
rpc UpdateNotetypeLegacy(generic.Json) returns (collection.OpChanges);
|
||||||
|
rpc AddOrUpdateNotetype(AddOrUpdateNotetypeRequest) returns (NotetypeId);
|
||||||
|
rpc GetStockNotetypeLegacy(StockNotetype) returns (generic.Json);
|
||||||
|
rpc GetNotetype(NotetypeId) returns (Notetype);
|
||||||
|
rpc GetNotetypeLegacy(NotetypeId) returns (generic.Json);
|
||||||
|
rpc GetNotetypeNames(generic.Empty) returns (NotetypeNames);
|
||||||
|
rpc GetNotetypeNamesAndCounts(generic.Empty) returns (NotetypeUseCounts);
|
||||||
|
rpc GetNotetypeIdByName(generic.String) returns (NotetypeId);
|
||||||
|
rpc RemoveNotetype(NotetypeId) returns (collection.OpChanges);
|
||||||
|
rpc GetAuxNotetypeConfigKey(GetAuxConfigKeyRequest) returns (generic.String);
|
||||||
|
rpc GetAuxTemplateConfigKey(GetAuxTemplateConfigKeyRequest)
|
||||||
|
returns (generic.String);
|
||||||
|
rpc GetChangeNotetypeInfo(GetChangeNotetypeInfoRequest)
|
||||||
|
returns (ChangeNotetypeInfo);
|
||||||
|
rpc ChangeNotetype(ChangeNotetypeRequest) returns (collection.OpChanges);
|
||||||
|
}
|
||||||
|
|
||||||
|
message NotetypeId {
|
||||||
|
int64 ntid = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Notetype {
|
||||||
|
message Config {
|
||||||
|
enum Kind {
|
||||||
|
KIND_NORMAL = 0;
|
||||||
|
KIND_CLOZE = 1;
|
||||||
|
}
|
||||||
|
message CardRequirement {
|
||||||
|
enum Kind {
|
||||||
|
KIND_NONE = 0;
|
||||||
|
KIND_ANY = 1;
|
||||||
|
KIND_ALL = 2;
|
||||||
|
}
|
||||||
|
uint32 card_ord = 1;
|
||||||
|
Kind kind = 2;
|
||||||
|
repeated uint32 field_ords = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
Kind kind = 1;
|
||||||
|
uint32 sort_field_idx = 2;
|
||||||
|
string css = 3;
|
||||||
|
/// This is now stored separately; retrieve with DefaultsForAdding()
|
||||||
|
int64 target_deck_id_unused = 4;
|
||||||
|
string latex_pre = 5;
|
||||||
|
string latex_post = 6;
|
||||||
|
bool latex_svg = 7;
|
||||||
|
repeated CardRequirement reqs = 8;
|
||||||
|
|
||||||
|
bytes other = 255;
|
||||||
|
}
|
||||||
|
message Field {
|
||||||
|
message Config {
|
||||||
|
bool sticky = 1;
|
||||||
|
bool rtl = 2;
|
||||||
|
string font_name = 3;
|
||||||
|
uint32 font_size = 4;
|
||||||
|
|
||||||
|
bytes other = 255;
|
||||||
|
}
|
||||||
|
generic.OptionalUInt32 ord = 1;
|
||||||
|
string name = 2;
|
||||||
|
Config config = 5;
|
||||||
|
}
|
||||||
|
message Template {
|
||||||
|
message Config {
|
||||||
|
string q_format = 1;
|
||||||
|
string a_format = 2;
|
||||||
|
string q_format_browser = 3;
|
||||||
|
string a_format_browser = 4;
|
||||||
|
int64 target_deck_id = 5;
|
||||||
|
string browser_font_name = 6;
|
||||||
|
uint32 browser_font_size = 7;
|
||||||
|
|
||||||
|
bytes other = 255;
|
||||||
|
}
|
||||||
|
|
||||||
|
generic.OptionalUInt32 ord = 1;
|
||||||
|
string name = 2;
|
||||||
|
int64 mtime_secs = 3;
|
||||||
|
sint32 usn = 4;
|
||||||
|
Config config = 5;
|
||||||
|
}
|
||||||
|
|
||||||
|
int64 id = 1;
|
||||||
|
string name = 2;
|
||||||
|
int64 mtime_secs = 3;
|
||||||
|
sint32 usn = 4;
|
||||||
|
Config config = 7;
|
||||||
|
repeated Field fields = 8;
|
||||||
|
repeated Template templates = 9;
|
||||||
|
}
|
||||||
|
|
||||||
|
message AddOrUpdateNotetypeRequest {
|
||||||
|
bytes json = 1;
|
||||||
|
bool preserve_usn_and_mtime = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message StockNotetype {
|
||||||
|
enum Kind {
|
||||||
|
BASIC = 0;
|
||||||
|
BASIC_AND_REVERSED = 1;
|
||||||
|
BASIC_OPTIONAL_REVERSED = 2;
|
||||||
|
BASIC_TYPING = 3;
|
||||||
|
CLOZE = 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
Kind kind = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message NotetypeNames {
|
||||||
|
repeated NotetypeNameId entries = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message NotetypeUseCounts {
|
||||||
|
repeated NotetypeNameIdUseCount entries = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
message NotetypeNameId {
|
||||||
|
int64 id = 1;
|
||||||
|
string name = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message NotetypeNameIdUseCount {
|
||||||
|
int64 id = 1;
|
||||||
|
string name = 2;
|
||||||
|
uint32 use_count = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message GetAuxConfigKeyRequest {
|
||||||
|
int64 id = 1;
|
||||||
|
string key = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message GetAuxTemplateConfigKeyRequest {
|
||||||
|
int64 notetype_id = 1;
|
||||||
|
uint32 card_ordinal = 2;
|
||||||
|
string key = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message GetChangeNotetypeInfoRequest {
|
||||||
|
int64 old_notetype_id = 1;
|
||||||
|
int64 new_notetype_id = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message ChangeNotetypeRequest {
|
||||||
|
repeated int64 note_ids = 1;
|
||||||
|
// -1 is used to represent null, as nullable repeated fields
|
||||||
|
// are unwieldy in protobuf
|
||||||
|
repeated int32 new_fields = 2;
|
||||||
|
repeated int32 new_templates = 3;
|
||||||
|
int64 old_notetype_id = 4;
|
||||||
|
int64 new_notetype_id = 5;
|
||||||
|
int64 current_schema = 6;
|
||||||
|
}
|
||||||
|
|
||||||
|
message ChangeNotetypeInfo {
|
||||||
|
repeated string old_field_names = 1;
|
||||||
|
repeated string old_template_names = 2;
|
||||||
|
repeated string new_field_names = 3;
|
||||||
|
repeated string new_template_names = 4;
|
||||||
|
ChangeNotetypeRequest input = 5;
|
||||||
|
}
|
|
@ -12,6 +12,10 @@ import anki.backend_pb2
|
||||||
import anki.i18n_pb2
|
import anki.i18n_pb2
|
||||||
import anki.cards_pb2
|
import anki.cards_pb2
|
||||||
import anki.collection_pb2
|
import anki.collection_pb2
|
||||||
|
import anki.decks_pb2
|
||||||
|
import anki.deckconfig_pb2
|
||||||
|
import anki.notes_pb2
|
||||||
|
import anki.notetypes_pb2
|
||||||
|
|
||||||
import stringcase
|
import stringcase
|
||||||
|
|
||||||
|
@ -171,6 +175,10 @@ service_modules = dict(
|
||||||
I18N=anki.i18n_pb2,
|
I18N=anki.i18n_pb2,
|
||||||
COLLECTION=anki.collection_pb2,
|
COLLECTION=anki.collection_pb2,
|
||||||
CARDS=anki.cards_pb2,
|
CARDS=anki.cards_pb2,
|
||||||
|
NOTES=anki.notes_pb2,
|
||||||
|
DECKS=anki.decks_pb2,
|
||||||
|
DECK_CONFIG=anki.deckconfig_pb2,
|
||||||
|
NOTETYPES=anki.notetypes_pb2,
|
||||||
)
|
)
|
||||||
|
|
||||||
for service in anki.backend_pb2.ServiceIndex.DESCRIPTOR.values:
|
for service in anki.backend_pb2.ServiceIndex.DESCRIPTOR.values:
|
||||||
|
|
|
@ -22,7 +22,6 @@ OpChanges = collection_pb2.OpChanges
|
||||||
OpChangesWithCount = collection_pb2.OpChangesWithCount
|
OpChangesWithCount = collection_pb2.OpChangesWithCount
|
||||||
OpChangesWithId = collection_pb2.OpChangesWithId
|
OpChangesWithId = collection_pb2.OpChangesWithId
|
||||||
OpChangesAfterUndo = collection_pb2.OpChangesAfterUndo
|
OpChangesAfterUndo = collection_pb2.OpChangesAfterUndo
|
||||||
DefaultsForAdding = _pb.DeckAndNotetype
|
|
||||||
BrowserRow = _pb.BrowserRow
|
BrowserRow = _pb.BrowserRow
|
||||||
BrowserColumns = _pb.BrowserColumns
|
BrowserColumns = _pb.BrowserColumns
|
||||||
|
|
||||||
|
@ -370,7 +369,7 @@ class Collection(DeprecatedNamesMixin):
|
||||||
|
|
||||||
def defaults_for_adding(
|
def defaults_for_adding(
|
||||||
self, *, current_review_card: Optional[Card]
|
self, *, current_review_card: Optional[Card]
|
||||||
) -> DefaultsForAdding:
|
) -> anki.notes.DefaultsForAdding:
|
||||||
"""Get starting deck and notetype for add screen.
|
"""Get starting deck and notetype for add screen.
|
||||||
An option in the preferences controls whether this will be based on the current deck
|
An option in the preferences controls whether this will be based on the current deck
|
||||||
or current notetype.
|
or current notetype.
|
||||||
|
|
|
@ -23,7 +23,7 @@ from typing import (
|
||||||
if TYPE_CHECKING:
|
if TYPE_CHECKING:
|
||||||
import anki
|
import anki
|
||||||
|
|
||||||
import anki.backend_pb2 as _pb
|
from anki import deckconfig_pb2, decks_pb2
|
||||||
from anki._legacy import DeprecatedNamesMixin, deprecated, print_deprecation_warning
|
from anki._legacy import DeprecatedNamesMixin, deprecated, print_deprecation_warning
|
||||||
from anki.cards import CardId
|
from anki.cards import CardId
|
||||||
from anki.collection import OpChanges, OpChangesWithCount, OpChangesWithId
|
from anki.collection import OpChanges, OpChangesWithCount, OpChangesWithId
|
||||||
|
@ -32,12 +32,12 @@ from anki.errors import NotFoundError
|
||||||
from anki.utils import from_json_bytes, ids2str, intTime, to_json_bytes
|
from anki.utils import from_json_bytes, ids2str, intTime, to_json_bytes
|
||||||
|
|
||||||
# public exports
|
# public exports
|
||||||
DeckTreeNode = _pb.DeckTreeNode
|
DeckTreeNode = decks_pb2.DeckTreeNode
|
||||||
DeckNameId = _pb.DeckNameId
|
DeckNameId = decks_pb2.DeckNameId
|
||||||
FilteredDeckConfig = _pb.Deck.Filtered
|
FilteredDeckConfig = decks_pb2.Deck.Filtered
|
||||||
DeckCollapseScope = _pb.SetDeckCollapsedRequest.Scope
|
DeckCollapseScope = decks_pb2.SetDeckCollapsedRequest.Scope
|
||||||
DeckConfigsForUpdate = _pb.DeckConfigsForUpdate
|
DeckConfigsForUpdate = deckconfig_pb2.DeckConfigsForUpdate
|
||||||
UpdateDeckConfigs = _pb.UpdateDeckConfigsRequest
|
UpdateDeckConfigs = deckconfig_pb2.UpdateDeckConfigsRequest
|
||||||
|
|
||||||
# type aliases until we can move away from dicts
|
# type aliases until we can move away from dicts
|
||||||
DeckDict = Dict[str, Any]
|
DeckDict = Dict[str, Any]
|
||||||
|
|
|
@ -12,7 +12,7 @@ import time
|
||||||
from typing import Any, Dict, List, NewType, Optional, Sequence, Tuple, Union
|
from typing import Any, Dict, List, NewType, Optional, Sequence, Tuple, Union
|
||||||
|
|
||||||
import anki # pylint: disable=unused-import
|
import anki # pylint: disable=unused-import
|
||||||
import anki.backend_pb2 as _pb
|
from anki import notetypes_pb2
|
||||||
from anki._legacy import DeprecatedNamesMixin, deprecated, print_deprecation_warning
|
from anki._legacy import DeprecatedNamesMixin, deprecated, print_deprecation_warning
|
||||||
from anki.collection import OpChanges, OpChangesWithId
|
from anki.collection import OpChanges, OpChangesWithId
|
||||||
from anki.consts import *
|
from anki.consts import *
|
||||||
|
@ -22,11 +22,11 @@ from anki.stdmodels import StockNotetypeKind
|
||||||
from anki.utils import checksum, from_json_bytes, to_json_bytes
|
from anki.utils import checksum, from_json_bytes, to_json_bytes
|
||||||
|
|
||||||
# public exports
|
# public exports
|
||||||
NotetypeNameId = _pb.NotetypeNameId
|
NotetypeNameId = notetypes_pb2.NotetypeNameId
|
||||||
NotetypeNameIdUseCount = _pb.NotetypeNameIdUseCount
|
NotetypeNameIdUseCount = notetypes_pb2.NotetypeNameIdUseCount
|
||||||
NotetypeNames = _pb.NotetypeNames
|
NotetypeNames = notetypes_pb2.NotetypeNames
|
||||||
ChangeNotetypeInfo = _pb.ChangeNotetypeInfo
|
ChangeNotetypeInfo = notetypes_pb2.ChangeNotetypeInfo
|
||||||
ChangeNotetypeRequest = _pb.ChangeNotetypeRequest
|
ChangeNotetypeRequest = notetypes_pb2.ChangeNotetypeRequest
|
||||||
|
|
||||||
# legacy types
|
# legacy types
|
||||||
NotetypeDict = Dict[str, Any]
|
NotetypeDict = Dict[str, Any]
|
||||||
|
@ -459,7 +459,9 @@ and notes.mid = ? and cards.ord = ?""",
|
||||||
def _availClozeOrds(
|
def _availClozeOrds(
|
||||||
self, notetype: NotetypeDict, flds: str, allow_empty: bool = True
|
self, notetype: NotetypeDict, flds: str, allow_empty: bool = True
|
||||||
) -> List[int]:
|
) -> List[int]:
|
||||||
note = _pb.Note(fields=[flds])
|
import anki.notes_pb2
|
||||||
|
|
||||||
|
note = anki.notes_pb2.Note(fields=[flds])
|
||||||
return list(self.col._backend.cloze_numbers_in_note(note))
|
return list(self.col._backend.cloze_numbers_in_note(note))
|
||||||
|
|
||||||
# @deprecated(replaced_by=add_template)
|
# @deprecated(replaced_by=add_template)
|
||||||
|
|
|
@ -9,15 +9,15 @@ import copy
|
||||||
from typing import Any, List, NewType, Optional, Sequence, Tuple, Union
|
from typing import Any, List, NewType, Optional, Sequence, Tuple, Union
|
||||||
|
|
||||||
import anki # pylint: disable=unused-import
|
import anki # pylint: disable=unused-import
|
||||||
import anki.backend_pb2 as _pb
|
from anki import hooks, notes_pb2
|
||||||
from anki import hooks
|
|
||||||
from anki._legacy import DeprecatedNamesMixin
|
from anki._legacy import DeprecatedNamesMixin
|
||||||
from anki.consts import MODEL_STD
|
from anki.consts import MODEL_STD
|
||||||
from anki.models import NotetypeDict, NotetypeId, TemplateDict
|
from anki.models import NotetypeDict, NotetypeId, TemplateDict
|
||||||
from anki.utils import joinFields
|
from anki.utils import joinFields
|
||||||
|
|
||||||
DuplicateOrEmptyResult = _pb.NoteFieldsCheckResponse.State
|
DuplicateOrEmptyResult = notes_pb2.NoteFieldsCheckResponse.State
|
||||||
NoteFieldsCheckResult = _pb.NoteFieldsCheckResponse.State
|
NoteFieldsCheckResult = notes_pb2.NoteFieldsCheckResponse.State
|
||||||
|
DefaultsForAdding = notes_pb2.DeckAndNotetype
|
||||||
|
|
||||||
# types
|
# types
|
||||||
NoteId = NewType("NoteId", int)
|
NoteId = NewType("NoteId", int)
|
||||||
|
@ -53,7 +53,7 @@ class Note(DeprecatedNamesMixin):
|
||||||
assert note
|
assert note
|
||||||
self._load_from_backend_note(note)
|
self._load_from_backend_note(note)
|
||||||
|
|
||||||
def _load_from_backend_note(self, note: _pb.Note) -> None:
|
def _load_from_backend_note(self, note: notes_pb2.Note) -> None:
|
||||||
self.id = NoteId(note.id)
|
self.id = NoteId(note.id)
|
||||||
self.guid = note.guid
|
self.guid = note.guid
|
||||||
self.mid = NotetypeId(note.notetype_id)
|
self.mid = NotetypeId(note.notetype_id)
|
||||||
|
@ -63,9 +63,9 @@ class Note(DeprecatedNamesMixin):
|
||||||
self.fields = list(note.fields)
|
self.fields = list(note.fields)
|
||||||
self._fmap = self.col.models.field_map(self.note_type())
|
self._fmap = self.col.models.field_map(self.note_type())
|
||||||
|
|
||||||
def _to_backend_note(self) -> _pb.Note:
|
def _to_backend_note(self) -> notes_pb2.Note:
|
||||||
hooks.note_will_flush(self)
|
hooks.note_will_flush(self)
|
||||||
return _pb.Note(
|
return notes_pb2.Note(
|
||||||
id=self.id,
|
id=self.id,
|
||||||
guid=self.guid,
|
guid=self.guid,
|
||||||
notetype_id=self.mid,
|
notetype_id=self.mid,
|
||||||
|
|
|
@ -5,6 +5,7 @@ from __future__ import annotations
|
||||||
|
|
||||||
import anki
|
import anki
|
||||||
import anki.backend_pb2 as _pb
|
import anki.backend_pb2 as _pb
|
||||||
|
from anki import decks_pb2
|
||||||
from anki.collection import OpChanges, OpChangesWithCount, OpChangesWithId
|
from anki.collection import OpChanges, OpChangesWithCount, OpChangesWithId
|
||||||
from anki.config import Config
|
from anki.config import Config
|
||||||
|
|
||||||
|
@ -22,7 +23,7 @@ from anki.utils import ids2str, intTime
|
||||||
CongratsInfo = _pb.CongratsInfoResponse
|
CongratsInfo = _pb.CongratsInfoResponse
|
||||||
UnburyDeck = _pb.UnburyDeckRequest
|
UnburyDeck = _pb.UnburyDeckRequest
|
||||||
BuryOrSuspend = _pb.BuryOrSuspendCardsRequest
|
BuryOrSuspend = _pb.BuryOrSuspendCardsRequest
|
||||||
FilteredDeckForUpdate = _pb.FilteredDeckForUpdate
|
FilteredDeckForUpdate = decks_pb2.FilteredDeckForUpdate
|
||||||
|
|
||||||
|
|
||||||
class SchedulerBase:
|
class SchedulerBase:
|
||||||
|
|
|
@ -6,11 +6,11 @@ from __future__ import annotations
|
||||||
from typing import Any, Callable, List, Tuple
|
from typing import Any, Callable, List, Tuple
|
||||||
|
|
||||||
import anki
|
import anki
|
||||||
import anki.backend_pb2 as _pb
|
from anki import notetypes_pb2
|
||||||
from anki.utils import from_json_bytes
|
from anki.utils import from_json_bytes
|
||||||
|
|
||||||
# pylint: disable=no-member
|
# pylint: disable=no-member
|
||||||
StockNotetypeKind = _pb.StockNotetype.Kind
|
StockNotetypeKind = notetypes_pb2.StockNotetype.Kind
|
||||||
|
|
||||||
# add-on authors can add ("note type name", function)
|
# add-on authors can add ("note type name", function)
|
||||||
# to this list to have it shown in the add/clone note type screen
|
# to this list to have it shown in the add/clone note type screen
|
||||||
|
|
|
@ -143,6 +143,13 @@ impl NotesService for Backend {
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn get_single_notetype_of_notes(&self, input: pb::NoteIds) -> Result<pb::NotetypeId> {
|
||||||
|
self.with_col(|col| {
|
||||||
|
col.get_single_notetype_of_notes(&input.note_ids.into_newtype(NoteId))
|
||||||
|
.map(Into::into)
|
||||||
|
})
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(super) fn to_note_ids(ids: Vec<i64>) -> Vec<NoteId> {
|
pub(super) fn to_note_ids(ids: Vec<i64>) -> Vec<NoteId> {
|
||||||
|
|
|
@ -159,13 +159,6 @@ impl NotetypesService for Backend {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_single_notetype_of_notes(&self, input: pb::NoteIds) -> Result<pb::NotetypeId> {
|
|
||||||
self.with_col(|col| {
|
|
||||||
col.get_single_notetype_of_notes(&input.note_ids.into_newtype(NoteId))
|
|
||||||
.map(Into::into)
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_change_notetype_info(
|
fn get_change_notetype_info(
|
||||||
&self,
|
&self,
|
||||||
input: pb::GetChangeNotetypeInfoRequest,
|
input: pb::GetChangeNotetypeInfoRequest,
|
||||||
|
|
|
@ -1,24 +1,24 @@
|
||||||
// Copyright: Ankitects Pty Ltd and contributors
|
// Copyright: Ankitects Pty Ltd and contributors
|
||||||
// License: GNU AGPL, version 3 or later; http://www.gnu.org/licenses/agpl.html
|
// License: GNU AGPL, version 3 or later; http://www.gnu.org/licenses/agpl.html
|
||||||
|
|
||||||
pub mod backend {
|
macro_rules! protobuf {
|
||||||
include!(concat!(env!("OUT_DIR"), "/anki.backend.rs"));
|
($ident:ident) => {
|
||||||
}
|
pub mod $ident {
|
||||||
pub mod i18n {
|
include!(concat!(
|
||||||
include!(concat!(env!("OUT_DIR"), "/anki.i18n.rs"));
|
env!("OUT_DIR"),
|
||||||
}
|
concat!("/anki.", stringify!($ident), ".rs")
|
||||||
pub mod generic {
|
));
|
||||||
include!(concat!(env!("OUT_DIR"), "/anki.generic.rs"));
|
}
|
||||||
}
|
pub use $ident::*;
|
||||||
pub mod cards {
|
};
|
||||||
include!(concat!(env!("OUT_DIR"), "/anki.cards.rs"));
|
|
||||||
}
|
|
||||||
pub mod collection {
|
|
||||||
include!(concat!(env!("OUT_DIR"), "/anki.collection.rs"));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub use backend::*;
|
protobuf!(backend);
|
||||||
pub use cards::*;
|
protobuf!(notes);
|
||||||
pub use collection::*;
|
protobuf!(notetypes);
|
||||||
pub use generic::*;
|
protobuf!(decks);
|
||||||
pub use i18n::*;
|
protobuf!(deckconfig);
|
||||||
|
protobuf!(i18n);
|
||||||
|
protobuf!(cards);
|
||||||
|
protobuf!(generic);
|
||||||
|
protobuf!(collection);
|
||||||
|
|
|
@ -5,7 +5,7 @@
|
||||||
@typescript-eslint/no-explicit-any: "off",
|
@typescript-eslint/no-explicit-any: "off",
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { Backend } from "lib/proto";
|
import { Notetypes } from "lib/proto";
|
||||||
import { ChangeNotetypeState, negativeOneToNull, MapContext } from "./lib";
|
import { ChangeNotetypeState, negativeOneToNull, MapContext } from "./lib";
|
||||||
import { get } from "svelte/store";
|
import { get } from "svelte/store";
|
||||||
|
|
||||||
|
@ -64,15 +64,15 @@ const exampleInfoSame = {
|
||||||
|
|
||||||
function differentState(): ChangeNotetypeState {
|
function differentState(): ChangeNotetypeState {
|
||||||
return new ChangeNotetypeState(
|
return new ChangeNotetypeState(
|
||||||
Backend.NotetypeNames.fromObject(exampleNames),
|
Notetypes.NotetypeNames.fromObject(exampleNames),
|
||||||
Backend.ChangeNotetypeInfo.fromObject(exampleInfoDifferent)
|
Notetypes.ChangeNotetypeInfo.fromObject(exampleInfoDifferent)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function sameState(): ChangeNotetypeState {
|
function sameState(): ChangeNotetypeState {
|
||||||
return new ChangeNotetypeState(
|
return new ChangeNotetypeState(
|
||||||
Backend.NotetypeNames.fromObject(exampleNames),
|
Notetypes.NotetypeNames.fromObject(exampleNames),
|
||||||
Backend.ChangeNotetypeInfo.fromObject(exampleInfoSame)
|
Notetypes.ChangeNotetypeInfo.fromObject(exampleInfoSame)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -5,20 +5,22 @@
|
||||||
@typescript-eslint/no-non-null-assertion: "off",
|
@typescript-eslint/no-non-null-assertion: "off",
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { Backend } from "lib/proto";
|
import { Notetypes } from "lib/proto";
|
||||||
import { postRequest } from "lib/postrequest";
|
import { postRequest } from "lib/postrequest";
|
||||||
import { readable, Readable } from "svelte/store";
|
import { readable, Readable } from "svelte/store";
|
||||||
import { isEqual } from "lodash-es";
|
import { isEqual } from "lodash-es";
|
||||||
|
|
||||||
export async function getNotetypeNames(): Promise<Backend.NotetypeNames> {
|
export async function getNotetypeNames(): Promise<Notetypes.NotetypeNames> {
|
||||||
return Backend.NotetypeNames.decode(await postRequest("/_anki/notetypeNames", ""));
|
return Notetypes.NotetypeNames.decode(
|
||||||
|
await postRequest("/_anki/notetypeNames", "")
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
export async function getChangeNotetypeInfo(
|
export async function getChangeNotetypeInfo(
|
||||||
oldNotetypeId: number,
|
oldNotetypeId: number,
|
||||||
newNotetypeId: number
|
newNotetypeId: number
|
||||||
): Promise<Backend.ChangeNotetypeInfo> {
|
): Promise<Notetypes.ChangeNotetypeInfo> {
|
||||||
return Backend.ChangeNotetypeInfo.decode(
|
return Notetypes.ChangeNotetypeInfo.decode(
|
||||||
await postRequest(
|
await postRequest(
|
||||||
"/_anki/changeNotetypeInfo",
|
"/_anki/changeNotetypeInfo",
|
||||||
JSON.stringify({ oldNotetypeId, newNotetypeId })
|
JSON.stringify({ oldNotetypeId, newNotetypeId })
|
||||||
|
@ -27,9 +29,9 @@ export async function getChangeNotetypeInfo(
|
||||||
}
|
}
|
||||||
|
|
||||||
export async function changeNotetype(
|
export async function changeNotetype(
|
||||||
input: Backend.ChangeNotetypeRequest
|
input: Notetypes.ChangeNotetypeRequest
|
||||||
): Promise<void> {
|
): Promise<void> {
|
||||||
const data: Uint8Array = Backend.ChangeNotetypeRequest.encode(input).finish();
|
const data: Uint8Array = Notetypes.ChangeNotetypeRequest.encode(input).finish();
|
||||||
await postRequest("/_anki/changeNotetype", data);
|
await postRequest("/_anki/changeNotetype", data);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -47,9 +49,9 @@ export function negativeOneToNull(list: number[]): (number | null)[] {
|
||||||
export class ChangeNotetypeInfoWrapper {
|
export class ChangeNotetypeInfoWrapper {
|
||||||
fields: (number | null)[];
|
fields: (number | null)[];
|
||||||
templates?: (number | null)[];
|
templates?: (number | null)[];
|
||||||
readonly info: Backend.ChangeNotetypeInfo;
|
readonly info: Notetypes.ChangeNotetypeInfo;
|
||||||
|
|
||||||
constructor(info: Backend.ChangeNotetypeInfo) {
|
constructor(info: Notetypes.ChangeNotetypeInfo) {
|
||||||
this.info = info;
|
this.info = info;
|
||||||
const templates = info.input!.newTemplates!;
|
const templates = info.input!.newTemplates!;
|
||||||
if (templates.length > 0) {
|
if (templates.length > 0) {
|
||||||
|
@ -111,13 +113,13 @@ export class ChangeNotetypeInfoWrapper {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
input(): Backend.ChangeNotetypeRequest {
|
input(): Notetypes.ChangeNotetypeRequest {
|
||||||
return this.info.input as Backend.ChangeNotetypeRequest;
|
return this.info.input as Notetypes.ChangeNotetypeRequest;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Pack changes back into input message for saving.
|
/// Pack changes back into input message for saving.
|
||||||
intoInput(): Backend.ChangeNotetypeRequest {
|
intoInput(): Notetypes.ChangeNotetypeRequest {
|
||||||
const input = this.info.input as Backend.ChangeNotetypeRequest;
|
const input = this.info.input as Notetypes.ChangeNotetypeRequest;
|
||||||
input.newFields = nullToNegativeOne(this.fields);
|
input.newFields = nullToNegativeOne(this.fields);
|
||||||
if (this.templates) {
|
if (this.templates) {
|
||||||
input.newTemplates = nullToNegativeOne(this.templates);
|
input.newTemplates = nullToNegativeOne(this.templates);
|
||||||
|
@ -143,10 +145,13 @@ export class ChangeNotetypeState {
|
||||||
|
|
||||||
private info_: ChangeNotetypeInfoWrapper;
|
private info_: ChangeNotetypeInfoWrapper;
|
||||||
private infoSetter!: (val: ChangeNotetypeInfoWrapper) => void;
|
private infoSetter!: (val: ChangeNotetypeInfoWrapper) => void;
|
||||||
private notetypeNames: Backend.NotetypeNames;
|
private notetypeNames: Notetypes.NotetypeNames;
|
||||||
private notetypesSetter!: (val: NotetypeListEntry[]) => void;
|
private notetypesSetter!: (val: NotetypeListEntry[]) => void;
|
||||||
|
|
||||||
constructor(notetypes: Backend.NotetypeNames, info: Backend.ChangeNotetypeInfo) {
|
constructor(
|
||||||
|
notetypes: Notetypes.NotetypeNames,
|
||||||
|
info: Notetypes.ChangeNotetypeInfo
|
||||||
|
) {
|
||||||
this.info_ = new ChangeNotetypeInfoWrapper(info);
|
this.info_ = new ChangeNotetypeInfoWrapper(info);
|
||||||
this.info = readable(this.info_, (set) => {
|
this.info = readable(this.info_, (set) => {
|
||||||
this.infoSetter = set;
|
this.infoSetter = set;
|
||||||
|
@ -197,7 +202,7 @@ export class ChangeNotetypeState {
|
||||||
await changeNotetype(this.dataForSaving());
|
await changeNotetype(this.dataForSaving());
|
||||||
}
|
}
|
||||||
|
|
||||||
dataForSaving(): Backend.ChangeNotetypeRequest {
|
dataForSaving(): Notetypes.ChangeNotetypeRequest {
|
||||||
return this.info_.intoInput();
|
return this.info_.intoInput();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -5,7 +5,7 @@
|
||||||
@typescript-eslint/no-explicit-any: "off",
|
@typescript-eslint/no-explicit-any: "off",
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { Backend } from "lib/proto";
|
import { DeckConfig } from "lib/proto";
|
||||||
import { DeckOptionsState } from "./lib";
|
import { DeckOptionsState } from "./lib";
|
||||||
import { get } from "svelte/store";
|
import { get } from "svelte/store";
|
||||||
|
|
||||||
|
@ -94,7 +94,7 @@ const exampleData = {
|
||||||
function startingState(): DeckOptionsState {
|
function startingState(): DeckOptionsState {
|
||||||
return new DeckOptionsState(
|
return new DeckOptionsState(
|
||||||
123,
|
123,
|
||||||
Backend.DeckConfigsForUpdate.fromObject(exampleData)
|
DeckConfig.DeckConfigsForUpdate.fromObject(exampleData)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -5,7 +5,7 @@
|
||||||
@typescript-eslint/no-non-null-assertion: "off",
|
@typescript-eslint/no-non-null-assertion: "off",
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { Backend } from "lib/proto";
|
import { DeckConfig } from "lib/proto";
|
||||||
import { postRequest } from "lib/postrequest";
|
import { postRequest } from "lib/postrequest";
|
||||||
import { Writable, writable, get, Readable, readable } from "svelte/store";
|
import { Writable, writable, get, Readable, readable } from "svelte/store";
|
||||||
import { isEqual, cloneDeep } from "lodash-es";
|
import { isEqual, cloneDeep } from "lodash-es";
|
||||||
|
@ -14,16 +14,16 @@ import type { DynamicSvelteComponent } from "sveltelib/dynamicComponent";
|
||||||
|
|
||||||
export async function getDeckOptionsInfo(
|
export async function getDeckOptionsInfo(
|
||||||
deckId: number
|
deckId: number
|
||||||
): Promise<Backend.DeckConfigsForUpdate> {
|
): Promise<DeckConfig.DeckConfigsForUpdate> {
|
||||||
return Backend.DeckConfigsForUpdate.decode(
|
return DeckConfig.DeckConfigsForUpdate.decode(
|
||||||
await postRequest("/_anki/deckConfigsForUpdate", JSON.stringify({ deckId }))
|
await postRequest("/_anki/deckConfigsForUpdate", JSON.stringify({ deckId }))
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
export async function saveDeckOptions(
|
export async function saveDeckOptions(
|
||||||
input: Backend.UpdateDeckConfigsRequest
|
input: DeckConfig.UpdateDeckConfigsRequest
|
||||||
): Promise<void> {
|
): Promise<void> {
|
||||||
const data: Uint8Array = Backend.UpdateDeckConfigsRequest.encode(input).finish();
|
const data: Uint8Array = DeckConfig.UpdateDeckConfigsRequest.encode(input).finish();
|
||||||
await postRequest("/_anki/updateDeckConfigs", data);
|
await postRequest("/_anki/updateDeckConfigs", data);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -31,7 +31,7 @@ export async function saveDeckOptions(
|
||||||
export type DeckOptionsId = number;
|
export type DeckOptionsId = number;
|
||||||
|
|
||||||
export interface ConfigWithCount {
|
export interface ConfigWithCount {
|
||||||
config: Backend.DeckConfig;
|
config: DeckConfig.DeckConfig;
|
||||||
useCount: number;
|
useCount: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -48,14 +48,14 @@ export interface ConfigListEntry {
|
||||||
current: boolean;
|
current: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
type ConfigInner = Backend.DeckConfig.Config;
|
type ConfigInner = DeckConfig.DeckConfig.Config;
|
||||||
export class DeckOptionsState {
|
export class DeckOptionsState {
|
||||||
readonly currentConfig: Writable<ConfigInner>;
|
readonly currentConfig: Writable<ConfigInner>;
|
||||||
readonly currentAuxData: Writable<Record<string, unknown>>;
|
readonly currentAuxData: Writable<Record<string, unknown>>;
|
||||||
readonly configList: Readable<ConfigListEntry[]>;
|
readonly configList: Readable<ConfigListEntry[]>;
|
||||||
readonly parentLimits: Readable<ParentLimits>;
|
readonly parentLimits: Readable<ParentLimits>;
|
||||||
readonly cardStateCustomizer: Writable<string>;
|
readonly cardStateCustomizer: Writable<string>;
|
||||||
readonly currentDeck: Backend.DeckConfigsForUpdate.CurrentDeck;
|
readonly currentDeck: DeckConfig.DeckConfigsForUpdate.CurrentDeck;
|
||||||
readonly defaults: ConfigInner;
|
readonly defaults: ConfigInner;
|
||||||
readonly addonComponents: Writable<DynamicSvelteComponent[]>;
|
readonly addonComponents: Writable<DynamicSvelteComponent[]>;
|
||||||
readonly v3Scheduler: boolean;
|
readonly v3Scheduler: boolean;
|
||||||
|
@ -70,12 +70,13 @@ export class DeckOptionsState {
|
||||||
private removedConfigs: DeckOptionsId[] = [];
|
private removedConfigs: DeckOptionsId[] = [];
|
||||||
private schemaModified: boolean;
|
private schemaModified: boolean;
|
||||||
|
|
||||||
constructor(targetDeckId: number, data: Backend.DeckConfigsForUpdate) {
|
constructor(targetDeckId: number, data: DeckConfig.DeckConfigsForUpdate) {
|
||||||
this.targetDeckId = targetDeckId;
|
this.targetDeckId = targetDeckId;
|
||||||
this.currentDeck = data.currentDeck as Backend.DeckConfigsForUpdate.CurrentDeck;
|
this.currentDeck =
|
||||||
|
data.currentDeck as DeckConfig.DeckConfigsForUpdate.CurrentDeck;
|
||||||
this.defaults = data.defaults!.config! as ConfigInner;
|
this.defaults = data.defaults!.config! as ConfigInner;
|
||||||
this.configs = data.allConfig.map((config) => {
|
this.configs = data.allConfig.map((config) => {
|
||||||
const configInner = config.config as Backend.DeckConfig;
|
const configInner = config.config as DeckConfig.DeckConfig;
|
||||||
return {
|
return {
|
||||||
config: configInner,
|
config: configInner,
|
||||||
useCount: config.useCount!,
|
useCount: config.useCount!,
|
||||||
|
@ -150,9 +151,9 @@ export class DeckOptionsState {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Clone the current config, making it current.
|
/// Clone the current config, making it current.
|
||||||
private addConfigFrom(name: string, source: Backend.DeckConfig.IConfig): void {
|
private addConfigFrom(name: string, source: DeckConfig.DeckConfig.IConfig): void {
|
||||||
const uniqueName = this.ensureNewNameUnique(name);
|
const uniqueName = this.ensureNewNameUnique(name);
|
||||||
const config = Backend.DeckConfig.create({
|
const config = DeckConfig.DeckConfig.create({
|
||||||
id: 0,
|
id: 0,
|
||||||
name: uniqueName,
|
name: uniqueName,
|
||||||
config: cloneDeep(source),
|
config: cloneDeep(source),
|
||||||
|
@ -188,7 +189,7 @@ export class DeckOptionsState {
|
||||||
this.updateConfigList();
|
this.updateConfigList();
|
||||||
}
|
}
|
||||||
|
|
||||||
dataForSaving(applyToChildren: boolean): Backend.UpdateDeckConfigsRequest {
|
dataForSaving(applyToChildren: boolean): DeckConfig.UpdateDeckConfigsRequest {
|
||||||
const modifiedConfigsExcludingCurrent = this.configs
|
const modifiedConfigsExcludingCurrent = this.configs
|
||||||
.map((c) => c.config)
|
.map((c) => c.config)
|
||||||
.filter((c, idx) => {
|
.filter((c, idx) => {
|
||||||
|
@ -202,7 +203,7 @@ export class DeckOptionsState {
|
||||||
// current must come last, even if unmodified
|
// current must come last, even if unmodified
|
||||||
this.configs[this.selectedIdx].config,
|
this.configs[this.selectedIdx].config,
|
||||||
];
|
];
|
||||||
return Backend.UpdateDeckConfigsRequest.create({
|
return DeckConfig.UpdateDeckConfigsRequest.create({
|
||||||
targetDeckId: this.targetDeckId,
|
targetDeckId: this.targetDeckId,
|
||||||
removedConfigIds: this.removedConfigs,
|
removedConfigIds: this.removedConfigs,
|
||||||
configs,
|
configs,
|
||||||
|
|
|
@ -4,4 +4,6 @@
|
||||||
import { anki } from "./backend_proto";
|
import { anki } from "./backend_proto";
|
||||||
import Backend = anki.backend;
|
import Backend = anki.backend;
|
||||||
import Cards = anki.cards;
|
import Cards = anki.cards;
|
||||||
export { Backend, Cards };
|
import DeckConfig = anki.deckconfig;
|
||||||
|
import Notetypes = anki.notetypes;
|
||||||
|
export { Backend, Cards, DeckConfig, Notetypes };
|
||||||
|
|
Loading…
Reference in a new issue