...

Source file src/github.com/google/go-github/v55/github/pulls_test.go

Documentation: github.com/google/go-github/v55/github

     1  // Copyright 2013 The go-github AUTHORS. All rights reserved.
     2  //
     3  // Use of this source code is governed by a BSD-style
     4  // license that can be found in the LICENSE file.
     5  
     6  package github
     7  
     8  import (
     9  	"context"
    10  	"encoding/json"
    11  	"fmt"
    12  	"io"
    13  	"net/http"
    14  	"strings"
    15  	"testing"
    16  
    17  	"github.com/google/go-cmp/cmp"
    18  )
    19  
    20  func TestPullRequestsService_List(t *testing.T) {
    21  	client, mux, _, teardown := setup()
    22  	defer teardown()
    23  
    24  	mux.HandleFunc("/repos/o/r/pulls", func(w http.ResponseWriter, r *http.Request) {
    25  		testMethod(t, r, "GET")
    26  		testFormValues(t, r, values{
    27  			"state":     "closed",
    28  			"head":      "h",
    29  			"base":      "b",
    30  			"sort":      "created",
    31  			"direction": "desc",
    32  			"page":      "2",
    33  		})
    34  		fmt.Fprint(w, `[{"number":1}]`)
    35  	})
    36  
    37  	opts := &PullRequestListOptions{"closed", "h", "b", "created", "desc", ListOptions{Page: 2}}
    38  	ctx := context.Background()
    39  	pulls, _, err := client.PullRequests.List(ctx, "o", "r", opts)
    40  	if err != nil {
    41  		t.Errorf("PullRequests.List returned error: %v", err)
    42  	}
    43  
    44  	want := []*PullRequest{{Number: Int(1)}}
    45  	if !cmp.Equal(pulls, want) {
    46  		t.Errorf("PullRequests.List returned %+v, want %+v", pulls, want)
    47  	}
    48  
    49  	const methodName = "List"
    50  	testBadOptions(t, methodName, func() (err error) {
    51  		_, _, err = client.PullRequests.List(ctx, "\n", "\n", opts)
    52  		return err
    53  	})
    54  
    55  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
    56  		got, resp, err := client.PullRequests.List(ctx, "o", "r", opts)
    57  		if got != nil {
    58  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want nil", methodName, got)
    59  		}
    60  		return resp, err
    61  	})
    62  }
    63  
    64  func TestPullRequestsService_ListPullRequestsWithCommit(t *testing.T) {
    65  	client, mux, _, teardown := setup()
    66  	defer teardown()
    67  
    68  	mux.HandleFunc("/repos/o/r/commits/sha/pulls", func(w http.ResponseWriter, r *http.Request) {
    69  		testMethod(t, r, "GET")
    70  		testHeader(t, r, "Accept", mediaTypeListPullsOrBranchesForCommitPreview)
    71  		testFormValues(t, r, values{
    72  			"page": "2",
    73  		})
    74  		fmt.Fprint(w, `[{"number":1}]`)
    75  	})
    76  
    77  	opts := &ListOptions{Page: 2}
    78  	ctx := context.Background()
    79  	pulls, _, err := client.PullRequests.ListPullRequestsWithCommit(ctx, "o", "r", "sha", opts)
    80  	if err != nil {
    81  		t.Errorf("PullRequests.ListPullRequestsWithCommit returned error: %v", err)
    82  	}
    83  
    84  	want := []*PullRequest{{Number: Int(1)}}
    85  	if !cmp.Equal(pulls, want) {
    86  		t.Errorf("PullRequests.ListPullRequestsWithCommit returned %+v, want %+v", pulls, want)
    87  	}
    88  
    89  	const methodName = "ListPullRequestsWithCommit"
    90  	testBadOptions(t, methodName, func() (err error) {
    91  		_, _, err = client.PullRequests.ListPullRequestsWithCommit(ctx, "\n", "\n", "\n", opts)
    92  		return err
    93  	})
    94  
    95  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
    96  		got, resp, err := client.PullRequests.ListPullRequestsWithCommit(ctx, "o", "r", "sha", opts)
    97  		if got != nil {
    98  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want nil", methodName, got)
    99  		}
   100  		return resp, err
   101  	})
   102  }
   103  
   104  func TestPullRequestsService_List_invalidOwner(t *testing.T) {
   105  	client, _, _, teardown := setup()
   106  	defer teardown()
   107  
   108  	ctx := context.Background()
   109  	_, _, err := client.PullRequests.List(ctx, "%", "r", nil)
   110  	testURLParseError(t, err)
   111  }
   112  
   113  func TestPullRequestsService_Get(t *testing.T) {
   114  	client, mux, _, teardown := setup()
   115  	defer teardown()
   116  
   117  	mux.HandleFunc("/repos/o/r/pulls/1", func(w http.ResponseWriter, r *http.Request) {
   118  		testMethod(t, r, "GET")
   119  		fmt.Fprint(w, `{"number":1}`)
   120  	})
   121  
   122  	ctx := context.Background()
   123  	pull, _, err := client.PullRequests.Get(ctx, "o", "r", 1)
   124  	if err != nil {
   125  		t.Errorf("PullRequests.Get returned error: %v", err)
   126  	}
   127  
   128  	want := &PullRequest{Number: Int(1)}
   129  	if !cmp.Equal(pull, want) {
   130  		t.Errorf("PullRequests.Get returned %+v, want %+v", pull, want)
   131  	}
   132  
   133  	const methodName = "Get"
   134  	testBadOptions(t, methodName, func() (err error) {
   135  		_, _, err = client.PullRequests.Get(ctx, "\n", "\n", -1)
   136  		return err
   137  	})
   138  
   139  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
   140  		got, resp, err := client.PullRequests.Get(ctx, "o", "r", 1)
   141  		if got != nil {
   142  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want nil", methodName, got)
   143  		}
   144  		return resp, err
   145  	})
   146  }
   147  
   148  func TestPullRequestsService_GetRaw_diff(t *testing.T) {
   149  	client, mux, _, teardown := setup()
   150  	defer teardown()
   151  
   152  	const rawStr = "@@diff content"
   153  
   154  	mux.HandleFunc("/repos/o/r/pulls/1", func(w http.ResponseWriter, r *http.Request) {
   155  		testMethod(t, r, "GET")
   156  		testHeader(t, r, "Accept", mediaTypeV3Diff)
   157  		fmt.Fprint(w, rawStr)
   158  	})
   159  
   160  	ctx := context.Background()
   161  	got, _, err := client.PullRequests.GetRaw(ctx, "o", "r", 1, RawOptions{Diff})
   162  	if err != nil {
   163  		t.Fatalf("PullRequests.GetRaw returned error: %v", err)
   164  	}
   165  	want := rawStr
   166  	if got != want {
   167  		t.Errorf("PullRequests.GetRaw returned %s want %s", got, want)
   168  	}
   169  
   170  	const methodName = "GetRaw"
   171  	testBadOptions(t, methodName, func() (err error) {
   172  		_, _, err = client.PullRequests.GetRaw(ctx, "\n", "\n", -1, RawOptions{Diff})
   173  		return err
   174  	})
   175  
   176  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
   177  		got, resp, err := client.PullRequests.GetRaw(ctx, "o", "r", 1, RawOptions{Diff})
   178  		if got != "" {
   179  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want nil", methodName, got)
   180  		}
   181  		return resp, err
   182  	})
   183  }
   184  
   185  func TestPullRequestsService_GetRaw_patch(t *testing.T) {
   186  	client, mux, _, teardown := setup()
   187  	defer teardown()
   188  
   189  	const rawStr = "@@patch content"
   190  
   191  	mux.HandleFunc("/repos/o/r/pulls/1", func(w http.ResponseWriter, r *http.Request) {
   192  		testMethod(t, r, "GET")
   193  		testHeader(t, r, "Accept", mediaTypeV3Patch)
   194  		fmt.Fprint(w, rawStr)
   195  	})
   196  
   197  	ctx := context.Background()
   198  	got, _, err := client.PullRequests.GetRaw(ctx, "o", "r", 1, RawOptions{Patch})
   199  	if err != nil {
   200  		t.Fatalf("PullRequests.GetRaw returned error: %v", err)
   201  	}
   202  	want := rawStr
   203  	if got != want {
   204  		t.Errorf("PullRequests.GetRaw returned %s want %s", got, want)
   205  	}
   206  }
   207  
   208  func TestPullRequestsService_GetRaw_invalid(t *testing.T) {
   209  	client, _, _, teardown := setup()
   210  	defer teardown()
   211  
   212  	ctx := context.Background()
   213  	_, _, err := client.PullRequests.GetRaw(ctx, "o", "r", 1, RawOptions{100})
   214  	if err == nil {
   215  		t.Fatal("PullRequests.GetRaw should return error")
   216  	}
   217  	if !strings.Contains(err.Error(), "unsupported raw type") {
   218  		t.Error("PullRequests.GetRaw should return unsupported raw type error")
   219  	}
   220  }
   221  
   222  func TestPullRequestsService_Get_links(t *testing.T) {
   223  	client, mux, _, teardown := setup()
   224  	defer teardown()
   225  
   226  	mux.HandleFunc("/repos/o/r/pulls/1", func(w http.ResponseWriter, r *http.Request) {
   227  		testMethod(t, r, "GET")
   228  		fmt.Fprint(w, `{
   229  			"number":1,
   230  			"_links":{
   231  				"self":{"href":"https://api.github.com/repos/octocat/Hello-World/pulls/1347"},
   232  				"html":{"href":"https://github.com/octocat/Hello-World/pull/1347"},
   233  				"issue":{"href":"https://api.github.com/repos/octocat/Hello-World/issues/1347"},
   234  				"comments":{"href":"https://api.github.com/repos/octocat/Hello-World/issues/1347/comments"},
   235  				"review_comments":{"href":"https://api.github.com/repos/octocat/Hello-World/pulls/1347/comments"},
   236  				"review_comment":{"href":"https://api.github.com/repos/octocat/Hello-World/pulls/comments{/number}"},
   237  				"commits":{"href":"https://api.github.com/repos/octocat/Hello-World/pulls/1347/commits"},
   238  				"statuses":{"href":"https://api.github.com/repos/octocat/Hello-World/statuses/6dcb09b5b57875f334f61aebed695e2e4193db5e"}
   239  				}
   240  			}`)
   241  	})
   242  
   243  	ctx := context.Background()
   244  	pull, _, err := client.PullRequests.Get(ctx, "o", "r", 1)
   245  	if err != nil {
   246  		t.Errorf("PullRequests.Get returned error: %v", err)
   247  	}
   248  
   249  	want := &PullRequest{
   250  		Number: Int(1),
   251  		Links: &PRLinks{
   252  			Self: &PRLink{
   253  				HRef: String("https://api.github.com/repos/octocat/Hello-World/pulls/1347"),
   254  			}, HTML: &PRLink{
   255  				HRef: String("https://github.com/octocat/Hello-World/pull/1347"),
   256  			}, Issue: &PRLink{
   257  				HRef: String("https://api.github.com/repos/octocat/Hello-World/issues/1347"),
   258  			}, Comments: &PRLink{
   259  				HRef: String("https://api.github.com/repos/octocat/Hello-World/issues/1347/comments"),
   260  			}, ReviewComments: &PRLink{
   261  				HRef: String("https://api.github.com/repos/octocat/Hello-World/pulls/1347/comments"),
   262  			}, ReviewComment: &PRLink{
   263  				HRef: String("https://api.github.com/repos/octocat/Hello-World/pulls/comments{/number}"),
   264  			}, Commits: &PRLink{
   265  				HRef: String("https://api.github.com/repos/octocat/Hello-World/pulls/1347/commits"),
   266  			}, Statuses: &PRLink{
   267  				HRef: String("https://api.github.com/repos/octocat/Hello-World/statuses/6dcb09b5b57875f334f61aebed695e2e4193db5e"),
   268  			},
   269  		},
   270  	}
   271  	if !cmp.Equal(pull, want) {
   272  		t.Errorf("PullRequests.Get returned %+v, want %+v", pull, want)
   273  	}
   274  }
   275  
   276  func TestPullRequestsService_Get_headAndBase(t *testing.T) {
   277  	client, mux, _, teardown := setup()
   278  	defer teardown()
   279  
   280  	mux.HandleFunc("/repos/o/r/pulls/1", func(w http.ResponseWriter, r *http.Request) {
   281  		testMethod(t, r, "GET")
   282  		fmt.Fprint(w, `{"number":1,"head":{"ref":"r2","repo":{"id":2}},"base":{"ref":"r1","repo":{"id":1}}}`)
   283  	})
   284  
   285  	ctx := context.Background()
   286  	pull, _, err := client.PullRequests.Get(ctx, "o", "r", 1)
   287  	if err != nil {
   288  		t.Errorf("PullRequests.Get returned error: %v", err)
   289  	}
   290  
   291  	want := &PullRequest{
   292  		Number: Int(1),
   293  		Head: &PullRequestBranch{
   294  			Ref:  String("r2"),
   295  			Repo: &Repository{ID: Int64(2)},
   296  		},
   297  		Base: &PullRequestBranch{
   298  			Ref:  String("r1"),
   299  			Repo: &Repository{ID: Int64(1)},
   300  		},
   301  	}
   302  	if !cmp.Equal(pull, want) {
   303  		t.Errorf("PullRequests.Get returned %+v, want %+v", pull, want)
   304  	}
   305  }
   306  
   307  func TestPullRequestsService_Get_urlFields(t *testing.T) {
   308  	client, mux, _, teardown := setup()
   309  	defer teardown()
   310  
   311  	mux.HandleFunc("/repos/o/r/pulls/1", func(w http.ResponseWriter, r *http.Request) {
   312  		testMethod(t, r, "GET")
   313  		fmt.Fprint(w, `{"number":1,
   314  			"url": "https://api.github.com/repos/octocat/Hello-World/pulls/1347",
   315  			"html_url": "https://github.com/octocat/Hello-World/pull/1347",
   316  			"issue_url": "https://api.github.com/repos/octocat/Hello-World/issues/1347",
   317  			"statuses_url": "https://api.github.com/repos/octocat/Hello-World/statuses/6dcb09b5b57875f334f61aebed695e2e4193db5e",
   318  			"diff_url": "https://github.com/octocat/Hello-World/pull/1347.diff",
   319  			"patch_url": "https://github.com/octocat/Hello-World/pull/1347.patch",
   320  			"review_comments_url": "https://api.github.com/repos/octocat/Hello-World/pulls/1347/comments",
   321  			"review_comment_url": "https://api.github.com/repos/octocat/Hello-World/pulls/comments{/number}"}`)
   322  	})
   323  
   324  	ctx := context.Background()
   325  	pull, _, err := client.PullRequests.Get(ctx, "o", "r", 1)
   326  	if err != nil {
   327  		t.Errorf("PullRequests.Get returned error: %v", err)
   328  	}
   329  
   330  	want := &PullRequest{
   331  		Number:            Int(1),
   332  		URL:               String("https://api.github.com/repos/octocat/Hello-World/pulls/1347"),
   333  		HTMLURL:           String("https://github.com/octocat/Hello-World/pull/1347"),
   334  		IssueURL:          String("https://api.github.com/repos/octocat/Hello-World/issues/1347"),
   335  		StatusesURL:       String("https://api.github.com/repos/octocat/Hello-World/statuses/6dcb09b5b57875f334f61aebed695e2e4193db5e"),
   336  		DiffURL:           String("https://github.com/octocat/Hello-World/pull/1347.diff"),
   337  		PatchURL:          String("https://github.com/octocat/Hello-World/pull/1347.patch"),
   338  		ReviewCommentsURL: String("https://api.github.com/repos/octocat/Hello-World/pulls/1347/comments"),
   339  		ReviewCommentURL:  String("https://api.github.com/repos/octocat/Hello-World/pulls/comments{/number}"),
   340  	}
   341  
   342  	if !cmp.Equal(pull, want) {
   343  		t.Errorf("PullRequests.Get returned %+v, want %+v", pull, want)
   344  	}
   345  }
   346  
   347  func TestPullRequestsService_Get_invalidOwner(t *testing.T) {
   348  	client, _, _, teardown := setup()
   349  	defer teardown()
   350  
   351  	ctx := context.Background()
   352  	_, _, err := client.PullRequests.Get(ctx, "%", "r", 1)
   353  	testURLParseError(t, err)
   354  }
   355  
   356  func TestPullRequestsService_Create(t *testing.T) {
   357  	client, mux, _, teardown := setup()
   358  	defer teardown()
   359  
   360  	input := &NewPullRequest{Title: String("t")}
   361  
   362  	mux.HandleFunc("/repos/o/r/pulls", func(w http.ResponseWriter, r *http.Request) {
   363  		v := new(NewPullRequest)
   364  		json.NewDecoder(r.Body).Decode(v)
   365  
   366  		testMethod(t, r, "POST")
   367  		if !cmp.Equal(v, input) {
   368  			t.Errorf("Request body = %+v, want %+v", v, input)
   369  		}
   370  
   371  		fmt.Fprint(w, `{"number":1}`)
   372  	})
   373  
   374  	ctx := context.Background()
   375  	pull, _, err := client.PullRequests.Create(ctx, "o", "r", input)
   376  	if err != nil {
   377  		t.Errorf("PullRequests.Create returned error: %v", err)
   378  	}
   379  
   380  	want := &PullRequest{Number: Int(1)}
   381  	if !cmp.Equal(pull, want) {
   382  		t.Errorf("PullRequests.Create returned %+v, want %+v", pull, want)
   383  	}
   384  
   385  	const methodName = "Create"
   386  	testBadOptions(t, methodName, func() (err error) {
   387  		_, _, err = client.PullRequests.Create(ctx, "\n", "\n", input)
   388  		return err
   389  	})
   390  
   391  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
   392  		got, resp, err := client.PullRequests.Create(ctx, "o", "r", input)
   393  		if got != nil {
   394  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want nil", methodName, got)
   395  		}
   396  		return resp, err
   397  	})
   398  }
   399  
   400  func TestPullRequestsService_Create_invalidOwner(t *testing.T) {
   401  	client, _, _, teardown := setup()
   402  	defer teardown()
   403  
   404  	ctx := context.Background()
   405  	_, _, err := client.PullRequests.Create(ctx, "%", "r", nil)
   406  	testURLParseError(t, err)
   407  }
   408  
   409  func TestPullRequestsService_UpdateBranch(t *testing.T) {
   410  	client, mux, _, teardown := setup()
   411  	defer teardown()
   412  
   413  	mux.HandleFunc("/repos/o/r/pulls/1/update-branch", func(w http.ResponseWriter, r *http.Request) {
   414  		testMethod(t, r, "PUT")
   415  		testHeader(t, r, "Accept", mediaTypeUpdatePullRequestBranchPreview)
   416  		fmt.Fprint(w, `
   417  			{
   418  			  "message": "Updating pull request branch.",
   419  			  "url": "https://github.com/repos/o/r/pulls/1"
   420  			}`)
   421  	})
   422  
   423  	opts := &PullRequestBranchUpdateOptions{
   424  		ExpectedHeadSHA: String("s"),
   425  	}
   426  
   427  	ctx := context.Background()
   428  	pull, _, err := client.PullRequests.UpdateBranch(ctx, "o", "r", 1, opts)
   429  	if err != nil {
   430  		t.Errorf("PullRequests.UpdateBranch returned error: %v", err)
   431  	}
   432  
   433  	want := &PullRequestBranchUpdateResponse{
   434  		Message: String("Updating pull request branch."),
   435  		URL:     String("https://github.com/repos/o/r/pulls/1"),
   436  	}
   437  
   438  	if !cmp.Equal(pull, want) {
   439  		t.Errorf("PullRequests.UpdateBranch returned %+v, want %+v", pull, want)
   440  	}
   441  
   442  	const methodName = "UpdateBranch"
   443  	testBadOptions(t, methodName, func() (err error) {
   444  		_, _, err = client.PullRequests.UpdateBranch(ctx, "\n", "\n", -1, opts)
   445  		return err
   446  	})
   447  
   448  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
   449  		got, resp, err := client.PullRequests.UpdateBranch(ctx, "o", "r", 1, opts)
   450  		if got != nil {
   451  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want nil", methodName, got)
   452  		}
   453  		return resp, err
   454  	})
   455  }
   456  
   457  func TestPullRequestsService_Edit(t *testing.T) {
   458  	client, mux, _, teardown := setup()
   459  	defer teardown()
   460  
   461  	tests := []struct {
   462  		input        *PullRequest
   463  		sendResponse string
   464  
   465  		wantUpdate string
   466  		want       *PullRequest
   467  	}{
   468  		{
   469  			input:        &PullRequest{Title: String("t")},
   470  			sendResponse: `{"number":1}`,
   471  			wantUpdate:   `{"title":"t"}`,
   472  			want:         &PullRequest{Number: Int(1)},
   473  		},
   474  		{
   475  			// base update
   476  			input:        &PullRequest{Base: &PullRequestBranch{Ref: String("master")}},
   477  			sendResponse: `{"number":1,"base":{"ref":"master"}}`,
   478  			wantUpdate:   `{"base":"master"}`,
   479  			want: &PullRequest{
   480  				Number: Int(1),
   481  				Base:   &PullRequestBranch{Ref: String("master")},
   482  			},
   483  		},
   484  	}
   485  
   486  	for i, tt := range tests {
   487  		madeRequest := false
   488  		mux.HandleFunc(fmt.Sprintf("/repos/o/r/pulls/%v", i), func(w http.ResponseWriter, r *http.Request) {
   489  			testMethod(t, r, "PATCH")
   490  			testBody(t, r, tt.wantUpdate+"\n")
   491  			io.WriteString(w, tt.sendResponse)
   492  			madeRequest = true
   493  		})
   494  
   495  		ctx := context.Background()
   496  		pull, _, err := client.PullRequests.Edit(ctx, "o", "r", i, tt.input)
   497  		if err != nil {
   498  			t.Errorf("%d: PullRequests.Edit returned error: %v", i, err)
   499  		}
   500  
   501  		if !cmp.Equal(pull, tt.want) {
   502  			t.Errorf("%d: PullRequests.Edit returned %+v, want %+v", i, pull, tt.want)
   503  		}
   504  
   505  		if !madeRequest {
   506  			t.Errorf("%d: PullRequest.Edit did not make the expected request", i)
   507  		}
   508  
   509  		const methodName = "Edit"
   510  		testBadOptions(t, methodName, func() (err error) {
   511  			_, _, err = client.PullRequests.Edit(ctx, "\n", "\n", -i, tt.input)
   512  			return err
   513  		})
   514  	}
   515  }
   516  
   517  func TestPullRequestsService_Edit_invalidOwner(t *testing.T) {
   518  	client, _, _, teardown := setup()
   519  	defer teardown()
   520  
   521  	ctx := context.Background()
   522  	_, _, err := client.PullRequests.Edit(ctx, "%", "r", 1, &PullRequest{})
   523  	testURLParseError(t, err)
   524  }
   525  
   526  func TestPullRequestsService_ListCommits(t *testing.T) {
   527  	client, mux, _, teardown := setup()
   528  	defer teardown()
   529  
   530  	mux.HandleFunc("/repos/o/r/pulls/1/commits", func(w http.ResponseWriter, r *http.Request) {
   531  		testMethod(t, r, "GET")
   532  		testFormValues(t, r, values{"page": "2"})
   533  		fmt.Fprint(w, `
   534  			[
   535  			  {
   536  			    "sha": "3",
   537  			    "parents": [
   538  			      {
   539  			        "sha": "2"
   540  			      }
   541  			    ]
   542  			  },
   543  			  {
   544  			    "sha": "2",
   545  			    "parents": [
   546  			      {
   547  			        "sha": "1"
   548  			      }
   549  			    ]
   550  			  }
   551  			]`)
   552  	})
   553  
   554  	opts := &ListOptions{Page: 2}
   555  	ctx := context.Background()
   556  	commits, _, err := client.PullRequests.ListCommits(ctx, "o", "r", 1, opts)
   557  	if err != nil {
   558  		t.Errorf("PullRequests.ListCommits returned error: %v", err)
   559  	}
   560  
   561  	want := []*RepositoryCommit{
   562  		{
   563  			SHA: String("3"),
   564  			Parents: []*Commit{
   565  				{
   566  					SHA: String("2"),
   567  				},
   568  			},
   569  		},
   570  		{
   571  			SHA: String("2"),
   572  			Parents: []*Commit{
   573  				{
   574  					SHA: String("1"),
   575  				},
   576  			},
   577  		},
   578  	}
   579  	if !cmp.Equal(commits, want) {
   580  		t.Errorf("PullRequests.ListCommits returned %+v, want %+v", commits, want)
   581  	}
   582  
   583  	const methodName = "ListCommits"
   584  	testBadOptions(t, methodName, func() (err error) {
   585  		_, _, err = client.PullRequests.ListCommits(ctx, "\n", "\n", -1, opts)
   586  		return err
   587  	})
   588  
   589  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
   590  		got, resp, err := client.PullRequests.ListCommits(ctx, "o", "r", 1, opts)
   591  		if got != nil {
   592  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want nil", methodName, got)
   593  		}
   594  		return resp, err
   595  	})
   596  }
   597  
   598  func TestPullRequestsService_ListFiles(t *testing.T) {
   599  	client, mux, _, teardown := setup()
   600  	defer teardown()
   601  
   602  	mux.HandleFunc("/repos/o/r/pulls/1/files", func(w http.ResponseWriter, r *http.Request) {
   603  		testMethod(t, r, "GET")
   604  		testFormValues(t, r, values{"page": "2"})
   605  		fmt.Fprint(w, `
   606  			[
   607  			  {
   608  			    "sha": "6dcb09b5b57875f334f61aebed695e2e4193db5e",
   609  			    "filename": "file1.txt",
   610  			    "status": "added",
   611  			    "additions": 103,
   612  			    "deletions": 21,
   613  			    "changes": 124,
   614  			    "patch": "@@ -132,7 +132,7 @@ module Test @@ -1000,7 +1000,7 @@ module Test"
   615  			  },
   616  			  {
   617  			    "sha": "f61aebed695e2e4193db5e6dcb09b5b57875f334",
   618  			    "filename": "file2.txt",
   619  			    "status": "modified",
   620  			    "additions": 5,
   621  			    "deletions": 3,
   622  			    "changes": 103,
   623  			    "patch": "@@ -132,7 +132,7 @@ module Test @@ -1000,7 +1000,7 @@ module Test"
   624  			  }
   625  			]`)
   626  	})
   627  
   628  	opts := &ListOptions{Page: 2}
   629  	ctx := context.Background()
   630  	commitFiles, _, err := client.PullRequests.ListFiles(ctx, "o", "r", 1, opts)
   631  	if err != nil {
   632  		t.Errorf("PullRequests.ListFiles returned error: %v", err)
   633  	}
   634  
   635  	want := []*CommitFile{
   636  		{
   637  			SHA:       String("6dcb09b5b57875f334f61aebed695e2e4193db5e"),
   638  			Filename:  String("file1.txt"),
   639  			Additions: Int(103),
   640  			Deletions: Int(21),
   641  			Changes:   Int(124),
   642  			Status:    String("added"),
   643  			Patch:     String("@@ -132,7 +132,7 @@ module Test @@ -1000,7 +1000,7 @@ module Test"),
   644  		},
   645  		{
   646  			SHA:       String("f61aebed695e2e4193db5e6dcb09b5b57875f334"),
   647  			Filename:  String("file2.txt"),
   648  			Additions: Int(5),
   649  			Deletions: Int(3),
   650  			Changes:   Int(103),
   651  			Status:    String("modified"),
   652  			Patch:     String("@@ -132,7 +132,7 @@ module Test @@ -1000,7 +1000,7 @@ module Test"),
   653  		},
   654  	}
   655  
   656  	if !cmp.Equal(commitFiles, want) {
   657  		t.Errorf("PullRequests.ListFiles returned %+v, want %+v", commitFiles, want)
   658  	}
   659  
   660  	const methodName = "ListFiles"
   661  	testBadOptions(t, methodName, func() (err error) {
   662  		_, _, err = client.PullRequests.ListFiles(ctx, "\n", "\n", -1, opts)
   663  		return err
   664  	})
   665  
   666  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
   667  		got, resp, err := client.PullRequests.ListFiles(ctx, "o", "r", 1, opts)
   668  		if got != nil {
   669  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want nil", methodName, got)
   670  		}
   671  		return resp, err
   672  	})
   673  }
   674  
   675  func TestPullRequestsService_IsMerged(t *testing.T) {
   676  	client, mux, _, teardown := setup()
   677  	defer teardown()
   678  
   679  	mux.HandleFunc("/repos/o/r/pulls/1/merge", func(w http.ResponseWriter, r *http.Request) {
   680  		testMethod(t, r, "GET")
   681  		w.WriteHeader(http.StatusNoContent)
   682  	})
   683  
   684  	ctx := context.Background()
   685  	isMerged, _, err := client.PullRequests.IsMerged(ctx, "o", "r", 1)
   686  	if err != nil {
   687  		t.Errorf("PullRequests.IsMerged returned error: %v", err)
   688  	}
   689  
   690  	want := true
   691  	if !cmp.Equal(isMerged, want) {
   692  		t.Errorf("PullRequests.IsMerged returned %+v, want %+v", isMerged, want)
   693  	}
   694  
   695  	const methodName = "IsMerged"
   696  	testBadOptions(t, methodName, func() (err error) {
   697  		_, _, err = client.PullRequests.IsMerged(ctx, "\n", "\n", -1)
   698  		return err
   699  	})
   700  
   701  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
   702  		got, resp, err := client.PullRequests.IsMerged(ctx, "o", "r", 1)
   703  		if got {
   704  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want false", methodName, got)
   705  		}
   706  		return resp, err
   707  	})
   708  }
   709  
   710  func TestPullRequestsService_Merge(t *testing.T) {
   711  	client, mux, _, teardown := setup()
   712  	defer teardown()
   713  
   714  	mux.HandleFunc("/repos/o/r/pulls/1/merge", func(w http.ResponseWriter, r *http.Request) {
   715  		testMethod(t, r, "PUT")
   716  		fmt.Fprint(w, `
   717  			{
   718  			  "sha": "6dcb09b5b57875f334f61aebed695e2e4193db5e",
   719  			  "merged": true,
   720  			  "message": "Pull Request successfully merged"
   721  			}`)
   722  	})
   723  
   724  	options := &PullRequestOptions{MergeMethod: "rebase"}
   725  	ctx := context.Background()
   726  	merge, _, err := client.PullRequests.Merge(ctx, "o", "r", 1, "merging pull request", options)
   727  	if err != nil {
   728  		t.Errorf("PullRequests.Merge returned error: %v", err)
   729  	}
   730  
   731  	want := &PullRequestMergeResult{
   732  		SHA:     String("6dcb09b5b57875f334f61aebed695e2e4193db5e"),
   733  		Merged:  Bool(true),
   734  		Message: String("Pull Request successfully merged"),
   735  	}
   736  	if !cmp.Equal(merge, want) {
   737  		t.Errorf("PullRequests.Merge returned %+v, want %+v", merge, want)
   738  	}
   739  
   740  	const methodName = "Merge"
   741  	testBadOptions(t, methodName, func() (err error) {
   742  		_, _, err = client.PullRequests.Merge(ctx, "\n", "\n", -1, "\n", options)
   743  		return err
   744  	})
   745  
   746  	testNewRequestAndDoFailure(t, methodName, client, func() (*Response, error) {
   747  		got, resp, err := client.PullRequests.Merge(ctx, "o", "r", 1, "merging pull request", options)
   748  		if got != nil {
   749  			t.Errorf("testNewRequestAndDoFailure %v = %#v, want nil", methodName, got)
   750  		}
   751  		return resp, err
   752  	})
   753  }
   754  
   755  // Test that different merge options produce expected PUT requests. See issue https://github.com/google/go-github/issues/500.
   756  func TestPullRequestsService_Merge_options(t *testing.T) {
   757  	client, mux, _, teardown := setup()
   758  	defer teardown()
   759  
   760  	tests := []struct {
   761  		options  *PullRequestOptions
   762  		wantBody string
   763  	}{
   764  		{
   765  			options:  nil,
   766  			wantBody: `{"commit_message":"merging pull request"}`,
   767  		},
   768  		{
   769  			options:  &PullRequestOptions{},
   770  			wantBody: `{"commit_message":"merging pull request"}`,
   771  		},
   772  		{
   773  			options:  &PullRequestOptions{MergeMethod: "rebase"},
   774  			wantBody: `{"commit_message":"merging pull request","merge_method":"rebase"}`,
   775  		},
   776  		{
   777  			options:  &PullRequestOptions{SHA: "6dcb09b5b57875f334f61aebed695e2e4193db5e"},
   778  			wantBody: `{"commit_message":"merging pull request","sha":"6dcb09b5b57875f334f61aebed695e2e4193db5e"}`,
   779  		},
   780  		{
   781  			options: &PullRequestOptions{
   782  				CommitTitle: "Extra detail",
   783  				SHA:         "6dcb09b5b57875f334f61aebed695e2e4193db5e",
   784  				MergeMethod: "squash",
   785  			},
   786  			wantBody: `{"commit_message":"merging pull request","commit_title":"Extra detail","merge_method":"squash","sha":"6dcb09b5b57875f334f61aebed695e2e4193db5e"}`,
   787  		},
   788  		{
   789  			options: &PullRequestOptions{
   790  				DontDefaultIfBlank: true,
   791  			},
   792  			wantBody: `{"commit_message":"merging pull request"}`,
   793  		},
   794  	}
   795  
   796  	for i, test := range tests {
   797  		madeRequest := false
   798  		mux.HandleFunc(fmt.Sprintf("/repos/o/r/pulls/%d/merge", i), func(w http.ResponseWriter, r *http.Request) {
   799  			testMethod(t, r, "PUT")
   800  			testBody(t, r, test.wantBody+"\n")
   801  			madeRequest = true
   802  		})
   803  		ctx := context.Background()
   804  		_, _, _ = client.PullRequests.Merge(ctx, "o", "r", i, "merging pull request", test.options)
   805  		if !madeRequest {
   806  			t.Errorf("%d: PullRequests.Merge(%#v): expected request was not made", i, test.options)
   807  		}
   808  	}
   809  }
   810  
   811  func TestPullRequestsService_Merge_Blank_Message(t *testing.T) {
   812  	client, mux, _, teardown := setup()
   813  	defer teardown()
   814  	madeRequest := false
   815  	expectedBody := ""
   816  	mux.HandleFunc("/repos/o/r/pulls/1/merge", func(w http.ResponseWriter, r *http.Request) {
   817  		testMethod(t, r, "PUT")
   818  		testBody(t, r, expectedBody+"\n")
   819  		madeRequest = true
   820  	})
   821  
   822  	ctx := context.Background()
   823  	expectedBody = `{}`
   824  	_, _, _ = client.PullRequests.Merge(ctx, "o", "r", 1, "", nil)
   825  	if !madeRequest {
   826  		t.Error("TestPullRequestsService_Merge_Blank_Message #1 did not make request")
   827  	}
   828  
   829  	madeRequest = false
   830  	opts := PullRequestOptions{
   831  		DontDefaultIfBlank: true,
   832  	}
   833  	expectedBody = `{"commit_message":""}`
   834  	_, _, _ = client.PullRequests.Merge(ctx, "o", "r", 1, "", &opts)
   835  	if !madeRequest {
   836  		t.Error("TestPullRequestsService_Merge_Blank_Message #2 did not make request")
   837  	}
   838  }
   839  
   840  func TestPullRequestMergeRequest_Marshal(t *testing.T) {
   841  	testJSONMarshal(t, &pullRequestMergeRequest{}, "{}")
   842  
   843  	u := &pullRequestMergeRequest{
   844  		CommitMessage: String("cm"),
   845  		CommitTitle:   "ct",
   846  		MergeMethod:   "mm",
   847  		SHA:           "sha",
   848  	}
   849  
   850  	want := `{
   851  		"commit_message": "cm",
   852  		"commit_title": "ct",
   853  		"merge_method": "mm",
   854  		"sha": "sha"
   855  	}`
   856  
   857  	testJSONMarshal(t, u, want)
   858  }
   859  
   860  func TestPullRequestMergeResult_Marshal(t *testing.T) {
   861  	testJSONMarshal(t, &PullRequestMergeResult{}, "{}")
   862  
   863  	u := &PullRequestMergeResult{
   864  		SHA:     String("sha"),
   865  		Merged:  Bool(false),
   866  		Message: String("msg"),
   867  	}
   868  
   869  	want := `{
   870  		"sha": "sha",
   871  		"merged": false,
   872  		"message": "msg"
   873  	}`
   874  
   875  	testJSONMarshal(t, u, want)
   876  }
   877  
   878  func TestPullRequestUpdate_Marshal(t *testing.T) {
   879  	testJSONMarshal(t, &pullRequestUpdate{}, "{}")
   880  
   881  	u := &pullRequestUpdate{
   882  		Title:               String("title"),
   883  		Body:                String("body"),
   884  		State:               String("state"),
   885  		Base:                String("base"),
   886  		MaintainerCanModify: Bool(false),
   887  	}
   888  
   889  	want := `{
   890  		"title": "title",
   891  		"body": "body",
   892  		"state": "state",
   893  		"base": "base",
   894  		"maintainer_can_modify": false
   895  	}`
   896  
   897  	testJSONMarshal(t, u, want)
   898  }
   899  
   900  func TestPullRequestBranchUpdateResponse_Marshal(t *testing.T) {
   901  	testJSONMarshal(t, &PullRequestBranchUpdateResponse{}, "{}")
   902  
   903  	u := &PullRequestBranchUpdateResponse{
   904  		Message: String("message"),
   905  		URL:     String("url"),
   906  	}
   907  
   908  	want := `{
   909  		"message": "message",
   910  		"url": "url"
   911  	}`
   912  
   913  	testJSONMarshal(t, u, want)
   914  }
   915  
   916  func TestPullRequestBranchUpdateOptions_Marshal(t *testing.T) {
   917  	testJSONMarshal(t, &PullRequestBranchUpdateOptions{}, "{}")
   918  
   919  	u := &PullRequestBranchUpdateOptions{
   920  		ExpectedHeadSHA: String("eh"),
   921  	}
   922  
   923  	want := `{
   924  		"expected_head_sha": "eh"
   925  	}`
   926  
   927  	testJSONMarshal(t, u, want)
   928  }
   929  
   930  func TestNewPullRequest_Marshal(t *testing.T) {
   931  	testJSONMarshal(t, &NewPullRequest{}, "{}")
   932  
   933  	u := &NewPullRequest{
   934  		Title:               String("eh"),
   935  		Head:                String("eh"),
   936  		HeadRepo:            String("eh"),
   937  		Base:                String("eh"),
   938  		Body:                String("eh"),
   939  		Issue:               Int(1),
   940  		MaintainerCanModify: Bool(false),
   941  		Draft:               Bool(false),
   942  	}
   943  
   944  	want := `{
   945  		"title": "eh",
   946  		"head": "eh",
   947  		"head_repo": "eh",
   948  		"base": "eh",
   949  		"body": "eh",
   950  		"issue": 1,
   951  		"maintainer_can_modify": false,
   952  		"draft": false
   953  	}`
   954  
   955  	testJSONMarshal(t, u, want)
   956  }
   957  
   958  func TestPullRequestBranch_Marshal(t *testing.T) {
   959  	testJSONMarshal(t, &PullRequestBranch{}, "{}")
   960  
   961  	u := &PullRequestBranch{
   962  		Label: String("label"),
   963  		Ref:   String("ref"),
   964  		SHA:   String("sha"),
   965  		Repo:  &Repository{ID: Int64(1)},
   966  		User: &User{
   967  			Login:           String("l"),
   968  			ID:              Int64(1),
   969  			URL:             String("u"),
   970  			AvatarURL:       String("a"),
   971  			GravatarID:      String("g"),
   972  			Name:            String("n"),
   973  			Company:         String("c"),
   974  			Blog:            String("b"),
   975  			Location:        String("l"),
   976  			Email:           String("e"),
   977  			Hireable:        Bool(true),
   978  			Bio:             String("b"),
   979  			TwitterUsername: String("t"),
   980  			PublicRepos:     Int(1),
   981  			Followers:       Int(1),
   982  			Following:       Int(1),
   983  			CreatedAt:       &Timestamp{referenceTime},
   984  			SuspendedAt:     &Timestamp{referenceTime},
   985  		},
   986  	}
   987  
   988  	want := `{
   989  		"label": "label",
   990  		"ref": "ref",
   991  		"sha": "sha",
   992  		"repo": {
   993  			"id": 1
   994  		},
   995  		"user": {
   996  			"login": "l",
   997  			"id": 1,
   998  			"avatar_url": "a",
   999  			"gravatar_id": "g",
  1000  			"name": "n",
  1001  			"company": "c",
  1002  			"blog": "b",
  1003  			"location": "l",
  1004  			"email": "e",
  1005  			"hireable": true,
  1006  			"bio": "b",
  1007  			"twitter_username": "t",
  1008  			"public_repos": 1,
  1009  			"followers": 1,
  1010  			"following": 1,
  1011  			"created_at": ` + referenceTimeStr + `,
  1012  			"suspended_at": ` + referenceTimeStr + `,
  1013  			"url": "u"
  1014  		}
  1015  	}`
  1016  
  1017  	testJSONMarshal(t, u, want)
  1018  }
  1019  
  1020  func TestPRLink_Marshal(t *testing.T) {
  1021  	testJSONMarshal(t, &PRLink{}, "{}")
  1022  
  1023  	u := &PRLink{
  1024  		HRef: String("href"),
  1025  	}
  1026  
  1027  	want := `{
  1028  		"href": "href"
  1029  	}`
  1030  
  1031  	testJSONMarshal(t, u, want)
  1032  }
  1033  
  1034  func TestPRLinks_Marshal(t *testing.T) {
  1035  	testJSONMarshal(t, &PRLinks{}, "{}")
  1036  
  1037  	u := &PRLinks{
  1038  		Self: &PRLink{
  1039  			HRef: String("href"),
  1040  		},
  1041  		HTML: &PRLink{
  1042  			HRef: String("href"),
  1043  		},
  1044  		Issue: &PRLink{
  1045  			HRef: String("href"),
  1046  		},
  1047  		Comments: &PRLink{
  1048  			HRef: String("href"),
  1049  		},
  1050  		ReviewComments: &PRLink{
  1051  			HRef: String("href"),
  1052  		},
  1053  		ReviewComment: &PRLink{
  1054  			HRef: String("href"),
  1055  		},
  1056  		Commits: &PRLink{
  1057  			HRef: String("href"),
  1058  		},
  1059  		Statuses: &PRLink{
  1060  			HRef: String("href"),
  1061  		},
  1062  	}
  1063  
  1064  	want := `{
  1065  		"self": {
  1066  			"href": "href"
  1067  		},
  1068  		"html": {
  1069  			"href": "href"
  1070  		},
  1071  		"issue": {
  1072  			"href": "href"
  1073  		},
  1074  		"comments": {
  1075  			"href": "href"
  1076  		},
  1077  		"review_comments": {
  1078  			"href": "href"
  1079  		},
  1080  		"review_comment": {
  1081  			"href": "href"
  1082  		},
  1083  		"commits": {
  1084  			"href": "href"
  1085  		},
  1086  		"statuses": {
  1087  			"href": "href"
  1088  		}
  1089  	}`
  1090  
  1091  	testJSONMarshal(t, u, want)
  1092  }
  1093  
  1094  func TestPullRequestAutoMerge_Marshal(t *testing.T) {
  1095  	testJSONMarshal(t, &PullRequestAutoMerge{}, "{}")
  1096  
  1097  	u := &PullRequestAutoMerge{
  1098  		EnabledBy: &User{
  1099  			Login:           String("l"),
  1100  			ID:              Int64(1),
  1101  			URL:             String("u"),
  1102  			AvatarURL:       String("a"),
  1103  			GravatarID:      String("g"),
  1104  			Name:            String("n"),
  1105  			Company:         String("c"),
  1106  			Blog:            String("b"),
  1107  			Location:        String("l"),
  1108  			Email:           String("e"),
  1109  			Hireable:        Bool(true),
  1110  			Bio:             String("b"),
  1111  			TwitterUsername: String("t"),
  1112  			PublicRepos:     Int(1),
  1113  			Followers:       Int(1),
  1114  			Following:       Int(1),
  1115  			CreatedAt:       &Timestamp{referenceTime},
  1116  			SuspendedAt:     &Timestamp{referenceTime},
  1117  		},
  1118  		MergeMethod:   String("mm"),
  1119  		CommitTitle:   String("ct"),
  1120  		CommitMessage: String("cm"),
  1121  	}
  1122  
  1123  	want := `{
  1124  		"enabled_by": {
  1125  			"login": "l",
  1126  			"id": 1,
  1127  			"avatar_url": "a",
  1128  			"gravatar_id": "g",
  1129  			"name": "n",
  1130  			"company": "c",
  1131  			"blog": "b",
  1132  			"location": "l",
  1133  			"email": "e",
  1134  			"hireable": true,
  1135  			"bio": "b",
  1136  			"twitter_username": "t",
  1137  			"public_repos": 1,
  1138  			"followers": 1,
  1139  			"following": 1,
  1140  			"created_at": ` + referenceTimeStr + `,
  1141  			"suspended_at": ` + referenceTimeStr + `,
  1142  			"url": "u"
  1143  		},
  1144  		"merge_method": "mm",
  1145  		"commit_title": "ct",
  1146  		"commit_message": "cm"
  1147  	}`
  1148  
  1149  	testJSONMarshal(t, u, want)
  1150  }
  1151  
  1152  func TestPullRequest_Marshal(t *testing.T) {
  1153  	testJSONMarshal(t, &PullRequest{}, "{}")
  1154  
  1155  	u := &PullRequest{
  1156  		ID:        Int64(1),
  1157  		Number:    Int(1),
  1158  		State:     String("state"),
  1159  		Locked:    Bool(false),
  1160  		Title:     String("title"),
  1161  		Body:      String("body"),
  1162  		CreatedAt: &Timestamp{referenceTime},
  1163  		UpdatedAt: &Timestamp{referenceTime},
  1164  		ClosedAt:  &Timestamp{referenceTime},
  1165  		MergedAt:  &Timestamp{referenceTime},
  1166  		Labels:    []*Label{{ID: Int64(1)}},
  1167  		User: &User{
  1168  			Login:           String("l"),
  1169  			ID:              Int64(1),
  1170  			URL:             String("u"),
  1171  			AvatarURL:       String("a"),
  1172  			GravatarID:      String("g"),
  1173  			Name:            String("n"),
  1174  			Company:         String("c"),
  1175  			Blog:            String("b"),
  1176  			Location:        String("l"),
  1177  			Email:           String("e"),
  1178  			Hireable:        Bool(true),
  1179  			Bio:             String("b"),
  1180  			TwitterUsername: String("t"),
  1181  			PublicRepos:     Int(1),
  1182  			Followers:       Int(1),
  1183  			Following:       Int(1),
  1184  			CreatedAt:       &Timestamp{referenceTime},
  1185  			SuspendedAt:     &Timestamp{referenceTime},
  1186  		},
  1187  		Draft:          Bool(false),
  1188  		Merged:         Bool(false),
  1189  		Mergeable:      Bool(false),
  1190  		MergeableState: String("ms"),
  1191  		MergedBy: &User{
  1192  			Login:           String("l"),
  1193  			ID:              Int64(1),
  1194  			URL:             String("u"),
  1195  			AvatarURL:       String("a"),
  1196  			GravatarID:      String("g"),
  1197  			Name:            String("n"),
  1198  			Company:         String("c"),
  1199  			Blog:            String("b"),
  1200  			Location:        String("l"),
  1201  			Email:           String("e"),
  1202  			Hireable:        Bool(true),
  1203  			Bio:             String("b"),
  1204  			TwitterUsername: String("t"),
  1205  			PublicRepos:     Int(1),
  1206  			Followers:       Int(1),
  1207  			Following:       Int(1),
  1208  			CreatedAt:       &Timestamp{referenceTime},
  1209  			SuspendedAt:     &Timestamp{referenceTime},
  1210  		},
  1211  		MergeCommitSHA:    String("mcs"),
  1212  		Rebaseable:        Bool(false),
  1213  		Comments:          Int(1),
  1214  		Commits:           Int(1),
  1215  		Additions:         Int(1),
  1216  		Deletions:         Int(1),
  1217  		ChangedFiles:      Int(1),
  1218  		URL:               String("url"),
  1219  		HTMLURL:           String("hurl"),
  1220  		IssueURL:          String("iurl"),
  1221  		StatusesURL:       String("surl"),
  1222  		DiffURL:           String("durl"),
  1223  		PatchURL:          String("purl"),
  1224  		CommitsURL:        String("curl"),
  1225  		CommentsURL:       String("comurl"),
  1226  		ReviewCommentsURL: String("rcurls"),
  1227  		ReviewCommentURL:  String("rcurl"),
  1228  		ReviewComments:    Int(1),
  1229  		Assignee: &User{
  1230  			Login:           String("l"),
  1231  			ID:              Int64(1),
  1232  			URL:             String("u"),
  1233  			AvatarURL:       String("a"),
  1234  			GravatarID:      String("g"),
  1235  			Name:            String("n"),
  1236  			Company:         String("c"),
  1237  			Blog:            String("b"),
  1238  			Location:        String("l"),
  1239  			Email:           String("e"),
  1240  			Hireable:        Bool(true),
  1241  			Bio:             String("b"),
  1242  			TwitterUsername: String("t"),
  1243  			PublicRepos:     Int(1),
  1244  			Followers:       Int(1),
  1245  			Following:       Int(1),
  1246  			CreatedAt:       &Timestamp{referenceTime},
  1247  			SuspendedAt:     &Timestamp{referenceTime},
  1248  		},
  1249  		Assignees: []*User{
  1250  			{
  1251  				Login:           String("l"),
  1252  				ID:              Int64(1),
  1253  				URL:             String("u"),
  1254  				AvatarURL:       String("a"),
  1255  				GravatarID:      String("g"),
  1256  				Name:            String("n"),
  1257  				Company:         String("c"),
  1258  				Blog:            String("b"),
  1259  				Location:        String("l"),
  1260  				Email:           String("e"),
  1261  				Hireable:        Bool(true),
  1262  				Bio:             String("b"),
  1263  				TwitterUsername: String("t"),
  1264  				PublicRepos:     Int(1),
  1265  				Followers:       Int(1),
  1266  				Following:       Int(1),
  1267  				CreatedAt:       &Timestamp{referenceTime},
  1268  				SuspendedAt:     &Timestamp{referenceTime},
  1269  			},
  1270  		},
  1271  		Milestone:           &Milestone{ID: Int64(1)},
  1272  		MaintainerCanModify: Bool(true),
  1273  		AuthorAssociation:   String("aa"),
  1274  		NodeID:              String("nid"),
  1275  		RequestedReviewers: []*User{
  1276  			{
  1277  				Login:           String("l"),
  1278  				ID:              Int64(1),
  1279  				URL:             String("u"),
  1280  				AvatarURL:       String("a"),
  1281  				GravatarID:      String("g"),
  1282  				Name:            String("n"),
  1283  				Company:         String("c"),
  1284  				Blog:            String("b"),
  1285  				Location:        String("l"),
  1286  				Email:           String("e"),
  1287  				Hireable:        Bool(true),
  1288  				Bio:             String("b"),
  1289  				TwitterUsername: String("t"),
  1290  				PublicRepos:     Int(1),
  1291  				Followers:       Int(1),
  1292  				Following:       Int(1),
  1293  				CreatedAt:       &Timestamp{referenceTime},
  1294  				SuspendedAt:     &Timestamp{referenceTime},
  1295  			},
  1296  		},
  1297  		AutoMerge: &PullRequestAutoMerge{
  1298  			EnabledBy: &User{
  1299  				Login:           String("l"),
  1300  				ID:              Int64(1),
  1301  				URL:             String("u"),
  1302  				AvatarURL:       String("a"),
  1303  				GravatarID:      String("g"),
  1304  				Name:            String("n"),
  1305  				Company:         String("c"),
  1306  				Blog:            String("b"),
  1307  				Location:        String("l"),
  1308  				Email:           String("e"),
  1309  				Hireable:        Bool(true),
  1310  				Bio:             String("b"),
  1311  				TwitterUsername: String("t"),
  1312  				PublicRepos:     Int(1),
  1313  				Followers:       Int(1),
  1314  				Following:       Int(1),
  1315  				CreatedAt:       &Timestamp{referenceTime},
  1316  				SuspendedAt:     &Timestamp{referenceTime},
  1317  			},
  1318  			MergeMethod:   String("mm"),
  1319  			CommitTitle:   String("ct"),
  1320  			CommitMessage: String("cm"),
  1321  		},
  1322  		RequestedTeams: []*Team{{ID: Int64(1)}},
  1323  		Links: &PRLinks{
  1324  			Self: &PRLink{
  1325  				HRef: String("href"),
  1326  			},
  1327  			HTML: &PRLink{
  1328  				HRef: String("href"),
  1329  			},
  1330  			Issue: &PRLink{
  1331  				HRef: String("href"),
  1332  			},
  1333  			Comments: &PRLink{
  1334  				HRef: String("href"),
  1335  			},
  1336  			ReviewComments: &PRLink{
  1337  				HRef: String("href"),
  1338  			},
  1339  			ReviewComment: &PRLink{
  1340  				HRef: String("href"),
  1341  			},
  1342  			Commits: &PRLink{
  1343  				HRef: String("href"),
  1344  			},
  1345  			Statuses: &PRLink{
  1346  				HRef: String("href"),
  1347  			},
  1348  		},
  1349  		Head: &PullRequestBranch{
  1350  			Ref:  String("r2"),
  1351  			Repo: &Repository{ID: Int64(2)},
  1352  		},
  1353  		Base: &PullRequestBranch{
  1354  			Ref:  String("r2"),
  1355  			Repo: &Repository{ID: Int64(2)},
  1356  		},
  1357  		ActiveLockReason: String("alr"),
  1358  	}
  1359  
  1360  	want := `{
  1361  		"id": 1,
  1362  		"number": 1,
  1363  		"state": "state",
  1364  		"locked": false,
  1365  		"title": "title",
  1366  		"body": "body",
  1367  		"created_at": ` + referenceTimeStr + `,
  1368  		"updated_at": ` + referenceTimeStr + `,
  1369  		"closed_at": ` + referenceTimeStr + `,
  1370  		"merged_at": ` + referenceTimeStr + `,
  1371  		"labels": [
  1372  			{
  1373  				"id": 1
  1374  			}
  1375  		],
  1376  		"user": {
  1377  			"login": "l",
  1378  			"id": 1,
  1379  			"avatar_url": "a",
  1380  			"gravatar_id": "g",
  1381  			"name": "n",
  1382  			"company": "c",
  1383  			"blog": "b",
  1384  			"location": "l",
  1385  			"email": "e",
  1386  			"hireable": true,
  1387  			"bio": "b",
  1388  			"twitter_username": "t",
  1389  			"public_repos": 1,
  1390  			"followers": 1,
  1391  			"following": 1,
  1392  			"created_at": ` + referenceTimeStr + `,
  1393  			"suspended_at": ` + referenceTimeStr + `,
  1394  			"url": "u"
  1395  		},
  1396  		"draft": false,
  1397  		"merged": false,
  1398  		"mergeable": false,
  1399  		"mergeable_state": "ms",
  1400  		"merged_by": {
  1401  			"login": "l",
  1402  			"id": 1,
  1403  			"avatar_url": "a",
  1404  			"gravatar_id": "g",
  1405  			"name": "n",
  1406  			"company": "c",
  1407  			"blog": "b",
  1408  			"location": "l",
  1409  			"email": "e",
  1410  			"hireable": true,
  1411  			"bio": "b",
  1412  			"twitter_username": "t",
  1413  			"public_repos": 1,
  1414  			"followers": 1,
  1415  			"following": 1,
  1416  			"created_at": ` + referenceTimeStr + `,
  1417  			"suspended_at": ` + referenceTimeStr + `,
  1418  			"url": "u"
  1419  		},
  1420  		"merge_commit_sha": "mcs",
  1421  		"rebaseable": false,
  1422  		"comments": 1,
  1423  		"commits": 1,
  1424  		"additions": 1,
  1425  		"deletions": 1,
  1426  		"changed_files": 1,
  1427  		"url": "url",
  1428  		"html_url": "hurl",
  1429  		"issue_url": "iurl",
  1430  		"statuses_url": "surl",
  1431  		"diff_url": "durl",
  1432  		"patch_url": "purl",
  1433  		"commits_url": "curl",
  1434  		"comments_url": "comurl",
  1435  		"review_comments_url": "rcurls",
  1436  		"review_comment_url": "rcurl",
  1437  		"review_comments": 1,
  1438  		"assignee": {
  1439  			"login": "l",
  1440  			"id": 1,
  1441  			"avatar_url": "a",
  1442  			"gravatar_id": "g",
  1443  			"name": "n",
  1444  			"company": "c",
  1445  			"blog": "b",
  1446  			"location": "l",
  1447  			"email": "e",
  1448  			"hireable": true,
  1449  			"bio": "b",
  1450  			"twitter_username": "t",
  1451  			"public_repos": 1,
  1452  			"followers": 1,
  1453  			"following": 1,
  1454  			"created_at": ` + referenceTimeStr + `,
  1455  			"suspended_at": ` + referenceTimeStr + `,
  1456  			"url": "u"
  1457  		},
  1458  		"assignees": [
  1459  			{
  1460  				"login": "l",
  1461  				"id": 1,
  1462  				"avatar_url": "a",
  1463  				"gravatar_id": "g",
  1464  				"name": "n",
  1465  				"company": "c",
  1466  				"blog": "b",
  1467  				"location": "l",
  1468  				"email": "e",
  1469  				"hireable": true,
  1470  				"bio": "b",
  1471  				"twitter_username": "t",
  1472  				"public_repos": 1,
  1473  				"followers": 1,
  1474  				"following": 1,
  1475  				"created_at": ` + referenceTimeStr + `,
  1476  				"suspended_at": ` + referenceTimeStr + `,
  1477  				"url": "u"
  1478  			}
  1479  		],
  1480  		"milestone": {
  1481  			"id": 1
  1482  		},
  1483  		"maintainer_can_modify": true,
  1484  		"author_association": "aa",
  1485  		"node_id": "nid",
  1486  		"requested_reviewers": [
  1487  			{
  1488  				"login": "l",
  1489  				"id": 1,
  1490  				"avatar_url": "a",
  1491  				"gravatar_id": "g",
  1492  				"name": "n",
  1493  				"company": "c",
  1494  				"blog": "b",
  1495  				"location": "l",
  1496  				"email": "e",
  1497  				"hireable": true,
  1498  				"bio": "b",
  1499  				"twitter_username": "t",
  1500  				"public_repos": 1,
  1501  				"followers": 1,
  1502  				"following": 1,
  1503  				"created_at": ` + referenceTimeStr + `,
  1504  				"suspended_at": ` + referenceTimeStr + `,
  1505  				"url": "u"
  1506  			}
  1507  		],
  1508  		"auto_merge": {
  1509  			"enabled_by": {
  1510  				"login": "l",
  1511  				"id": 1,
  1512  				"avatar_url": "a",
  1513  				"gravatar_id": "g",
  1514  				"name": "n",
  1515  				"company": "c",
  1516  				"blog": "b",
  1517  				"location": "l",
  1518  				"email": "e",
  1519  				"hireable": true,
  1520  				"bio": "b",
  1521  				"twitter_username": "t",
  1522  				"public_repos": 1,
  1523  				"followers": 1,
  1524  				"following": 1,
  1525  				"created_at": ` + referenceTimeStr + `,
  1526  				"suspended_at": ` + referenceTimeStr + `,
  1527  				"url": "u"
  1528  			},
  1529  			"merge_method": "mm",
  1530  			"commit_title": "ct",
  1531  			"commit_message": "cm"
  1532  		},
  1533  		"requested_teams": [
  1534  			{
  1535  				"id": 1
  1536  			}
  1537  		],
  1538  		"_links": {
  1539  			"self": {
  1540  				"href": "href"
  1541  			},
  1542  			"html": {
  1543  				"href": "href"
  1544  			},
  1545  			"issue": {
  1546  				"href": "href"
  1547  			},
  1548  			"comments": {
  1549  				"href": "href"
  1550  			},
  1551  			"review_comments": {
  1552  				"href": "href"
  1553  			},
  1554  			"review_comment": {
  1555  				"href": "href"
  1556  			},
  1557  			"commits": {
  1558  				"href": "href"
  1559  			},
  1560  			"statuses": {
  1561  				"href": "href"
  1562  			}
  1563  		},
  1564  		"head": {
  1565  			"ref": "r2",
  1566  			"repo": {
  1567  				"id": 2
  1568  			}
  1569  		},
  1570  		"base": {
  1571  			"ref": "r2",
  1572  			"repo": {
  1573  				"id": 2
  1574  			}
  1575  		},
  1576  		"active_lock_reason": "alr"
  1577  	}`
  1578  
  1579  	testJSONMarshal(t, u, want)
  1580  }
  1581  

View as plain text