   /**
    * Submit a score for a character.
    * Handles W.Rank snapshot at submission time.
    */
   async submit({ character, borrowedFrom, pts, k, d, atk, def, heal, slot, submittedByOfficer }: {
     character:          Character;
     borrowedFrom?:      UserKey;
     pts:                number;
     k?:                 number;
     d?:                 number;
     atk?:              number;
     def?:              number;
     heal?:             number;
     slot:               SlotHour;
     submittedByOfficer?: boolean;
   }): Promise<void> {
     const date       = new Date().toISOString().slice(0, 10);
     const historyKey = TGKey.current({ slot });
     const history    = loadHistory(historyKey);
 
     // Snapshot W.Rank before recording score
     const existingEntry = WRank.entry(character.name, character.nation);
     const wRankAtSubmission = existingEntry ? {
       rank:  existingEntry.currentRank,
       delta: existingEntry.currentRank - (existingEntry.previousRank ?? existingEntry.currentRank),
     } : undefined;
 
     const score: TGScore = {
       userKey:            character.ownerKey,
       playedBy:           borrowedFrom,
       characterName:      character.name,
       class:              character.class.key,
       nation:             character.nation,
       pts,
       k,
       d,
       atk,
       def,
       heal,
       submittedAt:        new Date().toISOString(),
       slot,
       date,
       submittedByOfficer: submittedByOfficer ?? false,
       wRankAtSubmission,
     };
 
     // Upsert — replace existing score for same character/slot
     history.scores = history.scores.filter(
       (s) => !(s.userKey === character.ownerKey &&
                s.characterName === character.name &&
                s.slot === slot &&
                s.date === date)
     );
     history.scores.push(score);
     saveHistory(historyKey, history);
 
     // Record in W.Rank
     WRank.recordScore(
       character.ownerKey,
       character.name,
       character.class.key,
       character.nation,
       pts,
       historyKey
     );
     await RuntimeEvents.emit("scoreSubmitted", { historyKey, character });
   },