Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
E
edx-platform
Overview
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
edx
edx-platform
Commits
fa285e09
Commit
fa285e09
authored
Sep 28, 2015
by
wajeeha-khalid
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
MA-1189 - Discussion API: implemented GET comment children
parent
450e625d
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
154 additions
and
7 deletions
+154
-7
lms/djangoapps/discussion_api/api.py
+45
-1
lms/djangoapps/discussion_api/serializers.py
+9
-0
lms/djangoapps/discussion_api/tests/test_api.py
+0
-2
lms/djangoapps/discussion_api/tests/test_views.py
+70
-2
lms/djangoapps/discussion_api/views.py
+30
-2
No files found.
lms/djangoapps/discussion_api/api.py
View file @
fa285e09
...
@@ -415,7 +415,7 @@ def get_comment_list(request, thread_id, endorsed, page, page_size, mark_as_read
...
@@ -415,7 +415,7 @@ def get_comment_list(request, thread_id, endorsed, page, page_size, mark_as_read
raise
Http404
raise
Http404
num_pages
=
(
resp_total
+
page_size
-
1
)
/
page_size
if
resp_total
else
1
num_pages
=
(
resp_total
+
page_size
-
1
)
/
page_size
if
resp_total
else
1
results
=
[
CommentSerializer
(
response
,
context
=
context
)
.
data
for
response
in
responses
]
results
=
[
CommentSerializer
(
response
,
remove_fields
=
[
"children"
],
context
=
context
)
.
data
for
response
in
responses
]
return
get_paginated_data
(
request
,
results
,
page
,
num_pages
)
return
get_paginated_data
(
request
,
results
,
page
,
num_pages
)
...
@@ -718,6 +718,50 @@ def get_thread(request, thread_id):
...
@@ -718,6 +718,50 @@ def get_thread(request, thread_id):
return
serializer
.
data
return
serializer
.
data
def
get_response_comments
(
request
,
comment_id
,
page
,
page_size
):
"""
Return the list of comments for the given thread response.
Arguments:
request: The django request object used for build_absolute_uri and
determining the requesting user.
comment_id: The id of the comment/response to get child comments for.
page: The page number (1-indexed) to retrieve
page_size: The number of comments to retrieve per page
Returns:
A paginated result containing a list of comments
"""
try
:
cc_comment
=
Comment
(
id
=
comment_id
)
.
retrieve
()
cc_thread
,
context
=
_get_thread_and_context
(
request
,
cc_comment
[
"thread_id"
])
if
cc_thread
[
"thread_type"
]
==
"question"
:
thread_responses
=
cc_thread
[
"endorsed_responses"
]
+
cc_thread
[
"non_endorsed_responses"
]
else
:
thread_responses
=
cc_thread
[
"children"
]
response_comments
=
[]
for
response
in
thread_responses
:
if
response
[
"id"
]
==
comment_id
:
response_comments
=
response
[
"children"
]
break
response_skip
=
page_size
*
(
page
-
1
)
paged_response_comments
=
response_comments
[
response_skip
:(
response_skip
+
page_size
)]
results
=
[
CommentSerializer
(
comment
,
context
=
context
)
.
data
for
comment
in
paged_response_comments
]
comments_count
=
len
(
response_comments
)
num_pages
=
(
comments_count
+
page_size
-
1
)
/
page_size
if
comments_count
else
1
return
get_paginated_data
(
request
,
results
,
page
,
num_pages
)
except
CommentClientRequestError
:
raise
Http404
def
delete_thread
(
request
,
thread_id
):
def
delete_thread
(
request
,
thread_id
):
"""
"""
Delete a thread.
Delete a thread.
...
...
lms/djangoapps/discussion_api/serializers.py
View file @
fa285e09
...
@@ -290,6 +290,15 @@ class CommentSerializer(_ContentSerializer):
...
@@ -290,6 +290,15 @@ class CommentSerializer(_ContentSerializer):
non_updatable_fields
=
NON_UPDATABLE_COMMENT_FIELDS
non_updatable_fields
=
NON_UPDATABLE_COMMENT_FIELDS
def
__init__
(
self
,
*
args
,
**
kwargs
):
remove_fields
=
kwargs
.
pop
(
'remove_fields'
,
None
)
super
(
CommentSerializer
,
self
)
.
__init__
(
*
args
,
**
kwargs
)
if
remove_fields
:
# for multiple fields in a list
for
field_name
in
remove_fields
:
self
.
fields
.
pop
(
field_name
)
def
get_endorsed_by
(
self
,
obj
):
def
get_endorsed_by
(
self
,
obj
):
"""
"""
Returns the username of the endorsing user, if the information is
Returns the username of the endorsing user, if the information is
...
...
lms/djangoapps/discussion_api/tests/test_api.py
View file @
fa285e09
...
@@ -1146,7 +1146,6 @@ class GetCommentListTest(CommentsServiceMockMixin, SharedModuleStoreTestCase):
...
@@ -1146,7 +1146,6 @@ class GetCommentListTest(CommentsServiceMockMixin, SharedModuleStoreTestCase):
"abuse_flagged"
:
False
,
"abuse_flagged"
:
False
,
"voted"
:
False
,
"voted"
:
False
,
"vote_count"
:
4
,
"vote_count"
:
4
,
"children"
:
[],
"editable_fields"
:
[
"abuse_flagged"
,
"voted"
],
"editable_fields"
:
[
"abuse_flagged"
,
"voted"
],
},
},
{
{
...
@@ -1166,7 +1165,6 @@ class GetCommentListTest(CommentsServiceMockMixin, SharedModuleStoreTestCase):
...
@@ -1166,7 +1165,6 @@ class GetCommentListTest(CommentsServiceMockMixin, SharedModuleStoreTestCase):
"abuse_flagged"
:
True
,
"abuse_flagged"
:
True
,
"voted"
:
False
,
"voted"
:
False
,
"vote_count"
:
7
,
"vote_count"
:
7
,
"children"
:
[],
"editable_fields"
:
[
"abuse_flagged"
,
"voted"
],
"editable_fields"
:
[
"abuse_flagged"
,
"voted"
],
},
},
]
]
...
...
lms/djangoapps/discussion_api/tests/test_views.py
View file @
fa285e09
...
@@ -662,7 +662,6 @@ class CommentViewSetListTest(DiscussionAPIViewTestMixin, ModuleStoreTestCase):
...
@@ -662,7 +662,6 @@ class CommentViewSetListTest(DiscussionAPIViewTestMixin, ModuleStoreTestCase):
"endorsed"
:
False
,
"endorsed"
:
False
,
"abuse_flaggers"
:
[],
"abuse_flaggers"
:
[],
"votes"
:
{
"up_count"
:
4
},
"votes"
:
{
"up_count"
:
4
},
"children"
:
[],
}]
}]
expected_comments
=
[{
expected_comments
=
[{
"id"
:
"test_comment"
,
"id"
:
"test_comment"
,
...
@@ -681,7 +680,6 @@ class CommentViewSetListTest(DiscussionAPIViewTestMixin, ModuleStoreTestCase):
...
@@ -681,7 +680,6 @@ class CommentViewSetListTest(DiscussionAPIViewTestMixin, ModuleStoreTestCase):
"abuse_flagged"
:
False
,
"abuse_flagged"
:
False
,
"voted"
:
True
,
"voted"
:
True
,
"vote_count"
:
4
,
"vote_count"
:
4
,
"children"
:
[],
"editable_fields"
:
[
"abuse_flagged"
,
"voted"
],
"editable_fields"
:
[
"abuse_flagged"
,
"voted"
],
}]
}]
self
.
register_get_thread_response
({
self
.
register_get_thread_response
({
...
@@ -1025,3 +1023,73 @@ class ThreadViewSetRetrieveTest(DiscussionAPIViewTestMixin, ModuleStoreTestCase)
...
@@ -1025,3 +1023,73 @@ class ThreadViewSetRetrieveTest(DiscussionAPIViewTestMixin, ModuleStoreTestCase)
self
.
register_get_thread_error_response
(
self
.
thread_id
,
404
)
self
.
register_get_thread_error_response
(
self
.
thread_id
,
404
)
response
=
self
.
client
.
get
(
self
.
url
)
response
=
self
.
client
.
get
(
self
.
url
)
self
.
assertEqual
(
response
.
status_code
,
404
)
self
.
assertEqual
(
response
.
status_code
,
404
)
@httpretty.activate
class
CommentViewSetRetrieveTest
(
DiscussionAPIViewTestMixin
,
ModuleStoreTestCase
):
"""Tests for CommentViewSet Retrieve"""
def
setUp
(
self
):
super
(
CommentViewSetRetrieveTest
,
self
)
.
setUp
()
self
.
url
=
reverse
(
"comment-detail"
,
kwargs
=
{
"comment_id"
:
"test_comment"
})
self
.
thread_id
=
"test_thread"
self
.
comment_id
=
"test_comment"
def
make_comment_data
(
self
,
comment_id
,
parent_id
=
None
,
children
=
[]):
# pylint: disable=W0102
"""
Returns comment dict object as returned by comments service
"""
return
make_minimal_cs_comment
({
"id"
:
comment_id
,
"parent_id"
:
parent_id
,
"course_id"
:
unicode
(
self
.
course
.
id
),
"thread_id"
:
self
.
thread_id
,
"thread_type"
:
"discussion"
,
"username"
:
self
.
user
.
username
,
"user_id"
:
str
(
self
.
user
.
id
),
"created_at"
:
"2015-06-03T00:00:00Z"
,
"updated_at"
:
"2015-06-03T00:00:00Z"
,
"body"
:
"Original body"
,
"children"
:
children
,
})
def
test_basic
(
self
):
self
.
register_get_user_response
(
self
.
user
)
cs_comment_child
=
self
.
make_comment_data
(
"test_child_comment"
,
self
.
comment_id
,
children
=
[])
cs_comment
=
self
.
make_comment_data
(
self
.
comment_id
,
None
,
[
cs_comment_child
])
cs_thread
=
make_minimal_cs_thread
({
"id"
:
self
.
thread_id
,
"course_id"
:
unicode
(
self
.
course
.
id
),
"children"
:
[
cs_comment
],
})
self
.
register_get_thread_response
(
cs_thread
)
self
.
register_get_comment_response
(
cs_comment
)
expected_response_data
=
{
"id"
:
"test_child_comment"
,
"parent_id"
:
self
.
comment_id
,
"thread_id"
:
self
.
thread_id
,
"author"
:
self
.
user
.
username
,
"author_label"
:
None
,
"raw_body"
:
"Original body"
,
"rendered_body"
:
"<p>Original body</p>"
,
"created_at"
:
"2015-06-03T00:00:00Z"
,
"updated_at"
:
"2015-06-03T00:00:00Z"
,
"children"
:
[],
"endorsed_at"
:
None
,
"endorsed"
:
False
,
"endorsed_by"
:
None
,
"endorsed_by_label"
:
None
,
"voted"
:
False
,
"vote_count"
:
0
,
"abuse_flagged"
:
False
,
"editable_fields"
:
[
"abuse_flagged"
,
"raw_body"
,
"voted"
]
}
response
=
self
.
client
.
get
(
self
.
url
)
self
.
assertEqual
(
response
.
status_code
,
200
)
self
.
assertEqual
(
json
.
loads
(
response
.
content
)[
'results'
][
0
],
expected_response_data
)
def
test_retrieve_nonexistent_comment
(
self
):
self
.
register_get_comment_error_response
(
self
.
comment_id
,
404
)
response
=
self
.
client
.
get
(
self
.
url
)
self
.
assertEqual
(
response
.
status_code
,
404
)
lms/djangoapps/discussion_api/views.py
View file @
fa285e09
...
@@ -18,6 +18,7 @@ from discussion_api.api import (
...
@@ -18,6 +18,7 @@ from discussion_api.api import (
delete_thread
,
delete_thread
,
delete_comment
,
delete_comment
,
get_comment_list
,
get_comment_list
,
get_response_comments
,
get_course
,
get_course
,
get_course_topics
,
get_course_topics
,
get_thread
,
get_thread
,
...
@@ -25,7 +26,7 @@ from discussion_api.api import (
...
@@ -25,7 +26,7 @@ from discussion_api.api import (
update_comment
,
update_comment
,
update_thread
,
update_thread
,
)
)
from
discussion_api.forms
import
CommentListGetForm
,
ThreadListGetForm
from
discussion_api.forms
import
CommentListGetForm
,
ThreadListGetForm
,
_PaginationForm
from
openedx.core.lib.api.view_utils
import
DeveloperErrorViewMixin
from
openedx.core.lib.api.view_utils
import
DeveloperErrorViewMixin
...
@@ -299,6 +300,8 @@ class CommentViewSet(_ViewMixin, DeveloperErrorViewMixin, ViewSet):
...
@@ -299,6 +300,8 @@ class CommentViewSet(_ViewMixin, DeveloperErrorViewMixin, ViewSet):
GET /api/discussion/v1/comments/?thread_id=0123456789abcdef01234567
GET /api/discussion/v1/comments/?thread_id=0123456789abcdef01234567
GET /api/discussion/v1/comments/2123456789abcdef01234555
POST /api/discussion/v1/comments/
POST /api/discussion/v1/comments/
{
{
"thread_id": "0123456789abcdef01234567",
"thread_id": "0123456789abcdef01234567",
...
@@ -310,7 +313,7 @@ class CommentViewSet(_ViewMixin, DeveloperErrorViewMixin, ViewSet):
...
@@ -310,7 +313,7 @@ class CommentViewSet(_ViewMixin, DeveloperErrorViewMixin, ViewSet):
DELETE /api/discussion/v1/comments/comment_id
DELETE /api/discussion/v1/comments/comment_id
**GET Parameters**:
**GET
Comment List
Parameters**:
* thread_id (required): The thread to retrieve comments for
* thread_id (required): The thread to retrieve comments for
...
@@ -325,6 +328,15 @@ class CommentViewSet(_ViewMixin, DeveloperErrorViewMixin, ViewSet):
...
@@ -325,6 +328,15 @@ class CommentViewSet(_ViewMixin, DeveloperErrorViewMixin, ViewSet):
* mark_as_read: Will mark the thread of the comments as read. (default
* mark_as_read: Will mark the thread of the comments as read. (default
is False)
is False)
**GET Child Comment List Parameters**:
* comment_id (required): The comment to retrieve child comments for
* page: The (1-indexed) page to retrieve (default is 1)
* page_size: The number of items per page (default is 10, max is 100)
**POST Parameters**:
**POST Parameters**:
* thread_id (required): The thread to post the comment in
* thread_id (required): The thread to post the comment in
...
@@ -420,6 +432,22 @@ class CommentViewSet(_ViewMixin, DeveloperErrorViewMixin, ViewSet):
...
@@ -420,6 +432,22 @@ class CommentViewSet(_ViewMixin, DeveloperErrorViewMixin, ViewSet):
)
)
)
)
def
retrieve
(
self
,
request
,
comment_id
=
None
):
"""
Implements the GET method for comments against response ID
"""
form
=
_PaginationForm
(
request
.
GET
)
if
not
form
.
is_valid
():
raise
ValidationError
(
form
.
errors
)
return
Response
(
get_response_comments
(
request
,
comment_id
,
form
.
cleaned_data
[
"page"
],
form
.
cleaned_data
[
"page_size"
]
)
)
def
create
(
self
,
request
):
def
create
(
self
,
request
):
"""
"""
Implements the POST method for the list endpoint as described in the
Implements the POST method for the list endpoint as described in the
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment