...

Source file src/github.com/shurcooL/graphql/graphql_test.go

Documentation: github.com/shurcooL/graphql

     1  package graphql_test
     2  
     3  import (
     4  	"context"
     5  	"io"
     6  	"io/ioutil"
     7  	"net/http"
     8  	"net/http/httptest"
     9  	"testing"
    10  
    11  	"github.com/shurcooL/graphql"
    12  )
    13  
    14  func TestClient_Query_partialDataWithErrorResponse(t *testing.T) {
    15  	mux := http.NewServeMux()
    16  	mux.HandleFunc("/graphql", func(w http.ResponseWriter, req *http.Request) {
    17  		w.Header().Set("Content-Type", "application/json")
    18  		mustWrite(w, `{
    19  			"data": {
    20  				"node1": {
    21  					"id": "MDEyOklzc3VlQ29tbWVudDE2OTQwNzk0Ng=="
    22  				},
    23  				"node2": null
    24  			},
    25  			"errors": [
    26  				{
    27  					"message": "Could not resolve to a node with the global id of 'NotExist'",
    28  					"type": "NOT_FOUND",
    29  					"path": [
    30  						"node2"
    31  					],
    32  					"locations": [
    33  						{
    34  							"line": 10,
    35  							"column": 4
    36  						}
    37  					]
    38  				}
    39  			]
    40  		}`)
    41  	})
    42  	client := graphql.NewClient("/graphql", &http.Client{Transport: localRoundTripper{handler: mux}})
    43  
    44  	var q struct {
    45  		Node1 *struct {
    46  			ID graphql.ID
    47  		} `graphql:"node1: node(id: \"MDEyOklzc3VlQ29tbWVudDE2OTQwNzk0Ng==\")"`
    48  		Node2 *struct {
    49  			ID graphql.ID
    50  		} `graphql:"node2: node(id: \"NotExist\")"`
    51  	}
    52  	err := client.Query(context.Background(), &q, nil)
    53  	if err == nil {
    54  		t.Fatal("got error: nil, want: non-nil")
    55  	}
    56  	if got, want := err.Error(), "Could not resolve to a node with the global id of 'NotExist'"; got != want {
    57  		t.Errorf("got error: %v, want: %v", got, want)
    58  	}
    59  	if q.Node1 == nil || q.Node1.ID != "MDEyOklzc3VlQ29tbWVudDE2OTQwNzk0Ng==" {
    60  		t.Errorf("got wrong q.Node1: %v", q.Node1)
    61  	}
    62  	if q.Node2 != nil {
    63  		t.Errorf("got non-nil q.Node2: %v, want: nil", *q.Node2)
    64  	}
    65  }
    66  
    67  func TestClient_Query_noDataWithErrorResponse(t *testing.T) {
    68  	mux := http.NewServeMux()
    69  	mux.HandleFunc("/graphql", func(w http.ResponseWriter, req *http.Request) {
    70  		w.Header().Set("Content-Type", "application/json")
    71  		mustWrite(w, `{
    72  			"errors": [
    73  				{
    74  					"message": "Field 'user' is missing required arguments: login",
    75  					"locations": [
    76  						{
    77  							"line": 7,
    78  							"column": 3
    79  						}
    80  					]
    81  				}
    82  			]
    83  		}`)
    84  	})
    85  	client := graphql.NewClient("/graphql", &http.Client{Transport: localRoundTripper{handler: mux}})
    86  
    87  	var q struct {
    88  		User struct {
    89  			Name graphql.String
    90  		}
    91  	}
    92  	err := client.Query(context.Background(), &q, nil)
    93  	if err == nil {
    94  		t.Fatal("got error: nil, want: non-nil")
    95  	}
    96  	if got, want := err.Error(), "Field 'user' is missing required arguments: login"; got != want {
    97  		t.Errorf("got error: %v, want: %v", got, want)
    98  	}
    99  	if q.User.Name != "" {
   100  		t.Errorf("got non-empty q.User.Name: %v", q.User.Name)
   101  	}
   102  }
   103  
   104  func TestClient_Query_errorStatusCode(t *testing.T) {
   105  	mux := http.NewServeMux()
   106  	mux.HandleFunc("/graphql", func(w http.ResponseWriter, req *http.Request) {
   107  		http.Error(w, "important message", http.StatusInternalServerError)
   108  	})
   109  	client := graphql.NewClient("/graphql", &http.Client{Transport: localRoundTripper{handler: mux}})
   110  
   111  	var q struct {
   112  		User struct {
   113  			Name graphql.String
   114  		}
   115  	}
   116  	err := client.Query(context.Background(), &q, nil)
   117  	if err == nil {
   118  		t.Fatal("got error: nil, want: non-nil")
   119  	}
   120  	if got, want := err.Error(), `non-200 OK status code: 500 Internal Server Error body: "important message\n"`; got != want {
   121  		t.Errorf("got error: %v, want: %v", got, want)
   122  	}
   123  	if q.User.Name != "" {
   124  		t.Errorf("got non-empty q.User.Name: %v", q.User.Name)
   125  	}
   126  }
   127  
   128  // Test that an empty (but non-nil) variables map is
   129  // handled no differently than a nil variables map.
   130  func TestClient_Query_emptyVariables(t *testing.T) {
   131  	mux := http.NewServeMux()
   132  	mux.HandleFunc("/graphql", func(w http.ResponseWriter, req *http.Request) {
   133  		body := mustRead(req.Body)
   134  		if got, want := body, `{"query":"{user{name}}"}`+"\n"; got != want {
   135  			t.Errorf("got body: %v, want %v", got, want)
   136  		}
   137  		w.Header().Set("Content-Type", "application/json")
   138  		mustWrite(w, `{"data": {"user": {"name": "Gopher"}}}`)
   139  	})
   140  	client := graphql.NewClient("/graphql", &http.Client{Transport: localRoundTripper{handler: mux}})
   141  
   142  	var q struct {
   143  		User struct {
   144  			Name string
   145  		}
   146  	}
   147  	err := client.Query(context.Background(), &q, map[string]interface{}{})
   148  	if err != nil {
   149  		t.Fatal(err)
   150  	}
   151  	if got, want := q.User.Name, "Gopher"; got != want {
   152  		t.Errorf("got q.User.Name: %q, want: %q", got, want)
   153  	}
   154  }
   155  
   156  // localRoundTripper is an http.RoundTripper that executes HTTP transactions
   157  // by using handler directly, instead of going over an HTTP connection.
   158  type localRoundTripper struct {
   159  	handler http.Handler
   160  }
   161  
   162  func (l localRoundTripper) RoundTrip(req *http.Request) (*http.Response, error) {
   163  	w := httptest.NewRecorder()
   164  	l.handler.ServeHTTP(w, req)
   165  	return w.Result(), nil
   166  }
   167  
   168  func mustRead(r io.Reader) string {
   169  	b, err := ioutil.ReadAll(r)
   170  	if err != nil {
   171  		panic(err)
   172  	}
   173  	return string(b)
   174  }
   175  
   176  func mustWrite(w io.Writer, s string) {
   177  	_, err := io.WriteString(w, s)
   178  	if err != nil {
   179  		panic(err)
   180  	}
   181  }
   182  

View as plain text