swap amount input

This commit is contained in:
thloyi
2026-04-16 14:24:14 +08:00
parent ab0e87a48a
commit e761fd6f84
29 changed files with 1542 additions and 214 deletions

View File

@@ -261,6 +261,19 @@ type PumpSwapArgs struct {
Amount2 uint64
}
func pumpAmmSwapAmountInfoFromArgs(args PumpSwapArgs) (swapMode SwapMode, fixedAmount decimal.Decimal, limitAmount decimal.Decimal, ok bool) {
switch {
case bytes.Equal(args.Discriminator[:], pumpAmmBuyV2Discriminator[:]):
return SwapModeExactIn, decimal.NewFromUint64(args.Amount1), decimal.NewFromUint64(args.Amount2), true
case bytes.Equal(args.Discriminator[:], pumpAmmBuyDiscriminator[:]):
return SwapModeExactOut, decimal.NewFromUint64(args.Amount1), decimal.NewFromUint64(args.Amount2), true
case bytes.Equal(args.Discriminator[:], pumpAmmSellDiscriminator[:]):
return SwapModeExactIn, decimal.NewFromUint64(args.Amount1), decimal.NewFromUint64(args.Amount2), true
default:
return SwapModeUnknown, decimal.Zero, decimal.Zero, false
}
}
func failedTxAmmBuyParser(tx *Tx, instruction Instruction, innerInstructions InnerInstructions, offset [2]uint) ([]Swap, [2]uint, error) {
if tx.Err == nil || tx.Err.UnKnown != "" {
return nil, increaseOffset(offset), fmt.Errorf("tx pump amm sell failed but error is nil, offset, %d, %d", offset[0], offset[1])
@@ -361,28 +374,30 @@ func failedTxAmmBuyParser(tx *Tx, instruction Instruction, innerInstructions Inn
}
baseReserve := getAccountBalanceAfterTx(result, instruction.Accounts[7])
quoteReserve := getAccountBalanceAfterTx(result, instruction.Accounts[8])
return []Swap{
{
Program: SolProgramPumpAMM,
Event: event,
Pool: tx.rawTx.accountList[instruction.Accounts[0]],
BaseMint: baseMint,
QuoteMint: quoteMint,
BaseTokenProgram: baseTokenProgram,
QuoteTokenProgram: quoteTokenProgram,
BaseMintDecimals: baseMintDecimals,
QuoteMintDecimals: quoteMintDecimals,
User: eventUser,
BaseAmount: decimal.NewFromUint64(tokenAmount),
QuoteAmount: decimal.NewFromUint64(quoteAmount),
BaseReserve: baseReserve,
QuoteReserve: quoteReserve,
Mayhem: isMayhemPump(result.accountList[instruction.Accounts[9]]),
UserBaseBalance: userBase,
UserQuoteBalance: userQuote,
EntryContract: entryContract,
},
}, offset, nil
swap := Swap{
Program: SolProgramPumpAMM,
Event: event,
Pool: tx.rawTx.accountList[instruction.Accounts[0]],
BaseMint: baseMint,
QuoteMint: quoteMint,
BaseTokenProgram: baseTokenProgram,
QuoteTokenProgram: quoteTokenProgram,
BaseMintDecimals: baseMintDecimals,
QuoteMintDecimals: quoteMintDecimals,
User: eventUser,
BaseAmount: decimal.NewFromUint64(tokenAmount),
QuoteAmount: decimal.NewFromUint64(quoteAmount),
BaseReserve: baseReserve,
QuoteReserve: quoteReserve,
Mayhem: isMayhemPump(result.accountList[instruction.Accounts[9]]),
UserBaseBalance: userBase,
UserQuoteBalance: userQuote,
EntryContract: entryContract,
}
if swapMode, fixedAmount, limitAmount, ok := pumpAmmSwapAmountInfoFromArgs(args); ok {
swap.SetSwapAmountInfo(swapMode, fixedAmount, limitAmount)
}
return []Swap{swap}, offset, nil
}
func failedTxAmmSellParser(tx *Tx, instruction Instruction, innerInstructions InnerInstructions, offset [2]uint) ([]Swap, [2]uint, error) {
@@ -479,28 +494,30 @@ func failedTxAmmSellParser(tx *Tx, instruction Instruction, innerInstructions In
}
baseReserve := getAccountBalanceAfterTx(result, instruction.Accounts[7])
quoteReserve := getAccountBalanceAfterTx(result, instruction.Accounts[8])
return []Swap{
{
Program: SolProgramPumpAMM,
Event: event,
Pool: tx.rawTx.accountList[instruction.Accounts[0]],
BaseMint: baseMint,
QuoteMint: quoteMint,
BaseTokenProgram: baseTokenProgram,
QuoteTokenProgram: quoteTokenProgram,
BaseMintDecimals: baseMintDecimals,
QuoteMintDecimals: quoteMintDecimals,
User: eventUser,
BaseAmount: decimal.NewFromUint64(tokenAmount),
QuoteAmount: decimal.NewFromUint64(quoteAmount),
BaseReserve: baseReserve,
QuoteReserve: quoteReserve,
Mayhem: isMayhemPump(result.accountList[instruction.Accounts[9]]),
UserBaseBalance: userBase,
UserQuoteBalance: userQuote,
EntryContract: entryContract,
},
}, offset, nil
swap := Swap{
Program: SolProgramPumpAMM,
Event: event,
Pool: tx.rawTx.accountList[instruction.Accounts[0]],
BaseMint: baseMint,
QuoteMint: quoteMint,
BaseTokenProgram: baseTokenProgram,
QuoteTokenProgram: quoteTokenProgram,
BaseMintDecimals: baseMintDecimals,
QuoteMintDecimals: quoteMintDecimals,
User: eventUser,
BaseAmount: decimal.NewFromUint64(tokenAmount),
QuoteAmount: decimal.NewFromUint64(quoteAmount),
BaseReserve: baseReserve,
QuoteReserve: quoteReserve,
Mayhem: isMayhemPump(result.accountList[instruction.Accounts[9]]),
UserBaseBalance: userBase,
UserQuoteBalance: userQuote,
EntryContract: entryContract,
}
if swapMode, fixedAmount, limitAmount, ok := pumpAmmSwapAmountInfoFromArgs(args); ok {
swap.SetSwapAmountInfo(swapMode, fixedAmount, limitAmount)
}
return []Swap{swap}, offset, nil
}
func ammBuyParser(tx *Tx, instruction Instruction, innerInstructions InnerInstructions, offset [2]uint) ([]Swap, [2]uint, error) {
@@ -599,30 +616,42 @@ func ammBuyParser(tx *Tx, instruction Instruction, innerInstructions InnerInstru
userQuote = userQuote.Add(decimal.NewFromUint64(userBalance))
}
isCashbackCoin := event.CashbackFeeBasisPoints > 0 || event.Cashback > 0
return []Swap{
{
Program: SolProgramPumpAMM,
Event: "buy",
Pool: event.Pool,
BaseMint: baseMint,
QuoteMint: quoteMint,
BaseTokenProgram: baseTokenProgram,
QuoteTokenProgram: quoteTokenProgram,
Creator: event.CoinCreator,
BaseMintDecimals: baseMintDecimals,
QuoteMintDecimals: quoteMintDecimals,
User: eventUser,
BaseAmount: decimal.NewFromUint64(event.BaseAmountOut),
QuoteAmount: decimal.NewFromUint64(event.UserQuoteAmountIn),
BaseReserve: decimal.NewFromUint64(event.PoolBaseTokenReserve - event.BaseAmountOut),
QuoteReserve: decimal.NewFromUint64(event.PoolQuoteTokenReserve + event.QuoteAmountIn),
Mayhem: isMayhemPump(result.accountList[instruction.Accounts[9]]),
Cashback: isCashbackCoin,
UserBaseBalance: userBase,
UserQuoteBalance: userQuote,
EntryContract: entryContract,
},
}, offset, nil
swap := Swap{
Program: SolProgramPumpAMM,
Event: "buy",
Pool: event.Pool,
BaseMint: baseMint,
QuoteMint: quoteMint,
BaseTokenProgram: baseTokenProgram,
QuoteTokenProgram: quoteTokenProgram,
Creator: event.CoinCreator,
BaseMintDecimals: baseMintDecimals,
QuoteMintDecimals: quoteMintDecimals,
User: eventUser,
BaseAmount: decimal.NewFromUint64(event.BaseAmountOut),
QuoteAmount: decimal.NewFromUint64(event.UserQuoteAmountIn),
BaseReserve: decimal.NewFromUint64(event.PoolBaseTokenReserve - event.BaseAmountOut),
QuoteReserve: decimal.NewFromUint64(event.PoolQuoteTokenReserve + event.QuoteAmountIn),
Mayhem: isMayhemPump(result.accountList[instruction.Accounts[9]]),
Cashback: isCashbackCoin,
UserBaseBalance: userBase,
UserQuoteBalance: userQuote,
EntryContract: entryContract,
}
if bytes.Equal(instruction.Data[:8], pumpAmmBuyV2Discriminator[:]) {
swap.SetSwapAmountInfo(
SwapModeExactIn,
decimal.NewFromUint64(event.UserQuoteAmountIn),
decimal.NewFromUint64(event.MinBaseAmountOut),
)
} else {
swap.SetSwapAmountInfo(
SwapModeExactOut,
decimal.NewFromUint64(event.BaseAmountOut),
decimal.NewFromUint64(event.MaxQuoteAmountIn),
)
}
return []Swap{swap}, offset, nil
}
func ammSellParser(tx *Tx, instruction Instruction, innerInstructions InnerInstructions, offset [2]uint) ([]Swap, [2]uint, error) {
@@ -722,30 +751,34 @@ func ammSellParser(tx *Tx, instruction Instruction, innerInstructions InnerInstr
userQuote = userQuote.Add(decimal.NewFromUint64(userBalance))
}
isCashbackCoin := event.CashbackFeeBasisPoints > 0 || event.Cashback > 0
return []Swap{
{
Program: SolProgramPumpAMM,
Event: "sell",
Pool: event.Pool,
BaseMint: baseMint,
QuoteMint: quoteMint,
BaseTokenProgram: baseTokenProgram,
QuoteTokenProgram: quoteTokenProgram,
Creator: event.CoinCreator,
BaseMintDecimals: baseMintDecimals,
QuoteMintDecimals: quoteMintDecimals,
User: eventUser,
BaseAmount: decimal.NewFromUint64(event.BaseAmountIn),
QuoteAmount: decimal.NewFromUint64(event.UserQuoteAmountOut),
BaseReserve: decimal.NewFromUint64(event.PoolBaseTokenReserves + event.BaseAmountIn),
QuoteReserve: decimal.NewFromUint64(event.PoolQuoteTokenReserves - event.QuoteAmountOut),
Mayhem: isMayhemPump(result.accountList[instruction.Accounts[9]]),
Cashback: isCashbackCoin,
UserBaseBalance: userBase,
UserQuoteBalance: userQuote,
EntryContract: entryContract,
},
}, offset, nil
swap := Swap{
Program: SolProgramPumpAMM,
Event: "sell",
Pool: event.Pool,
BaseMint: baseMint,
QuoteMint: quoteMint,
BaseTokenProgram: baseTokenProgram,
QuoteTokenProgram: quoteTokenProgram,
Creator: event.CoinCreator,
BaseMintDecimals: baseMintDecimals,
QuoteMintDecimals: quoteMintDecimals,
User: eventUser,
BaseAmount: decimal.NewFromUint64(event.BaseAmountIn),
QuoteAmount: decimal.NewFromUint64(event.UserQuoteAmountOut),
BaseReserve: decimal.NewFromUint64(event.PoolBaseTokenReserves + event.BaseAmountIn),
QuoteReserve: decimal.NewFromUint64(event.PoolQuoteTokenReserves - event.QuoteAmountOut),
Mayhem: isMayhemPump(result.accountList[instruction.Accounts[9]]),
Cashback: isCashbackCoin,
UserBaseBalance: userBase,
UserQuoteBalance: userQuote,
EntryContract: entryContract,
}
swap.SetSwapAmountInfo(
SwapModeExactIn,
decimal.NewFromUint64(event.BaseAmountIn),
decimal.NewFromUint64(event.MinQuoteAmountOut),
)
return []Swap{swap}, offset, nil
}
func depositParse(tx *Tx, instruction Instruction, innerInstructions InnerInstructions, offset [2]uint) ([]Swap, [2]uint, error) {