Skip to content

Commit 6302256

Browse files
committed
Endpoint to import a project
1 parent fe278cf commit 6302256

File tree

5 files changed

+103
-2
lines changed

5 files changed

+103
-2
lines changed

readthedocs/api/v3/mixins.py

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
from django.shortcuts import get_object_or_404
2-
from rest_framework.exceptions import NotFound
32

43
from readthedocs.builds.models import Version
54
from readthedocs.projects.models import Project
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
{
2+
"_links": {
3+
"_self": "https://readthedocs.org/api/v3/projects/test-project/",
4+
"builds": "https://readthedocs.org/api/v3/projects/test-project/builds/",
5+
"subprojects": "https://readthedocs.org/api/v3/projects/test-project/subprojects/",
6+
"superproject": "https://readthedocs.org/api/v3/projects/test-project/superproject/",
7+
"translations": "https://readthedocs.org/api/v3/projects/test-project/translations/",
8+
"versions": "https://readthedocs.org/api/v3/projects/test-project/versions/"
9+
},
10+
"created": "2019-04-29T14:00:00Z",
11+
"default_branch": "master",
12+
"default_version": "latest",
13+
"description": null,
14+
"id": 4,
15+
"language": {
16+
"code": "en",
17+
"name": "English"
18+
},
19+
"modified": "2019-04-29T14:00:00Z",
20+
"name": "Test Project",
21+
"privacy_level": {
22+
"code": "public",
23+
"name": "Public"
24+
},
25+
"programming_language": {
26+
"code": "words",
27+
"name": "Only Words"
28+
},
29+
"repository": {
30+
"type": "git",
31+
"url": "https://github.com/rtfd/template"
32+
},
33+
"slug": "test-project",
34+
"subproject_of": null,
35+
"tags": [],
36+
"translation_of": null,
37+
"urls": {
38+
"documentation": "http://readthedocs.org/docs/test-project/en/latest/",
39+
"project_homepage": null
40+
},
41+
"users": [
42+
{
43+
"created": "2019-04-29T10:00:00Z",
44+
"username": "testuser"
45+
}
46+
]
47+
}

readthedocs/api/v3/tests/test_projects.py

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import datetime
2+
import mock
23
import json
34
from pathlib import Path
45

@@ -372,3 +373,56 @@ def test_projects_versions_detail_unique(self):
372373

373374
)
374375
self.assertEqual(response.status_code, 200)
376+
377+
@mock.patch('readthedocs.api.v3.views.trigger_initial_build')
378+
@mock.patch('readthedocs.api.v3.views.project_import')
379+
def test_import_project(self, project_import, trigger_initial_build):
380+
data = {
381+
'name': 'Test Project',
382+
'repository': {
383+
'url': 'https://github.com/rtfd/template',
384+
'type': 'git',
385+
},
386+
}
387+
388+
self.client.credentials(HTTP_AUTHORIZATION=f'Token {self.token.key}')
389+
response = self.client.post(reverse('projects-list'), data)
390+
self.assertEqual(response.status_code, 201)
391+
392+
query = Project.objects.filter(slug='test-project')
393+
self.assertTrue(query.exists())
394+
395+
project = query.first()
396+
self.assertEqual(project.name, 'Test Project')
397+
self.assertEqual(project.slug, 'test-project')
398+
self.assertEqual(project.repo, 'https://github.com/rtfd/template')
399+
self.assertEqual(project.language, 'en')
400+
self.assertIn(self.me, project.users.all())
401+
402+
# Signal sent
403+
project_import.send.assert_has_calls(
404+
[
405+
mock.call(
406+
sender=project,
407+
request=mock.ANY,
408+
),
409+
],
410+
)
411+
412+
# Build triggered
413+
trigger_initial_build.assert_has_calls(
414+
[
415+
mock.call(
416+
project,
417+
self.me,
418+
),
419+
],
420+
)
421+
422+
response_json = response.json()
423+
response_json['created'] = '2019-04-29T14:00:00Z'
424+
response_json['modified'] = '2019-04-29T14:00:00Z'
425+
self.assertDictEqual(
426+
response_json,
427+
self._get_response_dict('projects-list_POST'),
428+
)

readthedocs/api/v3/views.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -136,7 +136,7 @@ def get_serializer_class(self):
136136
For GET it returns a serializer with many fields and on PUT/PATCH/POST,
137137
it return a serializer to validate just a few fields.
138138
"""
139-
if self.action in ('list', 'retrieve'):
139+
if self.action in ('list', 'retrieve', 'superproject'):
140140
return ProjectSerializer
141141
elif self.action in ('create',):
142142
return ProjectCreateSerializer

readthedocs/settings/base.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -512,6 +512,7 @@ def USE_PROMOS(self): # noqa
512512
'user': '60/minute',
513513
},
514514
'PAGE_SIZE': 10,
515+
'TEST_REQUEST_DEFAULT_FORMAT': 'json',
515516
}
516517

517518
SILENCED_SYSTEM_CHECKS = ['fields.W342', 'guardian.W001']

0 commit comments

Comments
 (0)