diff --git a/clients/stellarcore/client.go b/clients/stellarcore/client.go index 4641f29361..aa968f8c86 100644 --- a/clients/stellarcore/client.go +++ b/clients/stellarcore/client.go @@ -1,6 +1,7 @@ package stellarcore import ( + "bytes" "context" "encoding/json" "fmt" @@ -152,19 +153,19 @@ func (c *Client) SetCursor(ctx context.Context, id string, cursor int32) (err er return nil } -func (c *Client) GetLedgerEntries(ctx context.Context, ledgerSeq uint32, keys ...xdr.LedgerKey) (*proto.GetLedgerEntriesResponse, error) { - var resp *proto.GetLedgerEntriesResponse - return resp, c.makeLedgerKeyRequest(ctx, resp, "getledgerentries", ledgerSeq, keys...) +func (c *Client) GetLedgerEntries(ctx context.Context, ledgerSeq uint32, keys ...xdr.LedgerKey) (proto.GetLedgerEntriesResponse, error) { + var resp proto.GetLedgerEntriesResponse + return resp, c.makeLedgerKeyRequest(ctx, &resp, "getledgerentry", ledgerSeq, keys...) } -func (c *Client) getInvocationProof(ctx context.Context, ledgerSeq uint32, keys ...xdr.LedgerKey) (*proto.ProofResponse, error) { - var resp *proto.ProofResponse - return resp, c.makeLedgerKeyRequest(ctx, resp, "getinvocationproof", ledgerSeq, keys...) +func (c *Client) getInvocationProof(ctx context.Context, ledgerSeq uint32, keys ...xdr.LedgerKey) (proto.ProofResponse, error) { + var resp proto.ProofResponse + return resp, c.makeLedgerKeyRequest(ctx, &resp, "getinvocationproof", ledgerSeq, keys...) } -func (c *Client) getRestorationProof(ctx context.Context, ledgerSeq uint32, keys ...xdr.LedgerKey) (*proto.ProofResponse, error) { - var resp *proto.ProofResponse - return resp, c.makeLedgerKeyRequest(ctx, resp, "getrestorationproof", ledgerSeq, keys...) +func (c *Client) getRestorationProof(ctx context.Context, ledgerSeq uint32, keys ...xdr.LedgerKey) (proto.ProofResponse, error) { + var resp proto.ProofResponse + return resp, c.makeLedgerKeyRequest(ctx, &resp, "getrestorationproof", ledgerSeq, keys...) } // SubmitTransaction calls the `tx` command on the connected stellar core with the provided envelope @@ -268,19 +269,33 @@ func (c *Client) simpleGet( newPath string, query url.Values, ) (*http.Request, error) { - q := "" + u, err := url.Parse(c.URL) + if err != nil { + return nil, errors.Wrap(err, "unparseable url") + } + + u.Path = path.Join(u.Path, newPath) if query != nil { - q = query.Encode() + u.RawQuery = query.Encode() + } + newURL := u.String() + + var req *http.Request + req, err = http.NewRequestWithContext(ctx, http.MethodGet, newURL, nil) + if err != nil { + return nil, errors.Wrap(err, "failed to create request") } - return c.rawGet(ctx, newPath, q) + + return req, nil } -// rawGet returns a new GET request to the connected stellar-core using the -// provided path and a raw query string to construct the result. -func (c *Client) rawGet( +// rawPost returns a new POST request to the connected stellar-core using the +// provided path and the params values encoded as the request body to construct +// the result. +func (c *Client) rawPost( ctx context.Context, newPath string, - query string, + params string, ) (*http.Request, error) { u, err := url.Parse(c.URL) if err != nil { @@ -288,11 +303,14 @@ func (c *Client) rawGet( } u.Path = path.Join(u.Path, newPath) - u.RawQuery = query newURL := u.String() var req *http.Request - req, err = http.NewRequestWithContext(ctx, http.MethodGet, newURL, nil) + req, err = http.NewRequestWithContext( + ctx, + http.MethodPost, + newURL, + bytes.NewBuffer([]byte(params))) if err != nil { return nil, errors.Wrap(err, "failed to create request") } @@ -302,7 +320,7 @@ func (c *Client) rawGet( // makeLedgerKeyRequest is a generic method to perform a request in the form // `key=...&key=...&ledgerSeq=...` which is useful because three Stellar Core -// endpoints all use this request format. +// endpoints all use this request format. Be sure to pass `target by reference. func (c *Client) makeLedgerKeyRequest( ctx context.Context, target interface{}, @@ -317,7 +335,7 @@ func (c *Client) makeLedgerKeyRequest( } var req *http.Request - req, err = c.rawGet(ctx, endpoint, q) + req, err = c.rawPost(ctx, endpoint, q) if err != nil { return err } @@ -327,7 +345,7 @@ func (c *Client) makeLedgerKeyRequest( return err } - // returns nil if the error is nil + // wrap returns nil if the inner error is nil return errors.Wrap(json.NewDecoder(hresp.Body).Decode(&target), "json decode failed") } diff --git a/clients/stellarcore/client_test.go b/clients/stellarcore/client_test.go index 5bea23bd65..c646dd6e76 100644 --- a/clients/stellarcore/client_test.go +++ b/clients/stellarcore/client_test.go @@ -83,10 +83,10 @@ func TestGetLedgerEntries(t *testing.T) { hmock := httptest.NewClient() c := &Client{HTTP: hmock, URL: "http://localhost:11626"} - // happy path - new transaction - hmock.On("GET", "http://localhost:11626/getledgerentry"). + // happy path - fetch an entry + hmock.On("POST", "http://localhost:11626/getledgerentry"). ReturnString(http.StatusOK, - `{"ledger": 1234, "entries": [ {"e": "pretend it's xdr lol", "state": "Dead" }]}`, + `{"ledger": 1234, "entries": [ {"e": "pretend it's xdr lol", "state": "dead" }]}`, ) var key xdr.LedgerKey @@ -96,10 +96,9 @@ func TestGetLedgerEntries(t *testing.T) { resp, err := c.GetLedgerEntries(context.Background(), 1234, key) require.NoError(t, err) + require.NotNil(t, resp) require.EqualValues(t, 1234, resp.Ledger) require.Len(t, resp.Entries, 1) require.Equal(t, resp.Entries[0].State, proto.DeadState) - - require.EqualError(t, err, "exception in response: Set MANUAL_CLOSE=true") }