For the complete documentation index, see llms.txt. This page is also available as Markdown.

自定义持久化提供器

将默认会话存储替换为你自己的远程服务、加密文件存储或用于测试的内存实现。

Convai Unity SDK 将会话数据——连接状态、会话 ID、恢复令牌以及编辑器端用户 GUID——存储在 PlayerPrefs 默认通过 PlayerPrefsKeyValueStore。如果 PlayerPrefs 如果适用于你的部署,你就不需要此页面。 当你需要云端保存、加密存储、服务器端会话管理,或用于自动化测试和 CI 的隔离存储时,请替换持久化提供程序。

SDK 写入存储的内容

键前缀
内容
为什么这很重要

convai.session.*

会话 ID 和恢复令牌

允许 SDK 在不重新启动 AI 回合的情况下恢复已断开的会话

convai.end_user_id

仅编辑器可用的设备 GUID(回退)

由 DeviceEndUserIdProvider 在 Unity 编辑器中使用,当无法获取硬件 ID 时

convai.prefs.*

用户偏好设置(例如静音状态)

在应用启动之间持久保存 SDK 级设置

替换持久化提供程序也就替换了所有这些内容的读写位置。你的实现必须处理 SDK 涉及的每一个键——下面的适配器模式可确保不会遗漏任何内容。

持久化接口

IKeyValueStore — 简单存储

namespace Convai.Domain.Abstractions
{
    public interface IKeyValueStore
    {
        string GetString(string key, string defaultValue = null);
        void   SetString(string key, string value);
        bool   HasKey(string key);
        void   DeleteKey(string key);
        void   Save();
    }
}

Save() 在写入操作后被调用。对于内存存储,它是空操作;对于文件后端存储,它会刷新到磁盘。在不需要异步操作的本地存储场景中实现此接口。

IPersistenceProvider — 功能完整的存储

builder.UsePersistence() 接受 IPersistenceProvider. 如果你的实现是 IKeyValueStore,请将其包装在适配器中(参见 适配器模式 下文)。异步操作(SyncAsync, SaveVersionedAsync)如果你的后端是同步的,可以返回占位结果。

要实现哪个接口:

场景
实现

本地文件、加密 SQLite、内存

IKeyValueStore

云端保存、服务器端存储、多设备同步

IPersistenceProvider

现有 IKeyValueStore 并叠加云同步

两者都要——将同步/版本化操作委托给云客户端

支持类型

PersistenceResult

成员
类型
描述

成功

bool

操作是否成功。

错误消息

string

错误描述,如果 成功 为 false.

时间戳

DateTime

操作完成时刻。

版本

long

操作后的版本号(用于版本化操作)。

PersistenceResult.Succeeded(version)

静态

创建一个成功结果。

PersistenceResult.Failed(error)

静态

创建一个失败结果。

ConflictResolutionStrategy

由 SaveVersionedAsync 用于在异步/云场景中解决写入冲突。

值
行为

LastWriteWins

基于时间戳,最近写入的值获胜。

HighestVersionWins

版本号更高的值获胜。

LocalWins

本地数据始终覆盖远程数据。

RemoteWins

远程数据始终覆盖本地数据。

Manual

将冲突信息返回给调用方以便显式解决。

PersistenceOptions

实现示例

内存存储(测试 / CI)

适用于自动化测试和 CI 运行,在这些场景中,运行之间的持久状态会破坏结果。

加密文件存储

满足禁止明文的合规要求 PlayerPrefs 用于会话数据。

调用 Save() 在每次写入后,或定期刷新。写入会缓存在内存中——自上次 Save() 以来写入的数据会在崩溃时丢失。

适用于 IKeyValueStore 实现的适配器模式

builder.UsePersistence() 需要 IPersistenceProvider. 使用此适配器来包装任何 IKeyValueStore:

DeleteAll(string prefix) 在此适配器中返回失败结果。SDK 会在 DeleteAll 期间调用会话重置操作。如果你的部署需要完整的会话重置,请实现 DeleteAll 通过遍历存储的键并移除匹配前缀的键来实现。

注册提供器

故障排除

症状
可能原因
修复方法

重启后会话未恢复

GetString 返回 null 在重新加载时用于会话键

确保 Save() 会在应用退出前同步调用。订阅 Application.quitting 。

NullReferenceException 内部的 IPersistenceProvider 实现

在存储初始化之前调用异步方法

在提供程序的构造函数中初始化后端存储,然后再 UsePersistence() 被调用。

崩溃时数据丢失

SetString 写入会缓存在内存中,并且 Save() 未被调用

调用 Save() 在每次写入后,或在定时器上刷新。

会话重置没有清除所有 SDK 数据

DeleteAll(prefix) 在适配器中返回失败结果

实现 DeleteAll 通过遍历存储的键集合并移除与前缀匹配的条目。

下一步

凭证、身份和存储运行时模块系统实现自定义模块

最后更新于

这有帮助吗?