Skip to content

Commit 046e863

Browse files
committed
Update tests
1 parent 707b3ce commit 046e863

3 files changed

Lines changed: 270 additions & 0 deletions

File tree

bot/tests/conftest.py

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,8 @@
1313
from collections import defaultdict, namedtuple
1414
from configparser import ConfigParser
1515
from contextlib import contextmanager
16+
from datetime import UTC, datetime, timedelta
17+
from textwrap import dedent
1618
from unittest.mock import MagicMock
1719

1820
import hglib
@@ -282,6 +284,64 @@ def diff_search(request):
282284
yield PhabricatorAPI(url="http://phabricator.test/api/", api_key="deadbeef")
283285

284286

287+
@pytest.fixture
288+
def mock_github(mock_config):
289+
"""
290+
Mock default github API calls made by the client
291+
"""
292+
diff = dedent(
293+
"""diff --git a/path/to/test.cpp b/path/to/test.cpp
294+
index c57eff55..980a0d5f 100644
295+
--- a/path/to/test.cpp
296+
+++ b/path/to/test.cpp
297+
@@ -1 +1 @@
298+
-#include <random>
299+
+Hello World!
300+
"""
301+
)
302+
303+
responses.add(
304+
responses.GET,
305+
"https://github.tests.com/owner/repo-name/pull/1.diff",
306+
json=diff,
307+
)
308+
responses.add(
309+
responses.GET,
310+
"https://api.github.com:443/app/installations",
311+
json=[
312+
{
313+
"id": 123456789,
314+
"access_tokens_url": "https://github.tests.com/app/installations/123456789/access_tokens",
315+
}
316+
],
317+
)
318+
responses.add(
319+
responses.POST,
320+
"https://api.github.com:443/app/installations/123456789/access_tokens",
321+
json={
322+
"token": "auth_token",
323+
"expires_at": (datetime.now(UTC) + timedelta(1)).strftime(
324+
"%Y-%m-%dT%H:%M:%S.%fZ"
325+
),
326+
},
327+
)
328+
responses.add(
329+
responses.GET,
330+
"https://api.github.com:443/repos/owner/repo-name",
331+
json={"url": "https://api.github.com/repos/owner/repo-name"},
332+
)
333+
responses.add(
334+
responses.GET,
335+
"https://api.github.com:443/repos/owner/repo-name/pulls/1",
336+
json={"url": "https://api.github.com/repos/owner/repo-name/pulls/1"},
337+
)
338+
responses.add(
339+
responses.GET,
340+
"https://api.github.com:443/repos/owner/repo-name/commits/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
341+
json={"sha": "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"},
342+
)
343+
344+
285345
@pytest.fixture
286346
def mock_try_task():
287347
"""
@@ -290,6 +350,25 @@ def mock_try_task():
290350
return {"extra": {"code-review": {"phabricator-diff": "PHID-HMBT-test"}}}
291351

292352

353+
@pytest.fixture
354+
def mock_github_try_task():
355+
"""
356+
Mock a remote Try task definition from a github revision
357+
"""
358+
return {
359+
"extra": {
360+
"code-review": {
361+
"github": {
362+
"repo_url": "https://github.tests.com/owner/repo-name",
363+
"branch": "test",
364+
"pull_number": 1,
365+
"pull_head_sha": "a" * 40,
366+
}
367+
}
368+
}
369+
}
370+
371+
293372
@pytest.fixture
294373
def mock_decision_task():
295374
"""

