MOVINGBRICKS

package main

import (
    "encoding/json"
    "fmt"
    "io/ioutil"
    "net/http"
    "net/url"
    "sort"
    "strconv"
    "strings"
    "time"

    "github.com/davecgh/go-spew/spew"
)

const defProxy = "https://usr:psswd@192.168.1.148:8080"

var (
    KnownSymbols = []string{
        "BTC",
        "ETH",
        "USDT",
        "ETC",
    }
)

func findSuffix(pairname string) string {
    for _, suf := range KnownSymbols {
        if strings.HasSuffix(pairname, suf) {
            return suf
        }
    }
    return ""
}

func splitPair(pairname string) (string, string) {
    s := findSuffix(pairname)
    return pairname[:len(s)], pairname[len(pairname)-len(s):]
}

var (
    ExcludedSymbols = []string{
        "123456",
    }
)

func isExcludedSymbol(name string) bool {
    for _, v := range ExcludedSymbols {
        if v == name {
            return true
        }
    }
    return false
}

type BaItem struct {
    Symbol string `json:"symbol"`
    Price  string `json:"price"`

    Numerator   string
    Denominator string
    Rate        float64
}

type baItem BaItem

func (b *BaItem) UnmarshalJSON(bytes []byte) (err error) {
    j := baItem{}
    err = json.Unmarshal(bytes, &j)
    if err == nil {
        *b = BaItem(j)
        b.Numerator, b.Denominator = splitPair(b.Symbol)
        b.Rate, _ = strconv.ParseFloat(b.Price, 64)
    }
    return
}

func (b *BaItem) String() string {
    return fmt.Sprintf("%v=>%v:%f", b.Numerator, b.Denominator, b.Rate)
}

type TSnapshot []BaItem

type BaAgent struct {
    client *http.Client
}

type TsEntry struct {
    Timestamp time.Time
    Tsa       TSnapshot
}

func newConn() *http.Client {
    tr := &http.Transport{
        MaxIdleConns:       10,
        IdleConnTimeout:    10 * time.Second,
        DisableCompression: true,
        DisableKeepAlives:  false, //
    }
    url, eUrl := url.Parse(defProxy)
    if eUrl != nil {
        panic(eUrl)
    }
    tr.Proxy = http.ProxyURL(url)
    //tr.Proxy = http.ProxyFromEnvironment
    return &http.Client{
        Transport: tr,
    }
}

func NewBaAgent() *BaAgent {
    return &BaAgent{
        client: newConn(),
    }
}

func (b *BaAgent) GetSnapshot() (*TsEntry, error) {
    //~ As long as it could be made new from `make`
    const ticker_uri = "https://www.binance.com/api/v1/ticker/allPrices"
    resp, err := b.client.Get(ticker_uri)
    if err != nil {
        return nil, err
    }
    defer resp.Body.Close() // must do

    chunk, eChunk := ioutil.ReadAll(resp.Body)
    if eChunk != nil {
        return nil, eChunk
    }

    var tsa TSnapshot
    if e := json.Unmarshal(chunk, &tsa); e != nil {
        return nil, e
    }
    return &TsEntry{
        Timestamp: time.Now(),
        Tsa:       tsa,
    }, nil
}

type ExchangeItem struct {
    Name       string
    EthBtcPair float64
}

type ExchangeItemArr []ExchangeItem

func (s ExchangeItemArr) Len() int {
    return len(s)
}

func (s ExchangeItemArr) Swap(i, j int) {
    s[i], s[j] = s[j], s[i]
}

func (s ExchangeItemArr) Less(i, j int) bool {
    return s[i].EthBtcPair < s[j].EthBtcPair
}

func Traverse(snap TsEntry) {
    fmt.Printf("start analyzing %v\n", snap.Timestamp.Format(time.RFC822))
    fromMap := make(map[string]map[string]float64) // all initialized.
    // ico - to main-stream
    for _, ent := range snap.Tsa {
        if nil == fromMap[ent.Numerator] {
            fromMap[ent.Numerator] = make(map[string]float64)
        }
        fromMap[ent.Numerator][ent.Denominator] = ent.Rate
    }
    spew.Dump(fromMap)

    var exi []ExchangeItem
    stdR := fromMap["ETH"]["BTC"]
    //_ = stdR
    for kind, ent := range fromMap {
        b_rate, btcOK := ent["BTC"]
        e_rate, ethOK := ent["ETH"]
        if btcOK && ethOK {
            esteR := 1 / e_rate * b_rate
            //fmt.Printf("%v => %v\n", kind, esteR/stdR)
            exi = append(exi, ExchangeItem{kind, esteR / stdR})
        }
    }
    sort.Sort(ExchangeItemArr(exi))
    fmt.Println("******************************")
    spew.Dump(exi)
}

func main() {
    ba := NewBaAgent()
    if snap, e := ba.GetSnapshot(); nil == e {
        //fmt.Printf("%+v\n", snap)
        //spew.Dump(snap)
        for _, snap := range snap.Tsa {
            if isExcludedSymbol(snap.Symbol) {
                continue
            }
            found := false
            for _, n := range KnownSymbols {
                if strings.HasSuffix(snap.Symbol, n) {
                    found = true
                    break
                }
            }
            if !found {
                fmt.Printf("Unknown symbol: %v\n", snap.Symbol)
            }
        }
        fmt.Println()
        Traverse(*snap)
    } else {
        fmt.Printf("Error: %v\n", e)
    }
    //fmt.Println("bye")
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值