예제 #1
0
def dummy_battery(request,bid):
    '''dummy_battery lets the user run a faux battery (preview)'''

    battery = get_battery(bid,request)
    deployment = "docker-local"

    # Does the worker have experiments remaining?
    task_list = select_experiments(battery,uncompleted_experiments=battery.experiments.all())
    experimentTemplate = ExperimentTemplate.objects.filter(exp_id=task_list[0].template.exp_id)[0]
    experiment_type = get_experiment_type(experimentTemplate)
    task_list = battery.experiments.filter(template=experimentTemplate)
    result = None
    context = {"worker_id": "Dummy Worker"}
    if experiment_type in ["games","surveys"]:
        template = "%s/serve_battery_preview.html" %(experiment_type)
    else:
        template = "%s/serve_battery.html" %(experiment_type)

    return deploy_battery(deployment="docker-preview",
                          battery=battery,
                          experiment_type=experiment_type,
                          context=context,
                          task_list=task_list,
                          template=template,
                          result=result)
예제 #2
0
def delete_experiment_template(request, eid, do_redirect=True):
    experiment = get_experiment_template(eid, request)
    experiment_instances = Experiment.objects.filter(template=experiment)
    experiment_type = get_experiment_type(experiment)
    if check_experiment_edit_permission(request):
        # Static Files
        [e.delete() for e in experiment_instances]
        static_files_dir = os.path.join(media_dir, experiment_type,
                                        experiment.exp_id)
        if os.path.exists(static_files_dir):
            shutil.rmtree(static_files_dir)
        # delete associated results
        results = Result.objects.filter(experiment=experiment)
        [r.delete() for r in results]
        # Cognitive Atlas Task
        task = experiment.cognitive_atlas_task
        try:
            if experiment.cognitive_atlas_task.experiment_set.count() == 1:
                # We might want to delete concepts too? Ok for now.
                task.delete()
        except:
            pass
        experiment.delete()

    if do_redirect == True:
        return redirect('experiments')
예제 #3
0
def dummy_battery(request, bid):
    '''dummy_battery lets the user run a faux battery (preview)'''

    battery = get_battery(bid, request)
    deployment = "docker-local"

    # Does the worker have experiments remaining?
    task_list = select_experiments(
        battery, uncompleted_experiments=battery.experiments.all())
    experimentTemplate = ExperimentTemplate.objects.filter(
        exp_id=task_list[0].template.exp_id)[0]
    experiment_type = get_experiment_type(experimentTemplate)
    task_list = battery.experiments.filter(template=experimentTemplate)
    result = None
    context = {"worker_id": "Dummy Worker"}
    if experiment_type in ["games", "surveys"]:
        template = "%s/serve_battery_preview.html" % (experiment_type)
    else:
        template = "%s/serve_battery.html" % (experiment_type)

    return deploy_battery(deployment="docker-preview",
                          battery=battery,
                          experiment_type=experiment_type,
                          context=context,
                          task_list=task_list,
                          template=template,
                          result=result)
예제 #4
0
def view_experiment(request, eid, bid=None):

    # Determine permissions for edit and deletion
    context = dict()
    context["edit_permission"] = check_experiment_edit_permission(request)
    context["delete_permission"] = context["edit_permission"]

    # View an experiment associated with a battery
    if bid:
        experiment = get_experiment(eid, request)
        battery = get_battery(bid, request)
        context["edit_permission"] = check_battery_edit_permission(
            request, battery)
        context["delete_permission"] = context[
            "edit_permission"]  # same for now
        template = 'experiments/experiment_details.html'

    # An experiment template
    else:
        experiment = get_experiment_template(eid, request)
        template = 'experiments/experiment_template_details.html'
        context["experiment_type"] = get_experiment_type(experiment)
        battery = None

    context["battery"] = battery
    context["experiment"] = experiment

    return render_to_response(template, context)
예제 #5
0
def delete_experiment_template(request, eid, do_redirect=True):
    experiment = get_experiment_template(eid,request)
    experiment_instances = Experiment.objects.filter(template=experiment)
    experiment_type = get_experiment_type(experiment)
    if check_experiment_edit_permission(request):
        # Static Files
        [e.delete() for e in experiment_instances]
        static_files_dir = os.path.join(media_dir,experiment_type,experiment.exp_id)
        if os.path.exists(static_files_dir):
            shutil.rmtree(static_files_dir)
        # delete associated results
        results = Result.objects.filter(experiment=experiment)
        [r.delete() for r in results]
        # Cognitive Atlas Task
        task = experiment.cognitive_atlas_task
        try:
            if experiment.cognitive_atlas_task.experiment_set.count() == 1:
                # We might want to delete concepts too? Ok for now.
                task.delete()
        except:
            pass
        experiment.delete()

    if do_redirect == True:
        return redirect('experiments')
예제 #6
0
def view_experiment(request, eid, bid=None):

    # Determine permissions for edit and deletion
    context = dict()
    context["edit_permission"] = check_experiment_edit_permission(request)
    context["delete_permission"] = context["edit_permission"]

    # View an experiment associated with a battery
    if bid:
        experiment = get_experiment(eid,request)
        battery = get_battery(bid,request)
        context["edit_permission"] = check_battery_edit_permission(request,battery)
        context["delete_permission"] = context["edit_permission"] # same for now
        template = 'experiments/experiment_details.html'

    # An experiment template
    else:
        experiment = get_experiment_template(eid,request)
        template = 'experiments/experiment_template_details.html'
        context["experiment_type"] = get_experiment_type(experiment)
        battery = None

    context["battery"] = battery
    context["experiment"] = experiment

    return render_to_response(template, context)
예제 #7
0
def serve_battery(request,bid,userid=None):
    '''prepare for local serve of battery'''

    next_page = None
    battery = get_battery(bid,request)

    # No robots allowed!
    if request.user_agent.is_bot:
        return render_to_response("turk/robot_sorry.html")

    # Is userid not defined, redirect them to preview
    if userid == None:
        return preview_battery(request,bid)

    worker = get_worker(userid,create=False)
    if isinstance(worker,list): # no id means returning []
        return render_to_response("turk/invalid_id_sorry.html")

    # Try to get some info about browser, language, etc.
    browser = "%s,%s" %(request.user_agent.browser.family,request.user_agent.browser.version_string)
    platform = "%s,%s" %(request.user_agent.os.family,request.user_agent.os.version_string)
    deployment = "docker-local"

    # Does the worker have experiments remaining?
    uncompleted_experiments = get_worker_experiments(worker,battery)
    if len(uncompleted_experiments) == 0:
        # Thank you for your participation - no more experiments!
        return render_to_response("turk/worker_sorry.html")

    task_list = select_experiments(battery,uncompleted_experiments)
    experimentTemplate = ExperimentTemplate.objects.filter(exp_id=task_list[0].template.exp_id)[0]
    experiment_type = get_experiment_type(experimentTemplate)
    task_list = battery.experiments.filter(template=experimentTemplate)

    # Generate a new results object for the worker, assignment, experiment
    result,_ = Result.objects.update_or_create(worker=worker,
                                               experiment=experimentTemplate,
                                               battery=battery,
                                               defaults={"browser":browser,"platform":platform})
    result.save()

    context = {"worker_id": worker.id,
               "uniqueId":result.id}

    # If this is the last experiment, the finish button will link to a thank you page.
    if len(uncompleted_experiments) == 1:
        next_page = "/finished"

    # Determine template name based on template_type
    template = "%s/serve_battery.html" %(experiment_type)

    return deploy_battery(deployment="docker-local",
                          battery=battery,
                          experiment_type=experiment_type,
                          context=context,
                          task_list=task_list,
                          template=template,
                          next_page=next_page,
                          result=result)
예제 #8
0
def preview_experiment(request,eid):
    experiment = get_experiment_template(eid,request)
    experiment_type = get_experiment_type(experiment)
    experiment_folder = os.path.join(media_dir,experiment_type,experiment.exp_id)
    template = '%s/%s_preview.html' %(experiment_type,experiment_type[:-1])
    experiment_html = embed_experiment(experiment_folder,url_prefix="/")
    context = {"preview_html":experiment_html}
    return render_to_response(template, context)
예제 #9
0
def preview_experiment(request, eid):
    experiment = get_experiment_template(eid, request)
    experiment_type = get_experiment_type(experiment)
    experiment_folder = os.path.join(media_dir, experiment_type,
                                     experiment.exp_id)
    template = '%s/%s_preview.html' % (experiment_type, experiment_type[:-1])
    experiment_html = embed_experiment(experiment_folder, url_prefix="/")
    context = {"preview_html": experiment_html}
    return render_to_response(template, context)
