Repository: PyGithub/PyGithub

Issue:
dismiss a PR review?
Am I reading the docs correctly and understanding that there is no support for [dismissing a PR review](https://developer.github.com/v3/pulls/reviews/#dismiss-a-pull-request-review)?


Discussion:
Lacking this functionality, is there any functionality to use the PyGithub context or repo object, etc. to POST an arbitrary payload to an arbitrary URL, to temporarily fill gaps in functionality like this?

Resolving patch:
diff --git a/github/PullRequestReview.py b/github/PullRequestReview.py
--- a/github/PullRequestReview.py
+++ b/github/PullRequestReview.py
@@ -111,6 +111,19 @@ def submitted_at(self):
         self._completeIfNotSet(self._submitted_at)
         return self._submitted_at.value
 
+    def dismiss(self, message):
+        """
+        :calls: `PUT /repos/:owner/:repo/pulls/:number/reviews/:review_id/dismissals <https://developer.github.com/v3/pulls/reviews/>`_
+        :rtype: None
+        """
+        assert isinstance(message, (str, unicode)), message
+        post_parameters = {'message': message}
+        headers, data = self._requester.requestJsonAndCheck(
+            "PUT",
+            self.pull_request_url + "/reviews/%s/dismissals" % self.id,
+            input=post_parameters
+        )
+
     def _initAttributes(self):
         self._id = github.GithubObject.NotSet
         self._user = github.GithubObject.NotSet


Test patch:
diff --git a/github/tests/PullRequestReview.py b/github/tests/PullRequestReview.py
--- a/github/tests/PullRequestReview.py
+++ b/github/tests/PullRequestReview.py
@@ -49,6 +49,11 @@ def setUp(self):
         # Test ability to get a single review
         self.pullreview = self.pull.get_review(28482091)
 
+    def testDismiss(self):
+        self.pullreview.dismiss("with prejudice")
+        pr = self.pull.get_review(28482091)
+        self.assertEqual(pr.state, "DISMISSED")
+
     def testAttributes(self):
         self.assertEqual(self.pullreview.id, 28482091)
         self.assertEqual(self.pullreview.user.login, "jzelinskie")
diff --git a/github/tests/ReplayData/PullRequestReview.testDismiss.txt b/github/tests/ReplayData/PullRequestReview.testDismiss.txt
new file mode 100644
--- /dev/null
+++ b/github/tests/ReplayData/PullRequestReview.testDismiss.txt
@@ -0,0 +1,22 @@
+https
+PUT
+api.github.com
+None
+/repos/PyGithub/PyGithub/pulls/538/reviews/28482091/dismissals
+{'Authorization': 'Basic login_and_password_removed', 'User-Agent': 'PyGithub/Python', 'Content-Type': 'application/json'}
+{"message": "with prejudice"}
+200
+[('content-length', '1418'), ('x-runtime-rack', '0.166821'), ('vary', 'Accept, Authorization, Cookie, X-GitHub-OTP, Accept-Encoding'), ('x-oauth-scopes', 'admin:gpg_key, admin:org, admin:org_hook, admin:public_key, admin:repo_hook, delete_repo, gist, notifications, repo, user, write:discussion'), ('x-xss-protection', '1; mode=block'), ('x-content-type-options', 'nosniff'), ('x-accepted-oauth-scopes', ''), ('etag', '"f9b71d9dcbbfefb597df3b00efc8cb2a"'), ('cache-control', 'private, max-age=60, s-maxage=60'), ('referrer-policy', 'origin-when-cross-origin, strict-origin-when-cross-origin'), ('status', '200 OK'), ('x-ratelimit-remaining', '4545'), ('x-github-media-type', 'github.v3; format=json'), ('access-control-expose-headers', 'ETag, Link, Retry-After, X-GitHub-OTP, X-RateLimit-Limit, X-RateLimit-Remaining, X-RateLimit-Reset, X-OAuth-Scopes, X-Accepted-OAuth-Scopes, X-Poll-Interval'), ('x-github-request-id', 'DDDD:9B6D:C86D83:EADA76:5AB118D3'), ('date', 'Tue, 23 Feb 2018 23:42:09 GMT'), ('access-control-allow-origin', '*'), ('content-security-policy', "default-src 'none'"), ('strict-transport-security', 'max-age=31536000; includeSubdomains; preload'), ('server', 'GitHub.com'), ('x-ratelimit-limit', '5000'), ('x-frame-options', 'deny'), ('content-type', 'application/json; charset=utf-8'), ('x-ratelimit-reset', '1521556163')]
+{"id":28482091,"user":{"login":"jzelinskie","id":343539,"avatar_url":"https://avatars3.githubusercontent.com/u/343539?v=4","gravatar_id":"","url":"https://api.github.com/users/jzelinskie","html_url":"https://github.com/jzelinskie","followers_url":"https://api.github.com/users/jzelinskie/followers","following_url":"https://api.github.com/users/jzelinskie/following{/other_user}","gists_url":"https://api.github.com/users/jzelinskie/gists{/gist_id}","starred_url":"https://api.github.com/users/jzelinskie/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/jzelinskie/subscriptions","organizations_url":"https://api.github.com/users/jzelinskie/orgs","repos_url":"https://api.github.com/users/jzelinskie/repos","events_url":"https://api.github.com/users/jzelinskie/events{/privacy}","received_events_url":"https://api.github.com/users/jzelinskie/received_events","type":"User","site_admin":false},"body":"","state":"DISMISSED","html_url":"https://github.com/PyGithub/PyGithub/pull/538#pullrequestreview-28482091","pull_request_url":"https://api.github.com/repos/PyGithub/PyGithub/pulls/538","author_association":"OWNER","_links":{"html":{"href":"https://github.com/PyGithub/PyGithub/pull/538#pullrequestreview-28482091"},"pull_request":{"href":"https://api.github.com/repos/PyGithub/PyGithub/pulls/538"}},"submitted_at":"2017-03-22T19:06:59Z","commit_id":"7a0fcb27b7cd6c346fc3f76216ccb6e0f4ca3bcc"}
+
+https
+GET
+api.github.com
+None
+/repos/PyGithub/PyGithub/pulls/538/reviews/28482091
+{'Authorization': 'Basic login_and_password_removed', 'User-Agent': 'PyGithub/Python'}
+None
+200
+[('content-length', '1418'), ('x-runtime-rack', '0.166821'), ('vary', 'Accept, Authorization, Cookie, X-GitHub-OTP, Accept-Encoding'), ('x-oauth-scopes', 'admin:gpg_key, admin:org, admin:org_hook, admin:public_key, admin:repo_hook, delete_repo, gist, notifications, repo, user, write:discussion'), ('x-xss-protection', '1; mode=block'), ('x-content-type-options', 'nosniff'), ('x-accepted-oauth-scopes', ''), ('etag', '"a687dafdcbb9aeb597df3b00efc8cb2a"'), ('cache-control', 'private, max-age=60, s-maxage=60'), ('referrer-policy', 'origin-when-cross-origin, strict-origin-when-cross-origin'), ('status', '200 OK'), ('x-ratelimit-remaining', '4545'), ('x-github-media-type', 'github.v3; format=json'), ('access-control-expose-headers', 'ETag, Link, Retry-After, X-GitHub-OTP, X-RateLimit-Limit, X-RateLimit-Remaining, X-RateLimit-Reset, X-OAuth-Scopes, X-Accepted-OAuth-Scopes, X-Poll-Interval'), ('x-github-request-id', 'DDDD:9B6D:C86D83:EADA76:5AB118D3'), ('date', 'Tue, 23 Feb 2018 23:42:19 GMT'), ('access-control-allow-origin', '*'), ('content-security-policy', "default-src 'none'"), ('strict-transport-security', 'max-age=31536000; includeSubdomains; preload'), ('server', 'GitHub.com'), ('x-ratelimit-limit', '5000'), ('x-frame-options', 'deny'), ('content-type', 'application/json; charset=utf-8'), ('x-ratelimit-reset', '1521556163')]
+{"id":28482091,"user":{"login":"jzelinskie","id":343539,"avatar_url":"https://avatars3.githubusercontent.com/u/343539?v=4","gravatar_id":"","url":"https://api.github.com/users/jzelinskie","html_url":"https://github.com/jzelinskie","followers_url":"https://api.github.com/users/jzelinskie/followers","following_url":"https://api.github.com/users/jzelinskie/following{/other_user}","gists_url":"https://api.github.com/users/jzelinskie/gists{/gist_id}","starred_url":"https://api.github.com/users/jzelinskie/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/jzelinskie/subscriptions","organizations_url":"https://api.github.com/users/jzelinskie/orgs","repos_url":"https://api.github.com/users/jzelinskie/repos","events_url":"https://api.github.com/users/jzelinskie/events{/privacy}","received_events_url":"https://api.github.com/users/jzelinskie/received_events","type":"User","site_admin":false},"body":"","state":"DISMISSED","html_url":"https://github.com/PyGithub/PyGithub/pull/538#pullrequestreview-28482091","pull_request_url":"https://api.github.com/repos/PyGithub/PyGithub/pulls/538","author_association":"OWNER","_links":{"html":{"href":"https://github.com/PyGithub/PyGithub/pull/538#pullrequestreview-28482091"},"pull_request":{"href":"https://api.github.com/repos/PyGithub/PyGithub/pulls/538"}},"submitted_at":"2017-03-22T19:06:59Z","commit_id":"7a0fcb27b7cd6c346fc3f76216ccb6e0f4ca3bcc"}
+