def preview_battery(request, bid, no_send=None): # No robots allowed! if request.user_agent.is_bot: return render_to_response("messages/robot_sorry.html") battery = get_battery(bid, request) router_url = battery.get_router_url() # If the user has already started and authenticated worker = get_worker("DUMMY", create=True) request.session['worker_id'] = "DUMMY" # If no_send is defined, the user doesn't want to email results if no_send != None: request.session['no_send'] = "anything" # We set the userid in the template to send to the service worker before routing to battery context = { "instruction_forms": get_battery_intro(battery), "start_url": router_url, "userid": "DUMMY" } return render(request, "batteries/serve_battery_intro.html", context)
def serve_battery_gmail(request, bid): '''serves a battery, creating user with gmail''' # Check if the keyid is correct battery = get_battery(bid, request) uid = hashlib.md5(battery.name).hexdigest() if "keyid" in request.POST and "gmail" in request.POST: keyid = request.POST["keyid"] address = request.POST["gmail"] if uid == keyid: userid = hashlib.md5(address).hexdigest() worker = get_worker(userid, create=True) return redirect("intro_battery", bid=bid, userid=userid) else: return render_to_response("messages/robot_sorry.html") else: return render_to_response("messages/robot_sorry.html")
def reset_preview(request, bid, redirect=True): '''reset_preview will delete the battery experiments for the preview user, meaning the preview can be restarted :param bid: the battery id :param redirect: if True, will redirect back to battery page, with message of reset (default is True, should only be false if called by server) ''' preview_user = get_worker("DUMMY") battery = get_battery(bid, request) experiments = battery.experiment_set.all() preview_user.experiments_completed = preview_user.experiments_completed.exclude( id__in=[x.id for x in experiments]) preview_user.save() if redirect == True: message = "Dummy worker history successfully reset." return view_battery(request, battery.id, message=message)
def send_result(eid,wid,data): '''send_result will use the sendgrid email API to send a result object to a worker. If there is an error, the user will be emailed instead using expfactory email, and the battery status will be made inactive. :param eid: the experiment id :param data: the data object (json) ''' try: # Retrieve worker, experiment, and battery worker = get_worker(wid) experiment = Experiment.objects.get(id=eid) battery = experiment.battery # Generate email and send with sendgrid email = generate_email(battery,experiment,worker,data) sg = SendGridAPIClient(apikey=battery.sendgrid) response = sg.client.mail.send.post(request_body=email) if response.status_code != 202: failed_send(battery,experiment,worker) except: failed_send(battery,experiment,worker)
def serve_battery_anon(request, bid, keyid): '''serve an anonymous local battery, userid is generated upon going to link ''' # Check if the keyid is correct battery = get_battery(bid, request) uid = hashlib.md5(battery.name).hexdigest() if uid == keyid: # If the user has already started and authenticated userid = request.session.get('worker_id', None) if userid == None: userid = uuid.uuid4() worker = get_worker(userid, create=True) request.session['worker_id'] = worker.id return redirect("intro_battery", bid=bid, userid=userid) # Invalid URL for battery! else: return render_to_response("messages/robot_sorry.html")
def battery_router(request, bid, eid=None, userid=None, no_send=False): '''battery_router will direct the user (determined from the session variable) to an uncompleted experiment. If an experiment id is provided, the redirect is being sent from a completed experiment, and we log the experiment as completed first. :param bid: the battery id :param eid: the experiment id, if provided, means we are submitting a result :param userid: the userid, will be "DUMMY" if doing a battery preview :param no_send: don't send result to email, default is False ''' # No robots allowed! if request.user_agent.is_bot: return render_to_response("messages/robot_sorry.html") # Is this a valid user? preview = False if userid != "DUMMY": # not a preview battery userid = request.session.get('worker_id', None) if userid == None: return render_to_response("messages/invalid_id_sorry.html") else: # If no_send is defined, then don't send preview = True no_send = request.session.get('no_send', False) worker = get_worker(userid) # Retrieve the battery based on the bid battery = get_battery(bid, request) # If there is a post, we are finishing an experiment and sending data if request.method == "POST" and eid != None: experiment = get_experiment(eid, request) # If it's a survey, format the results before sending data = request.POST if experiment.template == "survey": data = complete_survey_result(experiment, data) else: data = dict(data) # Mark the experiment as completed if experiment not in worker.experiments_completed.all(): # Only send data if the user hasn't completed it yet if no_send != True: send_result.apply_async([experiment.id, worker.id, data]) worker.experiments_completed.add(experiment) worker.save() # Deploy the next experiment missing_batteries, blocking_batteries = check_battery_dependencies( battery, worker) if missing_batteries or blocking_batteries: return render_to_response("messages/battery_requirements_not_met.html", context={ 'missing_batteries': missing_batteries, 'blocking_batteries': blocking_batteries }) # Is the battery still active? if battery.active == False: context = {"contact_email": battery.email} return render(request, "messages/battery_inactive.html", context) # Does the worker have experiments remaining? uncompleted_experiments = get_worker_experiments(worker, battery) experiments_left = len(uncompleted_experiments) if experiments_left == 0: # If it's a preview, reset it before showing the final page if preview == True: reset_preview(request, bid, redirect=False) # Thank you for your participation - no more experiments! return render_to_response("messages/worker_sorry.html") next_experiment = select_experiments(battery, uncompleted_experiments)[0] # Redirect the user to the experiment! return HttpResponseRedirect(next_experiment.serve_url())