예제 #10
0
def find_variable(result, variable_name):

    # Surveys and games not yet implemented
    experiment_type = get_experiment_type(result.experiment)
    variables = []

    # For experiments
    if experiment_type == "experiments":
        taskdata = result.taskdata
        for trial in taskdata[0]["trialdata"]:
            if variable_name in trial.keys():
                variables.append(trial[variable_name])
    return variables
예제 #11
0
def find_variable(result,variable_name):

    # Surveys and games not yet implemented
    experiment_type = get_experiment_type(result.experiment)
    variables = []

    # For experiments
    if experiment_type == "experiments":
        taskdata = result.taskdata
        for trial in taskdata[0]["trialdata"]:
            if variable_name in trial.keys():
                variables.append(trial[variable_name])
    return variables
예제 #12
0
def update_experiment_template(request,eid):
    '''This will update static files, along with the config.json parameters'''
    context = {"experiments": ExperimentTemplate.objects.all()}
    if request.user.is_superuser:
        experiment = get_experiment_template(eid=eid,request=request)
        experiment_type = get_experiment_type(experiment)
        errored_experiments = install_experiments(experiment_tags=[experiment.exp_id],repo_type=experiment_type)
        if len(errored_experiments) > 0:
            message = "The experiments %s did not update successfully." %(",".join(errored_experiments))
        else:
            message = "Experiments updated successfully."
            experiments = ExperimentTemplate.objects.all()
            context = {"experiments":experiments,
                       "message":message}
    return render(request, "experiments/all_experiments.html", context)
예제 #13
0
def update_experiment_template(request, eid):
    '''This will update static files, along with the config.json parameters'''
    context = {"experiments": ExperimentTemplate.objects.all()}
    if request.user.is_superuser:
        experiment = get_experiment_template(eid=eid, request=request)
        experiment_type = get_experiment_type(experiment)
        errored_experiments = install_experiments(
            experiment_tags=[experiment.exp_id], repo_type=experiment_type)
        if len(errored_experiments) > 0:
            message = "The experiments %s did not update successfully." % (
                ",".join(errored_experiments))
        else:
            message = "Experiments updated successfully."
            experiments = ExperimentTemplate.objects.all()
            context = {"experiments": experiments, "message": message}
    return render(request, "experiments/all_experiments.html", context)
예제 #14
0
 def items(self):
     return [x for x in ExperimentTemplate.objects.all() if get_experiment_type(x) == "games"]
예제 #15
0
def serve_hit(request,hid):
    '''serve_hit runs the experiment after accepting a hit
    :param hid: the hit id
    :param wid: the worker id
    :param aid: the assignment id
    '''

    # No robots allowed!
    if request.user_agent.is_bot:
        return render_to_response("turk/robot_sorry.html")

    # Not allowed on tablet or phone
    if request.user_agent.is_pc:

        hit =  get_hit(hid,request)

        # Update the hit, only allow to continue if HIT is valid
        hit.update()
        if hit.status in ["D"]:
            return render_to_response("turk/hit_expired.html")

        battery = hit.battery
        aws = get_amazon_variables(request)

        if "" in [aws["worker_id"],aws["hit_id"]]:
            return render_to_response("turk/error_sorry.html")

        # Get Experiment Factory objects for each
        worker = get_worker(aws["worker_id"])

        check_battery_response = check_battery_view(battery, aws["worker_id"])
        if (check_battery_response):
            return check_battery_response

        # This is the submit URL, either external or sandbox
        host = get_host(hit)

        # Only supporting chrome
        if request.user_agent.browser.family != "Chrome":
            return render_to_response("turk/browser_sorry.html")

        # Try to get some info about browser, language, etc.
        browser = "%s,%s" %(request.user_agent.browser.family,request.user_agent.browser.version_string)
        platform = "%s,%s" %(request.user_agent.os.family,request.user_agent.os.version_string)

        # Initialize Assignment object, obtained from Amazon, and Result
        assignment,already_created = Assignment.objects.get_or_create(mturk_id=aws["assignment_id"],
                                                                      worker=worker,
                                                                      hit=hit)

        # if the assignment is new, we need to set up a task to run when the worker time runs out to allocate credit
        if already_created == True:
            assignment.accept_time = datetime.now()
            if hit.assignment_duration_in_hours != None:
                assign_experiment_credit.apply_async([worker.id],countdown=360*(hit.assignment_duration_in_hours))
            assignment.save()

        # Does the worker have experiments remaining for the hit?
        uncompleted_experiments = get_worker_experiments(worker,hit.battery)
        experiments_left = len(uncompleted_experiments)  
        if experiments_left == 0:
            # Thank you for your participation - no more experiments!
            return render_to_response("turk/worker_sorry.html")

        # if it's the last experiment, we will submit the result to amazon (only for surveys)
        last_experiment = False
        if experiments_left == 1:
            last_experiment = True

        task_list = select_experiments(battery,uncompleted_experiments)
        experimentTemplate = ExperimentTemplate.objects.filter(exp_id=task_list[0].template.exp_id)[0]
        experiment_type = get_experiment_type(experimentTemplate)
        task_list = battery.experiments.filter(template=experimentTemplate)
        template = "%s/mturk_battery.html" %(experiment_type)

        # Generate a new results object for the worker, assignment, experiment
        result,_ = Result.objects.update_or_create(worker=worker,
                                                   experiment=experimentTemplate,
                                                   assignment=assignment, # assignment has record of HIT
                                                   battery=hit.battery,
                                                   defaults={"browser":browser,"platform":platform})
        result.save()

        # Add variables to the context
        aws["amazon_host"] = host
        aws["uniqueId"] = result.id

        # If this is the last experiment, the finish button will link to a thank you page.
        if experiments_left == 1:
            next_page = "/finished"

        return deploy_battery(
            deployment="docker-mturk",
            battery=battery,
            experiment_type=experiment_type,
            context=aws,
            task_list=task_list,
            template=template,
            next_page=None,
            result=result,
            last_experiment=last_experiment,
            experiments_left=experiments_left-1
        )

    else:
        return render_to_response("turk/error_sorry.html")
