保存独立KV用户服务、固定会话存档与原业务接线,以及C3d资料缓存和C3e本人统计写。 保留原PF/AGG路线、业务公式和时序;榜单读取、好友资料、公告、匹配及首场景闸仍待完成。 验证:ServiceHost两条件各33组646断言;Unity CLI Loop编译0错误269警告。 包含相关方案、评审裁决、测试及状态文档。未操作服务器、正式账号或打包。
63 lines
2.6 KiB
Plaintext
63 lines
2.6 KiB
Plaintext
using System;
|
|
using System.Threading;
|
|
using System.Threading.Tasks;
|
|
|
|
namespace game.PlayerDataStorage
|
|
{
|
|
// A store belongs to one login. Callers retain this instance across awaits.
|
|
public interface IPlayerSaveStore
|
|
{
|
|
bool IsCurrent { get; }
|
|
PlayerSaveReadResult Read(string key);
|
|
PlayerSaveWriteResult Write(string key, string value, bool remoteStore = true);
|
|
Task<PlayerSaveConfirmation> WriteAndConfirmAsync(string key, string value, CancellationToken token = default);
|
|
Task<PlayerSaveConfirmation> ConfirmAsync(PlayerSaveReceipt receipt, CancellationToken token = default);
|
|
Task<PlayerSaveConfirmation> FlushAsync(CancellationToken token = default);
|
|
}
|
|
|
|
public sealed class PlayerSaveReadResult
|
|
{
|
|
public bool Success => Error == null;
|
|
public bool? Found { get; }
|
|
public string Value { get; }
|
|
public string Error { get; }
|
|
internal PlayerSaveReadResult(bool found, string value) { Found = found; Value = value; }
|
|
internal PlayerSaveReadResult(string error) { Error = error ?? "ReadFailed"; }
|
|
public string ValueOrThrow()
|
|
{
|
|
if (!Success) throw new InvalidOperationException("Player save read failed: " + Error);
|
|
return Value;
|
|
}
|
|
}
|
|
|
|
public sealed class PlayerSaveReceipt
|
|
{
|
|
internal readonly IPlayerSaveStore Store;
|
|
internal readonly object Ticket;
|
|
internal PlayerSaveReceipt(IPlayerSaveStore store, object ticket) { Store = store; Ticket = ticket; }
|
|
}
|
|
|
|
public sealed class PlayerSaveWriteResult
|
|
{
|
|
public bool Accepted => Error == null;
|
|
public string Error { get; }
|
|
public PlayerSaveReceipt Receipt { get; }
|
|
internal PlayerSaveWriteResult(PlayerSaveReceipt receipt) { Receipt = receipt; }
|
|
internal PlayerSaveWriteResult(string error) { Error = error ?? "WriteRejected"; }
|
|
public void RequireAccepted()
|
|
{
|
|
if (!Accepted) throw new InvalidOperationException("Player save write rejected: " + Error);
|
|
}
|
|
}
|
|
|
|
// Buffered and LocalOnly are deliberately different from cloud confirmation.
|
|
public enum PlayerSaveStatus { Confirmed, Buffered, LocalOnly, Rejected, Superseded, Unknown, Cancelled }
|
|
public sealed class PlayerSaveConfirmation
|
|
{
|
|
public PlayerSaveStatus Status { get; }
|
|
public bool Confirmed => Status == PlayerSaveStatus.Confirmed;
|
|
public string Error { get; }
|
|
internal PlayerSaveConfirmation(PlayerSaveStatus status, string error = null) { Status = status; Error = error; }
|
|
}
|
|
}
|