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
110637c0
Commit
110637c0
authored
Aug 06, 2012
by
kimth
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
XqueueInterface is a singleton instantiated object
parent
6c875206
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
74 additions
and
59 deletions
+74
-59
common/lib/capa/capa/responsetypes.py
+9
-7
common/lib/capa/capa/xqueue_interface.py
+65
-52
No files found.
common/lib/capa/capa/responsetypes.py
View file @
110637c0
...
...
@@ -29,6 +29,8 @@ import xqueue_interface
log
=
logging
.
getLogger
(
'mitx.'
+
__name__
)
qinterface
=
xqueue_interface
.
XqueueInterface
()
#-----------------------------------------------------------------------------
# Exceptions
...
...
@@ -809,7 +811,6 @@ class CodeResponse(LoncapaResponse):
def
setup_response
(
self
):
xml
=
self
.
xml
self
.
url
=
xml
.
get
(
'url'
)
self
.
queue_name
=
xml
.
get
(
'queuename'
,
self
.
system
.
xqueue_default_queuename
)
answer
=
xml
.
find
(
'answer'
)
...
...
@@ -877,16 +878,17 @@ class CodeResponse(LoncapaResponse):
# Submit request
if
hasattr
(
submission
,
'read'
):
# Test for whether submission is a file
error
=
xqueue_
interface
.
send_to_queue
(
header
=
xheader
,
body
=
json
.
dumps
(
contents
),
file_to_upload
=
submission
)
(
error
,
msg
)
=
q
interface
.
send_to_queue
(
header
=
xheader
,
body
=
json
.
dumps
(
contents
),
file_to_upload
=
submission
)
else
:
error
=
xqueue_
interface
.
send_to_queue
(
header
=
xheader
,
body
=
json
.
dumps
(
contents
))
(
error
,
msg
)
=
q
interface
.
send_to_queue
(
header
=
xheader
,
body
=
json
.
dumps
(
contents
))
cmap
=
CorrectMap
()
if
error
:
cmap
.
set
(
self
.
answer_id
,
queuekey
=
None
,
msg
=
'Unable to deliver your submission to grader! Please try again later'
)
cmap
.
set
(
self
.
answer_id
,
queuekey
=
None
,
msg
=
'Unable to deliver your submission to grader. (Reason:
%
s.) Please try again later.'
%
msg
)
else
:
# Non-null CorrectMap['queuekey'] indicates that the problem has been queued
cmap
.
set
(
self
.
answer_id
,
queuekey
=
queuekey
,
msg
=
'Submitted to grader'
)
...
...
common/lib/capa/capa/xqueue_interface.py
View file @
110637c0
...
...
@@ -3,6 +3,7 @@
#
import
hashlib
import
json
import
logging
import
requests
import
time
...
...
@@ -11,6 +12,8 @@ XQUEUE_LMS_AUTH = { 'username': 'LMS',
'password'
:
'PaloAltoCA'
}
XQUEUE_URL
=
'http://xqueue.edx.org'
log
=
logging
.
getLogger
(
'mitx.'
+
__name__
)
def
make_hashkey
(
seed
=
None
):
'''
Generate a string key by hashing
...
...
@@ -37,61 +40,10 @@ def make_xheader(lms_callback_url, lms_key, queue_name):
'queue_name'
:
queue_name
})
def
send_to_queue
(
header
,
body
,
file_to_upload
=
None
,
xqueue_url
=
XQUEUE_URL
):
'''
Submit a request to xqueue.
header: JSON-serialized dict in the format described in 'xqueue_interface.make_xheader'
body: Serialized data for the receipient behind the queueing service. The operation of
xqueue is agnostic to the contents of 'body'
file_to_upload: File object to be uploaded to xqueue along with queue request
Returns an 'error' flag indicating error in xqueue transaction
'''
# First, we login with our credentials
#------------------------------------------------------------
s
=
requests
.
session
()
try
:
r
=
s
.
post
(
xqueue_url
+
'/xqueue/login/'
,
data
=
{
'username'
:
XQUEUE_LMS_AUTH
[
'username'
],
'password'
:
XQUEUE_LMS_AUTH
[
'password'
]
})
except
Exception
as
err
:
msg
=
'Error in xqueue_interface.send_to_queue
%
s: Cannot connect to server url=
%
s'
%
(
err
,
xqueue_url
)
raise
Exception
(
msg
)
# Xqueue responses are JSON-serialized dicts
(
return_code
,
msg
)
=
parse_xreply
(
r
.
text
)
if
return_code
:
# Nonzero return code from xqueue indicates error
print
' Error in queue_interface.send_to_queue:
%
s'
%
msg
return
1
# Error
# Next, we can make a queueing request
#------------------------------------------------------------
payload
=
{
'xqueue_header'
:
header
,
'xqueue_body'
:
body
}
files
=
None
if
file_to_upload
is
not
None
:
files
=
{
file_to_upload
.
name
:
file_to_upload
}
try
:
r
=
s
.
post
(
xqueue_url
+
'/xqueue/submit/'
,
data
=
payload
,
files
=
files
)
except
Exception
as
err
:
msg
=
'Error in xqueue_interface.send_to_queue
%
s: Cannot connect to server url=
%
s'
%
(
err
,
xqueue_url
)
raise
Exception
(
msg
)
(
return_code
,
msg
)
=
parse_xreply
(
r
.
text
)
if
return_code
:
print
' Error in queue_interface.send_to_queue:
%
s'
%
msg
return
return_code
def
parse_xreply
(
xreply
):
'''
Parse the reply from xqueue. Messages are JSON-serialized dict:
{ 'return_code': 0 (success), 1 (fail)
,
{ 'return_code': 0 (success), 1 (fail)
'content': Message from xqueue (string)
}
'''
...
...
@@ -99,3 +51,64 @@ def parse_xreply(xreply):
return_code
=
xreply
[
'return_code'
]
content
=
xreply
[
'content'
]
return
(
return_code
,
content
)
class
XqueueInterface
:
'''
Interface to the external grading system
'''
def
__init__
(
self
,
url
=
XQUEUE_URL
,
auth
=
XQUEUE_LMS_AUTH
):
self
.
url
=
url
self
.
auth
=
auth
self
.
s
=
requests
.
session
()
self
.
_login
()
def
send_to_queue
(
self
,
header
,
body
,
file_to_upload
=
None
):
'''
Submit a request to xqueue.
header: JSON-serialized dict in the format described in 'xqueue_interface.make_xheader'
body: Serialized data for the receipient behind the queueing service. The operation of
xqueue is agnostic to the contents of 'body'
file_to_upload: File object to be uploaded to xqueue along with queue request
Returns (error_code, msg) where error_code != 0 indicates an error
'''
# Attempt to send to queue
(
error
,
msg
)
=
self
.
_send_to_queue
(
header
,
body
,
file_to_upload
)
if
error
and
(
msg
==
'login_required'
):
# Log in, then try again
self
.
_login
()
(
error
,
msg
)
=
self
.
_send_to_queue
(
header
,
body
,
file_to_upload
)
return
(
error
,
msg
)
def
_login
(
self
):
try
:
r
=
self
.
s
.
post
(
self
.
url
+
'/xqueue/login/'
,
data
=
{
'username'
:
self
.
auth
[
'username'
],
'password'
:
self
.
auth
[
'password'
]
})
except
requests
.
exceptions
.
ConnectionError
,
err
:
log
.
error
(
err
)
return
(
1
,
'cannot connect to server'
)
return
parse_xreply
(
r
.
text
)
def
_send_to_queue
(
self
,
header
,
body
,
file_to_upload
=
None
):
payload
=
{
'xqueue_header'
:
header
,
'xqueue_body'
:
body
}
files
=
None
if
file_to_upload
is
not
None
:
files
=
{
file_to_upload
.
name
:
file_to_upload
}
try
:
r
=
self
.
s
.
post
(
self
.
url
+
'/xqueue/submit/'
,
data
=
payload
,
files
=
files
)
except
requests
.
exceptions
.
ConnectionError
,
err
:
log
.
error
(
err
)
return
(
1
,
'cannot connect to server'
)
return
parse_xreply
(
r
.
text
)
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