mirror of
https://github.com/d0zingcat/gocryptotrader.git
synced 2026-05-31 07:26:44 +00:00
Initial implementation of HTTP mock testing framework (#310)
* Initial implementation of HTTP mock testing framework Convert to VCR testing server. Segregate live testing via build tags. Converted Binance to VCR server Convert Bitstamp to VCR mocking tests Added VCR mock testing for localbitcoins * Add server generation for concurrent testing * Fix linter issues * Fix linter issue * fix race - potentially * revert auto assigning of host vals * Fix requested changes * Adds mock testing for ANX Switch to using TestMain functionality Added cron job usage for travis-ci to live testing Added appveyor scheduled build check for live testing * WOOPS * silly correction * Fixes fantastic linter issues * fixed another whoopsie * WOOO! * Adds gemini mock testing with additional fixes * Add docs and sharedvalue * Added tls using httptest package * Fixed issues * added explicit mock recording reference to error * Fix requested changes * strip port from mock files as they are not needed on tls server * Change incorrect names * fix requested changes * lbank update * Fix another issue * Updated readme
This commit is contained in:
committed by
Adrian Gallagher
parent
a81ddead9e
commit
6d8ba0a96a
@@ -14,6 +14,7 @@ import (
|
||||
"time"
|
||||
|
||||
"github.com/thrasher-corp/gocryptotrader/common"
|
||||
"github.com/thrasher-corp/gocryptotrader/exchanges/mock"
|
||||
"github.com/thrasher-corp/gocryptotrader/exchanges/nonce"
|
||||
log "github.com/thrasher-corp/gocryptotrader/logger"
|
||||
)
|
||||
@@ -70,6 +71,7 @@ type Job struct {
|
||||
AuthRequest bool
|
||||
Verbose bool
|
||||
HTTPDebugging bool
|
||||
Record bool
|
||||
}
|
||||
|
||||
// NewRateLimit creates a new RateLimit
|
||||
@@ -264,13 +266,18 @@ func (r *Requester) checkRequest(method, path string, body io.Reader, headers ma
|
||||
}
|
||||
|
||||
// DoRequest performs a HTTP/HTTPS request with the supplied params
|
||||
func (r *Requester) DoRequest(req *http.Request, path string, body io.Reader, result interface{}, authRequest, verbose, httpDebug bool) error {
|
||||
func (r *Requester) DoRequest(req *http.Request, path string, body io.Reader, result interface{}, authRequest, verbose, httpDebug, httpRecord bool) error {
|
||||
if verbose {
|
||||
log.Debugf("%s exchange request path: %s requires rate limiter: %v", r.Name, path, r.RequiresRateLimiter())
|
||||
log.Debugf("%s exchange request path: %s requires rate limiter: %v",
|
||||
r.Name,
|
||||
path,
|
||||
r.RequiresRateLimiter())
|
||||
|
||||
for k, d := range req.Header {
|
||||
log.Debugf("%s exchange request header [%s]: %s", r.Name, k, d)
|
||||
}
|
||||
log.Debug(body)
|
||||
log.Debugf("%s exchange request type: %s", r.Name, req.Method)
|
||||
log.Debugf("%s exchange request body: %v", r.Name, body)
|
||||
}
|
||||
|
||||
var timeoutError error
|
||||
@@ -328,6 +335,14 @@ func (r *Requester) DoRequest(req *http.Request, path string, body io.Reader, re
|
||||
return err
|
||||
}
|
||||
|
||||
if httpRecord {
|
||||
// This dumps http responses for future mocking implementations
|
||||
err = mock.HTTPRecord(resp, r.Name, contents)
|
||||
if err != nil {
|
||||
return fmt.Errorf("mock recording failure %s", err)
|
||||
}
|
||||
}
|
||||
|
||||
if resp.StatusCode != 200 && resp.StatusCode != 201 && resp.StatusCode != 202 {
|
||||
err = fmt.Errorf("unsuccessful HTTP status code: %d", resp.StatusCode)
|
||||
if verbose {
|
||||
@@ -371,7 +386,7 @@ func (r *Requester) worker() {
|
||||
if !r.IsRateLimited(x.AuthRequest) {
|
||||
r.IncrementRequests(x.AuthRequest)
|
||||
|
||||
err := r.DoRequest(x.Request, x.Path, x.Body, x.Result, x.AuthRequest, x.Verbose, x.HTTPDebugging)
|
||||
err := r.DoRequest(x.Request, x.Path, x.Body, x.Result, x.AuthRequest, x.Verbose, x.HTTPDebugging, x.Record)
|
||||
x.JobResult <- &JobResult{
|
||||
Error: err,
|
||||
Result: x.Result,
|
||||
@@ -395,7 +410,7 @@ func (r *Requester) worker() {
|
||||
log.Debugf("%s request. No longer rate limited! Doing request", r.Name)
|
||||
}
|
||||
|
||||
err := r.DoRequest(x.Request, x.Path, x.Body, x.Result, x.AuthRequest, x.Verbose, x.HTTPDebugging)
|
||||
err := r.DoRequest(x.Request, x.Path, x.Body, x.Result, x.AuthRequest, x.Verbose, x.HTTPDebugging, x.Record)
|
||||
x.JobResult <- &JobResult{
|
||||
Error: err,
|
||||
Result: x.Result,
|
||||
@@ -408,7 +423,7 @@ func (r *Requester) worker() {
|
||||
}
|
||||
|
||||
// SendPayload handles sending HTTP/HTTPS requests
|
||||
func (r *Requester) SendPayload(method, path string, headers map[string]string, body io.Reader, result interface{}, authRequest, nonceEnabled, verbose, httpDebugging bool) error {
|
||||
func (r *Requester) SendPayload(method, path string, headers map[string]string, body io.Reader, result interface{}, authRequest, nonceEnabled, verbose, httpDebugging, record bool) error {
|
||||
if !nonceEnabled {
|
||||
r.lock()
|
||||
}
|
||||
@@ -444,7 +459,7 @@ func (r *Requester) SendPayload(method, path string, headers map[string]string,
|
||||
|
||||
if !r.RequiresRateLimiter() {
|
||||
r.unlock()
|
||||
return r.DoRequest(req, path, body, result, authRequest, verbose, httpDebugging)
|
||||
return r.DoRequest(req, path, body, result, authRequest, verbose, httpDebugging, record)
|
||||
}
|
||||
|
||||
if len(r.Jobs) == maxRequestJobs {
|
||||
@@ -473,6 +488,7 @@ func (r *Requester) SendPayload(method, path string, headers map[string]string,
|
||||
AuthRequest: authRequest,
|
||||
Verbose: verbose,
|
||||
HTTPDebugging: httpDebugging,
|
||||
Record: record,
|
||||
}
|
||||
|
||||
if verbose {
|
||||
|
||||
@@ -200,7 +200,7 @@ func TestCheckRequest(t *testing.T) {
|
||||
|
||||
func TestDoRequest(t *testing.T) {
|
||||
var test = new(Requester)
|
||||
err := test.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, false, false, true, false)
|
||||
err := test.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, false, false, true, false, false)
|
||||
if err == nil {
|
||||
t.Fatal("not iniitalised")
|
||||
}
|
||||
@@ -211,17 +211,17 @@ func TestDoRequest(t *testing.T) {
|
||||
}
|
||||
|
||||
r.Name = "bitfinex"
|
||||
err = r.SendPayload("BLAH", "https://www.google.com", nil, nil, nil, false, false, true, false)
|
||||
err = r.SendPayload("BLAH", "https://www.google.com", nil, nil, nil, false, false, true, false, false)
|
||||
if err == nil {
|
||||
t.Fatal("unexpected values")
|
||||
}
|
||||
|
||||
err = r.SendPayload(http.MethodGet, "", nil, nil, nil, false, false, true, false)
|
||||
err = r.SendPayload(http.MethodGet, "", nil, nil, nil, false, false, true, false, false)
|
||||
if err == nil {
|
||||
t.Fatal("unexpected values")
|
||||
}
|
||||
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, false, false, true, false)
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, false, false, true, false, false)
|
||||
if err != nil {
|
||||
t.Fatal("unexpected values")
|
||||
}
|
||||
@@ -233,7 +233,7 @@ func TestDoRequest(t *testing.T) {
|
||||
r.SetRateLimit(false, time.Second, 0)
|
||||
r.SetRateLimit(true, time.Second, 0)
|
||||
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, false, false, true, false)
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, false, false, true, false, false)
|
||||
if err != nil {
|
||||
t.Fatal("unexpected values")
|
||||
}
|
||||
@@ -250,7 +250,7 @@ func TestDoRequest(t *testing.T) {
|
||||
t.Fatal("unexepcted values")
|
||||
}
|
||||
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, false, false, true, false)
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, false, false, true, false, false)
|
||||
if err != nil {
|
||||
t.Fatal("unexpected values")
|
||||
}
|
||||
@@ -261,27 +261,27 @@ func TestDoRequest(t *testing.T) {
|
||||
t.Fatal("unexepcted values")
|
||||
}
|
||||
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, true, false, true, false)
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, nil, true, false, true, false, false)
|
||||
if err != nil {
|
||||
t.Fatal("unexpected values")
|
||||
}
|
||||
|
||||
var result interface{}
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, result, false, false, true, false)
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, result, false, false, true, false, false)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
headers := make(map[string]string)
|
||||
headers["content-type"] = "content/text"
|
||||
err = r.SendPayload(http.MethodPost, "https://bitfinex.com", headers, nil, result, false, false, true, false)
|
||||
err = r.SendPayload(http.MethodPost, "https://bitfinex.com", headers, nil, result, false, false, true, false, false)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
r.StartCycle()
|
||||
r.UnauthLimit.SetRequests(100)
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, result, false, false, false, false)
|
||||
err = r.SendPayload(http.MethodGet, "https://www.google.com", nil, nil, result, false, false, false, false, false)
|
||||
if err != nil {
|
||||
t.Fatal("unexpected values")
|
||||
}
|
||||
@@ -297,7 +297,7 @@ func TestDoRequest(t *testing.T) {
|
||||
}
|
||||
|
||||
r.HTTPClient.Timeout = 1 * time.Second
|
||||
err = r.SendPayload(http.MethodPost, "https://httpstat.us/200?sleep=20000", nil, nil, nil, false, false, true, false)
|
||||
err = r.SendPayload(http.MethodPost, "https://httpstat.us/200?sleep=20000", nil, nil, nil, false, false, true, false, false)
|
||||
if err == nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
@@ -327,6 +327,6 @@ func BenchmarkRequestLockMech(b *testing.B) {
|
||||
var r = new(Requester)
|
||||
var meep interface{}
|
||||
for n := 0; n < b.N; n++ {
|
||||
r.SendPayload(http.MethodGet, "127.0.0.1", nil, nil, &meep, false, false, false, false)
|
||||
r.SendPayload(http.MethodGet, "127.0.0.1", nil, nil, &meep, false, false, false, false, false)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user