예제 #16
0
 def items(self):
     return [
         x for x in ExperimentTemplate.objects.all()
         if get_experiment_type(x) == "games"
     ]
예제 #17
0
def sync(request,rid=None):
    '''localsync
    view/method for running experiments to get data from the server
    :param rid: the result object ID, obtained before user sees page
    '''

    if request.method == "POST":

        if rid != None:
        # Update the result, already has worker and assignment ID stored
            result,_ = Result.objects.get_or_create(id=rid)
            battery = result.battery
            experiment_template = get_experiment_type(result.experiment)
            if experiment_template == "experiments":
                data = json.loads(request.body)
                result.taskdata = data["taskdata"]["data"]
                result.current_trial = data["taskdata"]["currenttrial"]
                djstatus = data["djstatus"]
            elif experiment_template == "games":
                data = json.loads(request.body)
                redirect_url = data["redirect_url"]
                result.taskdata = data["taskdata"]
                djstatus = data["djstatus"]
            elif experiment_template == "surveys":
                data = request.POST
                redirect_url = data["url"]
                djstatus = data["djstatus"]
                # Remove keys we don't want
                data = remove_keys(data,["process","csrfmiddlewaretoken","url","djstatus"])
                result.taskdata = complete_survey_result(result.experiment.exp_id,data)

            result.save()

            # if the worker finished the current experiment
            if djstatus == "FINISHED":

                # Mark experiment as completed
                result.completed = True
                result.finishtime = timezone.now()
                result.version = result.experiment.version
                result.save()

                # Fire a task to check blacklist status, add bonus
                check_blacklist.apply_async([result.id])
                experiment_reward.apply_async([result.id])

                data = dict()
                data["finished_battery"] = "NOTFINISHED"
                data["djstatus"] = djstatus
                completed_experiments = get_worker_experiments(result.worker,battery,completed=True)
                completed_experiments = numpy.unique([x.template.exp_id for x in completed_experiments]).tolist()
                if len(completed_experiments) == battery.experiments.count():
                    assign_experiment_credit.apply_async([result.worker.id],countdown=60)
                    data["finished_battery"] = "FINISHED"

                # Refresh the page if we've completed a survey or game
                if experiment_template in ["surveys"]:
                    return redirect(redirect_url)

            data = json.dumps(data)

    else:
        data = json.dumps({"message":"received!"})

    return HttpResponse(data, content_type='application/json')
