PathrockNetwork Gno Explorer
HomeBlocksTransactionsRealmsPackagesValidatorsAnalytics

PathrockNetwork Gno Explorer — an independent explorer for Gno.land Mainnet (gnoland-1), operated by PathrockNetwork. Not an official Gno.land service.

gnowebarchive RPC

gno.land/r/gnoswap/position/v1

Realm
Open in gnoweb ↗

Overview

Kind
Realm (renderable)
Name
v1
Namespace
gnoswap / position
Files
17 (README)(gnomod.toml)
Exported functions
1
Module
gno.land/r/gnoswap/position/v1
gno
0.9

Files (17)

  • README.mdmarkdown
  • gnomod.tomltoml
  • assert.gnogno
  • burn.gnogno
  • doc.gnogno
  • errors.gnogno
  • getter.gnogno
  • init.gnogno
  • instance.gnogno
  • liquidity_management.gnogno
  • manager.gnogno
  • mint.gnogno
  • position.gnogno
  • render.gnogno
  • reposition.gnogno
  • type.gnogno
  • utils.gnogno
  • render.gnogno
    1package position23import (4	"chain"5	"strconv"6	"strings"78

    Functions

    • NewPositionV1(positionStore interface {GetPosition func(uint64) (gno.land/r/gnoswap/position.Position, bool); GetPositionNextID func() uint64; GetPositions func() *gno.land/p/nt/bptree/v0.BPTree; HasPosition func(uint64) bool; HasPositionNextIDStoreKey func() bool; HasPositionsStoreKey func() bool; RemovePosition func(int, .uverse.realm, uint64) .uverse.error; SetPosition func(int, .uverse.realm, uint64, gno.land/r/gnoswap/position.Position) .uverse.error; SetPositionNextID func(int, .uverse.realm, uint64) .uverse.error; SetPositions func(int, .uverse.realm, *gno.land/p/nt/bptree/v0.BPTree) .uverse.error}, accessor interface {Approve func(int, .uverse.realm, .uverse.address, gno.land/p/nt/grc721/v0.TokenID) .uverse.error; Burn func(int, .uverse.realm, gno.land/p/nt/grc721/v0.TokenID); Exists func(gno.land/p/nt/grc721/v0.TokenID) bool; Mint func(int, .uverse.realm, .uverse.address, gno.land/p/nt/grc721/v0.TokenID) gno.land/p/nt/grc721/v0.TokenID; OwnerOf func(gno.land/p/nt/grc721/v0.TokenID) (.uverse.address, .uverse.error); TotalSupply func() int64}) interface {CollectFee func(int, .uverse.realm, uint64) (uint64, string, string, string, string, string); DecreaseLiquidity func(int, .uverse.realm, uint64, string, string, string, int64) (uint64, string, string, string, string, string, string); GetPositionFeeGrowthInside0LastX128 func(uint64) (string, .uverse.error); GetPositionFeeGrowthInside1LastX128 func(uint64) (string, .uverse.error); GetPositionFeeGrowthInsideLastX128 func(uint64) (string, string, .uverse.error); GetPositionLiquidity func(uint64) (string, .uverse.error); GetPositionOperator func(uint64) (.uverse.address, .uverse.error); GetPositionOwner func(uint64) (.uverse.address, .uverse.error); GetPositionPoolKey func(uint64) (string, .uverse.error); GetPositionTickLower func(uint64) (int32, .uverse.error); GetPositionTickUpper func(uint64) (int32, .uverse.error); GetPositionTicks func(uint64) (int32, int32, .uverse.error); GetPositionTokenBalances func(uint64) (int64, int64, .uverse.error); GetPositionTokensOwed func(uint64) (int64, int64, .uverse.error); GetPositionTokensOwed0 func(uint64) (int64, .uverse.error); GetPositionTokensOwed1 func(uint64) (int64, .uverse.error); GetPositions func() *gno.land/p/nt/bptree/rotree/v0.ReadOnlyTree; GetUnclaimedFee func(uint64) (*gno.land/p/gnoswap/uint256/v1.Uint, *gno.land/p/gnoswap/uint256/v1.Uint, .uverse.error); IncreaseLiquidity func(int, .uverse.realm, uint64, string, string, string, string, int64) (uint64, string, string, string, string); IsBurned func(uint64) (bool, .uverse.error); IsInRange func(uint64) (bool, .uverse.error); Mint func(int, .uverse.realm, string, string, uint32, int32, int32, string, string, string, string, int64, .uverse.address, string) (uint64, string, string, string); Render func(string) string; Reposition func(int, .uverse.realm, uint64, int32, int32, string, string, string, string, int64) (uint64, string, int32, int32, string, string); SetPositionOperator func(int, .uverse.realm, uint64, .uverse.address)}

    Signatures reconstructed verbatim from vm/qfuncs — interface params keep their inline definitions.

    Rendered

    RenderedRawgnoweb ↗
    This realm does not provide renderable output (vm/qrender → NoRenderDeclError). View on gnoweb ↗

    vm/qrender output, sanitized (docs/render-security.md) and displayed in an empty-sandbox iframe — scripts, forms and popups cannot run. Links stay inert in-preview; right-click to open.

    "gno.land/p/moul/md/v0"
    9 "gno.land/p/moul/mdtable/v0"
    10 ufmt "gno.land/p/nt/ufmt/v0"
    11
    12 "gno.land/r/gnoswap/halt/v1"
    13 positionRoot "gno.land/r/gnoswap/position"
    14)
    15
    16func (p *positionV1) Render(path string) string {
    17 if path == "" {
    18 return p.renderSummary()
    19 }
    20
    21 positionID, ok := parsePositionRenderPath(path)
    22 if !ok {
    23 return "404\n"
    24 }
    25
    26 storedPosition, exists := p.store.GetPosition(positionID)
    27 if !exists {
    28 return "404\n"
    29 }
    30
    31 return p.renderPositionDetail(positionID, storedPosition)
    32}
    33
    34func (p *positionV1) renderSummary() string {
    35 out := md.H1("Gnoswap Position")
    36 out += md.Paragraph(
    37 "Position records remain stored after burning. The record count includes burned " +
    38 "positions and is not a count of active liquidity positions. Use " +
    39 md.InlineCode("id/<id>") + " for one stored record, for example " +
    40 md.Link("id/1", "/r/gnoswap/position:id/1") +
    41 ". The detail route performs one keyed lookup and does not enumerate positions or recompute claimable values.",
    42 )
    43 runtimeTable := mdtable.Table{
    44 Headers: []string{"Field", "Value"},
    45 Rows: [][]string{
    46 {"Realm address", md.InlineCode(chain.PackageAddress("gno.land/r/gnoswap/position").String())},
    47 {"Active implementation", renderPackageLink(positionRoot.GetImplementationPackagePath())},
    48 {"Position operations halted", ufmt.Sprintf("%t", halt.IsHaltedPosition())},
    49 {"Withdrawals halted", ufmt.Sprintf("%t", halt.IsHaltedWithdraw())},
    50 },
    51 }
    52 out += md.H2("Runtime") + runtimeTable.String()
    53
    54 records := mdtable.Table{
    55 Headers: []string{"Field", "Value"},
    56 Rows: [][]string{
    57 {"Stored position records (including burned)", ufmt.Sprintf("%d", p.store.GetPositions().Size())},
    58 {"Next position ID", ufmt.Sprintf("%d", p.store.GetPositionNextID())},
    59 },
    60 }
    61 return out + md.H2("Stored records") + records.String()
    62}
    63
    64func (p *positionV1) renderPositionDetail(positionID uint64, stored positionRoot.Position) string {
    65 status := "Active"
    66 if stored.Burned() {
    67 status = "Burned (record retained)"
    68 }
    69
    70 owner := "unavailable"
    71 ownerAddress, err := p.nftAccessor.OwnerOf(positionIdFrom(positionID))
    72 if err == nil && ownerAddress != "" {
    73 owner = ownerAddress.String()
    74 }
    75
    76 token0, token1, poolFee, validPoolKey := splitPoolKeyForRender(stored.PoolKey())
    77 token0Reference := "unavailable (stored pool key is not token0:token1:fee)"
    78 token1Reference := token0Reference
    79 if validPoolKey {
    80 token0Reference = renderPackageLink(token0)
    81 token1Reference = renderPackageLink(token1)
    82 }
    83
    84 out := md.H1(ufmt.Sprintf("Gnoswap Position %d", positionID))
    85 out += md.Paragraph(
    86 "This page reads one persisted position record. Stored accounting fields are " +
    87 "shown as stored; claimable fees and current token balances are recomputed " +
    88 "values and are intentionally not queried here.",
    89 )
    90 identity := mdtable.Table{
    91 Headers: []string{"Field", "Value"},
    92 Rows: [][]string{
    93 {"Position ID", ufmt.Sprintf("%d", positionID)},
    94 {"Status", status},
    95 {"Owner", owner},
    96 },
    97 }
    98 out += md.H2("Identity") + identity.String()
    99
    100 poolAndRange := mdtable.Table{
    101 Headers: []string{"Field", "Value"},
    102 Rows: [][]string{
    103 {"Pool key", md.InlineCode(stored.PoolKey())},
    104 {"Token 0 reference", token0Reference},
    105 {"Token 1 reference", token1Reference},
    106 {"Pool fee (from stored key)", poolFee},
    107 {"Lower tick (stored)", ufmt.Sprintf("%d", stored.TickLower())},
    108 {"Upper tick (stored)", ufmt.Sprintf("%d", stored.TickUpper())},
    109 },
    110 }
    111 out += md.H2("Pool and range") + poolAndRange.String()
    112
    113 accounting := mdtable.Table{
    114 Headers: []string{"Field", "Value"},
    115 Rows: [][]string{
    116 {"Liquidity (stored)", stored.Liquidity()},
    117 {"Fee growth token 0 inside, last X128 (stored)", stored.FeeGrowthInside0LastX128()},
    118 {"Fee growth token 1 inside, last X128 (stored)", stored.FeeGrowthInside1LastX128()},
    119 {"Token 0 owed (stored accounting)", ufmt.Sprintf("%d", stored.TokensOwed0())},
    120 {"Token 1 owed (stored accounting)", ufmt.Sprintf("%d", stored.TokensOwed1())},
    121 {"Claimable fees / current token balances", "Not rendered; would require recomputation"},
    122 },
    123 }
    124 return out + md.H2("Stored accounting") + accounting.String()
    125}
    126
    127func parsePositionRenderPath(path string) (uint64, bool) {
    128 const prefix = "id/"
    129 if len(path) <= len(prefix) || path[:len(prefix)] != prefix {
    130 return 0, false
    131 }
    132
    133 id := path[len(prefix):]
    134 for i := 0; i < len(id); i++ {
    135 if id[i] < '0' || id[i] > '9' {
    136 return 0, false
    137 }
    138 }
    139
    140 positionID, err := strconv.ParseUint(id, 10, 64)
    141 if err != nil {
    142 return 0, false
    143 }
    144
    145 return positionID, true
    146}
    147
    148func splitPoolKeyForRender(poolKey string) (string, string, string, bool) {
    149 parts := strings.Split(poolKey, ":")
    150 if len(parts) != 3 || parts[0] == "" || parts[1] == "" || parts[2] == "" {
    151 return "", "", "", false
    152 }
    153
    154 return parts[0], parts[1], parts[2], true
    155}
    156
    157func renderPackageLink(path string) string {
    158 if strings.HasPrefix(path, "gno.land/") {
    159 destination := strings.TrimPrefix(path, "gno.land")
    160 // Token references append .SYMBOL; link to the defining realm.
    161 if separator := strings.Index(destination, "."); separator >= 0 {
    162 destination = destination[:separator]
    163 }
    164 return md.Link(path, destination)
    165 }
    166
    167 return md.InlineCode(path)
    168}
    169