bot/tests/fixtures/private_key.pem

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
# THIS IS A FAKE PRIVATE KEY USED FOR TESTS
2+
-----BEGIN RSA PRIVATE KEY-----
3+
MIIEowIBAAKCAQEAjIf0Q38ga5TF9CbNXewI/duyPJgz/TJAvdHvexwtp3qIIWfH
4+
1CNK0NvcmaLWcvgyVn4nj8aLexQiJZQVQYII/YMwXAg2tK75dWkP56cWL0odb4Zs
5+
o2GU14xRGdonixVb8COC8CxiLzFGBXpY2gMfru/9di6/0hRY1o5Qd2aYrXZVHDpe
6+
0ATuIF0gR8MbMz8y8Azqvs+89epjAmKo+6+sU/7yITm9aJ685CEiug3127Kowk07
7+
TYeebXlzw2eqxcIw35loAs/oqyOIEX607KtVjCBl73FoEfuLHhsi1hFxBOg+HvXn
8+
TzdFiLN/99ZGRRMlJhZCw/DWpZ9uip5MrohneQIDAQABAoIBAD9TVELGGnngBIPM
9+
qGZWYobiZSLhAyxpZLskyuGTBQ+fK5DCD04MyT3slS+2LSSJq0VGe9VSBrBjli+Q
10+
1zM5wYtbfoM6QEyTPF4oBb7BkEGnCDSlQnctFcE7vaAEqiUGbvN7TRmlJmlVrtPx
11+
GfDDz5cpFfIXhuDHwnCMmL31QX+ITV8pmrYYwhpOp+js+25wA7PFzXhgqQtqgGbM
12+
L0O1Tn/POqTbEUBi/S95KwMnNYVEAx6lwmcpLb0KD3x2g0bkHFyeIc+pMeJa+3Kn
13+
OpY1DTlJP3nkpiLmpWIpKk4HMo6oZhcRo9DDLQtJzE+rllEwjZBrSKW3l4d3Eh6t
14+
itsGj7ECgYEA+9OcFcUuMVwFlknTVSoykGv4DQ2gcN/W+H70bYHgAAvjolYxnsQX
15+
hYucxJqTBaG8l5LXjlSynoqMnbm5FY1FLOu8lzt8YhPfc0f/N1jTVL5v52mxyUNr
16+
HjPcbbv9+vihcrhEFkhgRN/lzimv7Eweo5x4wlm8aLOIb/Eg8Y8Wth8CgYEAjtwq
17+
hsPdf0NP/tkJFSrB7Y2I1zBruNvTuJarcv1/w61XLEBR42Odq+Y11/crY8qkwK7z
18+
A5SOxsI6o/si2RDlSZJ5w8t+7Kz/yr5PSFcQHGsokIadQgXCP/hetS2eiNNH94vM
19+
YvwHvSl0ey47qK0h3ugqIZJ1pBSRc0NlfJz8v2cCgYEA0hXdd0QCn2cXuiNozPnh
20+
KR8J10nw+XmkC7dODzV0PFWu2DV0O/F3dg/c/x+9W8tsXD9C2RjL0vvfB45zXAl5
21+
FlqsALa9s8zEc5Yy0memFmKxVKuWiENYT+AQGvPklMVrWxtiofxLY+ot+2pHu6hd
22+
Pz1AeVMHnYl5X3oYc61d0x0CgYBBYT9RJ8hx2rN8lYVTm5rfBdwvZ2iVVH2jx8i1
23+
OpDDU8xGYzVW1JsvNY9ExEimRfJ6gFaVN+LT0cYWj/OV1eapchCp67KtzErQVaJh
24+
H/8uklghNIo50frhXeCyGCuqwM752o/yaRd9mcBGM5V4D6wloKjPboDKU+NxFdIX
25+
Yp1FVwKBgGgG4RA3UqAY51E7zA7k3WR3sj49c6oktXVi2n7FuO3PPVTg5LAZ/c81
26+
vVrip+dOQD53APtrwnFpDeM+AJ03RsIfjVVfB822xRpcy7jDA04bOmJ1Skouoptx
27+
CyIV/PUVbtmNdxJ6T1dCzAvhmK6895FK+xCwBnpaN213Nx/eG49+
28+
-----END RSA PRIVATE KEY-----

bot/tests/test_reporter_github.py