예제 #18
0
def serve_battery(request, bid, userid=None):
    '''prepare for local serve of battery'''

    next_page = None
    battery = get_battery(bid, request)

    # No robots allowed!
    if request.user_agent.is_bot:
        return render_to_response("turk/robot_sorry.html")

    # Is userid not defined, redirect them to preview
    if userid == None:
        return preview_battery(request, bid)

    worker = get_worker(userid, create=False)
    if isinstance(worker, list):  # no id means returning []
        return render_to_response("turk/invalid_id_sorry.html")

    # Try to get some info about browser, language, etc.
    browser = "%s,%s" % (request.user_agent.browser.family,
                         request.user_agent.browser.version_string)
    platform = "%s,%s" % (request.user_agent.os.family,
                          request.user_agent.os.version_string)
    deployment = "docker-local"

    # Does the worker have experiments remaining?
    uncompleted_experiments = get_worker_experiments(worker, battery)
    if len(uncompleted_experiments) == 0:
        # Thank you for your participation - no more experiments!
        return render_to_response("turk/worker_sorry.html")

    task_list = select_experiments(battery, uncompleted_experiments)
    experimentTemplate = ExperimentTemplate.objects.filter(
        exp_id=task_list[0].template.exp_id)[0]
    experiment_type = get_experiment_type(experimentTemplate)
    task_list = battery.experiments.filter(template=experimentTemplate)

    # Generate a new results object for the worker, assignment, experiment
    result, _ = Result.objects.update_or_create(worker=worker,
                                                experiment=experimentTemplate,
                                                battery=battery,
                                                defaults={
                                                    "browser": browser,
                                                    "platform": platform
                                                })
    result.save()

    context = {"worker_id": worker.id, "uniqueId": result.id}

    # If this is the last experiment, the finish button will link to a thank you page.
    if len(uncompleted_experiments) == 1:
        next_page = "/finished"

    # Determine template name based on template_type
    template = "%s/serve_battery.html" % (experiment_type)

    return deploy_battery(deployment="docker-local",
                          battery=battery,
                          experiment_type=experiment_type,
                          context=context,
                          task_list=task_list,
                          template=template,
                          next_page=next_page,
                          result=result)
예제 #19
0
def sync(request, rid=None):
    '''localsync
    view/method for running experiments to get data from the server
    :param rid: the result object ID, obtained before user sees page
    '''

    if request.method == "POST":

        if rid != None:
            # Update the result, already has worker and assignment ID stored
            result, _ = Result.objects.get_or_create(id=rid)
            battery = result.battery
            experiment_template = get_experiment_type(result.experiment)
            if experiment_template == "experiments":
                data = json.loads(request.body)
                result.taskdata = data["taskdata"]["data"]
                result.current_trial = data["taskdata"]["currenttrial"]
                djstatus = data["djstatus"]
            elif experiment_template == "games":
                data = json.loads(request.body)
                redirect_url = data["redirect_url"]
                result.taskdata = data["taskdata"]
                djstatus = data["djstatus"]
            elif experiment_template == "surveys":
                data = request.POST
                redirect_url = data["url"]
                djstatus = data["djstatus"]
                # Remove keys we don't want
                data = remove_keys(
                    data,
                    ["process", "csrfmiddlewaretoken", "url", "djstatus"])
                result.taskdata = complete_survey_result(
                    result.experiment.exp_id, data)

            result.save()

            # if the worker finished the current experiment
            if djstatus == "FINISHED":

                # Mark experiment as completed
                result.completed = True
                result.finishtime = timezone.now()
                result.version = result.experiment.version
                result.save()

                # Fire a task to check blacklist status
                check_blacklist.apply_async([result.id])

                data = dict()
                data["finished_battery"] = "NOTFINISHED"
                data["djstatus"] = djstatus
                completed_experiments = get_worker_experiments(result.worker,
                                                               battery,
                                                               completed=True)
                completed_experiments = numpy.unique([
                    x.template.exp_id for x in completed_experiments
                ]).tolist()
                if len(completed_experiments) == battery.experiments.count():
                    assign_experiment_credit.apply_async([result.worker.id],
                                                         countdown=60)
                    data["finished_battery"] = "FINISHED"

                # Refresh the page if we've completed a survey or game
                if experiment_template in ["surveys"]:
                    return redirect(redirect_url)

            data = json.dumps(data)

    else:
        data = json.dumps({"message": "received!"})

    return HttpResponse(data, content_type='application/json')
예제 #20
0
 def items(self):
     return [
         x for x in Experiment.objects.filter(battery__private=False)
         if get_experiment_type(x) == "custom"
     ]