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
be1adc38
Commit
be1adc38
authored
Dec 11, 2015
by
Sarina Canelake
Browse files
Options
Browse Files
Download
Plain Diff
Merge pull request #10964 from edx/kill-abtest
Remove outdated abtest_module
parents
557a411c
46bbd0a6
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
0 additions
and
160 deletions
+0
-160
common/lib/xmodule/setup.py
+0
-1
common/lib/xmodule/xmodule/abtest_module.py
+0
-159
No files found.
common/lib/xmodule/setup.py
View file @
be1adc38
from
setuptools
import
setup
,
find_packages
XMODULES
=
[
"abtest = xmodule.abtest_module:ABTestDescriptor"
,
"book = xmodule.backcompat_module:TranslateCustomTagDescriptor"
,
"chapter = xmodule.seq_module:SequenceDescriptor"
,
"combinedopenended = xmodule.combined_open_ended_module:CombinedOpenEndedDescriptor"
,
...
...
common/lib/xmodule/xmodule/abtest_module.py
deleted
100644 → 0
View file @
557a411c
import
random
import
logging
from
lxml
import
etree
from
xmodule.x_module
import
XModule
from
xmodule.raw_module
import
RawDescriptor
from
xmodule.xml_module
import
XmlDescriptor
from
xmodule.exceptions
import
InvalidDefinitionError
from
xblock.fields
import
String
,
Scope
,
Dict
DEFAULT
=
"_DEFAULT_GROUP"
log
=
logging
.
getLogger
(
__name__
)
def
group_from_value
(
groups
,
v
):
"""
Given group: (('a', 0.3), ('b', 0.4), ('c', 0.3)) and random value v
in [0,1], return the associated group (in the above case, return
'a' if v < 0.3, 'b' if 0.3 <= v < 0.7, and 'c' if v > 0.7
"""
sum
=
0
for
(
g
,
p
)
in
groups
:
sum
=
sum
+
p
if
sum
>
v
:
return
g
# Round off errors might cause us to run to the end of the list.
# If the do, return the last element.
return
g
class
ABTestFields
(
object
):
group_portions
=
Dict
(
help
=
"What proportions of students should go in each group"
,
default
=
{
DEFAULT
:
1
},
scope
=
Scope
.
content
)
group_assignments
=
Dict
(
help
=
"What group this user belongs to"
,
scope
=
Scope
.
preferences
,
default
=
{})
group_content
=
Dict
(
help
=
"What content to display to each group"
,
scope
=
Scope
.
content
,
default
=
{
DEFAULT
:
[]})
experiment
=
String
(
help
=
"Experiment that this A/B test belongs to"
,
scope
=
Scope
.
content
)
has_children
=
True
class
ABTestModule
(
ABTestFields
,
XModule
):
"""
Implements an A/B test with an aribtrary number of competing groups
"""
def
__init__
(
self
,
*
args
,
**
kwargs
):
super
(
ABTestModule
,
self
)
.
__init__
(
*
args
,
**
kwargs
)
if
self
.
group
is
None
:
self
.
group
=
group_from_value
(
self
.
group_portions
.
items
(),
random
.
uniform
(
0
,
1
)
)
@property
def
group
(
self
):
return
self
.
group_assignments
.
get
(
self
.
experiment
)
@group.setter
def
group
(
self
,
value
):
self
.
group_assignments
[
self
.
experiment
]
=
value
@group.deleter
def
group
(
self
):
del
self
.
group_assignments
[
self
.
experiment
]
def
get_child_descriptors
(
self
):
active_locations
=
set
(
self
.
group_content
[
self
.
group
])
return
[
desc
for
desc
in
self
.
descriptor
.
get_children
()
if
desc
.
location
.
to_deprecated_string
()
in
active_locations
]
def
displayable_items
(
self
):
# Most modules return "self" as the displayable_item. We never display ourself
# (which is why we don't implement get_html). We only display our children.
return
self
.
get_children
()
# TODO (cpennington): Use Groups should be a first class object, rather than being
# managed by ABTests
class
ABTestDescriptor
(
ABTestFields
,
RawDescriptor
,
XmlDescriptor
):
module_class
=
ABTestModule
show_in_read_only_mode
=
True
@classmethod
def
definition_from_xml
(
cls
,
xml_object
,
system
):
"""
XML Format:
<abtest experiment="experiment_name">
<group name="a" portion=".1"><contenta/></group>
<group name="b" portion=".2"><contentb/></group>
<default><contentdefault/></default>
</abtest>
"""
experiment
=
xml_object
.
get
(
'experiment'
)
if
experiment
is
None
:
raise
InvalidDefinitionError
(
"ABTests must specify an experiment. Not found in:
\n
{xml}"
.
format
(
xml
=
etree
.
tostring
(
xml_object
,
pretty_print
=
True
)))
group_portions
=
{}
group_content
=
{}
children
=
[]
for
group
in
xml_object
:
if
group
.
tag
==
'default'
:
name
=
DEFAULT
else
:
name
=
group
.
get
(
'name'
)
group_portions
[
name
]
=
float
(
group
.
get
(
'portion'
,
0
))
child_content_urls
=
[]
for
child
in
group
:
try
:
child_block
=
system
.
process_xml
(
etree
.
tostring
(
child
))
child_content_urls
.
append
(
child_block
.
scope_ids
.
usage_id
)
except
:
log
.
exception
(
"Unable to load child when parsing ABTest. Continuing..."
)
continue
group_content
[
name
]
=
child_content_urls
children
.
extend
(
child_content_urls
)
default_portion
=
1
-
sum
(
portion
for
(
name
,
portion
)
in
group_portions
.
items
()
)
if
default_portion
<
0
:
raise
InvalidDefinitionError
(
"ABTest portions must add up to less than or equal to 1"
)
group_portions
[
DEFAULT
]
=
default_portion
children
.
sort
()
return
{
'group_portions'
:
group_portions
,
'group_content'
:
group_content
,
},
children
def
definition_to_xml
(
self
,
resource_fs
):
xml_object
=
etree
.
Element
(
'abtest'
)
xml_object
.
set
(
'experiment'
,
self
.
experiment
)
for
name
,
group
in
self
.
group_content
.
items
():
if
name
==
DEFAULT
:
group_elem
=
etree
.
SubElement
(
xml_object
,
'default'
)
else
:
group_elem
=
etree
.
SubElement
(
xml_object
,
'group'
,
attrib
=
{
'portion'
:
str
(
self
.
group_portions
[
name
]),
'name'
:
name
,
})
for
child_loc
in
group
:
child
=
self
.
system
.
load_item
(
child_loc
)
self
.
runtime
.
add_block_as_child_node
(
child
,
group_elem
)
return
xml_object
def
has_dynamic_children
(
self
):
return
True
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