package pump_parser import ( "github.com/gagliardetto/solana-go" "github.com/mr-tron/base58" "github.com/shopspring/decimal" ) type Swap struct { Program string Event string Pool solana.PublicKey BaseMint solana.PublicKey QuoteMint solana.PublicKey BaseTokenProgram solana.PublicKey QuoteTokenProgram solana.PublicKey Creator solana.PublicKey BaseMintDecimals uint8 QuoteMintDecimals uint8 User solana.PublicKey BaseAmount decimal.Decimal QuoteAmount decimal.Decimal BaseReserve decimal.Decimal QuoteReserve decimal.Decimal Mayhem bool UserBaseBalance decimal.Decimal UserQuoteBalance decimal.Decimal EntryContract solana.PublicKey //For meteora dlmm StartBinId int32 EndBinId int32 BinChanges []DlmmBinLiquidityChange } type DlmmBinLiquidityChange struct { BinId int32 AmountX decimal.Decimal AmountY decimal.Decimal BpsToRemove uint16 } type platformInfo struct { Platform string PlatformFee decimal.Decimal } type mevInfo struct { MevAgent string MevAgentFee decimal.Decimal } type SolTransfer struct { From solana.PublicKey To solana.PublicKey Amount decimal.Decimal } type Tx struct { rawTx *RawTx Signer solana.PublicKey Err interface{} `json:"err,omitempty"` Swaps []Swap `json:"swaps,omitempty"` SolTransfer []SolTransfer `json:"sol_transfer,omitempty"` Block uint64 `json:"block"` BlockIndex uint64 `json:"index"` TxHash *[64]byte `json:"-"` BlockAt int64 `json:"block_at"` CuFee decimal.Decimal `json:"cu_fee"` cachedTxHash string Platform map[string]platformInfo `json:"platform"` MevAgent map[string]mevInfo ` json:"tx_mev_agent"` CUPrice decimal.Decimal ` json:"tx_cu_price"` BeforeSolBalance decimal.Decimal `json:"-"` AfterSOLBalance decimal.Decimal `json:"after_sol_balance"` // update tokenInfo Token map[solana.PublicKey]TokenMeta `gorm:"-"` // todo pool info ?? } func (tx *Tx) SetRawTx(t *RawTx) { tx.rawTx = t } func (tx *Tx) GetSignerTokenBalanceAfterTx(tokenProgram, tokenMint solana.PublicKey) decimal.Decimal { return GetTokenBalanceAfterTx(tx.rawTx, 0, tokenProgram, tokenMint) } type TokenMeta struct { Mint solana.PublicKey `json:"address"` TokenProgram solana.PublicKey `json:"token_program"` Decimals uint8 `json:"decimals"` Name string Symbol string Url string TotalSupply *decimal.Decimal } func (tx *Tx) GetTxHash() string { if tx.cachedTxHash != "" { return tx.cachedTxHash } if tx.TxHash == nil { return "" } tx.cachedTxHash = base58.Encode(tx.TxHash[:]) return tx.cachedTxHash } func (tx *Tx) CheckPlatform(swap Swap) (string, decimal.Decimal) { // hasSolProgramRaydiumLaunchLabBonk rawTx := tx.rawTx var platform string var platformFee decimal.Decimal if len(tx.Platform) == 0 { return PlatformNone, decimal.Zero } for p, info := range tx.Platform { platform = p platformFee = info.PlatformFee break } if swap.Event == "buy" && swap.Program == SolProgramRaydiumLaunchLabBonk { for _, p := range tx.Platform { switch p.Platform { case PlatformAxiom: if !checkBonkAxiomBuy(rawTx) { platform = PlatformFake } case PlatformGMGN: if !checkBonkGmgnBuy(rawTx) { platform = PlatformFake } } } } if platform != "" && platform != PlatformFake { if (swap.QuoteMint.Equals(wSolMint) || swap.QuoteMint.IsZero()) && platformFee.LessThan(swap.QuoteAmount.Div(decimal.New(1, int32(swap.QuoteMintDecimals))).Div(decimal.NewFromInt(10000)).Mul(decimal.NewFromInt(9))) { platform = PlatformFake } else if swap.BaseMint.Equals(wSolMint) && platformFee.LessThan(swap.QuoteAmount.Div(decimal.New(1, int32(swap.QuoteMintDecimals))).Div(decimal.NewFromInt(10000)).Mul(decimal.NewFromInt(9))) { platform = PlatformFake } } if platform == "" { platform = PlatformNone } return platform, platformFee } func (tx *Tx) CheckMevAgent() (string, decimal.Decimal) { var mevAgent = MevAgentUnknown var mevAgentFee = decimal.Zero for m, info := range tx.MevAgent { if len(tx.MevAgent) > 1 && info.MevAgent == MevAgentUnknown { continue } mevAgent = m mevAgentFee = info.MevAgentFee break } if len(tx.MevAgent) == 0 && mevAgent == MevAgentUnknown { // set the mev agent to none if the platform does not exist return "", decimal.Zero } return mevAgent, mevAgentFee } func (s Swap) CheckEntryContract() string { name, ok := entryContractAddresses[s.EntryContract] if ok { return name } return EntryContractUnknown } func (s Swap) CheckEntryContractV2() string { name, ok := entryContractAddresses[s.EntryContract] if ok { return name } return s.EntryContract.String() }