-
-
Notifications
You must be signed in to change notification settings - Fork 113
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* fix: holders fix: floor decorator in db init * S1028: should use fmt.Errorf(...) instead of errors.New(fmt.Sprintf(...)) (gosimple) * remove frequency override for holders
- Loading branch information
Showing
4 changed files
with
100 additions
and
40 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,49 +1,88 @@ | ||
package utils | ||
|
||
import ( | ||
"encoding/json" | ||
"fmt" | ||
"log" | ||
"io" | ||
"net/http" | ||
"strings" | ||
|
||
"github.com/PuerkitoBio/goquery" | ||
"time" | ||
) | ||
|
||
const ( | ||
ChainURL = "https://%s/token/%s" | ||
ChainURL = "https://api.covalenthq.com/v1/%s/tokens/%s/token_holders_v2/" | ||
) | ||
|
||
func GetHolders(chain, contract string) string { | ||
var holders string | ||
type Holders struct { | ||
Data struct { | ||
UpdatedAt time.Time `json:"updated_at"` | ||
ChainID int `json:"chain_id"` | ||
ChainName string `json:"chain_name"` | ||
Items []struct { | ||
ContractDecimals int `json:"contract_decimals"` | ||
ContractName string `json:"contract_name"` | ||
ContractTickerSymbol string `json:"contract_ticker_symbol"` | ||
ContractAddress string `json:"contract_address"` | ||
SupportsErc []string `json:"supports_erc"` | ||
LogoURL string `json:"logo_url"` | ||
Address string `json:"address"` | ||
Balance string `json:"balance"` | ||
TotalSupply string `json:"total_supply"` | ||
BlockHeight int `json:"block_height"` | ||
} `json:"items"` | ||
Pagination struct { | ||
HasMore bool `json:"has_more"` | ||
PageNumber int `json:"page_number"` | ||
PageSize int `json:"page_size"` | ||
TotalCount int `json:"total_count"` | ||
} `json:"pagination"` | ||
} `json:"data"` | ||
Error bool `json:"error"` | ||
ErrorMessage interface{} `json:"error_message"` | ||
ErrorCode interface{} `json:"error_code"` | ||
} | ||
|
||
func GetHolders(chain, contract, apiKey string) (int, error) { | ||
var holders Holders | ||
var result int | ||
|
||
switch chain { | ||
case "ethereum": | ||
chain = "etherscan.io" | ||
chain = "eth-mainnet" | ||
case "binance-smart-chain": | ||
chain = "bscscan.com" | ||
chain = "bsc-mainnet" | ||
default: | ||
chain = "etherscan.io" | ||
chain = "eth-mainnet" | ||
} | ||
|
||
reqUrl := fmt.Sprintf(ChainURL, chain, contract) | ||
|
||
req, err := http.NewRequest("GET", reqUrl, nil) | ||
req.SetBasicAuth(apiKey, "") | ||
if err != nil { | ||
return result, err | ||
} | ||
|
||
reqURL := fmt.Sprintf(ChainURL, chain, contract) | ||
req.Header.Add("User-Agent", "Mozilla/5.0") | ||
req.Header.Add("accept", "application/json") | ||
client := &http.Client{} | ||
resp, err := client.Do(req) | ||
if err != nil { | ||
return result, err | ||
} | ||
|
||
response, err := http.Get(reqURL) | ||
results, err := io.ReadAll(resp.Body) | ||
if err != nil { | ||
log.Fatal(err) | ||
return result, err | ||
} | ||
defer response.Body.Close() | ||
|
||
document, err := goquery.NewDocumentFromReader(response.Body) | ||
err = json.Unmarshal(results, &holders) | ||
if err != nil { | ||
log.Fatal("Error loading HTTP response body. ", err) | ||
return result, err | ||
} | ||
|
||
document.Find("div").Each(func(index int, element *goquery.Selection) { | ||
exists := element.HasClass("mr-3") | ||
if exists { | ||
holders = strings.TrimSpace(element.Text()) | ||
} | ||
}) | ||
if holders.Error { | ||
return result, fmt.Errorf("%v", holders.ErrorMessage) | ||
} | ||
|
||
return holders | ||
return holders.Data.Pagination.TotalCount, err | ||
} |