Lines changed: 163 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,163 @@
1+
# This Source Code Form is subject to the terms of the Mozilla Public
2+
# License, v. 2.0. If a copy of the MPL was not distributed with this
3+
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
4+
5+
6+
import json
7+
from pathlib import Path
8+
9+
import responses
10+
from conftest import FIXTURES_DIR
11+
12+
from code_review_bot.report.github import GithubReporter
13+
from code_review_bot.revisions import GithubRevision, Revision
14+
from code_review_bot.tasks.clang_tidy import ClangTidyIssue, ClangTidyTask
15+
from code_review_bot.tasks.coverage import CoverageIssue, ZeroCoverageTask
16+
17+
18+
def test_github_review(
19+
monkeypatch,
20+
mock_github,
21+
mock_config,
22+
phab,
23+
mock_github_try_task,
24+
mock_decision_task,
25+
mock_task,
26+
mock_backend_secret,
27+
):
28+
"""
29+
Report 2 cland tidy issues by pushing a review to a Github pull request
30+
"""
31+
revision = Revision.from_try_task(mock_github_try_task, mock_decision_task, None)
32+
assert isinstance(revision, GithubRevision)
33+
revision.lines = {
34+
# Add dummy lines diff
35+
"test.txt": [0],
36+
"path/to/test.cpp": [0],
37+
"another_test.cpp": [41, 42, 43],
38+
}
39+
revision.files = ["test.txt", "test.cpp", "another_test.cpp"]
40+
revision.id = 52
41+
monkeypatch.setattr(revision, "load_file", lambda x: "some_content")
42+
43+
reporter = GithubReporter(
44+
{
45+
"client_id": "client_id",
46+
"private_key_pem": (Path(FIXTURES_DIR) / "private_key.pem").read_text(),
47+
"installation_id": 123456789,
48+
}
49+
)
50+
51+
issue_clang_tidy = ClangTidyIssue(
52+
mock_task(ClangTidyTask, "source-test-clang-tidy"),
53+
revision,
54+
"another_test.cpp",
55+
"42",
56+
"51",
57+
"modernize-use-nullptr",
58+
"dummy message",
59+
)
60+
assert issue_clang_tidy.is_publishable()
61+
62+
issue_coverage = CoverageIssue(
63+
mock_task(ZeroCoverageTask, "coverage"),
64+
"path/to/test.cpp",
65+
"1",
66+
"This file is uncovered",
67+
revision,
68+
)
69+
assert issue_coverage.is_publishable()
70+
71+
responses.add(
72+
responses.POST,
73+
"https://api.github.com:443/repos/owner/repo-name/pulls/1/reviews",
74+
json={},
75+
)
76+
77+
reporter.publish([issue_clang_tidy, issue_coverage], revision, [], [], [])
78+
assert [(call.request.method, call.request.url) for call in responses.calls] == [
79+
("GET", "https://github.tests.com/owner/repo-name/pull/1.diff"),
80+
("GET", "https://api.github.com:443/app/installations"),
81+
(
82+
"POST",
83+
"https://api.github.com:443/app/installations/123456789/access_tokens",
84+
),
85+
("GET", "https://api.github.com:443/repos/owner/repo-name"),
86+
("GET", "https://api.github.com:443/repos/owner/repo-name/pulls/1"),
87+
(
88+
"GET",
89+
"https://api.github.com:443/repos/owner/repo-name/commits/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
90+
),
91+
("POST", "https://api.github.com:443/repos/owner/repo-name/pulls/1/reviews"),
92+
]
93+
review_creation = responses.calls[-1]
94+
assert json.loads(review_creation.request.body) == {
95+
"body": "2 issues have been found in this revision",
96+
"comments": [
97+
{
98+
"body": "dummy message",
99+
"path": "another_test.cpp",
100+
"line": 42,
101+
},
102+
{
103+
"body": "This file is uncovered",
104+
"path": "path/to/test.cpp",
105+
"line": 1,
106+
},
107+
],
108+
"commit_id": "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
109+
"event": "REQUEST_CHANGES",
110+
}
111+
112+
113+
def test_github_review_approve(
114+
monkeypatch,
115+
mock_github,
116+
mock_config,
117+
phab,
118+
mock_github_try_task,
119+
mock_decision_task,
120+
mock_task,
121+
mock_backend_secret,
122+
):
123+
"""In case no issue is found, the pull request is approved"""
124+
revision = Revision.from_try_task(mock_github_try_task, mock_decision_task, None)
125+
revision.lines = {}
126+
revision.files = ["test.txt", "test.cpp", "another_test.cpp"]
127+
revision.id = 52
128+
reporter = GithubReporter(
129+
{
130+
"client_id": "client_id",
131+
"private_key_pem": (Path(FIXTURES_DIR) / "private_key.pem").read_text(),
132+
"installation_id": 123456789,
133+
}
134+
)
135+
136+
responses.add(
137+
responses.POST,
138+
"https://api.github.com:443/repos/owner/repo-name/pulls/1/reviews",
139+
json={},
140+
)
141+
142+
reporter.publish([], revision, [], [], [])
143+
assert [(call.request.method, call.request.url) for call in responses.calls] == [
144+
("GET", "https://github.tests.com/owner/repo-name/pull/1.diff"),
145+
("GET", "https://api.github.com:443/app/installations"),
146+
(
147+
"POST",
148+
"https://api.github.com:443/app/installations/123456789/access_tokens",
149+
),
150+
("GET", "https://api.github.com:443/repos/owner/repo-name"),
151+
("GET", "https://api.github.com:443/repos/owner/repo-name/pulls/1"),
152+
(
153+
"GET",
154+
"https://api.github.com:443/repos/owner/repo-name/commits/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
155+
),
156+
("POST", "https://api.github.com:443/repos/owner/repo-name/pulls/1/reviews"),
157+
]
158+
review_creation = responses.calls[-1]
159+
assert json.loads(review_creation.request.body) == {
160+
"comments": [],
161+
"commit_id": "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
162+
"event": "APPROVE",
163+
}

0 commit comments

Comments
 (0)