Skip to content

Commit

Permalink
add bytes to string modifier for solana contracts
Browse files Browse the repository at this point in the history
  • Loading branch information
EasterTheBunny committed Feb 19, 2025
1 parent 6817814 commit 627ef4d
Show file tree
Hide file tree
Showing 2 changed files with 56 additions and 0 deletions.
36 changes: 36 additions & 0 deletions pkg/codec/byte_string_modifier.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package codec

import (
"bytes"
"fmt"
"reflect"

Expand Down Expand Up @@ -66,6 +67,41 @@ func NewPathTraverseAddressBytesToStringModifier(
return m
}

func NewConstrainedLengthBytesToStringModifier(
fields []string,
maxLen int,
) Modifier {
return NewPathTraverseAddressBytesToStringModifier(fields, &constrainedLengthBytesToStringModifier{maxLen: maxLen}, false)
}

func NewPathTraverseConstrainedLengthBytesToStringModifier(
fields []string,
maxLen int,
enablePathTraverse bool,
) Modifier {
return NewPathTraverseAddressBytesToStringModifier(fields, &constrainedLengthBytesToStringModifier{maxLen: maxLen}, enablePathTraverse)
}

type constrainedLengthBytesToStringModifier struct {
maxLen int
}

func (m constrainedLengthBytesToStringModifier) EncodeAddress(bts []byte) (string, error) {
return string(bytes.Trim(bts, "\x00")), nil
}

func (m constrainedLengthBytesToStringModifier) DecodeAddress(str string) ([]byte, error) {
output := make([]byte, m.maxLen)

copy(output, []byte(str)[:])

return output, nil
}

func (m constrainedLengthBytesToStringModifier) Length() int {
return m.maxLen
}

type bytesToStringModifier struct {
// Injected modifier that contains chain-specific logic
modifier AddressModifier
Expand Down
20 changes: 20 additions & 0 deletions pkg/codec/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,8 @@ func (m *ModifiersConfig) UnmarshalJSON(data []byte) error {
(*m)[i] = &PropertyExtractorConfig{}
case ModifierAddressToString:
(*m)[i] = &AddressBytesToStringModifierConfig{}
case ModifierBytesToString:
(*m)[i] = &ConstrainedBytesToStringModifierConfig{}
case ModifierWrapper:
(*m)[i] = &WrapperModifierConfig{}
case ModifierPreCodec:
Expand Down Expand Up @@ -103,6 +105,7 @@ const (
ModifierEpochToTime ModifierType = "epoch to time"
ModifierExtractProperty ModifierType = "extract property"
ModifierAddressToString ModifierType = "address to string"
ModifierBytesToString ModifierType = "constrained bytes to string"
ModifierWrapper ModifierType = "wrapper"
)

Expand Down Expand Up @@ -368,6 +371,23 @@ func (c *AddressBytesToStringModifierConfig) MarshalJSON() ([]byte, error) {
})
}

type ConstrainedBytesToStringModifierConfig struct {
Fields []string
MaxLen int
EnablePathTraverse bool
}

func (c *ConstrainedBytesToStringModifierConfig) ToModifier(_ ...mapstructure.DecodeHookFunc) (Modifier, error) {
return NewPathTraverseConstrainedLengthBytesToStringModifier(c.Fields, c.MaxLen, c.EnablePathTraverse), nil
}

func (c *ConstrainedBytesToStringModifierConfig) MarshalJSON() ([]byte, error) {
return json.Marshal(&modifierMarshaller[ConstrainedBytesToStringModifierConfig]{
Type: ModifierBytesToString,
T: c,
})
}

// WrapperModifierConfig replaces each field based on cfg map keys with a struct containing one field with the value of the original field which has is named based on map values.
// Wrapper modifier does not maintain the original pointers.
// Wrapper modifier config shouldn't edit fields that affect each other since the results are not deterministic.
Expand Down

0 comments on commit 627ef4d

Please sign in to comment.