背景简介GraphQL是由Facebook(现Meta)于2012年开发并在2015年开源的一种数据查询语言。与传统的RESTAPI相比,GraphQL提供了一种更加灵活高效的方式来请求和操作数据。通过其强类型系统和声明式查询语法,开发者可以在一次请求中精准获取所需的数据,避
GraphQL 是由 Facebook(现 Meta)于 2012 年开发并在 2015 年开源的一种数据查询语言。与传统的 REST API 相比,GraphQL 提供了一种更加灵活高效的方式来请求和操作数据。通过其强类型系统和声明式查询语法,开发者可以在一次请求中精准获取所需的数据,避免了冗余数据的传输和多次 API 调用的麻烦。
GraphQL 的发展经历了几个重要阶段:
GraphQL 被引入 Sui 区块链,旨在提供一种灵活高效的数据交互机制。通过 GraphQL 查询,开发者能够精确访问区块链上的动态数据(如交易、事件、对象等),实现高度自定义的链上分析和数据聚合需求。Sui GraphQL 还支持分片查询、分页和变量定义,为开发者提供更丰富的操作空间,同时优化了区块链节点的查询性能。
GraphQL 的引入不仅加速了 Sui 生态的开发效率,也为去中心化应用(DApps)的构建提供了强有力的支持,特别是在构建 DeFi、NFT 和社交应用时,开发者可以通过简单的查询语句获取复杂的数据组合。
通过本笔记的学习,我们可以了解如何在 Sui 中应用 GraphQL 进行高效开发,同时深入掌握其语法和操作模式。
GraphQL 服务允许通过 HTTP 头对请求行为进行调整。以下是常见头的用途:
x-sui-rpc-version
: 指定 RPC 版本(当前仅支持一个版本)。x-sui-rpc-show-usage
: 返回包含查询复杂度的额外信息。curl -i -X POST https://sui-mainnet.mystenlabs.com/graphql \
--header 'x-sui-rpc-show-usage: true' \
--header 'Content-Type: application/json' \
--data '{
"query": "query { epoch { referenceGasPrice } }"
}'
返回数据包括 referenceGasPrice
和额外的查询复杂度信息,例如输入/输出节点数、查询深度等。
变量允许动态输入,用以提高查询的可重用性。定义变量时需使用 $
符号,并指定类型(如 Int
)。变量在查询体中通过名称引用。
query ($epochID: Int) {
epoch(id: $epochID) {
referenceGasPrice
}
}
{
"epochID": 100
}
片段是可重用的查询片段,用于结构化和优化查询。以下片段示例展示了如何查询 Move 值。
query DynamicField {
object(
address: "0xb57fba584a700a5bcb40991e1b2e6bf68b0f3896d767a0da92e69de73de226ac"
) {
dynamicField(
name: {
type: "0x2::kiosk::Listing",
bcs: "NLArx1UJguOUYmXgNG8Pv8KbKXLjWtCi6i0Yeq1VhfwA",
}
) {
...DynamicFieldSelect
}
}
}
fragment DynamicFieldSelect on DynamicField {
name {
...MoveValueFields
}
value {
...DynamicFieldValueSelection
}
}
fragment MoveValueFields on MoveValue {
type {
repr
}
data
bcs
}
MoveValueFields
,避免冗长重复的字段定义。GraphQL 支持分页查询,用于处理大量结果。常见参数包括:
first
: 限制返回的最大数量,从开头截取。after
: 从指定游标(不包括)后开始。last
: 限制返回的最大数量,从结尾截取。before
: 从指定游标(不包括)前开始。查询第 97 个 epoch 的交易块:
query {
epoch(id: 97) {
transactionBlocks(first: 10) {
pageInfo {
hasNextPage
endCursor
}
nodes {
digest
sender {
address
}
gasInput {
gasPrice
gasBudget
}
}
}
}
}
GraphQL 服务对查询进行了以下限制:
{
serviceConfig {
maxQueryDepth
maxQueryNodes
maxOutputNodes
maxPageSize
requestTimeoutMs
}
}
通过 Sui 提供的在线 IDE,你可以轻松查看支持的 GraphQL schema。
在 IDE 中:
Ctrl+K
打开 Schema 搜索。query {
epoch {
referenceGasPrice
}
}
获取特定纪元(例如第100纪元)的详细信息,包括质押奖励、参考Gas价格、检查点数量和总Gas费用等。
query {
epoch(id: 100) {
epochId
totalStakeRewards
referenceGasPrice
totalCheckpoints
totalGasFees
storageFund {
totalObjectStorageRebates
nonRefundableBalance
}
}
}
通过交易摘要 (digest) 查找交易详细信息,例如 Gas 提供方地址、预算和执行效果。
query {
transactionBlock(digest: "FdKFgsQ9iRrxW6b1dh9WPGuNuaJWMXHJn1wqBQSqVqK2") {
gasInput {
gasSponsor {
address
}
gasPrice
gasBudget
}
effects {
status
timestamp
epoch {
epochId
referenceGasPrice
}
}
}
}
查询最近10条非系统交易:
query {
transactionBlocks(last: 10, filter: {kind: PROGRAMMABLE_TX}) {
nodes {
digest
kind {
__typename
}
}
}
}
查询涉及特定对象的交易:
query ($objectID: SuiAddress!) {
transactionBlocks(filter: {changedObject: $objectID}) {
nodes {
sender {
address
}
digest
}
}
}
变量:
{
"objectID": "0x11c6ae8432156527fc2e12e05ac7db79f2e972510a823a4ef2e670f27ad7b52f"
}
GraphQL可以通过别名和片段来优化查询结构。例如:
获取动态字段:
query DynamicField {
object(address: "0xb57fba584a700a5bcb40991e1b2e6bf68b0f3896d767a0da92e69de73de226ac") {
dynamicField(
name: {
type: "0x2::kiosk::Listing",
bcs: "NLArx1UJguOUYmXgNG8Pv8KbKXLjWtCi6i0Yeq1VhfwA"
}
) {
name {
...MoveValueFields
}
value {
__typename
... on MoveObject {
hasPublicTransfer
contents {
...MoveValueFields
}
}
}
}
}
}
fragment MoveValueFields on MoveValue {
type {
repr
}
data
bcs
}
执行交易需要两个参数:序列化的交易数据 (txBytes) 和签名 (signatures)。
mutation ($tx: String!, $sigs: [String!]!) {
executeTransactionBlock(txBytes: $tx, signatures: $sigs) {
errors
effects {
status
epoch {
startTimestamp
}
gasEffects {
gasSummary {
computationCost
}
}
}
}
}
变量:
{
"tx": "AAACACAZXApmrHgzTs3FGDyXWka+wmMCy2IwOdKLmTWHb5PnFQEASlCnLAw4qfzLF3unH9or5/L7YpOlReaSEWfoEwhTqpavSxAAAAAAACCUFUCOn8ljIxcG9O+CA1bzqjunqr4DLDSzSoNCkUvu2AEBAQEBAAEAALNQHmLi4jgC5MuwwmiMvZEeV5kuyh+waCS60voE7fpzAa3v/tOFuqDvQ+bjBpKTfjyL+6yIg+5eC3dKReVwghH/rksQAAAAAAAgxtZtKhXTr1zeFAo1JzEqVKn9J1H74ddbCJNVZGo2I1izUB5i4uI4AuTLsMJojL2RHleZLsofsGgkutL6BO36c+gDAAAAAAAAQEIPAAAAAAAA",
"sigs": [
"AB4ZihXxUMSs9Ju5Cstuuf/hvbTvvycuRk2TMuagLYNJgQuAeXmKyJF9DAXUtL8spIsHrDQgemn4NmojcNl8HQ3JFqhnaTC8gMX4fy/rGgqgL6CDcbikawUUjC4zlkflwg=="
]
}
通过上述案例,开发者可以掌握如何使用GraphQL高效查询和操作Sui区块链资源。GraphQL的灵活性和强大的数据操作能力,为开发Move语言的链上应用提供了重要支持。
总结
通过 GraphQL for Sui RPC,可以灵活地获取区块链数据,适配多种应用场景。掌握 Headers、变量、片段和分页等技巧,能够显著提升查询效率。同时需注意使用限制,以确保服务的高效和稳定。
请用微信关注《HOH水分子》公众号,我们将持续分享和制作变成语言教程,让大家对编程产生化学反应。
如果觉得我的文章对您有用,请随意打赏。你的支持将鼓励我继续创作!