跳到主要内容

API 参考:getOwnedObjects

检索由特定 32 字节 Sui 钱包地址拥有的链上对象的分页列表。

使用此方法可填充钱包仪表盘、用户库存界面和代币余额列表。由于单个账户可能持有数千个对象,Sui JSON-RPC API 会通过基于游标的分页机制,分页返回拥有的对象。由于 getOwnedObjects 是一项直接从全节点本地状态提供的读取操作,因此它会立即执行,无需提交交易或消耗 gas。

  • 类: SuiClient
  • 包: @mysten/sui/client
  • 操作类型: 读取操作(无需 gas,无需钱包签名)

概述​

调用 getOwnedObjects 会查询全节点索引,查找所有权归属于目标地址(AddressOwner)的对象。为避免高延迟和网络超时,全节点会分页返回结果,而非在单次响应中返回全部库存。

分页循环可视化​

游标分页流程图

签名​

签名
client.getOwnedObjects(input: GetOwnedObjectsParams): Promise<PaginatedObjectsResponse>

参数​

该方法接受一个包含以下属性的配置对象:

参数类型必填描述
ownerstring是目标钱包的 32 字节十六进制地址。
filterSuiObjectDataFilter否按类型、包或模块过滤结果的条件。
optionsSuiObjectDataOptions否包含额外详细信息的标志(例如 showType, showContent, showDisplay)。
cursorstring | null否来自先前响应的 nextCursor 令牌,用于获取后续页面。
limitnumber否每页返回的最大条目数(在公共 RPC 节点上,默认值和最大值通常为 50)。

SuiObjectDataFilter​

filter 参数可缩小全节点上的查询范围,从而节省带宽并减少客户端处理负担:

过滤键值类型描述
MatchAllSuiObjectDataFilter[]逻辑与(AND)。对象必须满足所有提供的过滤条件。
MatchAnySuiObjectDataFilter[]逻辑或(OR)。对象只要满足所提供的任一筛选条件即可。
StructTypestring对完全限定的 Move Struct 类型的精确匹配(例如 0x2::coin::Coin<0x2::sui::SUI>)。
Packagestring匹配从指定包 ID 内的模块实例化的任何对象。
MoveModule{ package: string, module: string }匹配包中特定模块内定义的任何对象。

返回值​

返回一个 Promise,该 Promise 解析为 PaginatedObjectsResponse 对象:

响应
{
"data": [
{ "data": { "objectId": "0xA...", "version": "1", "type": "0x2::coin::Coin<0x2::sui::SUI>" } },
{ "data": { "objectId": "0xB...", "version": "4", "type": "0x2::coin::Coin<0x2::sui::SUI>" } }
],
"hasNextPage": true,
"nextCursor": "0x12345...ResultCursor"
}

响应封装体包含以下字段:

字段类型描述
dataSuiObjectResponse[]当前页面的对象响应封装体数组。
hasNextPageboolean指示是否存在其他页面的对象。
nextCursorstring | null作为下次调用中游标传递的不透明分页令牌。当 hasNextPage 为 false 时,此值为 null。

代码示例​

获取资产列表的第一页​

检索某个地址拥有的前 5 个对象:

basicInventory.js
const response = await client.getOwnedObjects({
owner: '0x0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef',
limit: 5,
options: { showType: true }
});

response.data.forEach((item) => {
if (item.data) {
console.log(`ID: ${item.data.objectId}, Type: ${item.data.type}`);
}
});

按 Move 结构类型过滤资产​

仅查询用户拥有的 SUI 代币对象,排除其他代币和 NFT:

filterCoins.js
const response = await client.getOwnedObjects({
owner: '0x0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef',
filter: {
StructType: '0x2::coin::Coin<0x2::sui::SUI>'
},
options: { showContent: true }
});

console.log(`找到 ${response.data.length} 个 SUI 代币对象`);

分页遍历所有拥有的对象​

使用 while 循环遍历地址拥有的每个对象:

pagination.js
let hasNextPage = true;
let nextCursor = null;
const allObjects = [];

while (hasNextPage) {
const response = await client.getOwnedObjects({
owner: '0x0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef',
cursor: nextCursor,
limit: 50
});

allObjects.push(...response.data);

hasNextPage = response.hasNextPage;
nextCursor = response.nextCursor;
}

console.log(`共获取对象总数:${allObjects.length}`);

常见错误​

错误代码原因解决方法
cursor_invalid传递给 cursor 的字符串已过期、格式错误,或源自其他查询。请传入前一次查询中 nextCursor 返回的精确字符串。
limit_exceeded请求的 limit 超出了全节点允许的最大页面大小(通常为 50)。将 limit 参数减少至 50 个或更少。

另请参阅​