Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for the read half of the PR Review API #139

Merged
merged 18 commits into from
May 23, 2017

Conversation

mscharley
Copy link
Contributor

Just putting this up to solicit some initial feedback before I get too deep in the rest of this API.

Fixes GH-133

@mscharley mscharley changed the title Initial pass to add the read-only PR review API. Add support for the PR Review API May 19, 2017
Copy link
Contributor

@BenFradet BenFradet left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks like a good start 👍

@juanpedromoreno
Copy link
Member

@mscharley Indeed, it's looking nice 👏

pull_request_url: String)

sealed abstract class PullRequestReviewState(val value: String)
case class PRRStateApprove() extends PullRequestReviewState("APPROVE")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We could change these case classes by case objects, what do you think?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point, I'll do that.

@mscharley
Copy link
Contributor Author

This is ready for final review now.

@mscharley mscharley changed the title Add support for the PR Review API Add support for the read half of the PR Review API May 22, 2017
@mscharley
Copy link
Contributor Author

I've limited the scope of this PR to the read-only portion of the review API as this is all I need right now, I'm on a deadline, and the write half needs some special logic around draft reviews.

Copy link
Member

@juanpedromoreno juanpedromoreno left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks great, I've added some minor comments though, that would need to be addressed. Thanks!

@@ -128,6 +130,57 @@ createPullRequestIssue.exec[cats.Id, HttpResponse[String]]() match {

See [the API doc](https://developer.github.com/v3/pulls/#create-a-pull-request) for full reference.

## List pull requests
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

List reviews?


## Get an individual review

You can list the reviews for a pull request using `listReviews`, it takes as arguments:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

-You can list the reviews for a pull request using `listReviews`
+You can get an individual review for a pull request using `getReview`

user = user,
body = validCommentBody,
commit_id = validCommitSha,
state = PRRStateCommented(),
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This won't compile since PRRStateCommented is now a case object.

Copy link
Contributor

@BenFradet BenFradet left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, I have a few minors regarding doc and tests


As an example, if we wanted to see all the reviews for pull request 139 of `47deg/github4s`:

```scala
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You can use tut:silent instead of scala for code examples that do not create stuff.
That way your examples will be compiled when you run makeMicrosite.


As an example, if we wanted to see review 39355613 for pull request 139 of `47deg/github4s`:

```scala
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same

The `result` on the right is the matching [PullRequestReview][pr-scala].


See [the API doc](https://developer.github.com/v3/pulls/reviews/#list-reviews-on-a-pull-request) for full reference.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We usually have a link to the gh doc per endpoint, so this line should be in the # List reviews section and here the link should be changed to https://developer.github.com/v3/pulls/reviews/#get-a-single-review

@@ -128,6 +130,57 @@ createPullRequestIssue.exec[cats.Id, HttpResponse[String]]() match {

See [the API doc](https://developer.github.com/v3/pulls/#create-a-pull-request) for full reference.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since Reviews are a "sub-API" of the pull request API, we usually do subsections, so you'll end up with:

Pull request

List pull requests

...

Reviews

List reviews

Get an individual review

.withMethod("GET")
.withPath(s"/repos/$validRepoOwner/$validRepoName/pulls/$validPullRequestNumber/reviews")
.withHeader(not("Authorization")))
.respond(response.withStatusCode(unauthorizedStatusCode).withBody(unauthorizedResponse))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you're not using this endpoint in your tests, you can remove it 👍

.withPath(
s"/repos/$validRepoOwner/$validRepoName/pulls/$validPullRequestNumber/reviews/$validPullRequestReviewNumber")
.withHeader(not("Authorization")))
.respond(response.withStatusCode(unauthorizedStatusCode).withBody(unauthorizedResponse))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same

@@ -637,7 +673,7 @@ trait MockGithubApiServer extends MockServerService with FakeResponses with Test
request
.withMethod("POST")
.withPath(s"/repos/$validRepoOwner/$validRepoName/issues")
.withHeader(not("Authorization")))
.withHeader("Authorization", tokenHeader))
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Where did this come from? This should fail.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Did you sort this out in the end?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, same as above: the difference here are strictly correct but don't reflect how I actually just added a block of text, instead trying to find the way to represent that with the minimum of changes.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll double check when I get home just to be sure though.

@@ -598,29 +598,65 @@ trait MockGithubApiServer extends MockServerService with FakeResponses with Test
""".stripMargin)))
.respond(response.withStatusCode(createdStatusCode).withBody(validCreatePullRequest))

//Issues >> list
//PullRequests >> listReviews
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think I screwed something up big here.

@@ -11,6 +11,8 @@ with Github4s, you can:
- [List pull requests](#list-pull-requests)
- [List the files in a pull request](#list-the-files-in-a-pull-request)
- [Create a pull request](#create-a-pull-request)
- [List reviews](#list-reviews)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This link won't work since you changed your heading to "List pull request reviews"

.withPath(s"/repos/$validRepoOwner/$invalidRepoName/issues")
.withHeader(not("Authorization")))
.withHeader("Authorization", tokenHeader))
.respond(response.withStatusCode(notFoundStatusCode).withBody(notFoundResponse))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmmm I think things got mixed up because Issues >> List is testing for request without auth token: https://github.com/47deg/github4s/blob/master/github4s/jvm/src/test/scala/github4s/unit/ApiSpec.scala#L778-L782

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh yeah, there's a corresponding add for >>Issues >> Create lower down. Derp. Sometimes I hate how diffs work.


case class PullRequestReview(
id: Int,
user: User,
Copy link
Member

@juanpedromoreno juanpedromoreno May 22, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This field should be Option[User]. Recently, we've discovered when one user is removed, it's replaced by https://github.com/ghost (the Github API will return null).

Fix for the rest of the Apis:
#144

it should "return error when an invalid repo name is passed" in {
val response =
Github(accessToken).pullRequests
.getReview(validRepoOwner, validRepoName, validPullRequestNumber, validPullRequestReviewNumber)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't be in this way?

-.getReview(validRepoOwner, validRepoName, validPullRequestNumber, validPullRequestReviewNumber)
+.getReview(validRepoOwner, invalidRepoName, validPullRequestNumber, validPullRequestReviewNumber)

The test is failing since it returns success.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Doh. I had some failing tests from outside what I was working on, even with a Github key so it was hard to see 'everything green'. Thanks for catching this.

Copy link
Contributor

@BenFradet BenFradet left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

doc nits 👍

139)

listReviews.exec[cats.Id, HttpResponse[String]]() match {
case Left(e) => println("Something went wrong: s{e.getMessage}")
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should be:

case Left(e) => println(s"Something went wrong: ${e.getMessage}")

39355613)

review.exec[cats.Id, HttpResponse[String]]() match {
case Left(e) => println("Something went wrong: s{e.getMessage}")
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same

@juanpedromoreno
Copy link
Member

Please, also see this one #139 (review) ;)

Copy link
Member

@juanpedromoreno juanpedromoreno left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For changes added in commit abb7a87, it's needed to add the s interpolator at the beginning ;)

@@ -49,7 +49,7 @@ val prFilters = List(PRFilterOpen, PRFilterSortPopularity)
val listPullRequests = Github(accessToken).pullRequests.list("scala", "scala", prFilters)

listPullRequests.exec[cats.Id, HttpResponse[String]]() match {
case Left(e) => println("Something went wrong: s{e.getMessage}")
case Left(e) => println("Something went wrong: ${e.getMessage}")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

-case Left(e) => println("Something went wrong: ${e.getMessage}")
+case Left(e) => println(s"Something went wrong: ${e.getMessage}")

The s interpolator is needed at the beginning of the String :P

@@ -71,7 +71,7 @@ To list the files for a pull request:
val listPullRequestFiles = Github(accessToken).pullRequests.listFiles("47deg", "github4s", 102)

listPullRequestFiles.exec[cats.Id, HttpResponse[String]]() match {
case Left(e) => println("Something went wrong: s{e.getMessage}")
case Left(e) => println("Something went wrong: ${e.getMessage}")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same here

@mscharley
Copy link
Contributor Author

@juanpedromoreno That's already fixed, I noticed that when I did the merge.

Copy link
Member

@juanpedromoreno juanpedromoreno left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Great job, LGTM!

giphy 4

@juanpedromoreno
Copy link
Member

juanpedromoreno commented May 22, 2017

Before merging, let's wait until final @BenFradet 's 👍 , many thanks @mscharley !

Copy link
Contributor

@BenFradet BenFradet left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A couple of nits regarding the doc and a Q regarding the tests and we're good to go 👍


## List pull request reviews

You can list the reviews for a pull request using `listReviews`, it takes as arguments:
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

reflecting #146:
listReviews; it takes


## Get an individual review

You can get an individual review for a pull request using `getReview`, it takes as arguments:
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same


mockServer
.when(
request
.withMethod("GET")
.withPath(s"/repos/$validRepoOwner/$validRepoName/issues")
.withPath(s"/repos/$validRepoOwner/$validRepoName/pulls/$validPullRequestNumber/reviews")
.withHeader(not("Authorization")))
.respond(response.withStatusCode(unauthorizedStatusCode).withBody(unauthorizedResponse))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is still unused

@@ -637,7 +673,7 @@ trait MockGithubApiServer extends MockServerService with FakeResponses with Test
request
.withMethod("POST")
.withPath(s"/repos/$validRepoOwner/$validRepoName/issues")
.withHeader(not("Authorization")))
.withHeader("Authorization", tokenHeader))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Did you sort this out in the end?

Copy link
Contributor

@BenFradet BenFradet left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, thanks a lot 👍

@mscharley
Copy link
Contributor Author

mscharley commented May 23, 2017

Still not sure how this happened, looks like it was actually a regression. Is someone able to run the tests where they're known to be working before merging this? I'm still getting one failure locally but they look to me like they're related to my key rather than the test... but I could easily be wrong too.

[info] Activity >> Set a thread subscription                                            
[info] - should return the provided gist                            
[info] - should return a list of references              
[info] - should return at least one reference                             
[info] - should return an error when an invalid repository name is passed              
[info] - should return one commit                                          
[info] - should return an error when an invalid repository name is passed  
[info] - should return a list of issues                         
[info] - should return at least one issue for a valid query             
[info] - should return an empty result for a non existent query string
[info] - should edit the specified issue *** FAILED ***   
[info]   false was not equal to true (BaseIntegrationSpec.scala:47)

@BenFradet
Copy link
Contributor

The tests are passing locally for me.

@mscharley
Copy link
Contributor Author

👍 :shipit:

@BenFradet
Copy link
Contributor

BenFradet commented May 23, 2017

Merging when green 👍 (or red I should say)

@mscharley
Copy link
Contributor Author

The tests don't seem to work on Travis because I'm not a contributor so Travis valiantly refuses to give me your keys for running tests in case i'm evil and send them on somewhere else. There's a bunch of 401 (auth required) errors in the integration tests as a result.

@juanpedromoreno
Copy link
Member

juanpedromoreno commented May 23, 2017

Yeah, I'm not sure how could we make it work for project forks. We usually test the PRs locally. And yours are working fine 👍

@juanpedromoreno juanpedromoreno merged commit b8bb8e4 into 47degrees:master May 23, 2017
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants