Skip to content

Commit

Permalink
feat: crawll binance spot tx
Browse files Browse the repository at this point in the history
  • Loading branch information
trkhoi committed Apr 24, 2024
1 parent 0b5c68b commit 13ddc60
Show file tree
Hide file tree
Showing 22 changed files with 340 additions and 7 deletions.
28 changes: 28 additions & 0 deletions cmd/crawl-binance-spot-transactions/main.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package main

import (
"time"

"github.com/defipod/mochi/pkg/config"
"github.com/defipod/mochi/pkg/entities"
"github.com/defipod/mochi/pkg/job"
"github.com/defipod/mochi/pkg/logger"
)

func main() {
cfg := config.LoadConfig(config.DefaultConfigLoaders())
log := logger.NewLogrusLogger()
// *** entities ***
err := entities.Init(cfg, log)
if err != nil {
log.Fatal(err, "failed to init entities")
}
entity := entities.Get()
defer entity.GetSvc().Sentry.Flush(2 * time.Second)

if err := job.NewCrawlBinanceSpotTransactionsJob(entity, log).Run(); err != nil {
log.Fatal(err, "failed to run job")
}

log.Info("done")
}
2 changes: 2 additions & 0 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,7 @@ require (
github.com/leodido/go-urn v1.2.4 // indirect
github.com/linkedin/goavro/v2 v2.11.1 // indirect
github.com/magiconair/properties v1.8.7 // indirect
github.com/mattn/go-colorable v0.1.13 // indirect
github.com/mattn/go-isatty v0.0.20 // indirect
github.com/mattn/go-runewidth v0.0.14 // indirect
github.com/mattn/go-sqlite3 v2.0.1+incompatible // indirect
Expand Down Expand Up @@ -158,6 +159,7 @@ require (
github.com/consolelabs/mochi-typeset v0.0.0-20231120101232-7743776c4c84
github.com/gammazero/workerpool v1.1.3
github.com/getsentry/sentry-go v0.18.0
github.com/k0kubun/pp/v3 v3.2.0
github.com/pkg/errors v0.9.1
github.com/shopspring/decimal v1.2.0
github.com/xssnick/tonutils-go v1.8.5
Expand Down
7 changes: 7 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,8 @@ github.com/KyleBanks/depth v1.2.1 h1:5h8fQADFrWtarTdtDudMmGsC7GPbOAu6RVB3ffsVFHc
github.com/KyleBanks/depth v1.2.1/go.mod h1:jzSb9d0L43HxTQfT+oSA1EEp2q+ne2uh6XgeJcm8brE=
github.com/Masterminds/semver/v3 v3.1.1/go.mod h1:VPu/7SZ7ePZ3QOrcuXROw5FAcLl4a0cBrbBpGY/8hQs=
github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU=
github.com/PuerkitoBio/purell v1.1.1/go.mod h1:c11w/QuzBsJSee3cPx9rAFu61PvFxuPbtSwDGJws/X0=
github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578/go.mod h1:uGdkoq3SwY9Y+13GIhn11/XLaGBb4BfwItxLd5jeuXE=
github.com/StackExchange/wmi v0.0.0-20180116203802-5d049714c4a6 h1:fLjPD/aNc3UIOA6tDi6QXUemppXK3P9BI7mr2hd6gx8=
github.com/StackExchange/wmi v0.0.0-20180116203802-5d049714c4a6/go.mod h1:3eOhrUMpNV+6aFIbp5/iudMxNCF27Vw2OZgy4xEx0Fg=
github.com/VictoriaMetrics/fastcache v1.6.0 h1:C/3Oi3EiBCqufydp1neRZkqcwmEiuRT9c3fqvvgKm5o=
Expand Down Expand Up @@ -533,6 +535,8 @@ github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7V
github.com/julienschmidt/httprouter v1.3.0/go.mod h1:JR6WtHb+2LUe8TCKY3cZOxFyyO8IZAc4RVcycCCAKdM=
github.com/jung-kurt/gofpdf v1.0.3-0.20190309125859-24315acbbda5/go.mod h1:7Id9E/uU8ce6rXgefFLlgrJj/GYY22cpxn+r32jIOes=
github.com/jwilder/encoding v0.0.0-20170811194829-b4e1701a28ef/go.mod h1:Ct9fl0F6iIOGgxJ5npU/IUOhOhqlVrGjyIZc8/MagT0=
github.com/k0kubun/pp/v3 v3.2.0 h1:h33hNTZ9nVFNP3u2Fsgz8JXiF5JINoZfFq4SvKJwNcs=
github.com/k0kubun/pp/v3 v3.2.0/go.mod h1:ODtJQbQcIRfAD3N+theGCV1m/CBxweERz2dapdz1EwA=
github.com/karalabe/usb v0.0.0-20190919080040-51dc0efba356/go.mod h1:Od972xHfMJowv7NGVDiWVxk2zxnWgjLlJzE+F4F7AGU=
github.com/kisielk/errcheck v1.2.0/go.mod h1:/BMXB+zMLi60iA8Vv6Ksmxu/1UDYcXs4uQLJ+jE2L00=
github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
Expand Down Expand Up @@ -592,6 +596,7 @@ github.com/mattn/go-colorable v0.1.0/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaO
github.com/mattn/go-colorable v0.1.1/go.mod h1:FuOcm+DKB9mbwrcAfNl7/TZVBZ6rcnceauSikq3lYCQ=
github.com/mattn/go-colorable v0.1.6/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc=
github.com/mattn/go-colorable v0.1.13 h1:fFA4WZxdEF4tXPZVKMLwD8oUnCTTo08duU7wxecdEvA=
github.com/mattn/go-colorable v0.1.13/go.mod h1:7S9/ev0klgBDR4GtXTXX8a3vIGJpMovkB8vQcUbaXHg=
github.com/mattn/go-ieproxy v0.0.0-20190610004146-91bb50d98149/go.mod h1:31jz6HNzdxOmlERGGEc4v/dMssOfmp2p5bT/okiKFFc=
github.com/mattn/go-ieproxy v0.0.0-20190702010315-6dee0af9227d/go.mod h1:31jz6HNzdxOmlERGGEc4v/dMssOfmp2p5bT/okiKFFc=
github.com/mattn/go-isatty v0.0.4/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4=
Expand All @@ -601,6 +606,7 @@ github.com/mattn/go-isatty v0.0.7/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hd
github.com/mattn/go-isatty v0.0.9/go.mod h1:YNRxwqDuOph6SZLI9vUUz6OYw3QyUt7WiY2yME+cCiQ=
github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU=
github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94=
github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM=
github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY=
github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
github.com/mattn/go-runewidth v0.0.3/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU=
Expand Down Expand Up @@ -1058,6 +1064,7 @@ golang.org/x/sys v0.0.0-20211007075335-d3039528d8ac/go.mod h1:oPkhp1MJrh7nUepCBc
golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220908164124-27713097b956/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@

-- +migrate Up
create table if not exists binance_trackings (
id serial primary key,
profile_id text,
spot_last_time timestamp
);

create table binance_spot_transactions (
id serial,
profile_id text,
symbol text,
order_id integer,
order_list_id integer,
client_order_id text,
price text,
orig_qty text,
executed_qty text,
cumulative_quote_qty text,
status text,
time_in_force text,
type text,
side text,
stop_price text,
iceberg_qty text,
time timestamp,
update_time timestamp,
is_working boolean,
orig_quote_order_qty text,
working_time timestamp,
self_trade_prevention_mode text
);

create unique index binance_spot_transactions_profile_id_order_id_index on binance_spot_transactions (profile_id, order_id);
-- +migrate Down
drop table if exists binance_trackings;
drop index if exists binance_spot_transactions_profile_id_order_id_index;
drop table if exists binance_spot_transactions;
48 changes: 41 additions & 7 deletions pkg/entities/binance_data.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import (
"encoding/json"
"math/rand"
"strconv"
"time"

"github.com/defipod/mochi/pkg/consts"
"github.com/defipod/mochi/pkg/logger"
Expand Down Expand Up @@ -67,18 +68,51 @@ func (e *Entity) IntegrateBinanceData(req request.IntegrationBinanceData) (*mode
}

func (e *Entity) UnlinkBinance(req request.UnlinkBinance) error {
res, err := e.svc.MochiProfile.GetByDiscordID(req.DiscordUserId, true)
if err != nil {
res, err := e.svc.MochiProfile.GetByDiscordID(req.DiscordUserId, true)
if err != nil {
e.log.Fields(logger.Fields{"discordUserId": req.DiscordUserId}).Error(err, "[entities.UnlinkBinance] - fail to get profile by discord id")
return err
}
}

err = e.svc.MochiProfile.UnlinkDex(res.ID, consts.PlatformBinance)
err = e.svc.MochiProfile.UnlinkDex(res.ID, consts.PlatformBinance)
if err != nil {
e.log.Fields(logger.Fields{"profileId": res.ID, "platform": consts.PlatformBinance}).Error(err, "[entities.UnlinkBinance] - fail to unlink binance")
return err
e.log.Fields(logger.Fields{"profileId": res.ID, "platform": consts.PlatformBinance}).Error(err, "[entities.UnlinkBinance] - fail to unlink binance")
return err
}

return nil
return nil
}

func binanceStartTime() time.Time {
return time.Unix(1499943600, 0).UTC()
}
func (e *Entity) CrawlBinanceSpotTransactions() {
e.log.Info("Watching Binance account from profile ...")
// get all binance associated account
res, err := e.svc.MochiProfile.GetAllBinanceAccount()
if err != nil {
e.log.Error(err, "[entities.CrawlBinanceSpotTransactions] - fail to get all binance associated account")
return
}

for idx, binance := range res.Data {
binanceTracking, err := e.repo.BinanceTracking.FirstOrCreate(&model.BinanceTracking{ProfileId: binance.ProfileId, SpotLastTime: binanceStartTime()})
if err != nil {
e.log.Fields(logger.Fields{"profileId": binance.ProfileId}).Error(err, "[entities.CrawlBinanceSpotTransactions] - fail to first or create binance tracking")
continue
}
res.Data[idx].SpotLastTime = binanceTracking.SpotLastTime
}

for _, binance := range res.Data {
e.log.Fields(logger.Fields{"profileId": binance.ProfileId}).Info("[entities.CrawlBinanceSpotTransactions] - start crawling binance spot transactions")
// get spot transactions
startTime := strconv.Itoa(int(binance.SpotLastTime.UnixMilli()))
endTime := strconv.Itoa(int(time.Date(2024, 2, 20, 0, 0, 0, 0, time.UTC).UnixMilli()))
_, err := e.svc.Binance.GetSpotTransactions(binance.ApiKey, binance.ApiSecret, startTime, endTime)
if err != nil {
e.log.Fields(logger.Fields{"profileId": binance.ProfileId}).Error(err, "[entities.CrawlBinanceSpotTransactions] - fail to get spot transactions")
continue
}
}
}
24 changes: 24 additions & 0 deletions pkg/job/crawl_binance_spot_transactions.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package job

import (
"github.com/defipod/mochi/pkg/entities"
"github.com/defipod/mochi/pkg/logger"
)

type crawlBinanceSpotTransactions struct {
entity *entities.Entity
log logger.Logger
}

func NewCrawlBinanceSpotTransactionsJob(e *entities.Entity, l logger.Logger) Job {
return &crawlBinanceSpotTransactions{
entity: e,
log: l,
}
}

func (j *crawlBinanceSpotTransactions) Run() error {
j.log.Infof("Start crawling binance spot transaction ...")
j.entity.CrawlBinanceSpotTransactions()
return nil
}
28 changes: 28 additions & 0 deletions pkg/model/binance_spot_transaction.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package model

import "time"

type BinanceSpotTransaction struct {
ID int64 `json:"id"`
ProfileId string `json:"profile_id"`
Symbol string `json:"symbol"`
OrderId int64 `json:"order_id"`
OrderListId int64 `json:"order_list_id"`
ClientOrderId string `json:"client_order_id"`
Price string `json:"price"`
OrigQty string `json:"orig_qty"`
ExecutedQty string `json:"executed_qty"`
CummulativeQuoteQty string `json:"cummulative_quote_qty"`
Status string `json:"status"`
TimeInForce string `json:"time_in_force"`
Type string `json:"type"`
Side string `json:"side"`
StopPrice string `json:"stop_price"`
IcebergQty string `json:"iceberg_qty"`
Time time.Time `json:"time"`
UpdateTime time.Time `json:"update_time"`
IsWorking bool `json:"is_working"`
OrigQuoteOrderQty string `json:"orig_quote_order_qty"`
WorkingTime time.Time `json:"working_time"`
SelfTradePreventionMode string `json:"self_trade_prevention_mode"`
}
9 changes: 9 additions & 0 deletions pkg/model/binance_tracking.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package model

import "time"

type BinanceTracking struct {
ID int64 `json:"id"`
ProfileId string `json:"profile_id"`
SpotLastTime time.Time `json:"spot_last_time"`
}
19 changes: 19 additions & 0 deletions pkg/repo/binance_spot_transaction/pg.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package binancespottransaction

import (
"gorm.io/gorm"

"github.com/defipod/mochi/pkg/model"
)

type pg struct {
db *gorm.DB
}

func NewPG(db *gorm.DB) Store {
return &pg{db: db}
}

func (pg *pg) Create(tx *model.BinanceSpotTransaction) error {
return pg.db.Create(&tx).Error
}
7 changes: 7 additions & 0 deletions pkg/repo/binance_spot_transaction/store.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
package binancespottransaction

import "github.com/defipod/mochi/pkg/model"

type Store interface {
Create(tx *model.BinanceSpotTransaction) error
}
19 changes: 19 additions & 0 deletions pkg/repo/binance_tracking/pg.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package binancetracking

import (
"gorm.io/gorm"

"github.com/defipod/mochi/pkg/model"
)

type pg struct {
db *gorm.DB
}

func NewPG(db *gorm.DB) Store {
return &pg{db: db}
}

func (pg *pg) FirstOrCreate(binanceTracking *model.BinanceTracking) (*model.BinanceTracking, error) {
return binanceTracking, pg.db.Where("profile_id = ?", binanceTracking.ProfileId).FirstOrCreate(&binanceTracking).Error
}
7 changes: 7 additions & 0 deletions pkg/repo/binance_tracking/store.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
package binancetracking

import "github.com/defipod/mochi/pkg/model"

type Store interface {
FirstOrCreate(binanceTracking *model.BinanceTracking) (*model.BinanceTracking, error)
}
4 changes: 4 additions & 0 deletions pkg/repo/pg/repo.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ import (
ac "github.com/defipod/mochi/pkg/repo/airdrop_campaign"
autoActionHistory "github.com/defipod/mochi/pkg/repo/auto_action_history"
autoTrigger "github.com/defipod/mochi/pkg/repo/auto_trigger"
binancespottransaction "github.com/defipod/mochi/pkg/repo/binance_spot_transaction"
binacetracking "github.com/defipod/mochi/pkg/repo/binance_tracking"
"github.com/defipod/mochi/pkg/repo/chain"
coingeckoinfo "github.com/defipod/mochi/pkg/repo/coingecko_info"
coingeckosupportedtokens "github.com/defipod/mochi/pkg/repo/coingecko_supported_tokens"
Expand Down Expand Up @@ -190,5 +192,7 @@ func NewRepo(db *gorm.DB) *repo.Repo {
UserNotificationSetting: usernotificationsetting.NewPG(db),
NotificationFlag: notificationflag.NewPG(db),
TokenPriceSnapshot: tokenpricesnapshot.NewPG(db),
BinanceTracking: binacetracking.NewPG(db),
BinanceSpotTransaction: binancespottransaction.NewPG(db),
}
}
4 changes: 4 additions & 0 deletions pkg/repo/repo.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@ import (
ac "github.com/defipod/mochi/pkg/repo/airdrop_campaign"
autoActionHistory "github.com/defipod/mochi/pkg/repo/auto_action_history"
autoTrigger "github.com/defipod/mochi/pkg/repo/auto_trigger"
binancespottransaction "github.com/defipod/mochi/pkg/repo/binance_spot_transaction"
binancetracking "github.com/defipod/mochi/pkg/repo/binance_tracking"
"github.com/defipod/mochi/pkg/repo/chain"
coingeckoinfo "github.com/defipod/mochi/pkg/repo/coingecko_info"
coingeckosupportedtokens "github.com/defipod/mochi/pkg/repo/coingecko_supported_tokens"
Expand Down Expand Up @@ -185,4 +187,6 @@ type Repo struct {
UserNotificationSetting usernotificationsetting.Store
NotificationFlag notificationflag.Store
TokenPriceSnapshot tokenpricesnapshot.Store
BinanceTracking binancetracking.Store
BinanceSpotTransaction binancespottransaction.Store
}
23 changes: 23 additions & 0 deletions pkg/response/binance.go
Original file line number Diff line number Diff line change
Expand Up @@ -217,3 +217,26 @@ type BinanceApiTickerPriceResponse struct {
Symbol string `json:"symbol"`
Price string `json:"price"`
}

type BinanceSpotTransaction struct {
Symbol string `json:"symbol"`
OrderId int64 `json:"order_id"`
OrderListId int64 `json:"order_list_id"`
ClientOrderId string `json:"client_order_id"`
Price string `json:"price"`
OrigQty string `json:"orig_qty"`
ExecutedQty string `json:"executed_qty"`
CummulativeQuoteQty string `json:"cummulative_quote_qty"`
Status string `json:"status"`
TimeInForce string `json:"time_in_force"`
Type string `json:"type"`
Side string `json:"side"`
StopPrice string `json:"stop_price"`
IcebergQty string `json:"iceberg_qty"`
Time int64 `json:"time"`
UpdateTime int64 `json:"update_time"`
IsWorking bool `json:"is_working"`
OrigQuoteOrderQty string `json:"orig_quote_order_qty"`
WorkingTime int64 `json:"working_time"`
SelfTradePreventionMode string `json:"self_trade_prevention_mode"`
}
Loading

0 comments on commit 13ddc60

Please sign in to comment.