> For the complete documentation index, see [llms.txt](https://docs.convai.com/api-docs/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.convai.com/api-docs/zh/cha-jian-yu-ji-cheng/convai-unity-sdk/features/long-term-memory/long-term-memory-scripting-reference.md).

# 长期记忆脚本参考

Convai Unity SDK 中所有长期记忆脚本 API 的完整参考。涵盖 `ConvaiRestClient` 入口点、上面每个方法、 `MemoryService` 和 `EndUsersService`上的记忆相关方法、 `CharacterService`、身份接口以及所有数据模型类型。

{% hint style="warning" %}
**测试版 API。** `MemoryService` 和 `EndUsersService` 方法使用 Convai 测试版 API 端点。 `CharacterService` 方法（`GetMemoryEnabledAsync`, `SetMemoryEnabledAsync`）使用标准生产端点。签名稳定，但可能会更改。请在生产环境中锁定你的 SDK 版本。
{% endhint %}

***

### `ConvaiRestClient` 入口点

```csharp
命名空间 Convai.RestAPI

public sealed class ConvaiRestClient : IDisposable
```

所有 LTM 操作的主要入口。线程安全且可复用——请使用 `using` 语句在每次操作后释放，或者在应用程序生命周期内复用单个实例。

**构造函数：**

```csharp
// 使用 API 密钥字符串初始化（使用默认选项）
public ConvaiRestClient(string apiKey)

// 使用完整选项初始化（自定义超时、传输）
public ConvaiRestClient(ConvaiRestClientOptions options)
```

**与 LTM 相关的属性：**

| 属性         | 类型                 | 描述              |
| ---------- | ------------------ | --------------- |
| `Memory`   | `MemoryService`    | 按角色作用域划分的长期记忆操作 |
| `EndUsers` | `EndUsersService`  | 终端用户身份和记录管理     |
| `角色`       | `CharacterService` | 角色配置，包括记忆启用/禁用  |

**使用模式：**

```csharp
// 始终使用 'using' — ConvaiRestClient 实现了 IDisposable
using var client = new ConvaiRestClient(ConvaiSettings.Instance.ApiKey);
var response = await client.Memory.ListAsync(characterId, endUserId);
```

***

### `MemoryService`

```csharp
命名空间 Convai.RestAPI.Services

public sealed class MemoryService
```

通过以下方式访问 `ConvaiRestClient.Memory`。所有方法均为异步并支持取消。

***

#### `AddAsync`

为用户-角色对注入一个或多个自然语言事实。Convai 会对语义重叠的事实进行去重。

```csharp
public Task<AddMemoriesResponse> AddAsync(
    string characterId,
    string endUserId,
    IReadOnlyList<string> memories,
    IReadOnlyDictionary<string, object>? metadata = null,
    CancellationToken cancellationToken = default)
```

| 参数                  | 类型                                     | 描述                  |
| ------------------- | -------------------------------------- | ------------------- |
| `characterId`       | `string`                               | 来自 Convai 控制台的角色 ID |
| `endUserId`         | `string`                               | 稳定的用户标识符            |
| `memories`          | `IReadOnlyList<string>`                | 要存储的自然语言事实字符串       |
| `metadata`          | `IReadOnlyDictionary<string, object>?` | 附加到所有已添加记录的可选键值数据   |
| `cancellationToken` | `CancellationToken`                    | 可选的取消支持             |

**返回：** `Task<AddMemoriesResponse>`

***

#### `ListAsync`

使用按页码分页检索用户-角色对的存储记忆记录。

```csharp
public Task<MemoryListResponse> ListAsync(
    string characterId,
    string endUserId,
    int page = 1,
    int pageSize = 50,
    CancellationToken cancellationToken = default)
```

| 参数                  | 类型                  | 默认   | 描述         |
| ------------------- | ------------------- | ---- | ---------- |
| `characterId`       | `string`            | —    | 角色 ID      |
| `endUserId`         | `string`            | —    | 用户标识符      |
| `page`              | `int`               | `1`  | 页码（从 1 开始） |
| `pageSize`          | `int`               | `50` | 每页记录数      |
| `cancellationToken` | `CancellationToken` | —    | 可选取消       |

**返回：** `Task<MemoryListResponse>`

***

#### `GetAsync`

按 ID 检索单条记忆记录。

```csharp
public Task<MemoryRecord> GetAsync(
    string characterId,
    string endUserId,
    string memoryId,
    CancellationToken cancellationToken = default)
```

**返回：** `Task<MemoryRecord>`

***

#### `DeleteAsync`

按 ID 删除单条记忆记录。

```csharp
public Task<MemoryDeleteResponse> DeleteAsync(
    string characterId,
    string endUserId,
    string memoryId,
    CancellationToken cancellationToken = default)
```

**返回：** `Task<MemoryDeleteResponse>`

***

#### `DeleteAllAsync`

{% hint style="danger" %}
永久删除指定用户-角色对的所有记忆记录。无法撤销。
{% endhint %}

```csharp
public Task<MemoryDeleteAllResponse> DeleteAllAsync(
    string characterId,
    string endUserId,
    CancellationToken cancellationToken = default)
```

**返回：** `Task<MemoryDeleteAllResponse>`

***

### `EndUsersService`

```csharp
命名空间 Convai.RestAPI.Services

public sealed class EndUsersService
```

通过以下方式访问 `ConvaiRestClient.EndUsers`。所有方法均为异步并支持取消。

***

#### `GetAsync`

按标识符检索单个终端用户记录。

```csharp
public Task<EndUserDetails> GetAsync(
    string endUserId,
    CancellationToken cancellationToken = default)
```

**返回：** `Task<EndUserDetails>`

***

#### `ListAsync`

使用基于游标的分页和可选日期过滤列出终端用户记录。

```csharp
public Task<EndUsersListResponse> ListAsync(
    int limit = 50,
    string? cursor = null,
    string? activeAfter = null,
    string? activeBefore = null,
    CancellationToken cancellationToken = default)
```

| 参数                  | 类型                  | 默认     | 描述                        |
| ------------------- | ------------------- | ------ | ------------------------- |
| `limit`             | `int`               | `50`   | 每页记录数                     |
| `cursor`            | `string?`           | `null` | 来自上一响应的分页游标               |
| `activeAfter`       | `string?`           | `null` | ISO 8601 — 仅返回在此日期之后活跃的用户 |
| `activeBefore`      | `string?`           | `null` | ISO 8601 — 仅返回在此日期之前活跃的用户 |
| `cancellationToken` | `CancellationToken` | —      | 可选取消                      |

**返回：** `Task<EndUsersListResponse>`

***

#### `UpdateMetadataAsync`

对终端用户记录的元数据字典进行补丁更新。补丁中未包含的键将被保留。

```csharp
public Task<EndUserUpdateResponse> UpdateMetadataAsync(
    string endUserId,
    IReadOnlyDictionary<string, object> metadataPatch,
    CancellationToken cancellationToken = default)
```

**返回：** `Task<EndUserUpdateResponse>`

***

#### `DeleteAsync`

{% hint style="danger" %}
删除终端用户记录以及该用户在 **所有角色中的**所有记忆记录。无法撤销。
{% endhint %}

```csharp
public Task<EndUserDeleteResponse> DeleteAsync(
    string endUserId,
    CancellationToken cancellationToken = default)
```

**返回：** `Task<EndUserDeleteResponse>`

***

### `CharacterService` — 记忆方法

```csharp
命名空间 Convai.RestAPI.Services

public sealed class CharacterService
```

通过以下方式访问 `ConvaiRestClient.Characters`。这两个方法控制角色的 LTM 启用/禁用状态。

***

#### `GetMemoryEnabledAsync`

返回值 `true` 如果该角色已启用长期记忆。

```csharp
public Task<bool> GetMemoryEnabledAsync(
    string characterId,
    CancellationToken cancellationToken = default)
```

***

#### `SetMemoryEnabledAsync`

为该角色启用或禁用长期记忆。会全局影响该角色的所有部署。

```csharp
public Task SetMemoryEnabledAsync(
    string characterId,
    bool enabled,
    CancellationToken cancellationToken = default)
```

***

### 身份接口

#### `IEndUserIdentityProvider`

```csharp
命名空间 Convai.Domain.Identity

public interface IEndUserIdentityProvider
{
    string GetEndUserId();
}
```

实现此接口以提供自定义用户标识符。在第一次 `ConvaiManager.SetEndUserIdentityProvider(provider)` 调用之前 `ConnectAsync` 。

***

#### `IEndUserMetadataProvider`

```csharp
命名空间 Convai.Domain.Identity

public interface IEndUserMetadataProvider
{
    IReadOnlyDictionary<string, object> GetEndUserMetadata();
}
```

可选地与 `IEndUserIdentityProvider` 一起实现，以发送显示元数据。 `"name"` 键会填充 `EndUserDetails.DisplayName` 在编辑器面板中显示。使用以下方式注册： `ConvaiManager.SetEndUserMetadataProvider(provider)`.

***

#### `IEndUserIdProvider`

```csharp
命名空间 Convai.Domain.Identity

public interface IEndUserIdProvider
{
    string GenerateEndUserId();
}
```

用于生成稳定 ID 的底层接口。 `DeviceEndUserIdProvider` 同时实现了 `IEndUserIdProvider` 和 `IEndUserIdentityProvider`。对于自定义提供程序，请直接实现 `IEndUserIdentityProvider` ——它是 `ConvaiManager.SetEndUserIdentityProvider` 所接受的接口。

***

#### `DeviceEndUserIdProvider`

```csharp
命名空间 Convai.Runtime.Identity

public sealed class DeviceEndUserIdProvider : IEndUserIdProvider, IEndUserIdentityProvider
```

默认身份提供程序。自动注册——无需配置。

| 上下文               | 行为                                           |
| ----------------- | -------------------------------------------- |
| Unity 编辑器         | 读取或在 `PlayerPrefs["convai.end_user_id"]`     |
| 玩家构建版本 — 设备 ID 有效 | 返回值 `SystemInfo.deviceUniqueIdentifier`      |
| 玩家构建版本 — 设备 ID 无效 | 回退到 `PlayerPrefs["convai.end_user_id"]` GUID |

GUID 格式：不含连字符的 32 位十六进制字符串（例如， `a1b2c3d4e5f6789012345678abcdef01`).

