Skip to content

Commit

Permalink
add constant instruction name generation
Browse files Browse the repository at this point in the history
  • Loading branch information
lumtis committed Oct 9, 2024
1 parent 85149c3 commit 725db06
Show file tree
Hide file tree
Showing 3 changed files with 72 additions and 1 deletion.
13 changes: 13 additions & 0 deletions go-idl/generated/gateway.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

38 changes: 37 additions & 1 deletion go-idl/generator/generate.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import (
const (
codeGenerationDisclaimer = `// Code generated by go-idl. DO NOT EDIT.`
idlPrefix = "IDL"
discrimatorNamePrefix = "Discriminator"
instructionNamePrefix = "Instruction"
)

// generateIDLFile generates the Go code for the IDL struct.
Expand All @@ -27,6 +27,7 @@ func generateIDLFile(packagename, varname string, idl *types.IDL) string {
// IDL struct
sb.WriteString(fmt.Sprintf("var %s%s = ", idlPrefix, varname))
sb.WriteString(generateIDLTypeCode(idl))
sb.WriteString(generateInstructionNames(idl))

return sb.String()
}
Expand Down Expand Up @@ -144,3 +145,38 @@ func generateAccountCode(acc types.Account) string {
sb.WriteString(" },\n")
return sb.String()
}

// generateInstructionNames generates Go constants for a list of instruction names.
func generateInstructionNames(idl *types.IDL) string {
var builder strings.Builder

instructions := make([]string, 0, len(idl.Instructions))
for _, instr := range idl.Instructions {
instructions = append(instructions, instr.Name)
}

// Begin the const block.
builder.WriteString("const (\n")

// Iterate over the instructions and add each one as a constant.
for _, instruction := range instructions {
capitalizedName := capitalize(instruction)

// Write the constant definition.
builder.WriteString(fmt.Sprintf(" %s%s = \"%s\"\n", instructionNamePrefix, capitalizedName, instruction))
}

// End the const block.
builder.WriteString(")\n")

// Return the generated string.
return builder.String()
}

// capitalize returns the string with the first letter in uppercase.
func capitalize(s string) string {
if s == "" {
return s
}
return strings.ToUpper(string(s[0])) + s[1:]
}
22 changes: 22 additions & 0 deletions go-idl/types/idl.go
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package types

// IDL represents the interface definition language for a Solana program
// more info: https://solana.com/hi/docs/programs/anchor/idl
type IDL struct {
Address string `json:"address"`
Metadata Metadata `json:"metadata"`
Expand All @@ -9,20 +11,33 @@ type IDL struct {
Types []Type `json:"types"`
}

// GetDiscriminator returns the discriminator from the instruction name
func (i IDL) GetDiscriminator(name string) [8]byte {
for _, instr := range i.Instructions {
if instr.Name == name {
return instr.Discriminator
}
}
return [8]byte{}
}

// Metadata represents the metadata of the IDL
type Metadata struct {
Name string `json:"name"`
Version string `json:"version"`
Spec string `json:"spec"`
Description string `json:"description"`
}

// Instruction represents a single instruction in the IDL
type Instruction struct {
Name string `json:"name"`
Discriminator [8]byte `json:"discriminator"`
Accounts []Account `json:"accounts"`
Args []Arg `json:"args"`
}

// Account represents an account in the IDL
type Account struct {
Name string `json:"name"`
Writable bool `json:"writable,omitempty"`
Expand All @@ -31,36 +46,43 @@ type Account struct {
PDA *PDA `json:"pda,omitempty"`
}

// PDA represents a program-derived address in the IDL
type PDA struct {
Seeds []Seed `json:"seeds"`
}

// Seed represents a seed in the PDA
type Seed struct {
Kind string `json:"kind"`
Value []byte `json:"value,omitempty"`
}

// Arg represents an argument in the IDL
type Arg struct {
Name string `json:"name"`
Type interface{} `json:"type"`
}

// Error represents an error in the IDL
type Error struct {
Code int `json:"code"`
Name string `json:"name"`
Msg string `json:"msg"`
}

// Type represents a type in the IDL
type Type struct {
Name string `json:"name"`
Type TypeField `json:"type"`
}

// TypeField represents a field in a type in the IDL
type TypeField struct {
Kind string `json:"kind"`
Fields []Field `json:"fields"`
}

// Field represents a field in a type in the IDL
type Field struct {
Name string `json:"name"`
Type interface{} `json:"type"`
Expand Down

0 comments on commit 725db06

Please sign in to comment.