Compare commits
6 Commits
115b2f8c56
...
7c85ebf016
Author | SHA1 | Date |
---|---|---|
Mariano | 7c85ebf016 | |
Mariano | 4051ad491f | |
Mariano | 92b432a906 | |
Mariano | b4d7e3284e | |
Mariano | ce1b7707fb | |
ftocal | 9d280f7d5f |
|
@ -17,7 +17,7 @@ require (
|
||||||
github.com/shopspring/decimal v1.3.1
|
github.com/shopspring/decimal v1.3.1
|
||||||
github.com/spf13/cobra v1.7.0
|
github.com/spf13/cobra v1.7.0
|
||||||
github.com/wormhole-foundation/wormhole-explorer/common v0.0.0-00010101000000-000000000000
|
github.com/wormhole-foundation/wormhole-explorer/common v0.0.0-00010101000000-000000000000
|
||||||
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240109172745-cc0cd9fc5229
|
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240416174455-25e60611a867
|
||||||
go.mongodb.org/mongo-driver v1.11.2
|
go.mongodb.org/mongo-driver v1.11.2
|
||||||
go.uber.org/zap v1.26.0
|
go.uber.org/zap v1.26.0
|
||||||
gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22
|
gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22
|
||||||
|
|
|
@ -370,8 +370,8 @@ github.com/valyala/fasttemplate v1.0.1/go.mod h1:UQGH1tvbgY+Nz5t2n7tXsz52dQxojPU
|
||||||
github.com/valyala/fasttemplate v1.2.1/go.mod h1:KHLXt3tVN2HBp8eijSv/kGJopbvo7S+qRAEEKiv+SiQ=
|
github.com/valyala/fasttemplate v1.2.1/go.mod h1:KHLXt3tVN2HBp8eijSv/kGJopbvo7S+qRAEEKiv+SiQ=
|
||||||
github.com/valyala/tcplisten v1.0.0 h1:rBHj/Xf+E1tRGZyWIWwJDiRY0zc1Js+CV5DqwacVSA8=
|
github.com/valyala/tcplisten v1.0.0 h1:rBHj/Xf+E1tRGZyWIWwJDiRY0zc1Js+CV5DqwacVSA8=
|
||||||
github.com/valyala/tcplisten v1.0.0/go.mod h1:T0xQ8SeCZGxckz9qRXTfG43PvQ/mcWh7FwZEA7Ioqkc=
|
github.com/valyala/tcplisten v1.0.0/go.mod h1:T0xQ8SeCZGxckz9qRXTfG43PvQ/mcWh7FwZEA7Ioqkc=
|
||||||
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240109172745-cc0cd9fc5229 h1:fqcC4qwEVaJfcpqUVKi5+imz+JpxviQYPW4qu3zILz4=
|
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240416174455-25e60611a867 h1:GXUBP09C/bnEukdU6H2AY81d0m8UWrWEejDp6CgiFQA=
|
||||||
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240109172745-cc0cd9fc5229/go.mod h1:pE/jYet19kY4P3V6mE2+01zvEfxdyBqv6L6HsnSa5uc=
|
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240416174455-25e60611a867/go.mod h1:pE/jYet19kY4P3V6mE2+01zvEfxdyBqv6L6HsnSa5uc=
|
||||||
github.com/xdg-go/pbkdf2 v1.0.0 h1:Su7DPu48wXMwC3bs7MCNG+z4FhcyEuz5dlvchbq0B0c=
|
github.com/xdg-go/pbkdf2 v1.0.0 h1:Su7DPu48wXMwC3bs7MCNG+z4FhcyEuz5dlvchbq0B0c=
|
||||||
github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI=
|
github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI=
|
||||||
github.com/xdg-go/scram v1.1.1 h1:VOMT+81stJgXW3CpHyqHN3AXDYIMsx56mEFrB37Mb/E=
|
github.com/xdg-go/scram v1.1.1 h1:VOMT+81stJgXW3CpHyqHN3AXDYIMsx56mEFrB37Mb/E=
|
||||||
|
|
|
@ -0,0 +1,40 @@
|
||||||
|
import "date"
|
||||||
|
|
||||||
|
|
||||||
|
runTask = (start,stop,srcBucket,destBucket,destMeasurement) => {
|
||||||
|
|
||||||
|
data = from(bucket: srcBucket)
|
||||||
|
|> range(start: start,stop: stop)
|
||||||
|
|> filter(fn: (r) => r._measurement == "vaa_volume_v2" and r.version == "v2")
|
||||||
|
|> filter(fn: (r) => r._field == "volume" and r._value > 0)
|
||||||
|
|> drop(columns:["destination_chain","app_id","token_chain","token_address","version","_measurement","_time"])
|
||||||
|
|> rename(columns: {_start: "_time"})
|
||||||
|
|> group(columns: ["emitter_chain","_time"])
|
||||||
|
|
||||||
|
vols = data
|
||||||
|
|> sum(column: "_value")
|
||||||
|
|> set(key: "_field", value: "volume")
|
||||||
|
|> set(key: "to", value: string(v:stop))
|
||||||
|
|> set(key: "_measurement", value: destMeasurement)
|
||||||
|
|> to(bucket: destBucket)
|
||||||
|
|
||||||
|
return data
|
||||||
|
|> count(column: "_value")
|
||||||
|
|> set(key: "_field", value: "count")
|
||||||
|
|> set(key: "to", value: string(v:stop))
|
||||||
|
|> set(key: "_measurement", value: destMeasurement)
|
||||||
|
|> to(bucket: destBucket)
|
||||||
|
}
|
||||||
|
|
||||||
|
bucketInfinite = "wormscan"
|
||||||
|
destMeasurement = "emitter_chain_activity_1d"
|
||||||
|
|
||||||
|
stop = date.truncate(t: now(),unit: 1d)
|
||||||
|
start = date.sub(d: 1d, from: stop)
|
||||||
|
|
||||||
|
option task = {
|
||||||
|
name: "calculate chain activity per emitter every day",
|
||||||
|
every: 1d,
|
||||||
|
}
|
||||||
|
|
||||||
|
runTask(start:start, stop: stop, srcBucket: bucketInfinite, destBucket: bucketInfinite, destMeasurement: destMeasurement)
|
|
@ -0,0 +1,40 @@
|
||||||
|
import "date"
|
||||||
|
|
||||||
|
|
||||||
|
runTask = (start,stop,srcBucket,destBucket,destMeasurement) => {
|
||||||
|
|
||||||
|
data = from(bucket: srcBucket)
|
||||||
|
|> range(start: start,stop: stop)
|
||||||
|
|> filter(fn: (r) => r._measurement == "vaa_volume_v2" and r.version == "v2")
|
||||||
|
|> filter(fn: (r) => r._field == "volume" and r._value > 0)
|
||||||
|
|> drop(columns:["destination_chain","app_id","token_chain","token_address","version","_measurement","_time"])
|
||||||
|
|> rename(columns: {_start: "_time"})
|
||||||
|
|> group(columns: ["emitter_chain","_time"])
|
||||||
|
|
||||||
|
vols = data
|
||||||
|
|> sum(column: "_value")
|
||||||
|
|> set(key: "_field", value: "volume")
|
||||||
|
|> set(key: "to", value: string(v:stop))
|
||||||
|
|> set(key: "_measurement", value: destMeasurement)
|
||||||
|
|> to(bucket: destBucket)
|
||||||
|
|
||||||
|
return data
|
||||||
|
|> count(column: "_value")
|
||||||
|
|> set(key: "_field", value: "count")
|
||||||
|
|> set(key: "to", value: string(v:stop))
|
||||||
|
|> set(key: "_measurement", value: destMeasurement)
|
||||||
|
|> to(bucket: destBucket)
|
||||||
|
}
|
||||||
|
|
||||||
|
bucketInfinite = "wormscan"
|
||||||
|
destMeasurement = "emitter_chain_activity_1h"
|
||||||
|
|
||||||
|
stop = date.truncate(t: now(),unit: 1h)
|
||||||
|
start = date.sub(d: 1h, from: stop)
|
||||||
|
|
||||||
|
option task = {
|
||||||
|
name: "calculate chain activity per emitter every hour",
|
||||||
|
every: 1h,
|
||||||
|
}
|
||||||
|
|
||||||
|
runTask(start:start, stop: stop, srcBucket: bucketInfinite, destBucket: bucketInfinite, destMeasurement: destMeasurement)
|
|
@ -0,0 +1,37 @@
|
||||||
|
import "date"
|
||||||
|
|
||||||
|
runTask = (start,stop,srcBucket,destBucket,destMeasurement) => {
|
||||||
|
data = from(bucket: srcBucket)
|
||||||
|
|> range(start: start,stop: stop)
|
||||||
|
|> filter(fn: (r) => r._measurement == "vaa_volume_v2" and r._field == "volume")
|
||||||
|
|> group(columns: ["emitter_chain", "destination_chain", "app_id"])
|
||||||
|
|
||||||
|
data
|
||||||
|
|> sum(column: "_value")
|
||||||
|
|> set(key: "_field", value: "volume")
|
||||||
|
|> map(fn: (r) => ({ r with _time: start }))
|
||||||
|
|> set(key: "to", value: string(v:date.add(d: 1d, to: start)))
|
||||||
|
|> set(key: "_measurement", value: destMeasurement)
|
||||||
|
|> to(bucket: destBucket)
|
||||||
|
|
||||||
|
return data
|
||||||
|
|> count(column: "_value")
|
||||||
|
|> set(key: "_field", value: "count")
|
||||||
|
|> map(fn: (r) => ({ r with _time: start }))
|
||||||
|
|> set(key: "to", value: string(v:date.add(d: 1d, to: start)))
|
||||||
|
|> set(key: "_measurement", value: destMeasurement)
|
||||||
|
|> to(bucket: destBucket)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bucketInfinite = "wormscan"
|
||||||
|
destMeasurement = "chain_activity_1d"
|
||||||
|
stop = date.truncate(t: now(),unit: 24h)
|
||||||
|
start = date.sub(d: 1d, from: stop)
|
||||||
|
|
||||||
|
option task = {
|
||||||
|
name: "calculate chain activity every day",
|
||||||
|
every: 1d,
|
||||||
|
}
|
||||||
|
|
||||||
|
runTask(start:start, stop: stop, srcBucket: bucketInfinite, destBucket: bucketInfinite, destMeasurement: destMeasurement)
|
|
@ -0,0 +1,40 @@
|
||||||
|
import "date"
|
||||||
|
|
||||||
|
|
||||||
|
runTask = (start,stop,srcBucket,destBucket,destMeasurement) => {
|
||||||
|
|
||||||
|
data = from(bucket: srcBucket)
|
||||||
|
|> range(start: start,stop: stop)
|
||||||
|
|> filter(fn: (r) => r._measurement == "vaa_volume_v2" and r._field == "volume")
|
||||||
|
|> group(columns: ["emitter_chain", "destination_chain", "app_id"])
|
||||||
|
|
||||||
|
data
|
||||||
|
|> sum(column: "_value")
|
||||||
|
|> set(key: "_field", value: "volume")
|
||||||
|
|> map(fn: (r) => ({ r with _time: start }))
|
||||||
|
|> set(key: "to", value: string(v:date.add(d: 1h, to: start)))
|
||||||
|
|> set(key: "_measurement", value: destMeasurement)
|
||||||
|
|> to(bucket: destBucket)
|
||||||
|
|
||||||
|
return data
|
||||||
|
|> count(column: "_value")
|
||||||
|
|> set(key: "_field", value: "count")
|
||||||
|
|> map(fn: (r) => ({ r with _time: start }))
|
||||||
|
|> set(key: "to", value: string(v:date.add(d: 1h, to: start)))
|
||||||
|
|> set(key: "_measurement", value: destMeasurement)
|
||||||
|
|> to(bucket: destBucket)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bucketInfinite = "wormscan"
|
||||||
|
destMeasurement = "chain_activity_1h"
|
||||||
|
|
||||||
|
stop = date.truncate(t: now(),unit: 1h)
|
||||||
|
start = date.sub(d: 1h, from: stop)
|
||||||
|
|
||||||
|
option task = {
|
||||||
|
name: "calculate chain activity every hour",
|
||||||
|
every: 1h,
|
||||||
|
}
|
||||||
|
|
||||||
|
runTask(start:start, stop: stop, srcBucket: bucketInfinite, destBucket: bucketInfinite, destMeasurement: destMeasurement)
|
126
api/docs/docs.go
126
api/docs/docs.go
|
@ -1760,6 +1760,73 @@ const docTemplate = `{
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"/api/v1/x-chain-activity/tops": {
|
||||||
|
"get": {
|
||||||
|
"description": "Search, for a specific period of time, the number of transactions and the volume.",
|
||||||
|
"tags": [
|
||||||
|
"wormholescan"
|
||||||
|
],
|
||||||
|
"operationId": "x-chain-activity-tops",
|
||||||
|
"parameters": [
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "Time span, supported values: 1d, 1mo and 1y",
|
||||||
|
"name": "timespan",
|
||||||
|
"in": "query",
|
||||||
|
"required": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "From date, supported format 2006-01-02T15:04:05Z07:00",
|
||||||
|
"name": "from",
|
||||||
|
"in": "query",
|
||||||
|
"required": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "To date, supported format 2006-01-02T15:04:05Z07:00",
|
||||||
|
"name": "to",
|
||||||
|
"in": "query",
|
||||||
|
"required": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "Search by appId",
|
||||||
|
"name": "appId",
|
||||||
|
"in": "query"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "Search by sourceChain",
|
||||||
|
"name": "sourceChain",
|
||||||
|
"in": "query"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "Search by targetChain",
|
||||||
|
"name": "targetChain",
|
||||||
|
"in": "query"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"responses": {
|
||||||
|
"200": {
|
||||||
|
"description": "OK",
|
||||||
|
"schema": {
|
||||||
|
"type": "array",
|
||||||
|
"items": {
|
||||||
|
"$ref": "#/definitions/transactions.ChainActivityTopResult"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"400": {
|
||||||
|
"description": "Bad Request"
|
||||||
|
},
|
||||||
|
"500": {
|
||||||
|
"description": "Internal Server Error"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
"/swagger.json": {
|
"/swagger.json": {
|
||||||
"get": {
|
"get": {
|
||||||
"description": "Returns the swagger specification for this API.",
|
"description": "Returns the swagger specification for this API.",
|
||||||
|
@ -2674,17 +2741,17 @@ const docTemplate = `{
|
||||||
"type": "string"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"sourceChain": {
|
"sourceChain": {
|
||||||
"$ref": "#/definitions/operations.SourceChain"
|
"$ref": "#/definitions/operations.SourceChains"
|
||||||
},
|
},
|
||||||
"targetChain": {
|
"targetChain": {
|
||||||
"$ref": "#/definitions/operations.TargetChain"
|
"$ref": "#/definitions/operations.TargetChains"
|
||||||
},
|
},
|
||||||
"vaa": {
|
"vaa": {
|
||||||
"$ref": "#/definitions/operations.Vaa"
|
"$ref": "#/definitions/operations.Vaa"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"operations.SourceChain": {
|
"operations.SourceChains": {
|
||||||
"type": "object",
|
"type": "object",
|
||||||
"properties": {
|
"properties": {
|
||||||
"attribute": {
|
"attribute": {
|
||||||
|
@ -2748,7 +2815,7 @@ const docTemplate = `{
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"operations.TargetChain": {
|
"operations.TargetChains": {
|
||||||
"type": "object",
|
"type": "object",
|
||||||
"properties": {
|
"properties": {
|
||||||
"chainId": {
|
"chainId": {
|
||||||
|
@ -3325,6 +3392,29 @@ const docTemplate = `{
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"transactions.ChainActivityTopResult": {
|
||||||
|
"type": "object",
|
||||||
|
"properties": {
|
||||||
|
"count": {
|
||||||
|
"type": "integer"
|
||||||
|
},
|
||||||
|
"destination_chain": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"emitter_chain": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"from": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"to": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"volume": {
|
||||||
|
"type": "integer"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
"transactions.ChainPair": {
|
"transactions.ChainPair": {
|
||||||
"type": "object",
|
"type": "object",
|
||||||
"properties": {
|
"properties": {
|
||||||
|
@ -3591,7 +3681,6 @@ const docTemplate = `{
|
||||||
14,
|
14,
|
||||||
15,
|
15,
|
||||||
16,
|
16,
|
||||||
17,
|
|
||||||
18,
|
18,
|
||||||
19,
|
19,
|
||||||
20,
|
20,
|
||||||
|
@ -3599,24 +3688,35 @@ const docTemplate = `{
|
||||||
22,
|
22,
|
||||||
23,
|
23,
|
||||||
24,
|
24,
|
||||||
|
25,
|
||||||
26,
|
26,
|
||||||
28,
|
28,
|
||||||
29,
|
29,
|
||||||
30,
|
30,
|
||||||
32,
|
32,
|
||||||
|
33,
|
||||||
34,
|
34,
|
||||||
35,
|
35,
|
||||||
|
36,
|
||||||
|
37,
|
||||||
|
38,
|
||||||
|
39,
|
||||||
3104,
|
3104,
|
||||||
4000,
|
4000,
|
||||||
4001,
|
4001,
|
||||||
4002,
|
4002,
|
||||||
4003,
|
4003,
|
||||||
4004,
|
4004,
|
||||||
|
4005,
|
||||||
|
4006,
|
||||||
|
4007,
|
||||||
|
4008,
|
||||||
10002,
|
10002,
|
||||||
10003,
|
10003,
|
||||||
10004,
|
10004,
|
||||||
10005,
|
10005,
|
||||||
10006
|
10006,
|
||||||
|
10007
|
||||||
],
|
],
|
||||||
"x-enum-varnames": [
|
"x-enum-varnames": [
|
||||||
"ChainIDUnset",
|
"ChainIDUnset",
|
||||||
|
@ -3636,7 +3736,6 @@ const docTemplate = `{
|
||||||
"ChainIDCelo",
|
"ChainIDCelo",
|
||||||
"ChainIDNear",
|
"ChainIDNear",
|
||||||
"ChainIDMoonbeam",
|
"ChainIDMoonbeam",
|
||||||
"ChainIDNeon",
|
|
||||||
"ChainIDTerra2",
|
"ChainIDTerra2",
|
||||||
"ChainIDInjective",
|
"ChainIDInjective",
|
||||||
"ChainIDOsmosis",
|
"ChainIDOsmosis",
|
||||||
|
@ -3644,24 +3743,35 @@ const docTemplate = `{
|
||||||
"ChainIDAptos",
|
"ChainIDAptos",
|
||||||
"ChainIDArbitrum",
|
"ChainIDArbitrum",
|
||||||
"ChainIDOptimism",
|
"ChainIDOptimism",
|
||||||
|
"ChainIDGnosis",
|
||||||
"ChainIDPythNet",
|
"ChainIDPythNet",
|
||||||
"ChainIDXpla",
|
"ChainIDXpla",
|
||||||
"ChainIDBtc",
|
"ChainIDBtc",
|
||||||
"ChainIDBase",
|
"ChainIDBase",
|
||||||
"ChainIDSei",
|
"ChainIDSei",
|
||||||
|
"ChainIDRootstock",
|
||||||
"ChainIDScroll",
|
"ChainIDScroll",
|
||||||
"ChainIDMantle",
|
"ChainIDMantle",
|
||||||
|
"ChainIDBlast",
|
||||||
|
"ChainIDXLayer",
|
||||||
|
"ChainIDLinea",
|
||||||
|
"ChainIDBerachain",
|
||||||
"ChainIDWormchain",
|
"ChainIDWormchain",
|
||||||
"ChainIDCosmoshub",
|
"ChainIDCosmoshub",
|
||||||
"ChainIDEvmos",
|
"ChainIDEvmos",
|
||||||
"ChainIDKujira",
|
"ChainIDKujira",
|
||||||
"ChainIDNeutron",
|
"ChainIDNeutron",
|
||||||
"ChainIDCelestia",
|
"ChainIDCelestia",
|
||||||
|
"ChainIDStargaze",
|
||||||
|
"ChainIDSeda",
|
||||||
|
"ChainIDDymension",
|
||||||
|
"ChainIDProvenance",
|
||||||
"ChainIDSepolia",
|
"ChainIDSepolia",
|
||||||
"ChainIDArbitrumSepolia",
|
"ChainIDArbitrumSepolia",
|
||||||
"ChainIDBaseSepolia",
|
"ChainIDBaseSepolia",
|
||||||
"ChainIDOptimismSepolia",
|
"ChainIDOptimismSepolia",
|
||||||
"ChainIDHolesky"
|
"ChainIDHolesky",
|
||||||
|
"ChainIDPolygonSepolia"
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
"vaa.VaaDoc": {
|
"vaa.VaaDoc": {
|
||||||
|
|
|
@ -1753,6 +1753,73 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"/api/v1/x-chain-activity/tops": {
|
||||||
|
"get": {
|
||||||
|
"description": "Search, for a specific period of time, the number of transactions and the volume.",
|
||||||
|
"tags": [
|
||||||
|
"wormholescan"
|
||||||
|
],
|
||||||
|
"operationId": "x-chain-activity-tops",
|
||||||
|
"parameters": [
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "Time span, supported values: 1d, 1mo and 1y",
|
||||||
|
"name": "timespan",
|
||||||
|
"in": "query",
|
||||||
|
"required": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "From date, supported format 2006-01-02T15:04:05Z07:00",
|
||||||
|
"name": "from",
|
||||||
|
"in": "query",
|
||||||
|
"required": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "To date, supported format 2006-01-02T15:04:05Z07:00",
|
||||||
|
"name": "to",
|
||||||
|
"in": "query",
|
||||||
|
"required": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "Search by appId",
|
||||||
|
"name": "appId",
|
||||||
|
"in": "query"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "Search by sourceChain",
|
||||||
|
"name": "sourceChain",
|
||||||
|
"in": "query"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "string",
|
||||||
|
"description": "Search by targetChain",
|
||||||
|
"name": "targetChain",
|
||||||
|
"in": "query"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"responses": {
|
||||||
|
"200": {
|
||||||
|
"description": "OK",
|
||||||
|
"schema": {
|
||||||
|
"type": "array",
|
||||||
|
"items": {
|
||||||
|
"$ref": "#/definitions/transactions.ChainActivityTopResult"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"400": {
|
||||||
|
"description": "Bad Request"
|
||||||
|
},
|
||||||
|
"500": {
|
||||||
|
"description": "Internal Server Error"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
"/swagger.json": {
|
"/swagger.json": {
|
||||||
"get": {
|
"get": {
|
||||||
"description": "Returns the swagger specification for this API.",
|
"description": "Returns the swagger specification for this API.",
|
||||||
|
@ -3318,6 +3385,29 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"transactions.ChainActivityTopResult": {
|
||||||
|
"type": "object",
|
||||||
|
"properties": {
|
||||||
|
"count": {
|
||||||
|
"type": "integer"
|
||||||
|
},
|
||||||
|
"destination_chain": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"emitter_chain": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"from": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"to": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"volume": {
|
||||||
|
"type": "integer"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
"transactions.ChainPair": {
|
"transactions.ChainPair": {
|
||||||
"type": "object",
|
"type": "object",
|
||||||
"properties": {
|
"properties": {
|
||||||
|
@ -3584,7 +3674,6 @@
|
||||||
14,
|
14,
|
||||||
15,
|
15,
|
||||||
16,
|
16,
|
||||||
17,
|
|
||||||
18,
|
18,
|
||||||
19,
|
19,
|
||||||
20,
|
20,
|
||||||
|
@ -3592,24 +3681,35 @@
|
||||||
22,
|
22,
|
||||||
23,
|
23,
|
||||||
24,
|
24,
|
||||||
|
25,
|
||||||
26,
|
26,
|
||||||
28,
|
28,
|
||||||
29,
|
29,
|
||||||
30,
|
30,
|
||||||
32,
|
32,
|
||||||
|
33,
|
||||||
34,
|
34,
|
||||||
35,
|
35,
|
||||||
|
36,
|
||||||
|
37,
|
||||||
|
38,
|
||||||
|
39,
|
||||||
3104,
|
3104,
|
||||||
4000,
|
4000,
|
||||||
4001,
|
4001,
|
||||||
4002,
|
4002,
|
||||||
4003,
|
4003,
|
||||||
4004,
|
4004,
|
||||||
|
4005,
|
||||||
|
4006,
|
||||||
|
4007,
|
||||||
|
4008,
|
||||||
10002,
|
10002,
|
||||||
10003,
|
10003,
|
||||||
10004,
|
10004,
|
||||||
10005,
|
10005,
|
||||||
10006
|
10006,
|
||||||
|
10007
|
||||||
],
|
],
|
||||||
"x-enum-varnames": [
|
"x-enum-varnames": [
|
||||||
"ChainIDUnset",
|
"ChainIDUnset",
|
||||||
|
@ -3629,7 +3729,6 @@
|
||||||
"ChainIDCelo",
|
"ChainIDCelo",
|
||||||
"ChainIDNear",
|
"ChainIDNear",
|
||||||
"ChainIDMoonbeam",
|
"ChainIDMoonbeam",
|
||||||
"ChainIDNeon",
|
|
||||||
"ChainIDTerra2",
|
"ChainIDTerra2",
|
||||||
"ChainIDInjective",
|
"ChainIDInjective",
|
||||||
"ChainIDOsmosis",
|
"ChainIDOsmosis",
|
||||||
|
@ -3637,24 +3736,35 @@
|
||||||
"ChainIDAptos",
|
"ChainIDAptos",
|
||||||
"ChainIDArbitrum",
|
"ChainIDArbitrum",
|
||||||
"ChainIDOptimism",
|
"ChainIDOptimism",
|
||||||
|
"ChainIDGnosis",
|
||||||
"ChainIDPythNet",
|
"ChainIDPythNet",
|
||||||
"ChainIDXpla",
|
"ChainIDXpla",
|
||||||
"ChainIDBtc",
|
"ChainIDBtc",
|
||||||
"ChainIDBase",
|
"ChainIDBase",
|
||||||
"ChainIDSei",
|
"ChainIDSei",
|
||||||
|
"ChainIDRootstock",
|
||||||
"ChainIDScroll",
|
"ChainIDScroll",
|
||||||
"ChainIDMantle",
|
"ChainIDMantle",
|
||||||
|
"ChainIDBlast",
|
||||||
|
"ChainIDXLayer",
|
||||||
|
"ChainIDLinea",
|
||||||
|
"ChainIDBerachain",
|
||||||
"ChainIDWormchain",
|
"ChainIDWormchain",
|
||||||
"ChainIDCosmoshub",
|
"ChainIDCosmoshub",
|
||||||
"ChainIDEvmos",
|
"ChainIDEvmos",
|
||||||
"ChainIDKujira",
|
"ChainIDKujira",
|
||||||
"ChainIDNeutron",
|
"ChainIDNeutron",
|
||||||
"ChainIDCelestia",
|
"ChainIDCelestia",
|
||||||
|
"ChainIDStargaze",
|
||||||
|
"ChainIDSeda",
|
||||||
|
"ChainIDDymension",
|
||||||
|
"ChainIDProvenance",
|
||||||
"ChainIDSepolia",
|
"ChainIDSepolia",
|
||||||
"ChainIDArbitrumSepolia",
|
"ChainIDArbitrumSepolia",
|
||||||
"ChainIDBaseSepolia",
|
"ChainIDBaseSepolia",
|
||||||
"ChainIDOptimismSepolia",
|
"ChainIDOptimismSepolia",
|
||||||
"ChainIDHolesky"
|
"ChainIDHolesky",
|
||||||
|
"ChainIDPolygonSepolia"
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
"vaa.VaaDoc": {
|
"vaa.VaaDoc": {
|
||||||
|
|
|
@ -824,6 +824,21 @@ definitions:
|
||||||
$ref: '#/definitions/transactions.Tx'
|
$ref: '#/definitions/transactions.Tx'
|
||||||
type: array
|
type: array
|
||||||
type: object
|
type: object
|
||||||
|
transactions.ChainActivityTopResult:
|
||||||
|
properties:
|
||||||
|
count:
|
||||||
|
type: integer
|
||||||
|
destination_chain:
|
||||||
|
type: string
|
||||||
|
emitter_chain:
|
||||||
|
type: string
|
||||||
|
from:
|
||||||
|
type: string
|
||||||
|
to:
|
||||||
|
type: string
|
||||||
|
volume:
|
||||||
|
type: integer
|
||||||
|
type: object
|
||||||
transactions.ChainPair:
|
transactions.ChainPair:
|
||||||
properties:
|
properties:
|
||||||
destinationChain:
|
destinationChain:
|
||||||
|
@ -1012,7 +1027,6 @@ definitions:
|
||||||
- 14
|
- 14
|
||||||
- 15
|
- 15
|
||||||
- 16
|
- 16
|
||||||
- 17
|
|
||||||
- 18
|
- 18
|
||||||
- 19
|
- 19
|
||||||
- 20
|
- 20
|
||||||
|
@ -1020,24 +1034,35 @@ definitions:
|
||||||
- 22
|
- 22
|
||||||
- 23
|
- 23
|
||||||
- 24
|
- 24
|
||||||
|
- 25
|
||||||
- 26
|
- 26
|
||||||
- 28
|
- 28
|
||||||
- 29
|
- 29
|
||||||
- 30
|
- 30
|
||||||
- 32
|
- 32
|
||||||
|
- 33
|
||||||
- 34
|
- 34
|
||||||
- 35
|
- 35
|
||||||
|
- 36
|
||||||
|
- 37
|
||||||
|
- 38
|
||||||
|
- 39
|
||||||
- 3104
|
- 3104
|
||||||
- 4000
|
- 4000
|
||||||
- 4001
|
- 4001
|
||||||
- 4002
|
- 4002
|
||||||
- 4003
|
- 4003
|
||||||
- 4004
|
- 4004
|
||||||
|
- 4005
|
||||||
|
- 4006
|
||||||
|
- 4007
|
||||||
|
- 4008
|
||||||
- 10002
|
- 10002
|
||||||
- 10003
|
- 10003
|
||||||
- 10004
|
- 10004
|
||||||
- 10005
|
- 10005
|
||||||
- 10006
|
- 10006
|
||||||
|
- 10007
|
||||||
type: integer
|
type: integer
|
||||||
x-enum-varnames:
|
x-enum-varnames:
|
||||||
- ChainIDUnset
|
- ChainIDUnset
|
||||||
|
@ -1057,7 +1082,6 @@ definitions:
|
||||||
- ChainIDCelo
|
- ChainIDCelo
|
||||||
- ChainIDNear
|
- ChainIDNear
|
||||||
- ChainIDMoonbeam
|
- ChainIDMoonbeam
|
||||||
- ChainIDNeon
|
|
||||||
- ChainIDTerra2
|
- ChainIDTerra2
|
||||||
- ChainIDInjective
|
- ChainIDInjective
|
||||||
- ChainIDOsmosis
|
- ChainIDOsmosis
|
||||||
|
@ -1065,24 +1089,35 @@ definitions:
|
||||||
- ChainIDAptos
|
- ChainIDAptos
|
||||||
- ChainIDArbitrum
|
- ChainIDArbitrum
|
||||||
- ChainIDOptimism
|
- ChainIDOptimism
|
||||||
|
- ChainIDGnosis
|
||||||
- ChainIDPythNet
|
- ChainIDPythNet
|
||||||
- ChainIDXpla
|
- ChainIDXpla
|
||||||
- ChainIDBtc
|
- ChainIDBtc
|
||||||
- ChainIDBase
|
- ChainIDBase
|
||||||
- ChainIDSei
|
- ChainIDSei
|
||||||
|
- ChainIDRootstock
|
||||||
- ChainIDScroll
|
- ChainIDScroll
|
||||||
- ChainIDMantle
|
- ChainIDMantle
|
||||||
|
- ChainIDBlast
|
||||||
|
- ChainIDXLayer
|
||||||
|
- ChainIDLinea
|
||||||
|
- ChainIDBerachain
|
||||||
- ChainIDWormchain
|
- ChainIDWormchain
|
||||||
- ChainIDCosmoshub
|
- ChainIDCosmoshub
|
||||||
- ChainIDEvmos
|
- ChainIDEvmos
|
||||||
- ChainIDKujira
|
- ChainIDKujira
|
||||||
- ChainIDNeutron
|
- ChainIDNeutron
|
||||||
- ChainIDCelestia
|
- ChainIDCelestia
|
||||||
|
- ChainIDStargaze
|
||||||
|
- ChainIDSeda
|
||||||
|
- ChainIDDymension
|
||||||
|
- ChainIDProvenance
|
||||||
- ChainIDSepolia
|
- ChainIDSepolia
|
||||||
- ChainIDArbitrumSepolia
|
- ChainIDArbitrumSepolia
|
||||||
- ChainIDBaseSepolia
|
- ChainIDBaseSepolia
|
||||||
- ChainIDOptimismSepolia
|
- ChainIDOptimismSepolia
|
||||||
- ChainIDHolesky
|
- ChainIDHolesky
|
||||||
|
- ChainIDPolygonSepolia
|
||||||
vaa.VaaDoc:
|
vaa.VaaDoc:
|
||||||
properties:
|
properties:
|
||||||
appId:
|
appId:
|
||||||
|
@ -2326,6 +2361,52 @@ paths:
|
||||||
description: Internal Server Error
|
description: Internal Server Error
|
||||||
tags:
|
tags:
|
||||||
- wormholescan
|
- wormholescan
|
||||||
|
/api/v1/x-chain-activity/tops:
|
||||||
|
get:
|
||||||
|
description: Search, for a specific period of time, the number of transactions
|
||||||
|
and the volume.
|
||||||
|
operationId: x-chain-activity-tops
|
||||||
|
parameters:
|
||||||
|
- description: 'Time span, supported values: 1d, 1mo and 1y'
|
||||||
|
in: query
|
||||||
|
name: timespan
|
||||||
|
required: true
|
||||||
|
type: string
|
||||||
|
- description: From date, supported format 2006-01-02T15:04:05Z07:00
|
||||||
|
in: query
|
||||||
|
name: from
|
||||||
|
required: true
|
||||||
|
type: string
|
||||||
|
- description: To date, supported format 2006-01-02T15:04:05Z07:00
|
||||||
|
in: query
|
||||||
|
name: to
|
||||||
|
required: true
|
||||||
|
type: string
|
||||||
|
- description: Search by appId
|
||||||
|
in: query
|
||||||
|
name: appId
|
||||||
|
type: string
|
||||||
|
- description: Search by sourceChain
|
||||||
|
in: query
|
||||||
|
name: sourceChain
|
||||||
|
type: string
|
||||||
|
- description: Search by targetChain
|
||||||
|
in: query
|
||||||
|
name: targetChain
|
||||||
|
type: string
|
||||||
|
responses:
|
||||||
|
"200":
|
||||||
|
description: OK
|
||||||
|
schema:
|
||||||
|
items:
|
||||||
|
$ref: '#/definitions/transactions.ChainActivityTopResult'
|
||||||
|
type: array
|
||||||
|
"400":
|
||||||
|
description: Bad Request
|
||||||
|
"500":
|
||||||
|
description: Internal Server Error
|
||||||
|
tags:
|
||||||
|
- wormholescan
|
||||||
/swagger.json:
|
/swagger.json:
|
||||||
get:
|
get:
|
||||||
description: Returns the swagger specification for this API.
|
description: Returns the swagger specification for this API.
|
||||||
|
|
|
@ -113,7 +113,7 @@ type OperationQuery struct {
|
||||||
Address string
|
Address string
|
||||||
SourceChainIDs []vaa.ChainID
|
SourceChainIDs []vaa.ChainID
|
||||||
TargetChainIDs []vaa.ChainID
|
TargetChainIDs []vaa.ChainID
|
||||||
AppID []string
|
AppIDs []string
|
||||||
ExclusiveAppId bool
|
ExclusiveAppId bool
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -138,41 +138,19 @@ func buildQueryOperationsByChain(sourceChainIDs, targetChainIDs []vaa.ChainID) b
|
||||||
return bson.D{{Key: "$match", Value: bson.M{"$and": allMatch}}}
|
return bson.D{{Key: "$match", Value: bson.M{"$and": allMatch}}}
|
||||||
}
|
}
|
||||||
|
|
||||||
func buildQueryOperationsByAppID(appIDs []string, exclusive bool) []bson.D {
|
func buildQueryOperationsByAppID(appIDs []string, exclusive bool) bson.D {
|
||||||
var result []bson.D
|
if !exclusive {
|
||||||
|
return bson.D{{Key: "$match", Value: bson.M{"rawStandardizedProperties.appIds": bson.M{"$in": appIDs}}}}
|
||||||
/*
|
|
||||||
if appID == "" {
|
|
||||||
result = append(result, bson.D{{Key: "$match", Value: bson.M{}}})
|
|
||||||
return result
|
|
||||||
}
|
}
|
||||||
*/
|
matchAppID := bson.A{}
|
||||||
|
|
||||||
if exclusive {
|
|
||||||
if len(appIDs) == 1 {
|
|
||||||
result = append(result, bson.D{{Key: "$match", Value: bson.M{
|
|
||||||
"$and": bson.A{
|
|
||||||
bson.M{"rawStandardizedProperties.appIds": bson.M{"$eq": appIDs}},
|
|
||||||
bson.M{"rawStandardizedProperties.appIds": bson.M{"$size": 1}},
|
|
||||||
}}}})
|
|
||||||
} else {
|
|
||||||
a := bson.A{}
|
|
||||||
for _, appID := range appIDs {
|
for _, appID := range appIDs {
|
||||||
cond := bson.M{
|
cond := bson.M{"$and": bson.A{
|
||||||
"$and": bson.A{
|
|
||||||
bson.M{"rawStandardizedProperties.appIds": bson.M{"$eq": appID}},
|
bson.M{"rawStandardizedProperties.appIds": bson.M{"$eq": appID}},
|
||||||
bson.M{"rawStandardizedProperties.appIds": bson.M{"$size": 1}},
|
bson.M{"rawStandardizedProperties.appIds": bson.M{"$size": 1}},
|
||||||
}}
|
}}
|
||||||
a = append(a, cond)
|
matchAppID = append(matchAppID, cond)
|
||||||
}
|
}
|
||||||
result = append(result, bson.D{{Key: "$match", Value: bson.M{
|
return bson.D{{Key: "$match", Value: bson.M{"$or": matchAppID}}}
|
||||||
"$or": a}}})
|
|
||||||
}
|
|
||||||
|
|
||||||
} else {
|
|
||||||
result = append(result, bson.D{{Key: "$match", Value: bson.M{"rawStandardizedProperties.appIds": bson.M{"$in": appIDs}}}})
|
|
||||||
}
|
|
||||||
return result
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// findOperationsIdByAddress returns all operations filtered by address.
|
// findOperationsIdByAddress returns all operations filtered by address.
|
||||||
|
@ -253,14 +231,14 @@ func (r *Repository) FindByChainAndAppId(ctx context.Context, query OperationQue
|
||||||
|
|
||||||
var pipeline mongo.Pipeline
|
var pipeline mongo.Pipeline
|
||||||
|
|
||||||
if len(query.SourceChainIDs) != 0 || len(query.TargetChainIDs) != 0 {
|
if len(query.SourceChainIDs) > 0 || len(query.TargetChainIDs) > 0 {
|
||||||
matchBySourceTargetChain := buildQueryOperationsByChain(query.SourceChainIDs, query.TargetChainIDs)
|
matchBySourceTargetChain := buildQueryOperationsByChain(query.SourceChainIDs, query.TargetChainIDs)
|
||||||
pipeline = append(pipeline, matchBySourceTargetChain)
|
pipeline = append(pipeline, matchBySourceTargetChain)
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(query.AppID) > 0 {
|
if len(query.AppIDs) > 0 {
|
||||||
matchByAppId := buildQueryOperationsByAppID(query.AppID, query.ExclusiveAppId)
|
matchByAppId := buildQueryOperationsByAppID(query.AppIDs, query.ExclusiveAppId)
|
||||||
pipeline = append(pipeline, matchByAppId...)
|
pipeline = append(pipeline, matchByAppId)
|
||||||
}
|
}
|
||||||
|
|
||||||
pipeline = append(pipeline, bson.D{{Key: "$sort", Value: bson.D{
|
pipeline = append(pipeline, bson.D{{Key: "$sort", Value: bson.D{
|
||||||
|
|
|
@ -36,7 +36,7 @@ type OperationFilter struct {
|
||||||
Address string
|
Address string
|
||||||
SourceChainIDs []vaa.ChainID
|
SourceChainIDs []vaa.ChainID
|
||||||
TargetChainIDs []vaa.ChainID
|
TargetChainIDs []vaa.ChainID
|
||||||
AppID []string
|
AppIDs []string
|
||||||
ExclusiveAppId bool
|
ExclusiveAppId bool
|
||||||
Pagination pagination.Pagination
|
Pagination pagination.Pagination
|
||||||
}
|
}
|
||||||
|
@ -54,11 +54,11 @@ func (s *Service) FindAll(ctx context.Context, filter OperationFilter) ([]*Opera
|
||||||
Pagination: filter.Pagination,
|
Pagination: filter.Pagination,
|
||||||
SourceChainIDs: filter.SourceChainIDs,
|
SourceChainIDs: filter.SourceChainIDs,
|
||||||
TargetChainIDs: filter.TargetChainIDs,
|
TargetChainIDs: filter.TargetChainIDs,
|
||||||
AppID: filter.AppID,
|
AppIDs: filter.AppIDs,
|
||||||
ExclusiveAppId: filter.ExclusiveAppId,
|
ExclusiveAppId: filter.ExclusiveAppId,
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(operationQuery.AppID) != 0 || len(operationQuery.SourceChainIDs) > 0 || len(operationQuery.TargetChainIDs) > 0 {
|
if len(operationQuery.AppIDs) != 0 || len(operationQuery.SourceChainIDs) > 0 || len(operationQuery.TargetChainIDs) > 0 {
|
||||||
return s.repo.FindByChainAndAppId(ctx, operationQuery)
|
return s.repo.FindByChainAndAppId(ctx, operationQuery)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -143,6 +143,17 @@ type ChainActivityResult struct {
|
||||||
Volume uint64 `mapstructure:"_value" json:"volume"`
|
Volume uint64 `mapstructure:"_value" json:"volume"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type ChainActivityTopResult struct {
|
||||||
|
Time time.Time `json:"from" mapstructure:"_time"`
|
||||||
|
To string `json:"to" mapstructure:"to"`
|
||||||
|
ChainSourceID string `mapstructure:"emitter_chain" json:"emitter_chain"`
|
||||||
|
ChainDestinationID string `mapstructure:"destination_chain" json:"destination_chain,omitempty"`
|
||||||
|
Volume uint64 `mapstructure:"volume" json:"volume"`
|
||||||
|
Txs uint64 `mapstructure:"count" json:"count"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type ChainActivityTopResults []ChainActivityTopResult
|
||||||
|
|
||||||
type ChainActivityTimeSpan string
|
type ChainActivityTimeSpan string
|
||||||
|
|
||||||
const (
|
const (
|
||||||
|
@ -202,3 +213,25 @@ type TransactionDto struct {
|
||||||
Payload map[string]interface{} `bson:"payload"`
|
Payload map[string]interface{} `bson:"payload"`
|
||||||
StandardizedProperties map[string]interface{} `bson:"standardizedProperties"`
|
StandardizedProperties map[string]interface{} `bson:"standardizedProperties"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type ChainActivityTopsQuery struct {
|
||||||
|
SourceChains []sdk.ChainID `json:"source_chain"`
|
||||||
|
TargetChains []sdk.ChainID `json:"target_chain"`
|
||||||
|
AppId string `json:"app_id"`
|
||||||
|
From time.Time `json:"from"`
|
||||||
|
To time.Time `json:"to"`
|
||||||
|
Timespan Timespan `json:"timespan"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type Timespan string
|
||||||
|
|
||||||
|
const (
|
||||||
|
Hour Timespan = "1h"
|
||||||
|
Day Timespan = "1d"
|
||||||
|
Month Timespan = "1mo"
|
||||||
|
Year Timespan = "1y"
|
||||||
|
)
|
||||||
|
|
||||||
|
func (t Timespan) IsValid() bool {
|
||||||
|
return t == Hour || t == Day || t == Month || t == Year
|
||||||
|
}
|
||||||
|
|
|
@ -3,6 +3,7 @@ package transactions
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"github.com/valyala/fasthttp"
|
||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
"sync"
|
"sync"
|
||||||
|
@ -1048,3 +1049,348 @@ func (r *Repository) ListTransactionsByAddress(
|
||||||
|
|
||||||
return documents, nil
|
return documents, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (r *Repository) FindChainActivityTops(ctx *fasthttp.RequestCtx, q ChainActivityTopsQuery) ([]ChainActivityTopResult, error) {
|
||||||
|
query := r.buildChainActivityQueryTops(q)
|
||||||
|
result, err := r.queryAPI.Query(ctx, query)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
if result.Err() != nil {
|
||||||
|
return nil, result.Err()
|
||||||
|
}
|
||||||
|
var response []ChainActivityTopResult
|
||||||
|
for result.Next() {
|
||||||
|
var row ChainActivityTopResult
|
||||||
|
if err = mapstructure.Decode(result.Record().Values(), &row); err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
parsedTime, errTime := time.Parse(time.RFC3339Nano, row.To)
|
||||||
|
if errTime == nil {
|
||||||
|
row.To = parsedTime.Format(time.RFC3339)
|
||||||
|
}
|
||||||
|
response = append(response, row)
|
||||||
|
}
|
||||||
|
|
||||||
|
return response, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *Repository) buildChainActivityQueryTops(q ChainActivityTopsQuery) string {
|
||||||
|
|
||||||
|
var start, stop string
|
||||||
|
|
||||||
|
switch q.Timespan {
|
||||||
|
case Hour:
|
||||||
|
start = q.From.Truncate(1 * time.Hour).UTC().Format(time.RFC3339)
|
||||||
|
stop = q.To.Truncate(1 * time.Hour).UTC().Format(time.RFC3339)
|
||||||
|
case Day:
|
||||||
|
start = q.From.Truncate(24 * time.Hour).UTC().Format(time.RFC3339)
|
||||||
|
stop = q.To.Truncate(24 * time.Hour).UTC().Format(time.RFC3339)
|
||||||
|
case Month:
|
||||||
|
start = time.Date(q.From.Year(), q.From.Month(), 1, 0, 0, 0, 0, q.From.Location()).UTC().Format(time.RFC3339)
|
||||||
|
stop = time.Date(q.To.Year(), q.To.Month(), 1, 0, 0, 0, 0, q.To.Location()).UTC().Format(time.RFC3339)
|
||||||
|
default:
|
||||||
|
start = time.Date(q.From.Year(), 1, 1, 0, 0, 0, 0, q.From.Location()).UTC().Format(time.RFC3339)
|
||||||
|
stop = time.Date(q.To.Year(), 1, 1, 0, 0, 0, 0, q.To.Location()).UTC().Format(time.RFC3339)
|
||||||
|
}
|
||||||
|
|
||||||
|
filterTargetChain := ""
|
||||||
|
if len(q.TargetChains) > 0 {
|
||||||
|
val := fmt.Sprintf("r.destination_chain == \"%d\"", q.TargetChains[0])
|
||||||
|
buff := ""
|
||||||
|
for _, tc := range q.TargetChains[1:] {
|
||||||
|
buff += fmt.Sprintf("or r.destination_chain == \"%d\" ", tc)
|
||||||
|
}
|
||||||
|
filterTargetChain = fmt.Sprintf("|> filter(fn: (r) => %s %s)", val, buff)
|
||||||
|
}
|
||||||
|
|
||||||
|
filterSourceChain := ""
|
||||||
|
if len(q.SourceChains) > 0 {
|
||||||
|
val := fmt.Sprintf("r.emitter_chain == \"%d\"", q.SourceChains[0])
|
||||||
|
buff := ""
|
||||||
|
for _, tc := range q.SourceChains[1:] {
|
||||||
|
buff += fmt.Sprintf("or r.emitter_chain == \"%d\" ", tc)
|
||||||
|
}
|
||||||
|
filterSourceChain = fmt.Sprintf("|> filter(fn: (r) => %s %s)", val, buff)
|
||||||
|
}
|
||||||
|
|
||||||
|
filterAppId := ""
|
||||||
|
if q.AppId != "" {
|
||||||
|
filterAppId = "|> filter(fn: (r) => r.app_id == \"" + q.AppId + "\")"
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(q.TargetChains) == 0 && q.AppId == "" {
|
||||||
|
return r.buildQueryChainActivityTopsByEmitter(q, start, stop, filterSourceChain)
|
||||||
|
}
|
||||||
|
|
||||||
|
var query string
|
||||||
|
switch q.Timespan {
|
||||||
|
case Hour:
|
||||||
|
query = r.buildQueryChainActivityHourly(start, stop, filterSourceChain, filterTargetChain, filterAppId)
|
||||||
|
case Day:
|
||||||
|
query = r.buildQueryChainActivityDaily(start, stop, filterSourceChain, filterTargetChain, filterAppId)
|
||||||
|
case Month:
|
||||||
|
query = r.buildQueryChainActivityMonthly(start, stop, filterSourceChain, filterTargetChain, filterAppId)
|
||||||
|
default:
|
||||||
|
query = r.buildQueryChainActivityYearly(start, stop, filterSourceChain, filterTargetChain, filterAppId)
|
||||||
|
}
|
||||||
|
return query
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *Repository) buildQueryChainActivityTopsByEmitter(q ChainActivityTopsQuery, start, stop, filterSourceChain string) string {
|
||||||
|
|
||||||
|
measurement := ""
|
||||||
|
switch q.Timespan {
|
||||||
|
case Hour:
|
||||||
|
measurement = "emitter_chain_activity_1h"
|
||||||
|
default:
|
||||||
|
measurement = "emitter_chain_activity_1d"
|
||||||
|
}
|
||||||
|
|
||||||
|
if q.Timespan == Hour || q.Timespan == Day {
|
||||||
|
query := `
|
||||||
|
import "date"
|
||||||
|
|
||||||
|
from(bucket: "%s")
|
||||||
|
|> range(start: %s,stop: %s)
|
||||||
|
|> filter(fn: (r) => r._measurement == "%s")
|
||||||
|
%s
|
||||||
|
|> pivot(rowKey:["_time","emitter_chain"], columnKey: ["_field"], valueColumn: "_value")
|
||||||
|
|> sort(columns:["emitter_chain","_time"],desc:false)
|
||||||
|
`
|
||||||
|
return fmt.Sprintf(query, r.bucketInfiniteRetention, start, stop, measurement, filterSourceChain)
|
||||||
|
}
|
||||||
|
|
||||||
|
if q.Timespan == Month {
|
||||||
|
query := `
|
||||||
|
import "date"
|
||||||
|
import "join"
|
||||||
|
|
||||||
|
data = from(bucket: "%s")
|
||||||
|
|> range(start: %s,stop: %s)
|
||||||
|
|> filter(fn: (r) => r._measurement == "%s")
|
||||||
|
%s
|
||||||
|
|> drop(columns:["to"])
|
||||||
|
|> window(every: 1mo, period:1mo)
|
||||||
|
|> drop(columns:["_time"])
|
||||||
|
|> rename(columns: {_start: "_time"})
|
||||||
|
|> map(fn: (r) => ({r with to: string(v: r._stop)}))
|
||||||
|
|
||||||
|
vols = data
|
||||||
|
|> filter(fn: (r) => (r._field == "volume" and r._value > 0))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "volume"})
|
||||||
|
|
||||||
|
counts = data
|
||||||
|
|> filter(fn: (r) => (r._field == "count"))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "count"})
|
||||||
|
|
||||||
|
join.inner(
|
||||||
|
left: vols,
|
||||||
|
right: counts,
|
||||||
|
on: (l, r) => l._time == r._time and l.emitter_chain == r.emitter_chain,
|
||||||
|
as: (l, r) => ({l with count: r.count}),
|
||||||
|
)
|
||||||
|
|> group()
|
||||||
|
|> sort(columns:["emitter_chain","_time"],desc:false)
|
||||||
|
`
|
||||||
|
return fmt.Sprintf(query, r.bucketInfiniteRetention, start, stop, measurement, filterSourceChain)
|
||||||
|
}
|
||||||
|
|
||||||
|
query := `
|
||||||
|
import "date"
|
||||||
|
import "join"
|
||||||
|
|
||||||
|
data = from(bucket: "%s")
|
||||||
|
|> range(start: %s,stop: %s)
|
||||||
|
|> filter(fn: (r) => r._measurement == "%s")
|
||||||
|
%s
|
||||||
|
|> drop(columns:["to"])
|
||||||
|
|> window(every: 1y, period:1y)
|
||||||
|
|> drop(columns:["_time"])
|
||||||
|
|> rename(columns: {_start: "_time"})
|
||||||
|
|> map(fn: (r) => ({r with to: string(v: r._stop)}))
|
||||||
|
|
||||||
|
vols = data
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "volume"})
|
||||||
|
|
||||||
|
counts = data
|
||||||
|
|> filter(fn: (r) => (r._field == "count"))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "count"})
|
||||||
|
|
||||||
|
join.inner(
|
||||||
|
left: vols,
|
||||||
|
right: counts,
|
||||||
|
on: (l, r) => l._time == r._time and l.emitter_chain == r.emitter_chain,
|
||||||
|
as: (l, r) => ({l with count: r.count}),
|
||||||
|
)
|
||||||
|
|> group()
|
||||||
|
|> sort(columns:["emitter_chain","_time"],desc:false)
|
||||||
|
`
|
||||||
|
return fmt.Sprintf(query, r.bucketInfiniteRetention, start, stop, measurement, filterSourceChain)
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *Repository) buildQueryChainActivityHourly(start, stop, filterSourceChain, filterTargetChain, filterAppId string) string {
|
||||||
|
query := `
|
||||||
|
import "date"
|
||||||
|
import "join"
|
||||||
|
|
||||||
|
data = from(bucket: "%s")
|
||||||
|
|> range(start: %s,stop: %s)
|
||||||
|
|> filter(fn: (r) => r._measurement == "chain_activity_1h")
|
||||||
|
%s
|
||||||
|
%s
|
||||||
|
%s
|
||||||
|
|> drop(columns:["destination_chain"])
|
||||||
|
|
||||||
|
vols = data
|
||||||
|
|> filter(fn: (r) => (r._field == "volume" and r._value > 0))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "volume"})
|
||||||
|
|
||||||
|
counts = data
|
||||||
|
|> filter(fn: (r) => (r._field == "count"))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "count"})
|
||||||
|
|
||||||
|
join.inner(
|
||||||
|
left: vols,
|
||||||
|
right: counts,
|
||||||
|
on: (l, r) => l._time == r._time and l.to == r.to and l.emitter_chain == r.emitter_chain,
|
||||||
|
as: (l, r) => ({l with count: r.count}),
|
||||||
|
)
|
||||||
|
|> group()
|
||||||
|
|> sort(columns:["emitter_chain","_time"],desc:false)
|
||||||
|
`
|
||||||
|
return fmt.Sprintf(query, r.bucketInfiniteRetention, start, stop, filterSourceChain, filterTargetChain, filterAppId)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *Repository) buildQueryChainActivityDaily(start, stop, filterSourceChain, filterTargetChain, filterAppId string) string {
|
||||||
|
|
||||||
|
query := `
|
||||||
|
import "date"
|
||||||
|
import "join"
|
||||||
|
|
||||||
|
data = from(bucket: "%s")
|
||||||
|
|> range(start: %s,stop: %s)
|
||||||
|
|> filter(fn: (r) => r._measurement == "chain_activity_1d")
|
||||||
|
%s
|
||||||
|
%s
|
||||||
|
%s
|
||||||
|
|> drop(columns:["destination_chain"])
|
||||||
|
|
||||||
|
vols = data
|
||||||
|
|> filter(fn: (r) => (r._field == "volume" and r._value > 0))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "volume"})
|
||||||
|
|
||||||
|
counts = data
|
||||||
|
|> filter(fn: (r) => (r._field == "count"))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "count"})
|
||||||
|
|
||||||
|
join.inner(
|
||||||
|
left: vols,
|
||||||
|
right: counts,
|
||||||
|
on: (l, r) => l._time == r._time and l.to == r.to and l.emitter_chain == r.emitter_chain,
|
||||||
|
as: (l, r) => ({l with count: r.count}),
|
||||||
|
)
|
||||||
|
|> group()
|
||||||
|
|> sort(columns:["emitter_chain","_time"],desc:false)
|
||||||
|
`
|
||||||
|
return fmt.Sprintf(query, r.bucketInfiniteRetention, start, stop, filterSourceChain, filterTargetChain, filterAppId)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *Repository) buildQueryChainActivityMonthly(start, stop, filterSourceChain, filterTargetChain, filterAppId string) string {
|
||||||
|
query := `
|
||||||
|
import "date"
|
||||||
|
import "join"
|
||||||
|
|
||||||
|
data = from(bucket: "%s")
|
||||||
|
|> range(start: %s,stop: %s)
|
||||||
|
|> filter(fn: (r) => r._measurement == "chain_activity_1d")
|
||||||
|
%s
|
||||||
|
%s
|
||||||
|
%s
|
||||||
|
|> drop(columns:["destination_chain","to","app_id"])
|
||||||
|
|> window(every: 1mo, period:1mo)
|
||||||
|
|> drop(columns:["_time"])
|
||||||
|
|> rename(columns: {_start: "_time"})
|
||||||
|
|> map(fn: (r) => ({r with to: string(v: r._stop)}))
|
||||||
|
|
||||||
|
vols = data
|
||||||
|
|> filter(fn: (r) => (r._field == "volume" and r._value > 0))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "volume"})
|
||||||
|
|
||||||
|
counts = data
|
||||||
|
|> filter(fn: (r) => (r._field == "count"))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "count"})
|
||||||
|
|
||||||
|
join.inner(
|
||||||
|
left: vols,
|
||||||
|
right: counts,
|
||||||
|
on: (l, r) => l._time == r._time and l.emitter_chain == r.emitter_chain,
|
||||||
|
as: (l, r) => ({l with count: r.count}),
|
||||||
|
)
|
||||||
|
|> group()
|
||||||
|
|> sort(columns:["emitter_chain","_time"],desc:false)
|
||||||
|
`
|
||||||
|
return fmt.Sprintf(query, r.bucketInfiniteRetention, start, stop, filterSourceChain, filterTargetChain, filterAppId)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *Repository) buildQueryChainActivityYearly(start, stop, filterSourceChain, filterTargetChain, filterAppId string) string {
|
||||||
|
query := `
|
||||||
|
import "date"
|
||||||
|
import "join"
|
||||||
|
|
||||||
|
data = from(bucket: "%s")
|
||||||
|
|> range(start: %s,stop: %s)
|
||||||
|
|> filter(fn: (r) => r._measurement == "chain_activity_1d")
|
||||||
|
%s
|
||||||
|
%s
|
||||||
|
%s
|
||||||
|
|> drop(columns:["destination_chain","to","app_id"])
|
||||||
|
|> window(every: 1y, period:1y)
|
||||||
|
|> drop(columns:["_time"])
|
||||||
|
|> rename(columns: {_start: "_time"})
|
||||||
|
|> map(fn: (r) => ({r with to: string(v: r._stop)}))
|
||||||
|
|
||||||
|
vols = data
|
||||||
|
|> filter(fn: (r) => (r._field == "volume" and r._value > 0))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "volume"})
|
||||||
|
|
||||||
|
counts = data
|
||||||
|
|> filter(fn: (r) => (r._field == "count"))
|
||||||
|
|> group(columns:["_time","to","emitter_chain"])
|
||||||
|
|> sum()
|
||||||
|
|> rename(columns: {_value: "count"})
|
||||||
|
|
||||||
|
join.inner(
|
||||||
|
left: vols,
|
||||||
|
right: counts,
|
||||||
|
on: (l, r) => l._time == r._time and l.emitter_chain == r.emitter_chain,
|
||||||
|
as: (l, r) => ({l with count: r.count}),
|
||||||
|
)
|
||||||
|
|> group()
|
||||||
|
|> sort(columns:["emitter_chain","_time"],desc:false)
|
||||||
|
`
|
||||||
|
return fmt.Sprintf(query, r.bucketInfiniteRetention, start, stop, filterSourceChain, filterTargetChain, filterAppId)
|
||||||
|
}
|
||||||
|
|
|
@ -2,12 +2,13 @@ package transactions
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
errors "errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"github.com/valyala/fasthttp"
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/wormhole-foundation/wormhole-explorer/api/cacheable"
|
"github.com/wormhole-foundation/wormhole-explorer/api/cacheable"
|
||||||
"github.com/wormhole-foundation/wormhole-explorer/api/internal/errors"
|
|
||||||
errs "github.com/wormhole-foundation/wormhole-explorer/api/internal/errors"
|
errs "github.com/wormhole-foundation/wormhole-explorer/api/internal/errors"
|
||||||
"github.com/wormhole-foundation/wormhole-explorer/api/internal/metrics"
|
"github.com/wormhole-foundation/wormhole-explorer/api/internal/metrics"
|
||||||
"github.com/wormhole-foundation/wormhole-explorer/api/internal/pagination"
|
"github.com/wormhole-foundation/wormhole-explorer/api/internal/pagination"
|
||||||
|
@ -34,6 +35,7 @@ const (
|
||||||
topAssetsByVolumeKey = "wormscan:top-assets-by-volume"
|
topAssetsByVolumeKey = "wormscan:top-assets-by-volume"
|
||||||
topChainPairsByNumTransfersKey = "wormscan:top-chain-pairs-by-num-transfers"
|
topChainPairsByNumTransfersKey = "wormscan:top-chain-pairs-by-num-transfers"
|
||||||
chainActivityKey = "wormscan:chain-activity"
|
chainActivityKey = "wormscan:chain-activity"
|
||||||
|
chainActivityTopsKey = "wormscan:chain-activity-tops"
|
||||||
)
|
)
|
||||||
|
|
||||||
// NewService create a new Service.
|
// NewService create a new Service.
|
||||||
|
@ -157,7 +159,7 @@ func (s *Service) GetTransactionByID(
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
if len(output) == 0 {
|
if len(output) == 0 {
|
||||||
return nil, errors.ErrNotFound
|
return nil, errs.ErrNotFound
|
||||||
}
|
}
|
||||||
|
|
||||||
// Return matching document
|
// Return matching document
|
||||||
|
@ -167,3 +169,44 @@ func (s *Service) GetTransactionByID(
|
||||||
func (s *Service) GetTokenProvider() *domain.TokenProvider {
|
func (s *Service) GetTokenProvider() *domain.TokenProvider {
|
||||||
return s.tokenProvider
|
return s.tokenProvider
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (s *Service) GetChainActivityTops(ctx *fasthttp.RequestCtx, q ChainActivityTopsQuery) (ChainActivityTopResults, error) {
|
||||||
|
|
||||||
|
timeDuration := q.To.Sub(q.From)
|
||||||
|
|
||||||
|
if q.Timespan == Hour && timeDuration > 15*24*time.Hour {
|
||||||
|
return nil, errors.New("time range is too large for hourly data. Max time range allowed: 15 days")
|
||||||
|
}
|
||||||
|
|
||||||
|
if q.Timespan == Day {
|
||||||
|
if timeDuration < 24*time.Hour {
|
||||||
|
return nil, errors.New("time range is too small for daily data. Min time range allowed: 2 day")
|
||||||
|
}
|
||||||
|
|
||||||
|
if timeDuration > 365*24*time.Hour {
|
||||||
|
return nil, errors.New("time range is too large for daily data. Max time range allowed: 1 year")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if q.Timespan == Month {
|
||||||
|
if timeDuration < 30*24*time.Hour {
|
||||||
|
return nil, errors.New("time range is too small for monthly data. Min time range allowed: 60 days")
|
||||||
|
}
|
||||||
|
|
||||||
|
if timeDuration > 10*365*24*time.Hour {
|
||||||
|
return nil, errors.New("time range is too large for monthly data. Max time range allowed: 1 year")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if q.Timespan == Year {
|
||||||
|
if timeDuration < 365*24*time.Hour {
|
||||||
|
return nil, errors.New("time range is too small for yearly data. Min time range allowed: 1 year")
|
||||||
|
}
|
||||||
|
|
||||||
|
if timeDuration > 10*365*24*time.Hour {
|
||||||
|
return nil, errors.New("time range is too large for yearly data. Max time range allowed: 10 year")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return s.repo.FindChainActivityTops(ctx, q)
|
||||||
|
}
|
||||||
|
|
|
@ -61,23 +61,6 @@ func ExtractToChain(c *fiber.Ctx, l *zap.Logger) (*sdk.ChainID, error) {
|
||||||
return &result, nil
|
return &result, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func ExtractChain(c *fiber.Ctx, l *zap.Logger) (*sdk.ChainID, error) {
|
|
||||||
return extractChainQueryParam(c, l, "chain")
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
func ExtractSourceChain(c *fiber.Ctx, l *zap.Logger) (*sdk.ChainID, error) {
|
|
||||||
return extractChainQueryParam(c, l, "sourceChain")
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
func ExtractTargetChain(c *fiber.Ctx, l *zap.Logger) (*sdk.ChainID, error) {
|
|
||||||
return extractChainQueryParam(c, l, "targetChain")
|
|
||||||
}
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
func ExtractSourceChain(c *fiber.Ctx, l *zap.Logger) ([]sdk.ChainID, error) {
|
func ExtractSourceChain(c *fiber.Ctx, l *zap.Logger) ([]sdk.ChainID, error) {
|
||||||
param := c.Query("sourceChain")
|
param := c.Query("sourceChain")
|
||||||
if param == "" {
|
if param == "" {
|
||||||
|
@ -129,12 +112,10 @@ func parseChainIDParam(param string) (sdk.ChainID, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func extractChainQueryParam(c *fiber.Ctx, l *zap.Logger, queryParam string) (*sdk.ChainID, error) {
|
func extractChainQueryParam(c *fiber.Ctx, l *zap.Logger, queryParam string) (*sdk.ChainID, error) {
|
||||||
|
|
||||||
param := c.Query(queryParam)
|
param := c.Query(queryParam)
|
||||||
if param == "" {
|
if param == "" {
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
chain, err := strconv.ParseInt(param, 10, 16)
|
chain, err := strconv.ParseInt(param, 10, 16)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
requestID := fmt.Sprintf("%v", c.Locals("requestid"))
|
requestID := fmt.Sprintf("%v", c.Locals("requestid"))
|
||||||
|
@ -145,7 +126,6 @@ func extractChainQueryParam(c *fiber.Ctx, l *zap.Logger, queryParam string) (*sd
|
||||||
|
|
||||||
return nil, response.NewInvalidParamError(c, "INVALID CHAIN VALUE", errors.WithStack(err))
|
return nil, response.NewInvalidParamError(c, "INVALID CHAIN VALUE", errors.WithStack(err))
|
||||||
}
|
}
|
||||||
|
|
||||||
result := sdk.ChainID(chain)
|
result := sdk.ChainID(chain)
|
||||||
return &result, nil
|
return &result, nil
|
||||||
}
|
}
|
||||||
|
@ -346,17 +326,6 @@ func ExtractAppId(c *fiber.Ctx, l *zap.Logger) string {
|
||||||
return c.Query("appId")
|
return c.Query("appId")
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
func ExtractAppIds(c *fiber.Ctx, l *zap.Logger) []string {
|
|
||||||
query := c.Query("appId")
|
|
||||||
if query == "" {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
return strings.Split(query, ",")
|
|
||||||
}
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
func ExtractExclusiveAppId(c *fiber.Ctx) (bool, error) {
|
func ExtractExclusiveAppId(c *fiber.Ctx) (bool, error) {
|
||||||
query := c.Query("exclusiveAppId")
|
query := c.Query("exclusiveAppId")
|
||||||
if query == "" {
|
if query == "" {
|
||||||
|
@ -424,14 +393,13 @@ func ExtractTimeSpanAndSampleRate(c *fiber.Ctx, l *zap.Logger) (string, string,
|
||||||
return timeSpan, sampleRate, nil
|
return timeSpan, sampleRate, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func ExtractTime(c *fiber.Ctx, queryParam string) (*time.Time, error) {
|
func ExtractTime(c *fiber.Ctx, timeLayout, queryParam string) (*time.Time, error) {
|
||||||
// get the start_time from query params
|
// get the start_time from query params
|
||||||
date := c.Query(queryParam, "")
|
date := c.Query(queryParam, "")
|
||||||
if date == "" {
|
if date == "" {
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
t, err := time.Parse(timeLayout, date)
|
||||||
t, err := time.Parse("20060102T150405Z", date)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, response.NewInvalidQueryParamError(c, fmt.Sprintf("INVALID <%s> QUERY PARAMETER", queryParam), nil)
|
return nil, response.NewInvalidQueryParamError(c, fmt.Sprintf("INVALID <%s> QUERY PARAMETER", queryParam), nil)
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,14 +1,13 @@
|
||||||
package operations
|
package operations
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"strconv"
|
|
||||||
"strings"
|
|
||||||
|
|
||||||
"github.com/gofiber/fiber/v2"
|
"github.com/gofiber/fiber/v2"
|
||||||
"github.com/wormhole-foundation/wormhole-explorer/api/handlers/operations"
|
"github.com/wormhole-foundation/wormhole-explorer/api/handlers/operations"
|
||||||
"github.com/wormhole-foundation/wormhole-explorer/api/middleware"
|
"github.com/wormhole-foundation/wormhole-explorer/api/middleware"
|
||||||
"github.com/wormhole-foundation/wormhole-explorer/api/response"
|
"github.com/wormhole-foundation/wormhole-explorer/api/response"
|
||||||
"go.uber.org/zap"
|
"go.uber.org/zap"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Controller is the controller for the operation resource.
|
// Controller is the controller for the operation resource.
|
||||||
|
@ -76,8 +75,11 @@ func (c *Controller) FindAll(ctx *fiber.Ctx) error {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
//appID := middleware.ExtractAppId(ctx, c.logger)
|
var appIDs []string
|
||||||
appID := strings.Split(ctx.Query("appId"), ",")
|
appIDQueryParam := ctx.Query("appId")
|
||||||
|
if appIDQueryParam != "" {
|
||||||
|
appIDs = strings.Split(appIDQueryParam, ",")
|
||||||
|
}
|
||||||
|
|
||||||
exclusiveAppId, err := middleware.ExtractExclusiveAppId(ctx)
|
exclusiveAppId, err := middleware.ExtractExclusiveAppId(ctx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -85,7 +87,7 @@ func (c *Controller) FindAll(ctx *fiber.Ctx) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
searchBySourceTargetChain := len(sourceChain) != 0 || targetChain != nil
|
searchBySourceTargetChain := len(sourceChain) != 0 || targetChain != nil
|
||||||
searchByAppId := len(appID) != 0
|
searchByAppId := len(appIDs) != 0
|
||||||
|
|
||||||
if (searchByAddress || searchByTxHash) && (searchBySourceTargetChain || searchByAppId) {
|
if (searchByAddress || searchByTxHash) && (searchBySourceTargetChain || searchByAppId) {
|
||||||
return response.NewInvalidParamError(ctx, "address/txHash cannot be combined with sourceChain/targetChain/appId query filter", nil)
|
return response.NewInvalidParamError(ctx, "address/txHash cannot be combined with sourceChain/targetChain/appId query filter", nil)
|
||||||
|
@ -96,7 +98,7 @@ func (c *Controller) FindAll(ctx *fiber.Ctx) error {
|
||||||
Address: address,
|
Address: address,
|
||||||
SourceChainIDs: sourceChain,
|
SourceChainIDs: sourceChain,
|
||||||
TargetChainIDs: targetChain,
|
TargetChainIDs: targetChain,
|
||||||
AppID: appID,
|
AppIDs: appIDs,
|
||||||
ExclusiveAppId: exclusiveAppId,
|
ExclusiveAppId: exclusiveAppId,
|
||||||
Pagination: *pagination,
|
Pagination: *pagination,
|
||||||
}
|
}
|
||||||
|
|
|
@ -85,6 +85,7 @@ func RegisterRoutes(
|
||||||
api.Get("/last-txs", transactionCtrl.GetLastTransactions)
|
api.Get("/last-txs", transactionCtrl.GetLastTransactions)
|
||||||
api.Get("/scorecards", transactionCtrl.GetScorecards)
|
api.Get("/scorecards", transactionCtrl.GetScorecards)
|
||||||
api.Get("/x-chain-activity", transactionCtrl.GetChainActivity)
|
api.Get("/x-chain-activity", transactionCtrl.GetChainActivity)
|
||||||
|
api.Get("/x-chain-activity/tops", transactionCtrl.GetChainActivityTops)
|
||||||
api.Get("/top-assets-by-volume", transactionCtrl.GetTopAssets)
|
api.Get("/top-assets-by-volume", transactionCtrl.GetTopAssets)
|
||||||
api.Get("/top-chain-pairs-by-num-transfers", transactionCtrl.GetTopChainPairs)
|
api.Get("/top-chain-pairs-by-num-transfers", transactionCtrl.GetTopChainPairs)
|
||||||
api.Get("token/:chain/:token_address", transactionCtrl.GetTokenByChainAndAddress)
|
api.Get("token/:chain/:token_address", transactionCtrl.GetTokenByChainAndAddress)
|
||||||
|
|
|
@ -2,6 +2,7 @@ package transactions
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"strconv"
|
"strconv"
|
||||||
|
"time"
|
||||||
|
|
||||||
"github.com/gofiber/fiber/v2"
|
"github.com/gofiber/fiber/v2"
|
||||||
"github.com/shopspring/decimal"
|
"github.com/shopspring/decimal"
|
||||||
|
@ -182,6 +183,75 @@ func (c *Controller) GetTopAssets(ctx *fiber.Ctx) error {
|
||||||
return ctx.JSON(response)
|
return ctx.JSON(response)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetChainActivityTops godoc
|
||||||
|
// @Description Search for a specific period of time the number of transactions and the volume.
|
||||||
|
// @Tags wormholescan
|
||||||
|
// @ID x-chain-activity-tops
|
||||||
|
// @Method Get
|
||||||
|
// @Param timespan query string true "Time span, supported values: 1d, 1mo and 1y"
|
||||||
|
// @Param from query string true "From date, supported format 2006-01-02T15:04:05Z07:00"
|
||||||
|
// @Param to query string true "To date, supported format 2006-01-02T15:04:05Z07:00"
|
||||||
|
// @Param appId query string false "Search by appId"
|
||||||
|
// @Param sourceChain query string false "Search by sourceChain"
|
||||||
|
// @Param targetChain query string false "Search by targetChain"
|
||||||
|
// @Success 200 {object} transactions.ChainActivityTopResults
|
||||||
|
// @Failure 400
|
||||||
|
// @Failure 500
|
||||||
|
// @Router /api/v1/x-chain-activity/tops [get]
|
||||||
|
func (c *Controller) GetChainActivityTops(ctx *fiber.Ctx) error {
|
||||||
|
|
||||||
|
sourceChains, err := middleware.ExtractSourceChain(ctx, c.logger)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
targetChains, err := middleware.ExtractTargetChain(ctx, c.logger)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
from, err := middleware.ExtractTime(ctx, time.RFC3339, "from")
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
to, err := middleware.ExtractTime(ctx, time.RFC3339, "to")
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
if from == nil || to == nil {
|
||||||
|
return response.NewInvalidParamError(ctx, "missing from/to query params ", nil)
|
||||||
|
}
|
||||||
|
|
||||||
|
payload := transactions.ChainActivityTopsQuery{
|
||||||
|
SourceChains: sourceChains,
|
||||||
|
TargetChains: targetChains,
|
||||||
|
From: *from,
|
||||||
|
To: *to,
|
||||||
|
AppId: middleware.ExtractAppId(ctx, c.logger),
|
||||||
|
Timespan: transactions.Timespan(ctx.Query("timespan")),
|
||||||
|
}
|
||||||
|
|
||||||
|
if !payload.Timespan.IsValid() {
|
||||||
|
return response.NewInvalidParamError(ctx, "invalid timespan", nil)
|
||||||
|
}
|
||||||
|
|
||||||
|
nowUTC := time.Now().UTC()
|
||||||
|
if nowUTC.Before(payload.To.UTC()) {
|
||||||
|
payload.To = nowUTC
|
||||||
|
}
|
||||||
|
|
||||||
|
if payload.To.Sub(payload.From) <= 0 {
|
||||||
|
return response.NewInvalidParamError(ctx, "invalid time range", nil)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get the chain activity.
|
||||||
|
activity, err := c.srv.GetChainActivityTops(ctx.Context(), payload)
|
||||||
|
if err != nil {
|
||||||
|
c.logger.Error("Error getting chain activity", zap.Error(err))
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
return ctx.JSON(activity)
|
||||||
|
}
|
||||||
|
|
||||||
// GetChainActivity godoc
|
// GetChainActivity godoc
|
||||||
// @Description Returns a list of chain pairs by origin chain and destination chain.
|
// @Description Returns a list of chain pairs by origin chain and destination chain.
|
||||||
// @Description The list could be rendered by notional or transaction count.
|
// @Description The list could be rendered by notional or transaction count.
|
||||||
|
|
|
@ -4,6 +4,11 @@ package domain
|
||||||
func manualMainnetTokenList() []TokenMetadata {
|
func manualMainnetTokenList() []TokenMetadata {
|
||||||
return []TokenMetadata{
|
return []TokenMetadata{
|
||||||
{TokenChain: 1, TokenAddress: "6927fdc01ea906f96d7137874cdd7adad00ca35764619310e54196c781d84d5b", Symbol: "W", CoingeckoID: "wormhole", Decimals: 6}, // Addr: 85VBFQZC9TZkfaptBWjvUw7YbZjy52A6mjtPGjstQAmQ
|
{TokenChain: 1, TokenAddress: "6927fdc01ea906f96d7137874cdd7adad00ca35764619310e54196c781d84d5b", Symbol: "W", CoingeckoID: "wormhole", Decimals: 6}, // Addr: 85VBFQZC9TZkfaptBWjvUw7YbZjy52A6mjtPGjstQAmQ
|
||||||
|
{TokenChain: 2, TokenAddress: "000000000000000000000000b0ffa8000886e57f86dd5264b9582b2ad87b2b91", Symbol: "W", CoingeckoID: "wormhole", Decimals: 18}, // Addr: 0xB0fFa8000886e57F86dd5264b9582b2Ad87b2b91
|
||||||
|
{TokenChain: 23, TokenAddress: "000000000000000000000000b0ffa8000886e57f86dd5264b9582b2ad87b2b91", Symbol: "W", CoingeckoID: "wormhole", Decimals: 18}, // Addr: 0xB0fFa8000886e57F86dd5264b9582b2Ad87b2b91
|
||||||
|
{TokenChain: 24, TokenAddress: "000000000000000000000000b0ffa8000886e57f86dd5264b9582b2ad87b2b91", Symbol: "W", CoingeckoID: "wormhole", Decimals: 18}, // Addr: 0xB0fFa8000886e57F86dd5264b9582b2Ad87b2b91
|
||||||
|
{TokenChain: 30, TokenAddress: "000000000000000000000000b0ffa8000886e57f86dd5264b9582b2ad87b2b91", Symbol: "W", CoingeckoID: "wormhole", Decimals: 18}, // Addr: 0xB0fFa8000886e57F86dd5264b9582b2Ad87b2b91
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
23
jobs/go.mod
23
jobs/go.mod
|
@ -12,17 +12,17 @@ require (
|
||||||
github.com/stretchr/testify v1.8.4
|
github.com/stretchr/testify v1.8.4
|
||||||
github.com/test-go/testify v1.1.4
|
github.com/test-go/testify v1.1.4
|
||||||
github.com/wormhole-foundation/wormhole-explorer/common v0.0.0-20230713181709-0425a89e7533
|
github.com/wormhole-foundation/wormhole-explorer/common v0.0.0-20230713181709-0425a89e7533
|
||||||
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240109172745-cc0cd9fc5229
|
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240416174455-25e60611a867
|
||||||
go.mongodb.org/mongo-driver v1.11.2
|
go.mongodb.org/mongo-driver v1.11.2
|
||||||
go.uber.org/zap v1.25.0
|
go.uber.org/zap v1.26.0
|
||||||
)
|
)
|
||||||
|
|
||||||
require (
|
require (
|
||||||
github.com/algorand/go-algorand-sdk v1.23.0 // indirect
|
github.com/algorand/go-algorand-sdk v1.23.0 // indirect
|
||||||
github.com/algorand/go-codec/codec v1.1.8 // indirect
|
github.com/algorand/go-codec/codec v1.1.8 // indirect
|
||||||
github.com/andybalholm/brotli v1.0.5 // indirect
|
github.com/andybalholm/brotli v1.0.5 // indirect
|
||||||
github.com/benbjohnson/clock v1.3.5 // indirect
|
|
||||||
github.com/btcsuite/btcd/btcec/v2 v2.3.2 // indirect
|
github.com/btcsuite/btcd/btcec/v2 v2.3.2 // indirect
|
||||||
|
github.com/certusone/wormhole/node v0.0.0-20240416174455-25e60611a867 // indirect
|
||||||
github.com/cespare/xxhash/v2 v2.2.0 // indirect
|
github.com/cespare/xxhash/v2 v2.2.0 // indirect
|
||||||
github.com/cosmos/btcutil v1.0.5 // indirect
|
github.com/cosmos/btcutil v1.0.5 // indirect
|
||||||
github.com/davecgh/go-spew v1.1.1 // indirect
|
github.com/davecgh/go-spew v1.1.1 // indirect
|
||||||
|
@ -36,13 +36,12 @@ require (
|
||||||
github.com/holiman/uint256 v1.2.1 // indirect
|
github.com/holiman/uint256 v1.2.1 // indirect
|
||||||
github.com/influxdata/line-protocol v0.0.0-20210311194329-9aa0e372d097 // indirect
|
github.com/influxdata/line-protocol v0.0.0-20210311194329-9aa0e372d097 // indirect
|
||||||
github.com/joho/godotenv v1.5.1 // indirect
|
github.com/joho/godotenv v1.5.1 // indirect
|
||||||
github.com/klauspost/compress v1.16.7 // indirect
|
github.com/klauspost/compress v1.17.2 // indirect
|
||||||
github.com/mattn/go-colorable v0.1.13 // indirect
|
github.com/mattn/go-colorable v0.1.13 // indirect
|
||||||
github.com/mattn/go-isatty v0.0.19 // indirect
|
github.com/mattn/go-isatty v0.0.20 // indirect
|
||||||
github.com/mattn/go-runewidth v0.0.14 // indirect
|
github.com/mattn/go-runewidth v0.0.14 // indirect
|
||||||
github.com/montanaflynn/stats v0.7.0 // indirect
|
github.com/montanaflynn/stats v0.7.0 // indirect
|
||||||
github.com/mr-tron/base58 v1.2.0 // indirect
|
github.com/mr-tron/base58 v1.2.0 // indirect
|
||||||
github.com/onsi/gomega v1.27.8 // indirect
|
|
||||||
github.com/philhofer/fwd v1.1.2 // indirect
|
github.com/philhofer/fwd v1.1.2 // indirect
|
||||||
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect
|
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect
|
||||||
github.com/rivo/uniseg v0.2.0 // indirect
|
github.com/rivo/uniseg v0.2.0 // indirect
|
||||||
|
@ -51,7 +50,6 @@ require (
|
||||||
github.com/savsgio/gotils v0.0.0-20230208104028-c358bd845dee // indirect
|
github.com/savsgio/gotils v0.0.0-20230208104028-c358bd845dee // indirect
|
||||||
github.com/sethvargo/go-envconfig v1.0.0 // indirect
|
github.com/sethvargo/go-envconfig v1.0.0 // indirect
|
||||||
github.com/stretchr/objx v0.5.0 // indirect
|
github.com/stretchr/objx v0.5.0 // indirect
|
||||||
github.com/tidwall/pretty v1.2.1 // indirect
|
|
||||||
github.com/tinylib/msgp v1.1.8 // indirect
|
github.com/tinylib/msgp v1.1.8 // indirect
|
||||||
github.com/valyala/bytebufferpool v1.0.0 // indirect
|
github.com/valyala/bytebufferpool v1.0.0 // indirect
|
||||||
github.com/valyala/fasthttp v1.47.0 // indirect
|
github.com/valyala/fasthttp v1.47.0 // indirect
|
||||||
|
@ -61,11 +59,12 @@ require (
|
||||||
github.com/xdg-go/stringprep v1.0.4 // indirect
|
github.com/xdg-go/stringprep v1.0.4 // indirect
|
||||||
github.com/youmark/pkcs8 v0.0.0-20201027041543-1326539a0a0a // indirect
|
github.com/youmark/pkcs8 v0.0.0-20201027041543-1326539a0a0a // indirect
|
||||||
go.uber.org/multierr v1.11.0 // indirect
|
go.uber.org/multierr v1.11.0 // indirect
|
||||||
golang.org/x/crypto v0.14.0 // indirect
|
golang.org/x/crypto v0.19.0 // indirect
|
||||||
golang.org/x/net v0.17.0 // indirect
|
golang.org/x/net v0.21.0 // indirect
|
||||||
golang.org/x/sync v0.3.0 // indirect
|
golang.org/x/sync v0.4.0 // indirect
|
||||||
golang.org/x/sys v0.13.0 // indirect
|
golang.org/x/sys v0.17.0 // indirect
|
||||||
golang.org/x/text v0.13.0 // indirect
|
golang.org/x/text v0.14.0 // indirect
|
||||||
|
google.golang.org/protobuf v1.32.0 // indirect
|
||||||
gopkg.in/yaml.v3 v3.0.1 // indirect
|
gopkg.in/yaml.v3 v3.0.1 // indirect
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
43
jobs/go.sum
43
jobs/go.sum
|
@ -5,11 +5,12 @@ github.com/algorand/go-codec/codec v1.1.8 h1:lsFuhcOH2LiEhpBH3BVUUkdevVmwCRyvb7F
|
||||||
github.com/algorand/go-codec/codec v1.1.8/go.mod h1:tQ3zAJ6ijTps6V+wp8KsGDnPC2uhHVC7ANyrtkIY0bA=
|
github.com/algorand/go-codec/codec v1.1.8/go.mod h1:tQ3zAJ6ijTps6V+wp8KsGDnPC2uhHVC7ANyrtkIY0bA=
|
||||||
github.com/andybalholm/brotli v1.0.5 h1:8uQZIdzKmjc/iuPu7O2ioW48L81FgatrcpfFmiq/cCs=
|
github.com/andybalholm/brotli v1.0.5 h1:8uQZIdzKmjc/iuPu7O2ioW48L81FgatrcpfFmiq/cCs=
|
||||||
github.com/andybalholm/brotli v1.0.5/go.mod h1:fO7iG3H7G2nSZ7m0zPUDn85XEX2GTukHGRSepvi9Eig=
|
github.com/andybalholm/brotli v1.0.5/go.mod h1:fO7iG3H7G2nSZ7m0zPUDn85XEX2GTukHGRSepvi9Eig=
|
||||||
github.com/benbjohnson/clock v1.3.5 h1:VvXlSJBzZpA/zum6Sj74hxwYI2DIxRWuNIoXAzHZz5o=
|
github.com/btcsuite/btcd v0.22.1 h1:CnwP9LM/M9xuRrGSCGeMVs9iv09uMqwsVX7EeIpgV2c=
|
||||||
github.com/benbjohnson/clock v1.3.5/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA=
|
|
||||||
github.com/btcsuite/btcd/btcec/v2 v2.3.2 h1:5n0X6hX0Zk+6omWcihdYvdAlGf2DfasC0GMf7DClJ3U=
|
github.com/btcsuite/btcd/btcec/v2 v2.3.2 h1:5n0X6hX0Zk+6omWcihdYvdAlGf2DfasC0GMf7DClJ3U=
|
||||||
github.com/btcsuite/btcd/btcec/v2 v2.3.2/go.mod h1:zYzJ8etWJQIv1Ogk7OzpWjowwOdXY1W/17j2MW85J04=
|
github.com/btcsuite/btcd/btcec/v2 v2.3.2/go.mod h1:zYzJ8etWJQIv1Ogk7OzpWjowwOdXY1W/17j2MW85J04=
|
||||||
github.com/btcsuite/btcd/chaincfg/chainhash v1.0.1 h1:q0rUy8C/TYNBQS1+CGKw68tLOFYSNEs0TFnxxnS9+4U=
|
github.com/btcsuite/btcd/chaincfg/chainhash v1.0.1 h1:q0rUy8C/TYNBQS1+CGKw68tLOFYSNEs0TFnxxnS9+4U=
|
||||||
|
github.com/certusone/wormhole/node v0.0.0-20240416174455-25e60611a867 h1:Wdd/ZJuGD3logxkNuT3hA2aq0Uk5uDGMGhca+S1CDnM=
|
||||||
|
github.com/certusone/wormhole/node v0.0.0-20240416174455-25e60611a867/go.mod h1:vJHIhQ0MeHZfQ4OpGiUCm3LD3nrdfT1CEIh2JaPCCso=
|
||||||
github.com/cespare/xxhash/v2 v2.2.0 h1:DC2CZ1Ep5Y4k3ZQ899DldepgrayRUGE6BBZ/cd9Cj44=
|
github.com/cespare/xxhash/v2 v2.2.0 h1:DC2CZ1Ep5Y4k3ZQ899DldepgrayRUGE6BBZ/cd9Cj44=
|
||||||
github.com/cespare/xxhash/v2 v2.2.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
|
github.com/cespare/xxhash/v2 v2.2.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
|
||||||
github.com/cosmos/btcutil v1.0.5 h1:t+ZFcX77LpKtDBhjucvnOH8C2l2ioGsBNEQ3jef8xFk=
|
github.com/cosmos/btcutil v1.0.5 h1:t+ZFcX77LpKtDBhjucvnOH8C2l2ioGsBNEQ3jef8xFk=
|
||||||
|
@ -61,8 +62,8 @@ github.com/influxdata/line-protocol v0.0.0-20210311194329-9aa0e372d097/go.mod h1
|
||||||
github.com/joho/godotenv v1.5.1 h1:7eLL/+HRGLY0ldzfGMeQkb7vMd0as4CfYvUVzLqw0N0=
|
github.com/joho/godotenv v1.5.1 h1:7eLL/+HRGLY0ldzfGMeQkb7vMd0as4CfYvUVzLqw0N0=
|
||||||
github.com/joho/godotenv v1.5.1/go.mod h1:f4LDr5Voq0i2e/R5DDNOoa2zzDfwtkZa6DnEwAbqwq4=
|
github.com/joho/godotenv v1.5.1/go.mod h1:f4LDr5Voq0i2e/R5DDNOoa2zzDfwtkZa6DnEwAbqwq4=
|
||||||
github.com/klauspost/compress v1.13.6/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk=
|
github.com/klauspost/compress v1.13.6/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk=
|
||||||
github.com/klauspost/compress v1.16.7 h1:2mk3MPGNzKyxErAw8YaohYh69+pa4sIQSC0fPGCFR9I=
|
github.com/klauspost/compress v1.17.2 h1:RlWWUY/Dr4fL8qk9YG7DTZ7PDgME2V4csBXA8L/ixi4=
|
||||||
github.com/klauspost/compress v1.16.7/go.mod h1:ntbaceVETuRiXiv4DpjP66DpAtAGkEQskQzEyD//IeE=
|
github.com/klauspost/compress v1.17.2/go.mod h1:ntbaceVETuRiXiv4DpjP66DpAtAGkEQskQzEyD//IeE=
|
||||||
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
|
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
|
||||||
github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE=
|
github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE=
|
||||||
github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
|
github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
|
||||||
|
@ -82,8 +83,8 @@ github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hd
|
||||||
github.com/mattn/go-isatty v0.0.9/go.mod h1:YNRxwqDuOph6SZLI9vUUz6OYw3QyUt7WiY2yME+cCiQ=
|
github.com/mattn/go-isatty v0.0.9/go.mod h1:YNRxwqDuOph6SZLI9vUUz6OYw3QyUt7WiY2yME+cCiQ=
|
||||||
github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU=
|
github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU=
|
||||||
github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM=
|
github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM=
|
||||||
github.com/mattn/go-isatty v0.0.19 h1:JITubQf0MOLdlGRuRq+jtsDlekdYPia9ZFsB8h/APPA=
|
github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY=
|
||||||
github.com/mattn/go-isatty v0.0.19/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
|
github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
|
||||||
github.com/mattn/go-runewidth v0.0.14 h1:+xnbZSEeDbOIg5/mE6JF0w6n9duR1l3/WmbinWVwUuU=
|
github.com/mattn/go-runewidth v0.0.14 h1:+xnbZSEeDbOIg5/mE6JF0w6n9duR1l3/WmbinWVwUuU=
|
||||||
github.com/mattn/go-runewidth v0.0.14/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w=
|
github.com/mattn/go-runewidth v0.0.14/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w=
|
||||||
github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe/go.mod h1:wL8QJuTMNUDYhXwkmfOly8iTdp5TEcJFWZD2D7SIkUc=
|
github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe/go.mod h1:wL8QJuTMNUDYhXwkmfOly8iTdp5TEcJFWZD2D7SIkUc=
|
||||||
|
@ -93,8 +94,7 @@ github.com/mr-tron/base58 v1.2.0 h1:T/HDJBh4ZCPbU39/+c3rRvE0uKBQlU27+QI8LJ4t64o=
|
||||||
github.com/mr-tron/base58 v1.2.0/go.mod h1:BinMc/sQntlIE1frQmRFPUoPA1Zkr8VRgBdjWI2mNwc=
|
github.com/mr-tron/base58 v1.2.0/go.mod h1:BinMc/sQntlIE1frQmRFPUoPA1Zkr8VRgBdjWI2mNwc=
|
||||||
github.com/nxadm/tail v1.4.8 h1:nPr65rt6Y5JFSKQO7qToXr7pePgD6Gwiw05lkbyAQTE=
|
github.com/nxadm/tail v1.4.8 h1:nPr65rt6Y5JFSKQO7qToXr7pePgD6Gwiw05lkbyAQTE=
|
||||||
github.com/onsi/ginkgo v1.16.5 h1:8xi0RTUf59SOSfEtZMvwTvXYMzG4gV23XVHOZiXNtnE=
|
github.com/onsi/ginkgo v1.16.5 h1:8xi0RTUf59SOSfEtZMvwTvXYMzG4gV23XVHOZiXNtnE=
|
||||||
github.com/onsi/gomega v1.27.8 h1:gegWiwZjBsf2DgiSbf5hpokZ98JVDMcWkUiigk6/KXc=
|
github.com/onsi/gomega v1.30.0 h1:hvMK7xYz4D3HapigLTeGdId/NcfQx1VHMJc60ew99+8=
|
||||||
github.com/onsi/gomega v1.27.8/go.mod h1:2J8vzI/s+2shY9XHRApDkdgPo1TKT7P2u6fXeJKFnNQ=
|
|
||||||
github.com/philhofer/fwd v1.1.1/go.mod h1:gk3iGcWd9+svBvR0sR+KPcfE+RNWozjowpeBVG3ZVNU=
|
github.com/philhofer/fwd v1.1.1/go.mod h1:gk3iGcWd9+svBvR0sR+KPcfE+RNWozjowpeBVG3ZVNU=
|
||||||
github.com/philhofer/fwd v1.1.2 h1:bnDivRJ1EWPjUIRXV5KfORO897HTbpFAQddBdE8t7Gw=
|
github.com/philhofer/fwd v1.1.2 h1:bnDivRJ1EWPjUIRXV5KfORO897HTbpFAQddBdE8t7Gw=
|
||||||
github.com/philhofer/fwd v1.1.2/go.mod h1:qkPdfjR2SIEbspLqpe1tO4n5yICnr2DY7mqEx2tUTP0=
|
github.com/philhofer/fwd v1.1.2/go.mod h1:qkPdfjR2SIEbspLqpe1tO4n5yICnr2DY7mqEx2tUTP0=
|
||||||
|
@ -133,7 +133,6 @@ github.com/test-go/testify v1.1.4 h1:Tf9lntrKUMHiXQ07qBScBTSA0dhYQlu83hswqelv1iE
|
||||||
github.com/test-go/testify v1.1.4/go.mod h1:rH7cfJo/47vWGdi4GPj16x3/t1xGOj2YxzmNQzk2ghU=
|
github.com/test-go/testify v1.1.4/go.mod h1:rH7cfJo/47vWGdi4GPj16x3/t1xGOj2YxzmNQzk2ghU=
|
||||||
github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk=
|
github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk=
|
||||||
github.com/tidwall/pretty v1.2.1 h1:qjsOFOWWQl+N3RsoF5/ssm1pHmJJwhjlSbZ51I6wMl4=
|
github.com/tidwall/pretty v1.2.1 h1:qjsOFOWWQl+N3RsoF5/ssm1pHmJJwhjlSbZ51I6wMl4=
|
||||||
github.com/tidwall/pretty v1.2.1/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU=
|
|
||||||
github.com/tinylib/msgp v1.1.6/go.mod h1:75BAfg2hauQhs3qedfdDZmWAPcFMAvJE5b9rGOMufyw=
|
github.com/tinylib/msgp v1.1.6/go.mod h1:75BAfg2hauQhs3qedfdDZmWAPcFMAvJE5b9rGOMufyw=
|
||||||
github.com/tinylib/msgp v1.1.8 h1:FCXC1xanKO4I8plpHGH2P7koL/RzZs12l/+r7vakfm0=
|
github.com/tinylib/msgp v1.1.8 h1:FCXC1xanKO4I8plpHGH2P7koL/RzZs12l/+r7vakfm0=
|
||||||
github.com/tinylib/msgp v1.1.8/go.mod h1:qkpG+2ldGg4xRFmx+jfTvZPxfGFhi64BcnL9vkCm/Tw=
|
github.com/tinylib/msgp v1.1.8/go.mod h1:qkpG+2ldGg4xRFmx+jfTvZPxfGFhi64BcnL9vkCm/Tw=
|
||||||
|
@ -145,8 +144,8 @@ github.com/valyala/fasttemplate v1.0.1/go.mod h1:UQGH1tvbgY+Nz5t2n7tXsz52dQxojPU
|
||||||
github.com/valyala/fasttemplate v1.2.1/go.mod h1:KHLXt3tVN2HBp8eijSv/kGJopbvo7S+qRAEEKiv+SiQ=
|
github.com/valyala/fasttemplate v1.2.1/go.mod h1:KHLXt3tVN2HBp8eijSv/kGJopbvo7S+qRAEEKiv+SiQ=
|
||||||
github.com/valyala/tcplisten v1.0.0 h1:rBHj/Xf+E1tRGZyWIWwJDiRY0zc1Js+CV5DqwacVSA8=
|
github.com/valyala/tcplisten v1.0.0 h1:rBHj/Xf+E1tRGZyWIWwJDiRY0zc1Js+CV5DqwacVSA8=
|
||||||
github.com/valyala/tcplisten v1.0.0/go.mod h1:T0xQ8SeCZGxckz9qRXTfG43PvQ/mcWh7FwZEA7Ioqkc=
|
github.com/valyala/tcplisten v1.0.0/go.mod h1:T0xQ8SeCZGxckz9qRXTfG43PvQ/mcWh7FwZEA7Ioqkc=
|
||||||
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240109172745-cc0cd9fc5229 h1:fqcC4qwEVaJfcpqUVKi5+imz+JpxviQYPW4qu3zILz4=
|
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240416174455-25e60611a867 h1:GXUBP09C/bnEukdU6H2AY81d0m8UWrWEejDp6CgiFQA=
|
||||||
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240109172745-cc0cd9fc5229/go.mod h1:pE/jYet19kY4P3V6mE2+01zvEfxdyBqv6L6HsnSa5uc=
|
github.com/wormhole-foundation/wormhole/sdk v0.0.0-20240416174455-25e60611a867/go.mod h1:pE/jYet19kY4P3V6mE2+01zvEfxdyBqv6L6HsnSa5uc=
|
||||||
github.com/xdg-go/pbkdf2 v1.0.0 h1:Su7DPu48wXMwC3bs7MCNG+z4FhcyEuz5dlvchbq0B0c=
|
github.com/xdg-go/pbkdf2 v1.0.0 h1:Su7DPu48wXMwC3bs7MCNG+z4FhcyEuz5dlvchbq0B0c=
|
||||||
github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI=
|
github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI=
|
||||||
github.com/xdg-go/scram v1.1.1/go.mod h1:RaEWvsqvNKKvBPvcKeFjrG2cJqOkHTiyTpzz23ni57g=
|
github.com/xdg-go/scram v1.1.1/go.mod h1:RaEWvsqvNKKvBPvcKeFjrG2cJqOkHTiyTpzz23ni57g=
|
||||||
|
@ -166,8 +165,8 @@ go.mongodb.org/mongo-driver v1.11.2/go.mod h1:s7p5vEtfbeR1gYi6pnj3c3/urpbLv2T5Sf
|
||||||
go.uber.org/goleak v1.2.0 h1:xqgm/S+aQvhWFTtR0XK3Jvg7z8kGV8P4X14IzwN3Eqk=
|
go.uber.org/goleak v1.2.0 h1:xqgm/S+aQvhWFTtR0XK3Jvg7z8kGV8P4X14IzwN3Eqk=
|
||||||
go.uber.org/multierr v1.11.0 h1:blXXJkSxSSfBVBlC76pxqeO+LN3aDfLQo+309xJstO0=
|
go.uber.org/multierr v1.11.0 h1:blXXJkSxSSfBVBlC76pxqeO+LN3aDfLQo+309xJstO0=
|
||||||
go.uber.org/multierr v1.11.0/go.mod h1:20+QtiLqy0Nd6FdQB9TLXag12DsQkrbs3htMFfDN80Y=
|
go.uber.org/multierr v1.11.0/go.mod h1:20+QtiLqy0Nd6FdQB9TLXag12DsQkrbs3htMFfDN80Y=
|
||||||
go.uber.org/zap v1.25.0 h1:4Hvk6GtkucQ790dqmj7l1eEnRdKm3k3ZUrUMS2d5+5c=
|
go.uber.org/zap v1.26.0 h1:sI7k6L95XOKS281NhVKOFCUNIvv9e0w4BF8N3u+tCRo=
|
||||||
go.uber.org/zap v1.25.0/go.mod h1:JIAUzQIH94IC4fOJQm7gMmBJP5k7wQfdcnYdPoEXJYk=
|
go.uber.org/zap v1.26.0/go.mod h1:dtElttAiwGvoJ/vj4IwHBS/gXsEu/pZ50mUIRWuG0so=
|
||||||
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
|
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
|
||||||
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
||||||
golang.org/x/crypto v0.0.0-20200302210943-78000ba7a073/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
golang.org/x/crypto v0.0.0-20200302210943-78000ba7a073/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||||
|
@ -176,8 +175,9 @@ golang.org/x/crypto v0.0.0-20200820211705-5c72a883971a/go.mod h1:LzIPMQfyMNhhGPh
|
||||||
golang.org/x/crypto v0.0.0-20201221181555-eec23a3978ad/go.mod h1:jdWPYTVW3xRLrWPugEBEK3UY2ZEsg3UU495nc5E+M+I=
|
golang.org/x/crypto v0.0.0-20201221181555-eec23a3978ad/go.mod h1:jdWPYTVW3xRLrWPugEBEK3UY2ZEsg3UU495nc5E+M+I=
|
||||||
golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
|
golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
|
||||||
golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
|
golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
|
||||||
golang.org/x/crypto v0.14.0 h1:wBqGXzWJW6m1XrIKlAH0Hs1JJ7+9KBwnIO8v66Q9cHc=
|
|
||||||
golang.org/x/crypto v0.14.0/go.mod h1:MVFd36DqK4CsrnJYDkBA3VC4m2GkXAM0PvzMCn4JQf4=
|
golang.org/x/crypto v0.14.0/go.mod h1:MVFd36DqK4CsrnJYDkBA3VC4m2GkXAM0PvzMCn4JQf4=
|
||||||
|
golang.org/x/crypto v0.19.0 h1:ENy+Az/9Y1vSrlrvBSyna3PITt4tiZLf7sgCjZBX7Wo=
|
||||||
|
golang.org/x/crypto v0.19.0/go.mod h1:Iy9bg/ha4yyC70EfRS8jz+B6ybOBKMaSxLj6P6oBDfU=
|
||||||
golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||||
golang.org/x/mod v0.6.0-dev.0.20220106191415-9b9b3d81d5e3/go.mod h1:3p9vT2HGsQu2K1YbXdKPJLVgG5VJdoTa1poYQBtP1AY=
|
golang.org/x/mod v0.6.0-dev.0.20220106191415-9b9b3d81d5e3/go.mod h1:3p9vT2HGsQu2K1YbXdKPJLVgG5VJdoTa1poYQBtP1AY=
|
||||||
golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4=
|
golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4=
|
||||||
|
@ -195,15 +195,16 @@ golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug
|
||||||
golang.org/x/net v0.3.0/go.mod h1:MBQ8lrhLObU/6UmLb4fmbmk5OcyYmqtbGd/9yIeKjEE=
|
golang.org/x/net v0.3.0/go.mod h1:MBQ8lrhLObU/6UmLb4fmbmk5OcyYmqtbGd/9yIeKjEE=
|
||||||
golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
|
golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
|
||||||
golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg=
|
golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg=
|
||||||
golang.org/x/net v0.17.0 h1:pVaXccu2ozPjCXewfr1S7xza/zcXTity9cCdXQYSjIM=
|
|
||||||
golang.org/x/net v0.17.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE=
|
golang.org/x/net v0.17.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE=
|
||||||
|
golang.org/x/net v0.21.0 h1:AQyQV4dYCvJ7vGmJyKki9+PBdyvhkSd8EIx/qb0AYv4=
|
||||||
|
golang.org/x/net v0.21.0/go.mod h1:bIjVDfnllIU7BJ2DNgfnXvpSvtn8VRwhlsaeUTyUS44=
|
||||||
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.3.0 h1:ftCYgMx6zT/asHUrPw8BLLscYtGznsLAnjq5RH9P66E=
|
golang.org/x/sync v0.4.0 h1:zxkM55ReGkDlKSM+Fu41A+zmbZuaPVbGMzvvdUPznYQ=
|
||||||
golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y=
|
golang.org/x/sync v0.4.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y=
|
||||||
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||||
golang.org/x/sys v0.0.0-20190222072716-a9d3bda3a223/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
golang.org/x/sys v0.0.0-20190222072716-a9d3bda3a223/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||||
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
|
@ -226,8 +227,9 @@ golang.org/x/sys v0.3.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.13.0 h1:Af8nKPmuFypiUBjVoU9V20FiaFXOcuZI21p0ycVYYGE=
|
|
||||||
golang.org/x/sys v0.13.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.13.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
|
golang.org/x/sys v0.17.0 h1:25cE3gD+tdBA7lp7QfhuV+rJiE9YXTcS3VG1SqssI/Y=
|
||||||
|
golang.org/x/sys v0.17.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
|
||||||
golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw=
|
golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw=
|
||||||
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
||||||
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
|
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
|
||||||
|
@ -244,8 +246,9 @@ golang.org/x/text v0.3.8/go.mod h1:E6s5w1FMmriuDzIBO73fBruAKo1PCIq6d2Q6DHfQ8WQ=
|
||||||
golang.org/x/text v0.5.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
|
golang.org/x/text v0.5.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
|
||||||
golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
|
golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
|
||||||
golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
|
golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
|
||||||
golang.org/x/text v0.13.0 h1:ablQoSUd0tRdKxZewP80B+BaqeKJuVhuRxj/dkrun3k=
|
|
||||||
golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE=
|
golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE=
|
||||||
|
golang.org/x/text v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ=
|
||||||
|
golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU=
|
||||||
golang.org/x/time v0.0.0-20201208040808-7e3f01d25324/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
golang.org/x/time v0.0.0-20201208040808-7e3f01d25324/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||||
golang.org/x/time v0.0.0-20210220033141-f8bda1e9f3ba/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
golang.org/x/time v0.0.0-20210220033141-f8bda1e9f3ba/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||||
golang.org/x/time v0.3.0 h1:rg5rLMjNzMS1RkNLzCG38eapWhnYLFYXDXj2gOlr8j4=
|
golang.org/x/time v0.3.0 h1:rg5rLMjNzMS1RkNLzCG38eapWhnYLFYXDXj2gOlr8j4=
|
||||||
|
@ -262,6 +265,8 @@ golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8T
|
||||||
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
|
google.golang.org/protobuf v1.32.0 h1:pPC6BG5ex8PDFnkbrGU3EixyhKcQ2aDuBS36lqK/C7I=
|
||||||
|
google.golang.org/protobuf v1.32.0/go.mod h1:c6P6GXX6sHbq/GpV6MGZEdwhWPcYBgnhAHhKbcUYpos=
|
||||||
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||||
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||||
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk=
|
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk=
|
||||||
|
|
Loading…
Reference in New Issue