***

### 数据模型

#### `MemoryRecord`

```csharp
命名空间 Convai.RestAPI.Internal

public class MemoryRecord
```

| 属性          | JSON 键         | 类型                           | 描述               |
| ----------- | -------------- | ---------------------------- | ---------------- |
| `Id`        | `"id"`         | `string`                     | 唯一记录标识符          |
| `Memory`    | `"memory"`     | `string`                     | 以自然语言句子形式存储的事实   |
| `CreatedAt` | `"created_at"` | `string`                     | ISO 8601 创建时间戳   |
| `UpdatedAt` | `"updated_at"` | `string`                     | ISO 8601 最后更新时间戳 |
| `Metadata`  | `"metadata"`   | `Dictionary<string, object>` | 可选附加键值数据         |

***

#### `AddMemoriesResponse`

| 属性         | JSON 键       | 类型                      | 描述           |
| ---------- | ------------ | ----------------------- | ------------ |
| `Memories` | `"memories"` | `List<MemoryAddResult>` | 每个提交事实对应一个结果 |

#### `MemoryAddResult`

| 属性       | JSON 键     | 类型       | 描述                               |
| -------- | ---------- | -------- | -------------------------------- |
| `Id`     | `"id"`     | `string` | 已创建或更新记录的 ID                     |
| `事件`     | `"event"`  | `string` | `"add"` 用于新记录； `"update"` 用于去重更新 |
| `Memory` | `"memory"` | `string` | 由 Convai 存储的规范化事实文本              |

