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
d3d4d330
Commit
d3d4d330
authored
Sep 10, 2014
by
jsa
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Ensure group info is present in LMS responses.
TNL-24
parent
b3594b69
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
312 additions
and
53 deletions
+312
-53
lms/djangoapps/django_comment_client/base/tests.py
+107
-6
lms/djangoapps/django_comment_client/base/views.py
+30
-24
lms/djangoapps/django_comment_client/forum/tests.py
+128
-11
lms/djangoapps/django_comment_client/forum/views.py
+0
-0
lms/djangoapps/django_comment_client/tests/group_id.py
+30
-0
lms/djangoapps/django_comment_client/utils.py
+17
-12
No files found.
lms/djangoapps/django_comment_client/base/tests.py
View file @
d3d4d330
...
@@ -12,7 +12,7 @@ from opaque_keys.edx.locations import SlashSeparatedCourseKey
...
@@ -12,7 +12,7 @@ from opaque_keys.edx.locations import SlashSeparatedCourseKey
from
courseware.tests.modulestore_config
import
TEST_DATA_MIXED_MODULESTORE
from
courseware.tests.modulestore_config
import
TEST_DATA_MIXED_MODULESTORE
from
django_comment_client.base
import
views
from
django_comment_client.base
import
views
from
django_comment_client.tests.group_id
import
CohortedTopicGroupIdTestMixin
,
NonCohortedTopicGroupIdTestMixin
from
django_comment_client.tests.group_id
import
CohortedTopicGroupIdTestMixin
,
NonCohortedTopicGroupIdTestMixin
,
GroupIdAssertionMixin
from
django_comment_client.tests.utils
import
CohortedContentTestCase
from
django_comment_client.tests.utils
import
CohortedContentTestCase
from
django_comment_client.tests.unicode
import
UnicodeTestMixin
from
django_comment_client.tests.unicode
import
UnicodeTestMixin
from
django_comment_common.models
import
Role
,
FORUM_ROLE_STUDENT
from
django_comment_common.models
import
Role
,
FORUM_ROLE_STUDENT
...
@@ -29,15 +29,16 @@ CS_PREFIX = "http://localhost:4567/api/v1"
...
@@ -29,15 +29,16 @@ CS_PREFIX = "http://localhost:4567/api/v1"
class
MockRequestSetupMixin
(
object
):
class
MockRequestSetupMixin
(
object
):
def
_create_re
ps
onse_mock
(
self
,
data
):
def
_create_re
sp
onse_mock
(
self
,
data
):
return
Mock
(
text
=
json
.
dumps
(
data
),
json
=
Mock
(
return_value
=
data
))
\
return
Mock
(
text
=
json
.
dumps
(
data
),
json
=
Mock
(
return_value
=
data
))
def
_set_mock_request_data
(
self
,
mock_request
,
data
):
def
_set_mock_request_data
(
self
,
mock_request
,
data
):
mock_request
.
return_value
=
self
.
_create_re
ps
onse_mock
(
data
)
mock_request
.
return_value
=
self
.
_create_re
sp
onse_mock
(
data
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
class
CreateThreadGroupIdTestCase
(
class
CreateThreadGroupIdTestCase
(
MockRequestSetupMixin
,
CohortedContentTestCase
,
CohortedContentTestCase
,
CohortedTopicGroupIdTestMixin
,
CohortedTopicGroupIdTestMixin
,
NonCohortedTopicGroupIdTestMixin
NonCohortedTopicGroupIdTestMixin
...
@@ -45,6 +46,7 @@ class CreateThreadGroupIdTestCase(
...
@@ -45,6 +46,7 @@ class CreateThreadGroupIdTestCase(
cs_endpoint
=
"/threads"
cs_endpoint
=
"/threads"
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
):
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
):
self
.
_set_mock_request_data
(
mock_request
,
{})
mock_request
.
return_value
.
status_code
=
200
mock_request
.
return_value
.
status_code
=
200
request_data
=
{
"body"
:
"body"
,
"title"
:
"title"
,
"thread_type"
:
"discussion"
}
request_data
=
{
"body"
:
"body"
,
"title"
:
"title"
,
"thread_type"
:
"discussion"
}
if
pass_group_id
:
if
pass_group_id
:
...
@@ -59,6 +61,105 @@ class CreateThreadGroupIdTestCase(
...
@@ -59,6 +61,105 @@ class CreateThreadGroupIdTestCase(
commentable_id
=
commentable_id
commentable_id
=
commentable_id
)
)
def
test_group_info_in_response
(
self
,
mock_request
):
response
=
self
.
call_view
(
mock_request
,
"cohorted_topic"
,
self
.
student
,
None
)
self
.
_assert_json_response_contains_group_info
(
response
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
class
ThreadActionGroupIdTestCase
(
MockRequestSetupMixin
,
CohortedContentTestCase
,
GroupIdAssertionMixin
):
def
call_view
(
self
,
view_name
,
mock_request
,
user
=
None
,
post_params
=
None
,
view_args
=
None
):
self
.
_set_mock_request_data
(
mock_request
,
{
"user_id"
:
str
(
self
.
student
.
id
),
"group_id"
:
self
.
student_cohort
.
id
,
"closed"
:
False
,
"type"
:
"thread"
}
)
mock_request
.
return_value
.
status_code
=
200
request
=
RequestFactory
()
.
post
(
"dummy_url"
,
post_params
or
{})
request
.
user
=
user
or
self
.
student
request
.
view_name
=
view_name
return
getattr
(
views
,
view_name
)(
request
,
course_id
=
self
.
course
.
id
.
to_deprecated_string
(),
thread_id
=
"dummy"
,
**
(
view_args
or
{})
)
def
test_update
(
self
,
mock_request
):
response
=
self
.
call_view
(
"update_thread"
,
mock_request
,
post_params
=
{
"body"
:
"body"
,
"title"
:
"title"
}
)
self
.
_assert_json_response_contains_group_info
(
response
)
def
test_delete
(
self
,
mock_request
):
response
=
self
.
call_view
(
"delete_thread"
,
mock_request
)
self
.
_assert_json_response_contains_group_info
(
response
)
def
test_vote
(
self
,
mock_request
):
response
=
self
.
call_view
(
"vote_for_thread"
,
mock_request
,
view_args
=
{
"value"
:
"up"
}
)
self
.
_assert_json_response_contains_group_info
(
response
)
response
=
self
.
call_view
(
"undo_vote_for_thread"
,
mock_request
)
self
.
_assert_json_response_contains_group_info
(
response
)
def
test_flag
(
self
,
mock_request
):
response
=
self
.
call_view
(
"flag_abuse_for_thread"
,
mock_request
)
self
.
_assert_json_response_contains_group_info
(
response
)
response
=
self
.
call_view
(
"un_flag_abuse_for_thread"
,
mock_request
)
self
.
_assert_json_response_contains_group_info
(
response
)
def
test_pin
(
self
,
mock_request
):
response
=
self
.
call_view
(
"pin_thread"
,
mock_request
,
user
=
self
.
moderator
)
self
.
_assert_json_response_contains_group_info
(
response
)
response
=
self
.
call_view
(
"un_pin_thread"
,
mock_request
,
user
=
self
.
moderator
)
self
.
_assert_json_response_contains_group_info
(
response
)
def
test_openclose
(
self
,
mock_request
):
response
=
self
.
call_view
(
"openclose_thread"
,
mock_request
,
user
=
self
.
moderator
)
self
.
_assert_json_response_contains_group_info
(
response
,
lambda
d
:
d
[
'content'
]
)
@override_settings
(
MODULESTORE
=
TEST_DATA_MIXED_MODULESTORE
)
@override_settings
(
MODULESTORE
=
TEST_DATA_MIXED_MODULESTORE
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
...
@@ -678,9 +779,9 @@ class ViewPermissionsTestCase(UrlResetMixin, ModuleStoreTestCase, MockRequestSet
...
@@ -678,9 +779,9 @@ class ViewPermissionsTestCase(UrlResetMixin, ModuleStoreTestCase, MockRequestSet
def
handle_request
(
*
args
,
**
kwargs
):
def
handle_request
(
*
args
,
**
kwargs
):
url
=
args
[
1
]
url
=
args
[
1
]
if
"/threads/"
in
url
:
if
"/threads/"
in
url
:
return
self
.
_create_re
ps
onse_mock
(
thread_data
)
return
self
.
_create_re
sp
onse_mock
(
thread_data
)
elif
"/comments/"
in
url
:
elif
"/comments/"
in
url
:
return
self
.
_create_re
ps
onse_mock
(
comment_data
)
return
self
.
_create_re
sp
onse_mock
(
comment_data
)
else
:
else
:
raise
ArgumentError
(
"Bad url to mock request"
)
raise
ArgumentError
(
"Bad url to mock request"
)
mock_request
.
side_effect
=
handle_request
mock_request
.
side_effect
=
handle_request
...
...
lms/djangoapps/django_comment_client/base/views.py
View file @
d3d4d330
...
@@ -27,8 +27,7 @@ from django_comment_client.utils import (
...
@@ -27,8 +27,7 @@ from django_comment_client.utils import (
get_ability
,
get_ability
,
JsonError
,
JsonError
,
JsonResponse
,
JsonResponse
,
safe_content
,
prepare_content
,
add_thread_group_name
,
get_group_id_for_comments_service
get_group_id_for_comments_service
)
)
from
django_comment_client.permissions
import
check_permissions_by_view
,
cached_has_permission
from
django_comment_client.permissions
import
check_permissions_by_view
,
cached_has_permission
...
@@ -60,7 +59,7 @@ def ajax_content_response(request, course_key, content):
...
@@ -60,7 +59,7 @@ def ajax_content_response(request, course_key, content):
user_info
=
cc
.
User
.
from_django_user
(
request
.
user
)
.
to_dict
()
user_info
=
cc
.
User
.
from_django_user
(
request
.
user
)
.
to_dict
()
annotated_content_info
=
get_annotated_content_info
(
course_key
,
content
,
request
.
user
,
user_info
)
annotated_content_info
=
get_annotated_content_info
(
course_key
,
content
,
request
.
user
,
user_info
)
return
JsonResponse
({
return
JsonResponse
({
'content'
:
saf
e_content
(
content
,
course_key
),
'content'
:
prepar
e_content
(
content
,
course_key
),
'annotated_content_info'
:
annotated_content_info
,
'annotated_content_info'
:
annotated_content_info
,
})
})
...
@@ -122,12 +121,11 @@ def create_thread(request, course_id, commentable_id):
...
@@ -122,12 +121,11 @@ def create_thread(request, course_id, commentable_id):
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
.
follow
(
thread
)
user
.
follow
(
thread
)
data
=
thread
.
to_dict
()
data
=
thread
.
to_dict
()
add_thread_group_name
(
data
,
course_key
)
add_courseware_context
([
data
],
course
)
add_courseware_context
([
data
],
course
)
if
request
.
is_ajax
():
if
request
.
is_ajax
():
return
ajax_content_response
(
request
,
course_key
,
data
)
return
ajax_content_response
(
request
,
course_key
,
data
)
else
:
else
:
return
JsonResponse
(
saf
e_content
(
data
,
course_key
))
return
JsonResponse
(
prepar
e_content
(
data
,
course_key
))
@require_POST
@require_POST
...
@@ -146,10 +144,11 @@ def update_thread(request, course_id, thread_id):
...
@@ -146,10 +144,11 @@ def update_thread(request, course_id, thread_id):
thread
.
body
=
request
.
POST
[
"body"
]
thread
.
body
=
request
.
POST
[
"body"
]
thread
.
title
=
request
.
POST
[
"title"
]
thread
.
title
=
request
.
POST
[
"title"
]
thread
.
save
()
thread
.
save
()
if
request
.
is_ajax
():
if
request
.
is_ajax
():
return
ajax_content_response
(
request
,
course_key
,
thread
.
to_dict
())
return
ajax_content_response
(
request
,
course_key
,
thread
.
to_dict
())
else
:
else
:
return
JsonResponse
(
saf
e_content
(
thread
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepar
e_content
(
thread
.
to_dict
(),
course_key
))
def
_create_comment
(
request
,
course_key
,
thread_id
=
None
,
parent_id
=
None
):
def
_create_comment
(
request
,
course_key
,
thread_id
=
None
,
parent_id
=
None
):
...
@@ -190,7 +189,7 @@ def _create_comment(request, course_key, thread_id=None, parent_id=None):
...
@@ -190,7 +189,7 @@ def _create_comment(request, course_key, thread_id=None, parent_id=None):
if
request
.
is_ajax
():
if
request
.
is_ajax
():
return
ajax_content_response
(
request
,
course_key
,
comment
.
to_dict
())
return
ajax_content_response
(
request
,
course_key
,
comment
.
to_dict
())
else
:
else
:
return
JsonResponse
(
saf
e_content
(
comment
.
to_dict
(),
course
.
id
))
return
JsonResponse
(
prepar
e_content
(
comment
.
to_dict
(),
course
.
id
))
@require_POST
@require_POST
...
@@ -218,7 +217,8 @@ def delete_thread(request, course_id, thread_id):
...
@@ -218,7 +217,8 @@ def delete_thread(request, course_id, thread_id):
course_key
=
SlashSeparatedCourseKey
.
from_deprecated_string
(
course_id
)
course_key
=
SlashSeparatedCourseKey
.
from_deprecated_string
(
course_id
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
.
delete
()
thread
.
delete
()
return
JsonResponse
(
safe_content
(
thread
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepare_content
(
thread
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -238,7 +238,7 @@ def update_comment(request, course_id, comment_id):
...
@@ -238,7 +238,7 @@ def update_comment(request, course_id, comment_id):
if
request
.
is_ajax
():
if
request
.
is_ajax
():
return
ajax_content_response
(
request
,
course_key
,
comment
.
to_dict
())
return
ajax_content_response
(
request
,
course_key
,
comment
.
to_dict
())
else
:
else
:
return
JsonResponse
(
saf
e_content
(
comment
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepar
e_content
(
comment
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -254,7 +254,7 @@ def endorse_comment(request, course_id, comment_id):
...
@@ -254,7 +254,7 @@ def endorse_comment(request, course_id, comment_id):
comment
.
endorsed
=
request
.
POST
.
get
(
'endorsed'
,
'false'
)
.
lower
()
==
'true'
comment
.
endorsed
=
request
.
POST
.
get
(
'endorsed'
,
'false'
)
.
lower
()
==
'true'
comment
.
endorsement_user_id
=
request
.
user
.
id
comment
.
endorsement_user_id
=
request
.
user
.
id
comment
.
save
()
comment
.
save
()
return
JsonResponse
(
saf
e_content
(
comment
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepar
e_content
(
comment
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -269,10 +269,10 @@ def openclose_thread(request, course_id, thread_id):
...
@@ -269,10 +269,10 @@ def openclose_thread(request, course_id, thread_id):
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
.
closed
=
request
.
POST
.
get
(
'closed'
,
'false'
)
.
lower
()
==
'true'
thread
.
closed
=
request
.
POST
.
get
(
'closed'
,
'false'
)
.
lower
()
==
'true'
thread
.
save
()
thread
.
save
()
thread
=
thread
.
to_dict
()
return
JsonResponse
({
return
JsonResponse
({
'content'
:
safe_content
(
thread
,
course_key
),
'content'
:
prepare_content
(
thread
.
to_dict
()
,
course_key
),
'ability'
:
get_ability
(
course_key
,
thread
,
request
.
user
),
'ability'
:
get_ability
(
course_key
,
thread
.
to_dict
()
,
request
.
user
),
})
})
...
@@ -301,7 +301,7 @@ def delete_comment(request, course_id, comment_id):
...
@@ -301,7 +301,7 @@ def delete_comment(request, course_id, comment_id):
course_key
=
SlashSeparatedCourseKey
.
from_deprecated_string
(
course_id
)
course_key
=
SlashSeparatedCourseKey
.
from_deprecated_string
(
course_id
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
comment
.
delete
()
comment
.
delete
()
return
JsonResponse
(
saf
e_content
(
comment
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepar
e_content
(
comment
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -315,7 +315,7 @@ def vote_for_comment(request, course_id, comment_id, value):
...
@@ -315,7 +315,7 @@ def vote_for_comment(request, course_id, comment_id, value):
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
user
.
vote
(
comment
,
value
)
user
.
vote
(
comment
,
value
)
return
JsonResponse
(
saf
e_content
(
comment
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepar
e_content
(
comment
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -330,7 +330,7 @@ def undo_vote_for_comment(request, course_id, comment_id):
...
@@ -330,7 +330,7 @@ def undo_vote_for_comment(request, course_id, comment_id):
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
user
.
unvote
(
comment
)
user
.
unvote
(
comment
)
return
JsonResponse
(
saf
e_content
(
comment
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepar
e_content
(
comment
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -345,7 +345,8 @@ def vote_for_thread(request, course_id, thread_id, value):
...
@@ -345,7 +345,8 @@ def vote_for_thread(request, course_id, thread_id, value):
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
user
.
vote
(
thread
,
value
)
user
.
vote
(
thread
,
value
)
return
JsonResponse
(
safe_content
(
thread
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepare_content
(
thread
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -360,7 +361,8 @@ def flag_abuse_for_thread(request, course_id, thread_id):
...
@@ -360,7 +361,8 @@ def flag_abuse_for_thread(request, course_id, thread_id):
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
.
flagAbuse
(
user
,
thread
)
thread
.
flagAbuse
(
user
,
thread
)
return
JsonResponse
(
safe_content
(
thread
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepare_content
(
thread
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -377,7 +379,8 @@ def un_flag_abuse_for_thread(request, course_id, thread_id):
...
@@ -377,7 +379,8 @@ def un_flag_abuse_for_thread(request, course_id, thread_id):
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
remove_all
=
cached_has_permission
(
request
.
user
,
'openclose_thread'
,
course_key
)
or
has_access
(
request
.
user
,
'staff'
,
course
)
remove_all
=
cached_has_permission
(
request
.
user
,
'openclose_thread'
,
course_key
)
or
has_access
(
request
.
user
,
'staff'
,
course
)
thread
.
unFlagAbuse
(
user
,
thread
,
remove_all
)
thread
.
unFlagAbuse
(
user
,
thread
,
remove_all
)
return
JsonResponse
(
safe_content
(
thread
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepare_content
(
thread
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -392,7 +395,7 @@ def flag_abuse_for_comment(request, course_id, comment_id):
...
@@ -392,7 +395,7 @@ def flag_abuse_for_comment(request, course_id, comment_id):
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
comment
.
flagAbuse
(
user
,
comment
)
comment
.
flagAbuse
(
user
,
comment
)
return
JsonResponse
(
saf
e_content
(
comment
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepar
e_content
(
comment
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -409,7 +412,7 @@ def un_flag_abuse_for_comment(request, course_id, comment_id):
...
@@ -409,7 +412,7 @@ def un_flag_abuse_for_comment(request, course_id, comment_id):
remove_all
=
cached_has_permission
(
request
.
user
,
'openclose_thread'
,
course_key
)
or
has_access
(
request
.
user
,
'staff'
,
course
)
remove_all
=
cached_has_permission
(
request
.
user
,
'openclose_thread'
,
course_key
)
or
has_access
(
request
.
user
,
'staff'
,
course
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
comment
=
cc
.
Comment
.
find
(
comment_id
)
comment
.
unFlagAbuse
(
user
,
comment
,
remove_all
)
comment
.
unFlagAbuse
(
user
,
comment
,
remove_all
)
return
JsonResponse
(
saf
e_content
(
comment
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepar
e_content
(
comment
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -424,7 +427,8 @@ def undo_vote_for_thread(request, course_id, thread_id):
...
@@ -424,7 +427,8 @@ def undo_vote_for_thread(request, course_id, thread_id):
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
user
.
unvote
(
thread
)
user
.
unvote
(
thread
)
return
JsonResponse
(
safe_content
(
thread
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepare_content
(
thread
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -439,7 +443,8 @@ def pin_thread(request, course_id, thread_id):
...
@@ -439,7 +443,8 @@ def pin_thread(request, course_id, thread_id):
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
.
pin
(
user
,
thread_id
)
thread
.
pin
(
user
,
thread_id
)
return
JsonResponse
(
safe_content
(
thread
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepare_content
(
thread
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
@@ -454,7 +459,8 @@ def un_pin_thread(request, course_id, thread_id):
...
@@ -454,7 +459,8 @@ def un_pin_thread(request, course_id, thread_id):
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
user
=
cc
.
User
.
from_django_user
(
request
.
user
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
=
cc
.
Thread
.
find
(
thread_id
)
thread
.
un_pin
(
user
,
thread_id
)
thread
.
un_pin
(
user
,
thread_id
)
return
JsonResponse
(
safe_content
(
thread
.
to_dict
(),
course_key
))
return
JsonResponse
(
prepare_content
(
thread
.
to_dict
(),
course_key
))
@require_POST
@require_POST
...
...
lms/djangoapps/django_comment_client/forum/tests.py
View file @
d3d4d330
...
@@ -122,7 +122,7 @@ def make_mock_request_impl(text, thread_id="dummy_thread_id", group_id=None):
...
@@ -122,7 +122,7 @@ def make_mock_request_impl(text, thread_id="dummy_thread_id", group_id=None):
def
mock_request_impl
(
*
args
,
**
kwargs
):
def
mock_request_impl
(
*
args
,
**
kwargs
):
url
=
args
[
1
]
url
=
args
[
1
]
data
=
None
data
=
None
if
url
.
endswith
(
"threads"
):
if
url
.
endswith
(
"threads"
)
or
url
.
endswith
(
"user_profile"
)
:
data
=
{
data
=
{
"collection"
:
[
make_mock_thread_data
(
text
,
thread_id
,
False
,
group_id
=
group_id
)]
"collection"
:
[
make_mock_thread_data
(
text
,
thread_id
,
False
,
group_id
=
group_id
)]
}
}
...
@@ -406,15 +406,19 @@ class SingleThreadAccessTestCase(CohortedContentTestCase):
...
@@ -406,15 +406,19 @@ class SingleThreadAccessTestCase(CohortedContentTestCase):
class
SingleThreadGroupIdTestCase
(
CohortedContentTestCase
,
CohortedTopicGroupIdTestMixin
):
class
SingleThreadGroupIdTestCase
(
CohortedContentTestCase
,
CohortedTopicGroupIdTestMixin
):
cs_endpoint
=
"/threads"
cs_endpoint
=
"/threads"
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
):
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
,
is_ajax
=
False
):
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy context"
,
group_id
=
self
.
student_cohort
.
id
)
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy context"
,
group_id
=
self
.
student_cohort
.
id
)
request_data
=
{}
request_data
=
{}
if
pass_group_id
:
if
pass_group_id
:
request_data
[
"group_id"
]
=
group_id
request_data
[
"group_id"
]
=
group_id
headers
=
{}
if
is_ajax
:
headers
[
'HTTP_X_REQUESTED_WITH'
]
=
"XMLHttpRequest"
request
=
RequestFactory
()
.
get
(
request
=
RequestFactory
()
.
get
(
"dummy_url"
,
"dummy_url"
,
data
=
request_data
data
=
request_data
,
**
headers
)
)
request
.
user
=
user
request
.
user
=
user
mako_middleware_process_request
(
request
)
mako_middleware_process_request
(
request
)
...
@@ -425,6 +429,28 @@ class SingleThreadGroupIdTestCase(CohortedContentTestCase, CohortedTopicGroupIdT
...
@@ -425,6 +429,28 @@ class SingleThreadGroupIdTestCase(CohortedContentTestCase, CohortedTopicGroupIdT
"dummy_thread_id"
"dummy_thread_id"
)
)
def
test_group_info_in_html_response
(
self
,
mock_request
):
response
=
self
.
call_view
(
mock_request
,
"cohorted_topic"
,
self
.
student
,
self
.
student_cohort
.
id
,
is_ajax
=
False
)
self
.
_assert_html_response_contains_group_info
(
response
)
def
test_group_info_in_ajax_response
(
self
,
mock_request
):
response
=
self
.
call_view
(
mock_request
,
"cohorted_topic"
,
self
.
student
,
self
.
student_cohort
.
id
,
is_ajax
=
True
)
self
.
_assert_json_response_contains_group_info
(
response
,
lambda
d
:
d
[
'content'
]
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
class
InlineDiscussionGroupIdTestCase
(
class
InlineDiscussionGroupIdTestCase
(
...
@@ -435,7 +461,17 @@ class InlineDiscussionGroupIdTestCase(
...
@@ -435,7 +461,17 @@ class InlineDiscussionGroupIdTestCase(
cs_endpoint
=
"/threads"
cs_endpoint
=
"/threads"
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
):
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
):
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy content"
)
kwargs
=
{}
if
group_id
:
# avoid causing a server error when the LMS chokes attempting
# to find a group name for the group_id, when we're testing with
# an invalid one.
try
:
CourseUserGroup
.
objects
.
get
(
id
=
group_id
)
kwargs
[
'group_id'
]
=
group_id
except
CourseUserGroup
.
DoesNotExist
:
pass
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy content"
,
**
kwargs
)
request_data
=
{}
request_data
=
{}
if
pass_group_id
:
if
pass_group_id
:
...
@@ -451,20 +487,38 @@ class InlineDiscussionGroupIdTestCase(
...
@@ -451,20 +487,38 @@ class InlineDiscussionGroupIdTestCase(
commentable_id
commentable_id
)
)
def
test_group_info_in_ajax_response
(
self
,
mock_request
):
response
=
self
.
call_view
(
mock_request
,
"cohorted_topic"
,
self
.
student
,
self
.
student_cohort
.
id
)
self
.
_assert_json_response_contains_group_info
(
response
,
lambda
d
:
d
[
'discussion_data'
][
0
]
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
class
ForumFormDiscussionGroupIdTestCase
(
CohortedContentTestCase
,
CohortedTopicGroupIdTestMixin
):
class
ForumFormDiscussionGroupIdTestCase
(
CohortedContentTestCase
,
CohortedTopicGroupIdTestMixin
):
cs_endpoint
=
"/threads"
cs_endpoint
=
"/threads"
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
):
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
,
is_ajax
=
False
):
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy content"
)
kwargs
=
{}
if
group_id
:
kwargs
[
'group_id'
]
=
group_id
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy content"
,
**
kwargs
)
request_data
=
{}
request_data
=
{}
if
pass_group_id
:
if
pass_group_id
:
request_data
[
"group_id"
]
=
group_id
request_data
[
"group_id"
]
=
group_id
headers
=
{}
if
is_ajax
:
headers
[
'HTTP_X_REQUESTED_WITH'
]
=
"XMLHttpRequest"
request
=
RequestFactory
()
.
get
(
request
=
RequestFactory
()
.
get
(
"dummy_url"
,
"dummy_url"
,
data
=
request_data
data
=
request_data
,
**
headers
)
)
request
.
user
=
user
request
.
user
=
user
mako_middleware_process_request
(
request
)
mako_middleware_process_request
(
request
)
...
@@ -473,20 +527,47 @@ class ForumFormDiscussionGroupIdTestCase(CohortedContentTestCase, CohortedTopicG
...
@@ -473,20 +527,47 @@ class ForumFormDiscussionGroupIdTestCase(CohortedContentTestCase, CohortedTopicG
self
.
course
.
id
.
to_deprecated_string
()
self
.
course
.
id
.
to_deprecated_string
()
)
)
def
test_group_info_in_html_response
(
self
,
mock_request
):
response
=
self
.
call_view
(
mock_request
,
"cohorted_topic"
,
self
.
student
,
self
.
student_cohort
.
id
)
self
.
_assert_html_response_contains_group_info
(
response
)
def
test_group_info_in_ajax_response
(
self
,
mock_request
):
response
=
self
.
call_view
(
mock_request
,
"cohorted_topic"
,
self
.
student
,
self
.
student_cohort
.
id
,
is_ajax
=
True
)
self
.
_assert_json_response_contains_group_info
(
response
,
lambda
d
:
d
[
'discussion_data'
][
0
]
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
class
UserProfileDiscussionGroupIdTestCase
(
CohortedContentTestCase
,
CohortedTopicGroupIdTestMixin
):
class
UserProfileDiscussionGroupIdTestCase
(
CohortedContentTestCase
,
CohortedTopicGroupIdTestMixin
):
cs_endpoint
=
"/active_threads"
cs_endpoint
=
"/active_threads"
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
):
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
,
is_ajax
=
False
):
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy content"
)
kwargs
=
{}
if
group_id
:
kwargs
[
'group_id'
]
=
group_id
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy content"
,
**
kwargs
)
request_data
=
{}
request_data
=
{}
if
pass_group_id
:
if
pass_group_id
:
request_data
[
"group_id"
]
=
group_id
request_data
[
"group_id"
]
=
group_id
headers
=
{}
if
is_ajax
:
headers
[
'HTTP_X_REQUESTED_WITH'
]
=
"XMLHttpRequest"
request
=
RequestFactory
()
.
get
(
request
=
RequestFactory
()
.
get
(
"dummy_url"
,
"dummy_url"
,
data
=
request_data
data
=
request_data
,
**
headers
)
)
request
.
user
=
user
request
.
user
=
user
mako_middleware_process_request
(
request
)
mako_middleware_process_request
(
request
)
...
@@ -496,13 +577,38 @@ class UserProfileDiscussionGroupIdTestCase(CohortedContentTestCase, CohortedTopi
...
@@ -496,13 +577,38 @@ class UserProfileDiscussionGroupIdTestCase(CohortedContentTestCase, CohortedTopi
user
.
id
user
.
id
)
)
def
test_group_info_in_html_response
(
self
,
mock_request
):
response
=
self
.
call_view
(
mock_request
,
"cohorted_topic"
,
self
.
student
,
self
.
student_cohort
.
id
,
is_ajax
=
False
)
self
.
_assert_html_response_contains_group_info
(
response
)
def
test_group_info_in_ajax_response
(
self
,
mock_request
):
response
=
self
.
call_view
(
mock_request
,
"cohorted_topic"
,
self
.
student
,
self
.
student_cohort
.
id
,
is_ajax
=
True
)
self
.
_assert_json_response_contains_group_info
(
response
,
lambda
d
:
d
[
'discussion_data'
][
0
]
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
@patch
(
'lms.lib.comment_client.utils.requests.request'
)
class
FollowedThreadsDiscussionGroupIdTestCase
(
CohortedContentTestCase
,
CohortedTopicGroupIdTestMixin
):
class
FollowedThreadsDiscussionGroupIdTestCase
(
CohortedContentTestCase
,
CohortedTopicGroupIdTestMixin
):
cs_endpoint
=
"/subscribed_threads"
cs_endpoint
=
"/subscribed_threads"
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
):
def
call_view
(
self
,
mock_request
,
commentable_id
,
user
,
group_id
,
pass_group_id
=
True
):
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy content"
)
kwargs
=
{}
if
group_id
:
kwargs
[
'group_id'
]
=
group_id
mock_request
.
side_effect
=
make_mock_request_impl
(
"dummy content"
,
**
kwargs
)
request_data
=
{}
request_data
=
{}
if
pass_group_id
:
if
pass_group_id
:
...
@@ -519,6 +625,17 @@ class FollowedThreadsDiscussionGroupIdTestCase(CohortedContentTestCase, Cohorted
...
@@ -519,6 +625,17 @@ class FollowedThreadsDiscussionGroupIdTestCase(CohortedContentTestCase, Cohorted
user
.
id
user
.
id
)
)
def
test_group_info_in_ajax_response
(
self
,
mock_request
):
response
=
self
.
call_view
(
mock_request
,
"cohorted_topic"
,
self
.
student
,
self
.
student_cohort
.
id
)
self
.
_assert_json_response_contains_group_info
(
response
,
lambda
d
:
d
[
'discussion_data'
][
0
]
)
@override_settings
(
MODULESTORE
=
TEST_DATA_MIXED_MODULESTORE
)
@override_settings
(
MODULESTORE
=
TEST_DATA_MIXED_MODULESTORE
)
@patch
(
'requests.request'
)
@patch
(
'requests.request'
)
...
...
lms/djangoapps/django_comment_client/forum/views.py
View file @
d3d4d330
This diff is collapsed.
Click to expand it.
lms/djangoapps/django_comment_client/tests/group_id.py
View file @
d3d4d330
import
json
import
re
from
course_groups.models
import
CourseUserGroup
class
GroupIdAssertionMixin
(
object
):
class
GroupIdAssertionMixin
(
object
):
def
_data_or_params_cs_request
(
self
,
mock_request
):
def
_data_or_params_cs_request
(
self
,
mock_request
):
"""
"""
...
@@ -17,6 +22,31 @@ class GroupIdAssertionMixin(object):
...
@@ -17,6 +22,31 @@ class GroupIdAssertionMixin(object):
self
.
assertTrue
(
mock_request
.
called
)
self
.
assertTrue
(
mock_request
.
called
)
self
.
assertNotIn
(
"group_id"
,
self
.
_data_or_params_cs_request
(
mock_request
))
self
.
assertNotIn
(
"group_id"
,
self
.
_data_or_params_cs_request
(
mock_request
))
def
_assert_html_response_contains_group_info
(
self
,
response
):
group_info
=
{
"group_id"
:
None
,
"group_name"
:
None
}
match
=
re
.
search
(
r'"group_id": ([\d]*)'
,
response
.
content
)
if
match
and
match
.
group
(
1
)
!=
''
:
group_info
[
"group_id"
]
=
int
(
match
.
group
(
1
))
match
=
re
.
search
(
r'"group_name": "([^&]*)"'
,
response
.
content
)
if
match
:
group_info
[
"group_name"
]
=
match
.
group
(
1
)
self
.
_assert_thread_contains_group_info
(
group_info
)
def
_assert_json_response_contains_group_info
(
self
,
response
,
extract_thread
=
None
):
"""
:param extract_thread: a function which accepts a dictionary (complete
json response payload) and returns another dictionary (first
occurrence of a thread model within that payload). if None is
passed, the identity function is assumed.
"""
payload
=
json
.
loads
(
response
.
content
)
thread
=
extract_thread
(
payload
)
if
extract_thread
else
payload
self
.
_assert_thread_contains_group_info
(
thread
)
def
_assert_thread_contains_group_info
(
self
,
thread
):
self
.
assertEqual
(
thread
[
'group_id'
],
self
.
student_cohort
.
id
)
self
.
assertEqual
(
thread
[
'group_name'
],
self
.
student_cohort
.
name
)
class
CohortedTopicGroupIdTestMixin
(
GroupIdAssertionMixin
):
class
CohortedTopicGroupIdTestMixin
(
GroupIdAssertionMixin
):
"""
"""
...
...
lms/djangoapps/django_comment_client/utils.py
View file @
d3d4d330
...
@@ -366,7 +366,16 @@ def add_courseware_context(content_list, course):
...
@@ -366,7 +366,16 @@ def add_courseware_context(content_list, course):
content
.
update
({
"courseware_url"
:
url
,
"courseware_title"
:
title
})
content
.
update
({
"courseware_url"
:
url
,
"courseware_title"
:
title
})
def
safe_content
(
content
,
course_id
,
is_staff
=
False
):
def
prepare_content
(
content
,
course_key
,
is_staff
=
False
):
"""
This function is used to pre-process thread and comment models in various
ways before adding them to the HTTP response. This includes fixing empty
attribute fields, enforcing author anonymity, and enriching metadata around
group ownership and response endorsement.
@TODO: not all response pre-processing steps are currently integrated into
this function.
"""
fields
=
[
fields
=
[
'id'
,
'title'
,
'body'
,
'course_id'
,
'anonymous'
,
'anonymous_to_peers'
,
'id'
,
'title'
,
'body'
,
'course_id'
,
'anonymous'
,
'anonymous_to_peers'
,
'endorsed'
,
'parent_id'
,
'thread_id'
,
'votes'
,
'closed'
,
'created_at'
,
'endorsed'
,
'parent_id'
,
'thread_id'
,
'votes'
,
'closed'
,
'created_at'
,
...
@@ -407,20 +416,16 @@ def safe_content(content, course_id, is_staff=False):
...
@@ -407,20 +416,16 @@ def safe_content(content, course_id, is_staff=False):
for
child_content_key
in
[
"children"
,
"endorsed_responses"
,
"non_endorsed_responses"
]:
for
child_content_key
in
[
"children"
,
"endorsed_responses"
,
"non_endorsed_responses"
]:
if
child_content_key
in
content
:
if
child_content_key
in
content
:
safe_
children
=
[
children
=
[
safe_content
(
child
,
course_id
,
is_staff
)
for
child
in
content
[
child_content_key
]
prepare_content
(
child
,
course_key
,
is_staff
)
for
child
in
content
[
child_content_key
]
]
]
content
[
child_content_key
]
=
safe_children
content
[
child_content_key
]
=
children
return
content
# Augment the specified thread info to include the group name if a group id is present.
if
content
.
get
(
'group_id'
)
is
not
None
:
content
[
'group_name'
]
=
get_cohort_by_id
(
course_key
,
content
.
get
(
'group_id'
))
.
name
def
add_thread_group_name
(
thread_info
,
course_key
):
return
content
"""
Augment the specified thread info to include the group name if a group id is present.
"""
if
thread_info
.
get
(
'group_id'
)
is
not
None
:
thread_info
[
'group_name'
]
=
get_cohort_by_id
(
course_key
,
thread_info
.
get
(
'group_id'
))
.
name
def
get_group_id_for_comments_service
(
request
,
course_key
,
commentable_id
=
None
):
def
get_group_id_for_comments_service
(
request
,
course_key
,
commentable_id
=
None
):
...
...
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