***

#### `MemoryListResponse`

| 属性           | JSON 键          | 类型                   | 描述         |
| ------------ | --------------- | -------------------- | ---------- |
| `Memories`   | `"memories"`    | `List<MemoryRecord>` | 此页上的记录     |
| `TotalCount` | `"total_count"` | `int`                | 跨所有页面的记录总数 |
| `Page`       | `"page"`        | `int`                | 当前页码       |
| `PageSize`   | `"page_size"`   | `int`                | 每页记录数      |
| `HasMore`    | `"has_more"`    | `bool`               | 是否存在更多页面   |

***

#### `MemoryDeleteResponse`

| 属性         | JSON 键        | 类型       | 描述                 |
| ---------- | ------------- | -------- | ------------------ |
| `Message`  | `"message"`   | `string` | 人类可读的结果消息          |
| `MemoryId` | `"memory_id"` | `string` | 已删除记录的 ID          |
| `Deleted`  | `"deleted"`   | `bool`   | `true` 如果找到了并删除了记录 |

***

#### `MemoryDeleteAllResponse`

| 属性            | JSON 键           | 类型       | 描述         |
| ------------- | ---------------- | -------- | ---------- |
| `Message`     | `"message"`      | `string` | 人类可读的结果消息  |
| `CharacterId` | `"character_id"` | `string` | 其记忆已被清除的角色 |
| `最终用户 ID`     | `"end_user_id"`  | `string` | 其记忆已被清除的用户 |

***

#### `EndUserDetails`

| 属性               | JSON 键                | 类型                           | 备注                                                                                                               |
| ---------------- | --------------------- | ---------------------------- | ---------------------------------------------------------------------------------------------------------------- |
| `最终用户 ID`        | `"end_user_id"`       | `string`                     | 稳定标识符                                                                                                            |
| `LastActiveTs`   | `"last_active_ts"`    | `string`                     | ISO 8601 最后会话时间戳                                                                                                 |
| `LastLtmUsageTs` | `"last_ltm_usage_ts"` | `string`                     | ISO 8601 最后一次 LTM 交互                                                                                             |
| `Metadata`       | `"end_user_metadata"` | `Dictionary<string, object>` | 由以下发送 `IEndUserMetadataProvider`                                                                                 |
| `DisplayName`    | —                     | `string`                     | **计算得出** — `Metadata["name"]` 如果存在且非空；否则 `"User {EndUserId[..8]}"`，并可选附加相对最后活跃时间（例如， `"User a1b2c3d4 (3d ago)"`) |
| `ShortId`        | —                     | `string`                     | **计算得出** — 的截断形式 `最终用户 ID` 用于显示                                                                                  |

***

#### `EndUsersListResponse`

| 属性           | JSON 键          | 类型                     | 描述                        |
| ------------ | --------------- | ---------------------- | ------------------------- |
| `EndUsers`   | `"end_users"`   | `List<EndUserDetails>` | 此页上的记录                    |
| `TotalCount` | `"total_count"` | `int`                  | 终端用户记录总数                  |
| `NextCursor` | `"next_cursor"` | `string`               | 下一页的游标令牌； `null` 当没有后续页面时 |
| `HasMore`    | `"has_more"`    | `bool`                 | 是否存在更多页面                  |

***

#### `EndUserUpdateResponse`

扩展 `EndUserDetails` 并增加一个字段：

| 属性        | JSON 键      | 类型       | 描述        |
| --------- | ----------- | -------- | --------- |
| `Message` | `"message"` | `string` | 人类可读的结果消息 |

***

#### `EndUserDeleteResponse`

| 属性        | JSON 键          | 类型       | 描述                 |
| --------- | --------------- | -------- | ------------------ |
| `Message` | `"message"`     | `string` | 人类可读的结果消息          |
| `最终用户 ID` | `"end_user_id"` | `string` | 已删除用户的 ID          |
| `Deleted` | `"deleted"`     | `bool`   | `true` 如果找到了并删除了记录 |

***

#### `MemorySettings`

| 属性          | JSON 键      | 类型     | 默认      | 描述          |
| ----------- | ----------- | ------ | ------- | ----------- |
| `IsEnabled` | `"enabled"` | `bool` | `false` | 角色是否启用了 LTM |

***

### 错误处理

失败的操作会抛出 `ConvaiRestException`:

```csharp
try
{
    var response = await client.Memory.ListAsync(characterId, endUserId);
}
catch (ConvaiRestException ex)
{
    Debug.LogError($"LTM API error {ex.StatusCode}: {ex.Message}");
}
```

参见 [排查长期记忆问题](/api-docs/zh/cha-jian-yu-ji-cheng/convai-unity-sdk/features/long-term-memory/troubleshooting-and-diagnostics.md) 以获取完整的 HTTP 状态码参考。

***

### 下一步

{% content-ref url="/pages/d41fbdd4f21a090aa6d7e39be7a7eb215d0435c2" %}
[长期记忆使用示例](/api-docs/zh/cha-jian-yu-ji-cheng/convai-unity-sdk/features/long-term-memory/usage-examples.md)
{% endcontent-ref %}

{% content-ref url="/pages/7a63a06da6d31beb01ce563b8e8b3398f3436122" %}
[排查长期记忆问题](/api-docs/zh/cha-jian-yu-ji-cheng/convai-unity-sdk/features/long-term-memory/troubleshooting-and-diagnostics.md)
{% endcontent-ref %}


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.convai.com/api-docs/zh/cha-jian-yu-ji-cheng/convai-unity-sdk/features/long-term-memory/long-term-memory-scripting-reference.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
